Cleanup: remove redundant doxygen \file argument
[blender.git] / intern / ghost / intern / GHOST_SystemWin32.h
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
17  * All rights reserved.
18  */
19
20 /** \file \ingroup GHOST
21  * Declaration of GHOST_SystemWin32 class.
22  */
23
24 #ifndef __GHOST_SYSTEMWIN32_H__
25 #define __GHOST_SYSTEMWIN32_H__
26
27 #ifndef WIN32
28 #error WIN32 only!
29 #endif // WIN32
30
31 /* require Windows XP or newer */
32 #undef _WIN32_WINNT
33 #define _WIN32_WINNT 0x501
34
35 #define WIN32_LEAN_AND_MEAN
36 #include <windows.h>
37 #include <ole2.h> // for drag-n-drop
38
39 #include "GHOST_System.h"
40
41 class GHOST_EventButton;
42 class GHOST_EventCursor;
43 class GHOST_EventKey;
44 class GHOST_EventWheel;
45 class GHOST_EventWindow;
46 class GHOST_EventDragnDrop;
47
48 class GHOST_WindowWin32;
49
50 /**
51  * WIN32 Implementation of GHOST_System class.
52  * \see GHOST_System.
53  */
54 class GHOST_SystemWin32 : public GHOST_System {
55 public:
56         /**
57          * Constructor.
58          */
59         GHOST_SystemWin32();
60
61         /**
62          * Destructor.
63          */
64         ~GHOST_SystemWin32();
65
66         /***************************************************************************************
67          ** Time(r) functionality
68          ***************************************************************************************/
69
70         /**
71          * Returns the system time.
72          * Returns the number of milliseconds since the start of the system process.
73          * This overloaded method uses the high frequency timer if available.
74          * \return The number of milliseconds.
75          */
76         GHOST_TUns64 getMilliSeconds() const;
77
78         /***************************************************************************************
79          ** Display/window management functionality
80          ***************************************************************************************/
81
82         /**
83          * Returns the number of displays on this system.
84          * \return The number of displays.
85          */
86         GHOST_TUns8 getNumDisplays() const;
87
88         /**
89          * Returns the dimensions of the main display on this system.
90          * \return The dimension of the main display.
91          */
92         void getMainDisplayDimensions(GHOST_TUns32& width, GHOST_TUns32& height) const;
93
94         /**
95          * Returns the dimensions of all displays on this system.
96          * \return The dimension of the main display.
97          */
98         void getAllDisplayDimensions(GHOST_TUns32& width, GHOST_TUns32& height) const;
99
100         /**
101          * Create a new window.
102          * The new window is added to the list of windows managed.
103          * Never explicitly delete the window, use disposeWindow() instead.
104          * \param       title   The name of the window (displayed in the title bar of the window if the OS supports it).
105          * \param       left    The coordinate of the left edge of the window.
106          * \param       top             The coordinate of the top edge of the window.
107          * \param       width   The width the window.
108          * \param       height  The height the window.
109          * \param       state   The state of the window when opened.
110          * \param       type    The type of drawing context installed in this window.
111          * \param glSettings: Misc OpenGL settings.
112          * \param exclusive: Use to show the window ontop and ignore others (used fullscreen).
113          * \param       parentWindow    Parent (embedder) window
114          * \return      The new window (or 0 if creation failed).
115          */
116         GHOST_IWindow *createWindow(
117             const STR_String& title,
118             GHOST_TInt32 left, GHOST_TInt32 top, GHOST_TUns32 width, GHOST_TUns32 height,
119             GHOST_TWindowState state, GHOST_TDrawingContextType type,
120             GHOST_GLSettings glSettings,
121             const bool exclusive = false,
122             const GHOST_TEmbedderWindowID parentWindow = 0);
123
124
125         /**
126          * Create a new offscreen context.
127          * Never explicitly delete the window, use disposeContext() instead.
128          * \return  The new context (or 0 if creation failed).
129          */
130         GHOST_IContext *createOffscreenContext();
131
132         /**
133          * Dispose of a context.
134          * \param   context Pointer to the context to be disposed.
135          * \return  Indication of success.
136          */
137         GHOST_TSuccess disposeContext(GHOST_IContext *context);
138
139         /***************************************************************************************
140          ** Event management functionality
141          ***************************************************************************************/
142
143         /**
144          * Gets events from the system and stores them in the queue.
145          * \param waitForEvent Flag to wait for an event (or return immediately).
146          * \return Indication of the presence of events.
147          */
148         bool processEvents(bool waitForEvent);
149
150
151         /***************************************************************************************
152          ** Cursor management functionality
153          ***************************************************************************************/
154
155         /**
156          * Returns the current location of the cursor (location in screen coordinates)
157          * \param x                     The x-coordinate of the cursor.
158          * \param y                     The y-coordinate of the cursor.
159          * \return                      Indication of success.
160          */
161         GHOST_TSuccess getCursorPosition(GHOST_TInt32& x, GHOST_TInt32& y) const;
162
163         /**
164          * Updates the location of the cursor (location in screen coordinates).
165          * \param x                     The x-coordinate of the cursor.
166          * \param y                     The y-coordinate of the cursor.
167          * \return                      Indication of success.
168          */
169         GHOST_TSuccess setCursorPosition(GHOST_TInt32 x, GHOST_TInt32 y);
170
171         /***************************************************************************************
172          ** Access to mouse button and keyboard states.
173          ***************************************************************************************/
174
175         /**
176          * Returns the state of all modifier keys.
177          * \param keys  The state of all modifier keys (true == pressed).
178          * \return              Indication of success.
179          */
180         GHOST_TSuccess getModifierKeys(GHOST_ModifierKeys& keys) const;
181
182         /**
183          * Returns the state of the mouse buttons (ouside the message queue).
184          * \param buttons       The state of the buttons.
185          * \return                      Indication of success.
186          */
187         GHOST_TSuccess getButtons(GHOST_Buttons& buttons) const;
188
189         /**
190          * Returns unsigned char from CUT_BUFFER0
191          * \param selection             Used by X11 only
192          * \return                              Returns the Clipboard
193          */
194         GHOST_TUns8 *getClipboard(bool selection) const;
195
196         /**
197          * Puts buffer to system clipboard
198          * \param selection             Used by X11 only
199          * \return                              No return
200          */
201         void putClipboard(GHOST_TInt8 *buffer, bool selection) const;
202
203         /**
204          * Creates a drag'n'drop event and pushes it immediately onto the event queue.
205          * Called by GHOST_DropTargetWin32 class.
206          * \param eventType The type of drag'n'drop event
207          * \param draggedObjectType The type object concerned (currently array of file names, string, ?bitmap)
208          * \param mouseX x mouse coordinate (in window coordinates)
209          * \param mouseY y mouse coordinate
210          * \param window The window on which the event occurred
211          * \return Indication whether the event was handled.
212          */
213         static GHOST_TSuccess pushDragDropEvent(GHOST_TEventType eventType, GHOST_TDragnDropTypes draggedObjectType, GHOST_WindowWin32 *window, int mouseX, int mouseY, void *data);
214
215         /**
216          * Confirms quitting he program when there is just one window left open
217          * in the application
218          */
219         int confirmQuit(GHOST_IWindow *window) const;
220
221 protected:
222         /**
223          * Initializes the system.
224          * For now, it just registers the window class (WNDCLASS).
225          * \return A success value.
226          */
227         GHOST_TSuccess init();
228
229         /**
230          * Closes the system down.
231          * \return A success value.
232          */
233         GHOST_TSuccess exit();
234
235         /**
236          * Converts raw WIN32 key codes from the wndproc to GHOST keys.
237          * \param vKey          The virtual key from hardKey
238          * \param ScanCode      The ScanCode of pressed key (similar to PS/2 Set 1)
239          * \param extend        Flag if key is not primly (left or right)
240          * \return The GHOST key (GHOST_kKeyUnknown if no match).
241          */
242         GHOST_TKey convertKey(short vKey, short ScanCode, short extend) const;
243
244         /**
245          * Catches raw WIN32 key codes from WM_INPUT in the wndproc.
246          * \param raw           RawInput structure with detailed info about the key event
247          * \param keyDown       Pointer flag that specify if a key is down
248          * \param vk            Pointer to virtual key
249          * \return The GHOST key (GHOST_kKeyUnknown if no match).
250          */
251         GHOST_TKey hardKey(RAWINPUT const& raw, int *keyDown, char *vk);
252
253         /**
254          * Creates mouse button event.
255          * \param type          The type of event to create.
256          * \param window        The window receiving the event (the active window).
257          * \param mask          The button mask of this event.
258          * \return The event created.
259          */
260         static GHOST_EventButton *processButtonEvent(GHOST_TEventType type, GHOST_WindowWin32 *window, GHOST_TButtonMask mask);
261
262         /**
263          * Creates cursor event.
264          * \param type          The type of event to create.
265          * \param window        The window receiving the event (the active window).
266          * \return The event created.
267          */
268         static GHOST_EventCursor *processCursorEvent(GHOST_TEventType type, GHOST_WindowWin32 *window);
269
270         /**
271          * Handles a mouse wheel event.
272          * \param window        The window receiving the event (the active window).
273          * \param wParam        The wParam from the wndproc
274          * \param lParam        The lParam from the wndproc
275          */
276         static void processWheelEvent(GHOST_WindowWin32 *window, WPARAM wParam, LPARAM lParam);
277
278         /**
279          * Creates a key event and updates the key data stored locally (m_modifierKeys).
280          * In most cases this is a straightforward conversion of key codes.
281          * For the modifier keys however, we want to distinguish left and right keys.
282          * \param window        The window receiving the event (the active window).
283          * \param raw           RawInput structure with detailed info about the key event
284          */
285         static GHOST_EventKey *processKeyEvent(GHOST_WindowWin32 *window, RAWINPUT const& raw);
286
287         /**
288          * Process special keys (VK_OEM_*), to see if current key layout
289          * gives us anything special, like ! on french AZERTY.
290          * \param vKey          The virtual key from hardKey
291          * \param scanCode      The ScanCode of pressed key (simular to PS/2 Set 1)
292          */
293         GHOST_TKey processSpecialKey(short vKey, short scanCode) const;
294
295         /**
296          * Creates a window event.
297          * \param type          The type of event to create.
298          * \param window        The window receiving the event (the active window).
299          * \return The event created.
300          */
301         static GHOST_Event *processWindowEvent(GHOST_TEventType type, GHOST_WindowWin32 *window);
302
303 #ifdef WITH_INPUT_IME
304         /**
305          * Creates a IME event.
306          * \param type          The type of event to create.
307          * \param window                The window receiving the event (the active window).
308          * \param data          IME data.
309          * \return The event created.
310          */
311         static GHOST_Event *processImeEvent(GHOST_TEventType type, GHOST_WindowWin32 *window, GHOST_TEventImeData *data);
312 #endif // WITH_INPUT_IME
313
314         /**
315          * Handles minimum window size.
316          * \param minmax        The MINMAXINFO structure.
317          */
318         static void processMinMaxInfo(MINMAXINFO *minmax);
319
320 #ifdef WITH_INPUT_NDOF
321         /**
322          * Handles Motion and Button events from a SpaceNavigator or related device.
323          * Instead of returning an event object, this function communicates directly
324          * with the GHOST_NDOFManager.
325          * \param raw           RawInput structure with detailed info about the NDOF event
326          * \return Whether an event was generated and sent.
327          */
328         bool processNDOF(RAWINPUT const& raw);
329 #endif
330
331         /**
332          * Returns the local state of the modifier keys (from the message queue).
333          * \param keys The state of the keys.
334          */
335         inline void retrieveModifierKeys(GHOST_ModifierKeys& keys) const;
336
337         /**
338          * Stores the state of the modifier keys locally.
339          * For internal use only!
340          * param keys The new state of the modifier keys.
341          */
342         inline void storeModifierKeys(const GHOST_ModifierKeys& keys);
343
344         /**
345          * Check current key layout for AltGr
346          */
347         inline void handleKeyboardChange(void);
348
349         /**
350          * Windows call back routine for our window class.
351          */
352         static LRESULT WINAPI s_wndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
353
354         /**
355          * Toggles console
356          * \param action
357          * - 0 - Hides
358          * - 1 - Shows
359          * - 2 - Toggles
360          * - 3 - Hides if it runs not from  command line
361          * - * - Does nothing
362          * \return current status (1 -visible, 0 - hidden)
363          */
364         int toggleConsole(int action);
365
366         /** The current state of the modifier keys. */
367         GHOST_ModifierKeys m_modifierKeys;
368         /** State variable set at initialization. */
369         bool m_hasPerformanceCounter;
370         /** High frequency timer variable. */
371         __int64 m_freq;
372         /** High frequency timer variable. */
373         __int64 m_start;
374         /** AltGr on current keyboard layout. */
375         bool m_hasAltGr;
376         /** language identifier. */
377         WORD m_langId;
378         /** stores keyboard layout. */
379         HKL m_keylayout;
380
381         /** Console status */
382         int m_consoleStatus;
383
384         /** Wheel delta accumulator **/
385         int m_wheelDeltaAccum;
386 };
387
388 inline void GHOST_SystemWin32::retrieveModifierKeys(GHOST_ModifierKeys& keys) const
389 {
390         keys = m_modifierKeys;
391 }
392
393 inline void GHOST_SystemWin32::storeModifierKeys(const GHOST_ModifierKeys& keys)
394 {
395         m_modifierKeys = keys;
396 }
397
398 inline void GHOST_SystemWin32::handleKeyboardChange(void)
399 {
400         m_keylayout = GetKeyboardLayout(0); // get keylayout for current thread
401         int i;
402         SHORT s;
403
404         // save the language identifier.
405         m_langId = LOWORD(m_keylayout);
406
407         for (m_hasAltGr = false, i = 32; i < 256; ++i) {
408                 s = VkKeyScanEx((char)i, m_keylayout);
409                 // s == -1 means no key that translates passed char code
410                 // high byte contains shift state. bit 2 ctrl pressed, bit 4 alt pressed
411                 // if both are pressed, we have AltGr keycombo on keylayout
412                 if (s != -1 && (s & 0x600) == 0x600) {
413                         m_hasAltGr = true;
414                         break;
415                 }
416         }
417 }
418 #endif // __GHOST_SYSTEMWIN32_H__