sgl

view src/wsys_cocoa.m @ 15:a16b34ac3f2a

bah
author John Tsiombikas <nuclear@member.fsf.org>
date Tue, 17 May 2011 11:21:09 +0300
parents 5b8fb89fe63f
children 01a576351090 ee7b3a898b6b
line source
1 /* mac-framework: -framework Cocoa */
3 #include "config.h"
5 #ifdef USE_WSYS_MODULE_COCOA
7 #import <Cocoa/Cocoa.h>
8 #include "sgl.h"
9 #include "wsys.h"
11 @interface OpenGLView : NSOpenGLView
12 {
13 int foo;
14 }
16 /*-(id) initWithFrame: (NSRect) frameRect;*/
18 -(void) drawRect: (NSRect) rect;
19 -(void) reshape;
20 /*-(void) keyDown: (NSEvent*) ev;
21 -(void) keyUp: (NSEvent*) ev;
22 -(void) mouseDown: (NSEvent*) ev;
23 -(void) mouseUp: (NSEvent*) ev;
24 -(void) rightMouseDown: (NSEvent*) ev;
25 -(void) rightMouseUp: (NSEvent*) ev;
26 -(void) otherMouseDown: (NSEvent*) ev;
27 -(void) otherMouseUp: (NSEvent*) ev;
28 -(void) mouseDragged: (NSEvent*) ev;
29 -(void) rightMouseDragged: (NSEvent*) ev;
30 -(void) otherMouseDragged: (NSEvent*) ev;*/
32 -(BOOL) acceptsFirstResponder;
33 @end
35 struct window {
36 int wid;
37 int width, height;
38 NSWindow *win;
39 OpenGLView *view;
40 NSOpenGLContext *ctx;
41 int needs_redisplay;
42 struct window *next;
43 };
46 static int init(void);
47 static void shutdown(void);
49 /* video mode switching */
50 static int set_vidmode(int xsz, int ysz);
51 static int get_vidmode(int *xsz, int *ysz);
53 /* create/destroy windows */
54 static int create_window(int xsz, int ysz, unsigned int flags);
55 static void close_window(int wid);
57 /* window management */
58 static int set_active(int wid);
59 static struct window *find_window(int wid);
60 static int activate_window(struct window *win);
61 static int set_title(const char *str);
62 static void redisplay(void);
63 static void swap_buffers(void);
65 static int get_modifiers(void);
67 /* event handling and friends */
68 static void set_event(int idx, int enable);
69 static int process_events(void);
70 static int handle_event(NSEvent *ev);
73 static struct wsys_module ws = {
74 "cocoa", 0,
75 init,
76 shutdown,
77 set_vidmode,
78 get_vidmode,
79 create_window,
80 close_window,
81 set_active,
82 set_title,
83 redisplay,
84 swap_buffers,
85 get_modifiers,
86 set_event,
87 process_events,
88 0
89 };
91 static NSApplication *app;
92 static struct window *winlist, *active_win;
95 void sgl_register_cocoa(void)
96 {
97 sgl_register_module(&ws);
98 }
101 @implementation OpenGLView
103 -(void) drawRect: (NSRect) rect
104 {
105 sgl_display_callback_t func = sgl_get_callback(SGL_DISPLAY);
106 if(func) {
107 func();
108 }
109 }
111 -(void) reshape
112 {
113 NSSize sz;
114 sgl_reshape_callback_t func;
116 sz = [self bounds].size;
118 if((func = sgl_get_callback(SGL_RESHAPE)) && (sz.width != active_win->width ||
119 sz.height != active_win->height)) {
120 active_win->width = sz.width;
121 active_win->height = sz.height;
122 func(sz.width, sz.height);
123 }
124 }
126 -(BOOL) acceptsFirstResponder
127 {
128 return YES;
129 }
130 @end
132 static int init(void)
133 {
134 app = [NSApplication sharedApplication];
135 return 0;
136 }
138 static void shutdown(void)
139 {
140 while(winlist) {
141 struct window *win = winlist;
142 winlist = winlist->next;
144 /* TODO destroy window */
145 free(win);
146 }
147 }
150 /* video mode switching */
151 static int set_vidmode(int xsz, int ysz)
152 {
153 return 0; /* TODO */
154 }
156 static int get_vidmode(int *xsz, int *ysz)
157 {
158 return 0; /* TODO */
159 }
162 /* create/destroy windows */
163 static int create_window(int xsz, int ysz, unsigned int flags)
164 {
165 NSWindow *nswin;
166 NSRect rect;
167 OpenGLView *view;
168 unsigned int style;
169 struct window *win;
170 static int next_id = 1;
172 if(!(win = malloc(sizeof *win))) {
173 return -1;
174 }
176 /* create the window and attach the OpenGL view */
177 rect.origin.x = rect.origin.y = 0;
178 rect.size.width = xsz;
179 rect.size.height = ysz;
181 style = NSTitledWindowMask | NSClosableWindowMask | NSMiniaturizableWindowMask |
182 NSResizableWindowMask;
184 nswin = [[NSWindow alloc] initWithContentRect: rect styleMask: style
185 backing: NSBackingStoreBuffered defer: YES];
186 view = [[OpenGLView alloc] initWithFrame: rect];
187 [nswin setContentView: view];
188 [view release];
190 win->win = nswin;
191 win->view = view;
192 win->ctx = [view openGLContext];
193 win->wid = next_id++;
194 win->needs_redisplay = 1;
195 win->next = winlist;
196 winlist = win;
198 if(!active_win) {
199 activate_window(win);
200 }
201 return win->wid;
202 }
204 static void close_window(int wid)
205 {
206 struct window *win, *prev, dummy;
207 sgl_close_callback_t close_func;
209 dummy.next = win = winlist;
210 prev = &dummy;
212 while(win) {
213 if(win->wid == wid) {
214 if(!(close_func = sgl_get_callback(SGL_CLOSE))) {
215 close_func(wid);
216 }
217 [win->win close];
219 if(active_win == win) {
220 activate_window(winlist);
221 }
223 prev->next = win->next;
224 free(win);
225 return;
226 }
227 prev = win;
228 win = win->next;
229 }
230 }
233 /* window management */
234 static int set_active(int wid)
235 {
236 struct window *win = find_window(wid);
237 return activate_window(win);
238 }
240 static struct window *find_window(int wid)
241 {
242 struct window *win = winlist;
244 while(win) {
245 if(win->wid == wid) {
246 return win;
247 }
248 win = win->next;
249 }
250 return 0;
251 }
253 static int activate_window(struct window *win)
254 {
255 if(!win) {
256 return -1;
257 }
258 [win->ctx makeCurrentContext];
259 active_win = win;
260 return 0;
261 }
263 static int set_title(const char *str)
264 {
265 NSString *nsstr;
267 nsstr = [[NSString alloc] initWithCString: str encoding: NSASCIIStringEncoding];
268 [active_win->win setTitle: nsstr];
269 [nsstr release];
270 return 0;
271 }
273 static void redisplay(void)
274 {
275 active_win->needs_redisplay = 1;
276 }
278 static void swap_buffers(void)
279 {
280 [active_win->ctx flushBuffer];
281 }
284 static int get_modifiers(void)
285 {
286 return 0; /* TODO */
287 }
290 /* event handling and friends */
291 static void set_event(int idx, int enable)
292 {
293 }
295 static int process_events(void)
296 {
297 NSAutoreleasePool *pool;
298 sgl_idle_callback_t idle;
299 sgl_display_callback_t disp;
300 struct window *win;
301 int res = 0;
303 pool = [[NSAutoreleasePool alloc] init];
305 idle = sgl_get_callback(SGL_IDLE);
306 disp = sgl_get_callback(SGL_DISPLAY);
308 win = winlist;
309 while(win) {
310 if(win->needs_redisplay && disp) {
311 activate_window(win);
312 disp();
313 win->needs_redisplay = 0;
314 }
315 win = win->next;
316 }
318 for(;;) {
319 NSEvent *ev = [app nextEventMatchingMask: NSAnyEventMask
320 untilDate: [NSDate distantPast] inMode: NSDefaultRunLoopMode dequeue: YES];
321 if(ev == nil) {
322 break;
323 }
325 res = handle_event(ev);
326 }
328 if(idle) {
329 idle();
330 }
332 [pool drain];
333 return 0;
334 }
336 static int handle_event(NSEvent *ev)
337 {
338 switch([ev type]) {
339 case NSKeyDown:
340 case NSKeyUp:
341 printf("key pressed\n");
342 break;
344 default:
345 break;
346 }
347 return 0;
348 }
350 #endif /* USE_WSYS_MODULE_COCOA */