52 #include <OpenGL/OpenGL.h> |
52 #include <OpenGL/OpenGL.h> |
53 #include <OpenGL/gl.h> |
53 #include <OpenGL/gl.h> |
54 #include <OpenGL/glext.h> |
54 #include <OpenGL/glext.h> |
55 #include <Carbon/Carbon.h> |
55 #include <Carbon/Carbon.h> |
56 #include <QuickTime/QuickTime.h> |
56 #include <QuickTime/QuickTime.h> |
57 #include <IOKit/IOKitLib.h> /* For powersave handling */ |
57 #include <IOKit/IOKitLib.h> /* For powersave handling */ |
58 #include <pthread.h> |
58 #include <pthread.h> |
59 |
59 |
60 #include "SDL_thread.h" |
60 #include "SDL_thread.h" |
61 #include "SDL_video.h" |
61 #include "SDL_video.h" |
62 #include "SDL_error.h" |
62 #include "SDL_error.h" |
63 #include "SDL_timer.h" |
63 #include "SDL_timer.h" |
64 #include "SDL_syswm.h" |
64 #include "SDL_syswm.h" |
65 #include "SDL_sysvideo.h" |
65 #include "SDL_sysvideo.h" |
66 #include "SDL_pixels_c.h" |
66 #include "SDL_pixels_c.h" |
67 #include "SDL_events_c.h" |
67 #include "SDL_events_c.h" |
68 |
|
69 /* |
|
70 Add methods to get at private members of NSScreen. |
|
71 Since there is a bug in Apple's screen switching code |
|
72 that does not update this variable when switching |
|
73 to fullscreen, we'll set it manually (but only for the |
|
74 main screen). |
|
75 */ |
|
76 @interface NSScreen (NSScreenAccess) |
|
77 - (void) setFrame:(NSRect)frame; |
|
78 @end |
|
79 |
|
80 @implementation NSScreen (NSScreenAccess) |
|
81 - (void) setFrame:(NSRect)frame; |
|
82 { |
|
83 _frame = frame; |
|
84 } |
|
85 @end |
|
86 |
|
87 /* |
|
88 This is a workaround to directly access NSOpenGLContext's CGL context |
|
89 We need this to check for errors NSOpenGLContext doesn't support |
|
90 */ |
|
91 @interface NSOpenGLContext (CGLContextAccess) |
|
92 - (CGLContextObj) cglContext; |
|
93 @end |
|
94 |
|
95 @implementation NSOpenGLContext (CGLContextAccess) |
|
96 - (CGLContextObj) cglContext; |
|
97 { |
|
98 return _contextAuxiliary; |
|
99 } |
|
100 @end |
|
101 |
|
102 /* |
|
103 Structure for rez switch gamma fades |
|
104 We can hide the monitor flicker by setting the gamma tables to 0 |
|
105 */ |
|
106 #define QZ_GAMMA_TABLE_SIZE 256 |
|
107 |
|
108 typedef struct { |
|
109 |
|
110 CGGammaValue red[QZ_GAMMA_TABLE_SIZE]; |
|
111 CGGammaValue green[QZ_GAMMA_TABLE_SIZE]; |
|
112 CGGammaValue blue[QZ_GAMMA_TABLE_SIZE]; |
|
113 |
|
114 } SDL_QuartzGammaTable; |
|
115 |
68 |
116 /* Main driver structure to store required state information */ |
69 /* Main driver structure to store required state information */ |
117 typedef struct SDL_PrivateVideoData { |
70 typedef struct SDL_PrivateVideoData { |
118 |
71 |
119 CGDirectDisplayID display; /* 0 == main display (only support single display) */ |
72 CGDirectDisplayID display; /* 0 == main display (only support single display) */ |
129 Uint32 warp_ticks; /* timestamp when the warp occured */ |
82 Uint32 warp_ticks; /* timestamp when the warp occured */ |
130 NSWindow *window; /* Cocoa window to implement the SDL window */ |
83 NSWindow *window; /* Cocoa window to implement the SDL window */ |
131 NSQuickDrawView *view; /* the window's view; draw 2D and OpenGL into this view */ |
84 NSQuickDrawView *view; /* the window's view; draw 2D and OpenGL into this view */ |
132 SDL_Surface *resize_icon; /* icon for the resize badge, we have to draw it by hand */ |
85 SDL_Surface *resize_icon; /* icon for the resize badge, we have to draw it by hand */ |
133 SDL_GrabMode current_grab_mode; /* default value is SDL_GRAB_OFF */ |
86 SDL_GrabMode current_grab_mode; /* default value is SDL_GRAB_OFF */ |
134 BOOL in_foreground; /* boolean; indicate if app is in foreground or not */ |
|
135 SDL_Rect **client_mode_list; /* resolution list to pass back to client */ |
87 SDL_Rect **client_mode_list; /* resolution list to pass back to client */ |
136 SDLKey keymap[256]; /* Mac OS X to SDL key mapping */ |
88 SDLKey keymap[256]; /* Mac OS X to SDL key mapping */ |
137 Uint32 current_mods; /* current keyboard modifiers, to track modifier state */ |
89 Uint32 current_mods; /* current keyboard modifiers, to track modifier state */ |
138 Uint32 last_virtual_button;/* last virtual mouse button pressed */ |
90 Uint32 last_virtual_button;/* last virtual mouse button pressed */ |
139 io_connect_t power_connection; /* used with IOKit to detect wake from sleep */ |
91 io_connect_t power_connection; /* used with IOKit to detect wake from sleep */ |
140 Uint8 expect_mouse_up; /* used to determine when to send mouse up events */ |
92 Uint8 expect_mouse_up; /* used to determine when to send mouse up events */ |
141 Uint8 grab_state; /* used to manage grab behavior */ |
93 Uint8 grab_state; /* used to manage grab behavior */ |
142 NSPoint cursor_loc; /* saved cursor coords, for activate/deactivate when grabbed */ |
94 NSPoint cursor_loc; /* saved cursor coords, for activate/deactivate when grabbed */ |
143 BOOL cursor_visible; /* tells if cursor was instructed to be hidden or not (SDL_ShowCursor) */ |
95 BOOL cursor_should_be_visible; /* tells if cursor is supposed to be visible (SDL_ShowCursor) */ |
144 BOOL cursor_hidden; /* tells if cursor is *actually* hidden or not */ |
96 BOOL cursor_visible; /* tells if cursor is *actually* visible or not */ |
145 Uint8* sw_buffers[2]; /* pointers to the two software buffers for double-buffer emulation */ |
97 Uint8* sw_buffers[2]; /* pointers to the two software buffers for double-buffer emulation */ |
146 SDL_Thread *thread; /* thread for async updates to the screen */ |
98 SDL_Thread *thread; /* thread for async updates to the screen */ |
147 SDL_sem *sem1, *sem2; /* synchronization for async screen updates */ |
99 SDL_sem *sem1, *sem2; /* synchronization for async screen updates */ |
148 Uint8 *current_buffer; /* the buffer being copied to the screen */ |
100 Uint8 *current_buffer; /* the buffer being copied to the screen */ |
149 BOOL quit_thread; /* used to quit the async blitting thread */ |
101 BOOL quit_thread; /* used to quit the async blitting thread */ |
174 #define video_set (this->hidden->video_set) |
126 #define video_set (this->hidden->video_set) |
175 #define warp_ticks (this->hidden->warp_ticks) |
127 #define warp_ticks (this->hidden->warp_ticks) |
176 #define warp_flag (this->hidden->warp_flag) |
128 #define warp_flag (this->hidden->warp_flag) |
177 #define resize_icon (this->hidden->resize_icon) |
129 #define resize_icon (this->hidden->resize_icon) |
178 #define current_grab_mode (this->hidden->current_grab_mode) |
130 #define current_grab_mode (this->hidden->current_grab_mode) |
179 #define in_foreground (this->hidden->in_foreground) |
|
180 #define client_mode_list (this->hidden->client_mode_list) |
131 #define client_mode_list (this->hidden->client_mode_list) |
181 #define keymap (this->hidden->keymap) |
132 #define keymap (this->hidden->keymap) |
182 #define current_mods (this->hidden->current_mods) |
133 #define current_mods (this->hidden->current_mods) |
183 #define last_virtual_button (this->hidden->last_virtual_button) |
134 #define last_virtual_button (this->hidden->last_virtual_button) |
184 #define power_connection (this->hidden->power_connection) |
135 #define power_connection (this->hidden->power_connection) |
185 #define expect_mouse_up (this->hidden->expect_mouse_up) |
136 #define expect_mouse_up (this->hidden->expect_mouse_up) |
186 #define grab_state (this->hidden->grab_state) |
137 #define grab_state (this->hidden->grab_state) |
187 #define cursor_loc (this->hidden->cursor_loc) |
138 #define cursor_loc (this->hidden->cursor_loc) |
|
139 #define cursor_should_be_visible (this->hidden->cursor_should_be_visible) |
188 #define cursor_visible (this->hidden->cursor_visible) |
140 #define cursor_visible (this->hidden->cursor_visible) |
189 #define cursor_hidden (this->hidden->cursor_hidden) |
|
190 #define sw_buffers (this->hidden->sw_buffers) |
141 #define sw_buffers (this->hidden->sw_buffers) |
191 #define thread (this->hidden->thread) |
142 #define thread (this->hidden->thread) |
192 #define sem1 (this->hidden->sem1) |
143 #define sem1 (this->hidden->sem1) |
193 #define sem2 (this->hidden->sem2) |
144 #define sem2 (this->hidden->sem2) |
194 #define current_buffer (this->hidden->current_buffer) |
145 #define current_buffer (this->hidden->current_buffer) |
195 #define quit_thread (this->hidden->quit_thread) |
146 #define quit_thread (this->hidden->quit_thread) |
196 |
|
197 #define yuv_idh (this->hidden->yuv_idh) |
|
198 #define yuv_matrix (this->hidden->yuv_matrix) |
|
199 #define yuv_codec (this->hidden->yuv_codec) |
|
200 #define yuv_seq (this->hidden->yuv_seq) |
|
201 #define yuv_pixmap (this->hidden->yuv_pixmap) |
|
202 #define yuv_data (this->hidden->yuv_data) |
|
203 #define yuv_width (this->hidden->yuv_width) |
|
204 #define yuv_height (this->hidden->yuv_height) |
|
205 #define yuv_port (this->hidden->yuv_port) |
|
206 |
|
207 |
147 |
208 /* grab states - the input is in one of these states */ |
148 /* grab states - the input is in one of these states */ |
209 enum { |
149 enum { |
210 QZ_UNGRABBED = 0, |
150 QZ_UNGRABBED = 0, |
211 QZ_VISIBLE_GRAB, |
151 QZ_VISIBLE_GRAB, |
218 QZ_DISABLE_GRAB, |
158 QZ_DISABLE_GRAB, |
219 QZ_HIDECURSOR, |
159 QZ_HIDECURSOR, |
220 QZ_SHOWCURSOR |
160 QZ_SHOWCURSOR |
221 }; |
161 }; |
222 |
162 |
223 /* |
|
224 Obscuring code: maximum number of windows above ours (inclusive) |
|
225 |
|
226 Note: this doesn't work too well in practice and should be |
|
227 phased out when we add OpenGL 2D acceleration. It was never |
|
228 enabled in the first place, so this shouldn't be a problem ;-) |
|
229 */ |
|
230 #define kMaxWindows 256 |
|
231 |
|
232 /* Some of the Core Graphics Server API for obscuring code */ |
|
233 #define kCGSWindowLevelTop 2147483632 |
|
234 #define kCGSWindowLevelDockIconDrag 500 |
|
235 #define kCGSWindowLevelDockMenu 101 |
|
236 #define kCGSWindowLevelMenuIgnore 21 |
|
237 #define kCGSWindowLevelMenu 20 |
|
238 #define kCGSWindowLevelDockLabel 12 |
|
239 #define kCGSWindowLevelDockIcon 11 |
|
240 #define kCGSWindowLevelDock 10 |
|
241 #define kCGSWindowLevelUtility 3 |
|
242 #define kCGSWindowLevelNormal 0 |
|
243 |
|
244 /* |
|
245 For completeness; We never use these window levels, they are always below us |
|
246 #define kCGSWindowLevelMBarShadow -20 |
|
247 #define kCGSWindowLevelDesktopPicture -2147483647 |
|
248 #define kCGSWindowLevelDesktop -2147483648 |
|
249 */ |
|
250 |
|
251 typedef CGError CGSError; |
|
252 typedef long CGSWindowCount; |
|
253 typedef void * CGSConnectionID; |
|
254 typedef int CGSWindowID; |
|
255 typedef CGSWindowID* CGSWindowIDList; |
|
256 typedef CGWindowLevel CGSWindowLevel; |
|
257 typedef NSRect CGSRect; |
|
258 |
|
259 extern CGSConnectionID _CGSDefaultConnection (); |
|
260 |
|
261 extern CGSError CGSGetOnScreenWindowList (CGSConnectionID cid, |
|
262 CGSConnectionID owner, |
|
263 CGSWindowCount listCapacity, |
|
264 CGSWindowIDList list, |
|
265 CGSWindowCount *listCount); |
|
266 |
|
267 extern CGSError CGSGetScreenRectForWindow (CGSConnectionID cid, |
|
268 CGSWindowID wid, |
|
269 CGSRect *rect); |
|
270 |
|
271 extern CGWindowLevel CGSGetWindowLevel (CGSConnectionID cid, |
|
272 CGSWindowID wid, |
|
273 CGSWindowLevel *level); |
|
274 |
|
275 extern CGSError CGSDisplayHWFill (CGDirectDisplayID id, unsigned int x, unsigned int y, |
|
276 unsigned int w, unsigned int h, unsigned int color); |
|
277 |
|
278 extern CGSError CGSDisplayCanHWFill (CGDirectDisplayID id); |
|
279 |
|
280 extern CGSError CGSGetMouseEnabledFlags (CGSConnectionID cid, CGSWindowID wid, int *flags); |
|
281 |
|
282 int CGSDisplayHWSync (CGDirectDisplayID id); |
|
283 |
|
284 /* Bootstrap functions */ |
|
285 static int QZ_Available (); |
|
286 static SDL_VideoDevice* QZ_CreateDevice (int device_index); |
|
287 static void QZ_DeleteDevice (SDL_VideoDevice *device); |
|
288 |
|
289 /* Initialization, Query, Setup, and Redrawing functions */ |
|
290 static int QZ_VideoInit (_THIS, SDL_PixelFormat *video_format); |
|
291 |
|
292 static SDL_Rect** QZ_ListModes (_THIS, SDL_PixelFormat *format, |
|
293 Uint32 flags); |
|
294 static void QZ_UnsetVideoMode (_THIS); |
|
295 |
|
296 static SDL_Surface* QZ_SetVideoMode (_THIS, SDL_Surface *current, |
|
297 int width, int height, int bpp, |
|
298 Uint32 flags); |
|
299 static int QZ_ToggleFullScreen (_THIS, int on); |
|
300 static int QZ_SetColors (_THIS, int first_color, |
|
301 int num_colors, SDL_Color *colors); |
|
302 |
|
303 static int QZ_LockDoubleBuffer (_THIS, SDL_Surface *surface); |
|
304 static void QZ_UnlockDoubleBuffer (_THIS, SDL_Surface *surface); |
|
305 static int QZ_ThreadFlip (_THIS); |
|
306 static int QZ_FlipDoubleBuffer (_THIS, SDL_Surface *surface); |
|
307 static void QZ_DoubleBufferUpdate (_THIS, int num_rects, SDL_Rect *rects); |
|
308 |
|
309 static void QZ_DirectUpdate (_THIS, int num_rects, SDL_Rect *rects); |
|
310 static int QZ_LockWindow (_THIS, SDL_Surface *surface); |
|
311 static void QZ_UnlockWindow (_THIS, SDL_Surface *surface); |
|
312 static void QZ_UpdateRects (_THIS, int num_rects, SDL_Rect *rects); |
|
313 static void QZ_VideoQuit (_THIS); |
|
314 |
|
315 /* Hardware surface functions (for fullscreen mode only) */ |
|
316 #if 0 /* Not used (apparently, it's really slow) */ |
|
317 static int QZ_FillHWRect (_THIS, SDL_Surface *dst, SDL_Rect *rect, Uint32 color); |
|
318 #endif |
|
319 static int QZ_LockHWSurface(_THIS, SDL_Surface *surface); |
|
320 static void QZ_UnlockHWSurface(_THIS, SDL_Surface *surface); |
|
321 static void QZ_FreeHWSurface (_THIS, SDL_Surface *surface); |
|
322 /* static int QZ_FlipHWSurface (_THIS, SDL_Surface *surface); */ |
|
323 |
|
324 /* Gamma Functions */ |
163 /* Gamma Functions */ |
325 static int QZ_SetGamma (_THIS, float red, float green, float blue); |
164 int QZ_SetGamma (_THIS, float red, float green, float blue); |
326 static int QZ_GetGamma (_THIS, float *red, float *green, float *blue); |
165 int QZ_GetGamma (_THIS, float *red, float *green, float *blue); |
327 static int QZ_SetGammaRamp (_THIS, Uint16 *ramp); |
166 int QZ_SetGammaRamp (_THIS, Uint16 *ramp); |
328 static int QZ_GetGammaRamp (_THIS, Uint16 *ramp); |
167 int QZ_GetGammaRamp (_THIS, Uint16 *ramp); |
329 |
168 |
330 /* OpenGL functions */ |
169 /* OpenGL functions */ |
331 static int QZ_SetupOpenGL (_THIS, int bpp, Uint32 flags); |
170 int QZ_SetupOpenGL (_THIS, int bpp, Uint32 flags); |
332 static void QZ_TearDownOpenGL (_THIS); |
171 void QZ_TearDownOpenGL (_THIS); |
333 static void* QZ_GL_GetProcAddress (_THIS, const char *proc); |
172 void* QZ_GL_GetProcAddress (_THIS, const char *proc); |
334 static int QZ_GL_GetAttribute (_THIS, SDL_GLattr attrib, int* value); |
173 int QZ_GL_GetAttribute (_THIS, SDL_GLattr attrib, int* value); |
335 static int QZ_GL_MakeCurrent (_THIS); |
174 int QZ_GL_MakeCurrent (_THIS); |
336 static void QZ_GL_SwapBuffers (_THIS); |
175 void QZ_GL_SwapBuffers (_THIS); |
337 static int QZ_GL_LoadLibrary (_THIS, const char *location); |
176 int QZ_GL_LoadLibrary (_THIS, const char *location); |
338 |
|
339 /* Private function to warp the cursor (used internally) */ |
|
340 static void QZ_PrivateWarpCursor (_THIS, int x, int y); |
|
341 |
177 |
342 /* Cursor and Mouse functions */ |
178 /* Cursor and Mouse functions */ |
343 static void QZ_FreeWMCursor (_THIS, WMcursor *cursor); |
179 void QZ_FreeWMCursor (_THIS, WMcursor *cursor); |
344 static WMcursor* QZ_CreateWMCursor (_THIS, Uint8 *data, Uint8 *mask, |
180 WMcursor* QZ_CreateWMCursor (_THIS, Uint8 *data, Uint8 *mask, |
345 int w, int h, int hot_x, int hot_y); |
181 int w, int h, int hot_x, int hot_y); |
346 static int QZ_ShowWMCursor (_THIS, WMcursor *cursor); |
182 int QZ_ShowWMCursor (_THIS, WMcursor *cursor); |
347 static void QZ_WarpWMCursor (_THIS, Uint16 x, Uint16 y); |
183 void QZ_WarpWMCursor (_THIS, Uint16 x, Uint16 y); |
348 static void QZ_MoveWMCursor (_THIS, int x, int y); |
184 void QZ_MoveWMCursor (_THIS, int x, int y); |
349 static void QZ_CheckMouseMode (_THIS); |
185 void QZ_CheckMouseMode (_THIS); |
350 |
186 |
351 /* Event functions */ |
187 /* Event functions */ |
352 static void QZ_InitOSKeymap (_THIS); |
188 void QZ_InitOSKeymap (_THIS); |
353 static void QZ_PumpEvents (_THIS); |
189 void QZ_PumpEvents (_THIS); |
354 |
190 |
355 /* Window Manager functions */ |
191 /* Window Manager functions */ |
356 static void QZ_SetCaption (_THIS, const char *title, const char *icon); |
192 void QZ_SetCaption (_THIS, const char *title, const char *icon); |
357 static void QZ_SetIcon (_THIS, SDL_Surface *icon, Uint8 *mask); |
193 void QZ_SetIcon (_THIS, SDL_Surface *icon, Uint8 *mask); |
358 static int QZ_IconifyWindow (_THIS); |
194 int QZ_IconifyWindow (_THIS); |
359 static SDL_GrabMode QZ_GrabInput (_THIS, SDL_GrabMode grab_mode); |
195 SDL_GrabMode QZ_GrabInput (_THIS, SDL_GrabMode grab_mode); |
360 /*static int QZ_GetWMInfo (_THIS, SDL_SysWMinfo *info);*/ |
196 /*int QZ_GetWMInfo (_THIS, SDL_SysWMinfo *info);*/ |
361 |
197 |
362 /* YUV functions */ |
198 /* YUV functions */ |
363 static SDL_Overlay* QZ_CreateYUVOverlay (_THIS, int width, int height, |
199 SDL_Overlay* QZ_CreateYUVOverlay (_THIS, int width, int height, |
364 Uint32 format, SDL_Surface *display); |
200 Uint32 format, SDL_Surface *display); |
|
201 |
|
202 |
|
203 /* Private functions (used internally) */ |
|
204 void QZ_PrivateWarpCursor (_THIS, int x, int y); |
|
205 void QZ_ChangeGrabState (_THIS, int action); |
|
206 void QZ_RegisterForSleepNotifications (_THIS); |
|
207 void QZ_ShowMouse (_THIS); |
|
208 void QZ_HideMouse (_THIS); |
|
209 void QZ_PrivateGlobalToLocal (_THIS, NSPoint *p); |
|
210 void QZ_PrivateCocoaToSDL (_THIS, NSPoint *p); |
|
211 |