]> git.tdb.fi Git - libs/gui.git/blob - source/graphics/cocoa/cocoawindow.m
Subclass NSWindow to eat keyDown events so they won't beep
[libs/gui.git] / source / graphics / cocoa / cocoawindow.m
1 #import <AppKit/NSApplication.h>
2 #import <AppKit/NSWindow.h>
3 #import <CoreFoundation/CFArray.h>
4 #include "cocoadisplay.h"
5 #include "cocoawindow.h"
6
7 @interface MspWindow: NSWindow {
8         int dummy_member;
9 }
10
11 - (BOOL)windowShouldClose:(id)sender;
12 - (void)keyDown:(NSEvent *)event;
13
14 @end
15
16 struct _CocoaWindow
17 {
18         CocoaDisplay *display;
19         __strong NSWindow *window;
20         NSUInteger style;
21 };
22
23 CFMutableDictionaryRef windows = NULL;
24
25 CocoaWindow *create_window(CocoaDisplay *display, unsigned width, unsigned height, bool fullscreen, bool resizable)
26 {
27         NSRect rect = NSMakeRect(0, 0, width, height);
28         NSUInteger style = NSTitledWindowMask|NSClosableWindowMask;
29         if(resizable)
30                 style |= NSResizableWindowMask;
31         NSWindow *window = [MspWindow alloc];
32         window = [window initWithContentRect:rect styleMask:style backing:NSBackingStoreBuffered defer:NO];
33         [window setAcceptsMouseMovedEvents:YES];
34
35         (void)fullscreen;
36
37         CocoaWindow *wrapper = (CocoaWindow *)malloc(sizeof(CocoaWindow));
38         wrapper->display = display;
39         wrapper->window = window;
40         wrapper->style = style;
41
42         if(!windows)
43                 windows = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
44         CFDictionaryAddValue(windows, window, wrapper);
45
46         return wrapper;
47 }
48
49 void destroy_window(CocoaWindow *window)
50 {
51         CFDictionaryRemoveValue(windows, window->window);
52         if(!CFDictionaryGetCount(windows))
53         {
54                 CFRelease(windows);
55                 windows = NULL;
56         }
57
58         [window->window release];
59         free(window);
60 }
61
62 NSWindow *get_native_window(CocoaWindow *window)
63 {
64         return window->window;
65 }
66
67 CocoaWindow *lookup_window(NSWindow *window)
68 {
69         return (CocoaWindow *)CFDictionaryGetValue(windows, window);
70 }
71
72 void set_window_title(CocoaWindow *window, const char *title)
73 {
74         [window->window setTitle:[NSString stringWithCString:title encoding:NSUTF8StringEncoding]];
75 }
76
77 void set_window_size(CocoaWindow *window, unsigned width, unsigned height)
78 {
79         NSRect rect = NSMakeRect(0, 0, width, height);
80         rect = [NSWindow frameRectForContentRect:rect styleMask:window->style];
81         [window->window setFrame:rect display:YES];
82 }
83
84 void show_window(CocoaWindow *window)
85 {
86         [window->window makeKeyAndOrderFront:nil];
87         [NSApp activateIgnoringOtherApps:NO];
88 }
89
90 void hide_window(CocoaWindow *window)
91 {
92         (void)window;
93 }
94
95 @implementation MspWindow
96
97 - (BOOL)windowShouldClose:(id)sender
98 {
99         CocoaWindow *window = lookup_window((NSWindow *)sender);
100         if(window)
101         {
102                 CocoaEvent event;
103                 event.any.type = WINDOW_CLOSED;
104                 event.any.window = window;
105                 queue_event(window->display, &event);
106                 return NO;
107         }
108         return YES;
109 }
110
111 - (void)keyDown:(NSEvent *)event
112 {
113         // Eat the event to avoid beeping
114         (void)event;
115 }
116
117 @end