1 /*
2  * OpenClonk, http://www.openclonk.org
3  *
4  * Copyright (c) 2005-2009, RedWolf Design GmbH, http://www.clonk.de/
5  * Copyright (c) 2009-2016, The OpenClonk Team and contributors
6  *
7  * Distributed under the terms of the ISC license; see accompanying file
8  * "COPYING" for details.
9  *
10  * "Clonk" is a registered trademark of Matthes Bender, used with permission.
11  * See accompanying file "TRADEMARK" for details.
12  *
13  * To redistribute this file separately, substitute the full license texts
14  * for the above references.
15  */
16 
17 /* A wrapper class to OS dependent event and window interfaces */
18 
19 #ifndef INC_STDWINDOW
20 #define INC_STDWINDOW
21 
22 #include "C4ForbidLibraryCompilation.h"
23 
24 #if defined(USE_SDL_MAINLOOP)
25 #include <SDL.h>
26 #define MK_SHIFT (KMOD_LSHIFT | KMOD_RSHIFT)
27 #define MK_CONTROL (KMOD_LCTRL | KMOD_RCTRL)
28 #define MK_ALT (KMOD_LALT | KMOD_RALT)
29 #elif defined(USE_CONSOLE)
30 #ifndef _WIN32
31 #define MK_SHIFT 0
32 #define MK_CONTROL 0
33 #endif
34 #define MK_ALT 0
35 #elif defined(USE_COCOA)
36 // declare as extern variables and initialize them in StdMacWindow.mm so as to not include objc headers
37 extern int MK_SHIFT;
38 extern int MK_CONTROL;
39 extern int MK_ALT;
40 #elif defined(USE_WIN32_WINDOWS)
41 #include "platform/C4windowswrapper.h"
42 #ifndef MK_ALT
43 #define MK_ALT 0x20 // as defined in oleidl.h
44 #endif
45 #endif
46 
47 #if defined(USE_WIN32_WINDOWS) || defined(USE_CONSOLE) || defined(USE_SDL_MAINLOOP)
48 #define K_ESCAPE 1
49 #define K_1 2
50 #define K_2 3
51 #define K_3 4
52 #define K_4 5
53 #define K_5 6
54 #define K_6 7
55 #define K_7 8
56 #define K_8 9
57 #define K_9 10
58 #define K_0 11
59 #define K_MINUS 12
60 #define K_EQUAL 13
61 #define K_BACK 14
62 #define K_TAB 15
63 #define K_Q 16
64 #define K_W 17
65 #define K_E 18
66 #define K_R 19
67 #define K_T 20
68 #define K_Y 21
69 #define K_U 22
70 #define K_I 23
71 #define K_O 24
72 #define K_P 25
73 #define K_LEFT_BRACKET 26
74 #define K_RIGHT_BRACKET 27
75 #define K_RETURN 28
76 #define K_CONTROL_L 29
77 #define K_A 30
78 #define K_S 31
79 #define K_D 32
80 #define K_F 33
81 #define K_G 34
82 #define K_H 35
83 #define K_J 36
84 #define K_K 37
85 #define K_L 38
86 #define K_SEMICOLON 39
87 #define K_APOSTROPHE 40
88 #define K_GRAVE_ACCENT 41
89 #define K_SHIFT_L 42
90 #define K_BACKSLASH 43
91 #define K_Z 44
92 #define K_X 45
93 #define K_C 46
94 #define K_V 47
95 #define K_B 48
96 #define K_N 49
97 #define K_M 50
98 #define K_COMMA 51
99 #define K_PERIOD 52
100 #define K_SLASH 53
101 #define K_SHIFT_R 54
102 #define K_MULTIPLY 55
103 #define K_ALT_L 56
104 #define K_SPACE 57
105 #define K_CAPS 58
106 #define K_F1 59
107 #define K_F2 60
108 #define K_F3 61
109 #define K_F4 62
110 #define K_F5 63
111 #define K_F6 64
112 #define K_F7 65
113 #define K_F8 66
114 #define K_F9 67
115 #define K_F10 68
116 #define K_NUM 69
117 #define K_SCROLL 70
118 #define K_SUBTRACT 74
119 #define K_ADD 78
120 #define K_86 86
121 #define K_F11 87
122 #define K_F12 88
123 
124 /*
125 // starting from here, scancodes between windows and linux differ
126 // this is not used because the windows scancodes are converted to
127 // unix scancodes in C4WindowWin32.cpp ConvertToUnixScancode
128 #if defined(USE_WIN32_WINDOWS)
129 #define K_HOME 71
130 #define K_UP 72
131 #define K_PAGEUP 73
132 #define K_LEFT 75
133 #define K_CENTER 76
134 #define K_RIGHT 77
135 #define K_END 79
136 #define K_DOWN 80
137 #define K_PAGEDOWN 81
138 #define K_INSERT 82
139 #define K_DELETE 83
140 #define K_WIN_L 91
141 #define K_WIN_R 92
142 #define K_MENU 93
143 #define K_PAUSE 69 // same as numlock?!
144 #define K_PRINT 55 // same as multiply?!
145 #define K_ALT_R K_ALT_L // 29 56
146 #define K_CONTROL_R K_CONTROL_L // 29 29
147 #define K_NUM_RETURN K_RETURN // 28 57
148 #define K_NUM7 K_HOME
149 #define K_NUM8 K_UP
150 #define K_NUM9 K_PAGEUP
151 #define K_NUM4 K_LEFT
152 #define K_NUM5 K_CENTER
153 #define K_NUM6 K_RIGHT
154 #define K_NUM1 K_END
155 #define K_NUM2 K_DOWN
156 #define K_NUM3 K_PAGEDOWN
157 #define K_NUM0 K_INSERT
158 #define K_DECIMAL K_DELETE
159 #define K_DIVIDE K_SLASH
160 #elif defined(USE_X11) || defined(USE_CONSOLE)
161 */
162 #define K_NUM7 71
163 #define K_NUM8 72
164 #define K_NUM9 73
165 #define K_NUM4 75
166 #define K_NUM5 76
167 #define K_NUM6 77
168 #define K_NUM1 79
169 #define K_NUM2 80
170 #define K_NUM3 81
171 #define K_NUM0 82
172 #define K_DECIMAL 83
173 #define K_DIVIDE 98
174 
175 #define K_ALT_R 100
176 #define K_CONTROL_R 97
177 #define K_NUM_RETURN 96
178 
179 #define K_HOME 102
180 #define K_UP 103
181 #define K_PAGEUP 104
182 #define K_LEFT 105
183 #define K_RIGHT 106
184 #define K_END 107
185 #define K_DOWN 108
186 #define K_PAGEDOWN 109
187 #define K_INSERT 110
188 #define K_DELETE 111
189 #define K_WIN_L 125
190 #define K_WIN_R 126
191 #define K_MENU 127
192 #define K_PAUSE 119
193 #define K_PRINT 99
194 #define K_CENTER 76
195 
196 #elif defined(USE_COCOA)
197 #import "platform/ObjectiveCAssociated.h"
198 // FIXME
199 // declare as extern variables and initialize them in StdMacWindow.mm so as to not include objc headers
200 const int CocoaKeycodeOffset = 300;
201 extern C4KeyCode K_SHIFT_L;
202 extern C4KeyCode K_SHIFT_R;
203 extern C4KeyCode K_CONTROL_L;
204 extern C4KeyCode K_CONTROL_R;
205 extern C4KeyCode K_ALT_L;
206 extern C4KeyCode K_ALT_R;
207 extern C4KeyCode K_COMMAND_L;
208 extern C4KeyCode K_COMMAND_R;
209 extern C4KeyCode K_F1;
210 extern C4KeyCode K_F2;
211 extern C4KeyCode K_F3;
212 extern C4KeyCode K_F4;
213 extern C4KeyCode K_F5;
214 extern C4KeyCode K_F6;
215 extern C4KeyCode K_F7;
216 extern C4KeyCode K_F8;
217 extern C4KeyCode K_F9;
218 extern C4KeyCode K_F10;
219 extern C4KeyCode K_F11;
220 extern C4KeyCode K_F12;
221 extern C4KeyCode K_ADD;
222 extern C4KeyCode K_SUBTRACT;
223 extern C4KeyCode K_MULTIPLY;
224 extern C4KeyCode K_ESCAPE;
225 extern C4KeyCode K_PAUSE;
226 extern C4KeyCode K_TAB;
227 extern C4KeyCode K_RETURN;
228 extern C4KeyCode K_DELETE;
229 extern C4KeyCode K_INSERT;
230 extern C4KeyCode K_BACK;
231 extern C4KeyCode K_SPACE;
232 extern C4KeyCode K_UP;
233 extern C4KeyCode K_DOWN;
234 extern C4KeyCode K_LEFT;
235 extern C4KeyCode K_RIGHT;
236 extern C4KeyCode K_HOME;
237 extern C4KeyCode K_END;
238 extern C4KeyCode K_SCROLL;
239 extern C4KeyCode K_MENU;
240 extern C4KeyCode K_PAGEUP;
241 extern C4KeyCode K_PAGEDOWN;
242 extern C4KeyCode K_M;
243 extern C4KeyCode K_T;
244 extern C4KeyCode K_W;
245 extern C4KeyCode K_I;
246 extern C4KeyCode K_C;
247 extern C4KeyCode K_V;
248 extern C4KeyCode K_X;
249 extern C4KeyCode K_A;
250 extern C4KeyCode K_NUM;
251 extern C4KeyCode K_PRINT;
252 extern C4KeyCode K_CENTER;
253 #endif
254 
255 
256 class C4Window
257 #ifdef USE_COCOA
258 	: public ObjectiveCAssociated
259 #endif
260 {
261 public:
262 	enum WindowKind
263 	{
264 		W_GuiWindow,
265 		W_Console,
266 		W_Viewport,
267 		W_Fullscreen,
268 		W_Control // wrapper to a render target control inside a window
269 	};
270 public:
271 	C4Window ();
272 	virtual ~C4Window ();
273 	bool Active{false};
274 	C4Surface * pSurface{nullptr};
275 	WindowKind eKind;
276 	virtual void Clear();
277 	// Only when the wm requests a close
278 	// For example, when the user clicks the little x in the corner or uses Alt-F4
279 	virtual void Close() = 0;
280 	// Keypress(es) translated to a char
CharIn(const char *)281 	virtual void CharIn(const char *) { }
282 
283 	// Reinitialize the window with updated configuration settings.
284 	// Keep window kind, title and size as they are. Currently the only point
285 	// at which it makes sense for this function to be called is when the
286 	// multisampling configuration option changes, since, for the change to
287 	// take effect, we need to choose another visual or pixel format, respectively.
288 	virtual bool ReInit(C4AbstractApp* pApp);
289 
290 	// Creates a list of available samples for multisampling
291 	virtual void EnumerateMultiSamples(std::vector<int>& samples) const;
292 
293 	bool StorePosition(const char *szWindowName, const char *szSubKey, bool fStoreSize = true);
294 	bool RestorePosition(const char *szWindowName, const char *szSubKey, bool fHidden = false);
295 	bool GetSize(C4Rect * pRect);
296 	void SetSize(unsigned int cx, unsigned int cy); // resize
297 	void SetTitle(const char * Title);
298 	void FlashWindow();
299 	void GrabMouse(bool grab);
300 	// request that this window be redrawn in the near future (including immediately)
301 	virtual void RequestUpdate();
302 	// Invokes actual drawing code - should not be called directly
303 	virtual void PerformUpdate();
304 
305 public:
306 #if defined(USE_WIN32_WINDOWS)
307 	HWND hWindow{nullptr};
Win32DialogMessageHandling(MSG * msg)308 	virtual bool Win32DialogMessageHandling(MSG * msg) { return false; };
309 #elif defined(USE_SDL_MAINLOOP)
310 	SDL_Window * window;
311 	void HandleSDLEvent(SDL_WindowEvent &e);
312 #endif
313 #ifdef USE_WGL
314 	HWND renderwnd;
315 #endif
316 #ifdef WITH_QT_EDITOR
317 	class QOpenGLWidget *glwidget{nullptr};
318 #endif
319 protected:
320 	virtual C4Window * Init(WindowKind windowKind, C4AbstractApp * pApp, const char * Title, const C4Rect * size);
321 	friend class C4Draw;
322 	friend class CStdGL;
323 	friend class CStdGLCtx;
324 	friend class C4AbstractApp;
325 };
326 
327 #endif // INC_STDWINDOW
328