1 |
/******************************************************************************* |
= |
1 |
/******************************************************************************* |
2 |
* Copyright (c) 2000, 2005 IBM Corporation and others. |
|
2 |
* Copyright (c) 2000, 2005 IBM Corporation and others. |
3 |
* All rights reserved. This program and the accompanying materials |
|
3 |
* All rights reserved. This program and the accompanying materials |
4 |
* are made available under the terms of the Eclipse Public License v1.0 |
|
4 |
* are made available under the terms of the Eclipse Public License v1.0 |
5 |
* which accompanies this distribution, and is available at |
|
5 |
* which accompanies this distribution, and is available at |
6 |
* http://www.eclipse.org/legal/epl-v10.html |
|
6 |
* http://www.eclipse.org/legal/epl-v10.html |
7 |
* |
|
7 |
* |
8 |
* Contributors: |
|
8 |
* Contributors: |
9 |
* IBM Corporation - initial API and implementation |
|
9 |
* IBM Corporation - initial API and implementation |
10 |
*******************************************************************************/ |
|
10 |
*******************************************************************************/ |
|
|
<> |
11 |
|
|
|
|
12 |
/******************************************************************************* |
|
|
|
13 |
* Additions/modifications to this source file by Oracle America, Inc. 2011 |
|
|
|
14 |
*******************************************************************************/ |
|
|
|
15 |
|
11 |
#define _WIN32_WINNT 0x0500 |
= |
16 |
#define _WIN32_WINNT 0x0500 |
12 |
|
|
17 |
|
13 |
#include "ugl_win32.h" |
|
18 |
#include "ugl_win32.h" |
14 |
|
|
19 |
|
15 |
#include "Callback.h" |
|
20 |
#include "Callback.h" |
16 |
#include "UGL_Win32_DC.h" |
|
21 |
#include "UGL_Win32_DC.h" |
17 |
#include "UGL_Win32_Display.h" |
|
22 |
#include "UGL_Win32_Display.h" |
18 |
#include "UGL_Win32_Widget.h" |
|
23 |
#include "UGL_Win32_Widget.h" |
19 |
#include "UGL_Win32_Menu.h" |
|
24 |
#include "UGL_Win32_Menu.h" |
20 |
#include "UGL_Win32_Tray.h" |
|
25 |
#include "UGL_Win32_Tray.h" |
21 |
#include "KeyUtils.h" |
|
26 |
#include "KeyUtils.h" |
22 |
|
|
27 |
|
23 |
#include "Shell.h" |
|
28 |
#include "Shell.h" |
24 |
#include "Color.h" |
|
29 |
#include "Color.h" |
25 |
#include "Button.h" |
|
30 |
#include "Button.h" |
26 |
#include "Label.h" |
|
31 |
#include "Label.h" |
27 |
#include "TextArea.h" |
|
32 |
#include "TextArea.h" |
28 |
#include "Composite.h" |
|
33 |
#include "Composite.h" |
29 |
#include "List.h" |
|
34 |
#include "List.h" |
30 |
#include "Combo.h" |
|
35 |
#include "Combo.h" |
31 |
#include "Device.h" |
|
36 |
#include "Device.h" |
32 |
|
|
37 |
|
33 |
#include "Display.h" |
|
38 |
#include "Display.h" |
34 |
#include <stdio.h> |
|
39 |
#include <stdio.h> |
35 |
#include <shlwapi.h> |
|
40 |
#include <shlwapi.h> |
36 |
|
|
41 |
|
37 |
static LRESULT CALLBACK creationProc(HWND, UINT, WPARAM, LPARAM); |
|
42 |
static LRESULT CALLBACK creationProc(HWND, UINT, WPARAM, LPARAM); |
38 |
|
|
43 |
|
39 |
static VOID CALLBACK _Timer_Proc(HWND, UINT, UINT_PTR, DWORD); |
|
44 |
static VOID CALLBACK _Timer_Proc(HWND, UINT, UINT_PTR, DWORD); |
40 |
void _Dispose_Display(UGL_Int handle, UGL_Error uglError); |
|
45 |
void _Dispose_Display(UGL_Int handle, UGL_Error uglError); |
41 |
|
|
46 |
|
42 |
#define MENU_ITEMS_INCREMENT 4 |
|
47 |
#define MENU_ITEMS_INCREMENT 4 |
43 |
|
|
48 |
|
44 |
/** |
|
49 |
/** |
45 |
* Strange behavior happens when menu IDs less than 108 are used. The |
|
50 |
* Strange behavior happens when menu IDs less than 108 are used. The |
46 |
* PocketPC will display some system menus when certian low IDs are used. |
|
51 |
* PocketPC will display some system menus when certian low IDs are used. |
47 |
* This offset is the difference between the menu item index in the global |
|
52 |
* This offset is the difference between the menu item index in the global |
48 |
* list and the value of the id. |
|
53 |
* list and the value of the id. |
49 |
*/ |
|
54 |
*/ |
50 |
#define MENU_ITEM_ID_OFFSET 108 |
|
55 |
#define MENU_ITEM_ID_OFFSET 108 |
51 |
|
|
56 |
|
52 |
HINSTANCE g_hInstance = NULL; |
|
57 |
HINSTANCE g_hInstance = NULL; |
53 |
BOOL WINAPI DllMain(HANDLE hInstDLL, DWORD dwReason, LPVOID lpvReserved) |
|
58 |
BOOL WINAPI DllMain(HANDLE hInstDLL, DWORD dwReason, LPVOID lpvReserved) |
54 |
{ |
|
59 |
{ |
55 |
if (dwReason == DLL_PROCESS_ATTACH) { |
|
60 |
if (dwReason == DLL_PROCESS_ATTACH) { |
56 |
if (g_hInstance == NULL) g_hInstance = hInstDLL; |
|
61 |
if (g_hInstance == NULL) g_hInstance = hInstDLL; |
57 |
} |
|
62 |
} |
58 |
return TRUE; |
|
63 |
return TRUE; |
59 |
} |
|
64 |
} |
60 |
|
|
65 |
|
61 |
//======================================================================================== |
|
66 |
//======================================================================================== |
62 |
|
|
67 |
|
63 |
CallbackLookup* Display_GetCallbacks(UGL_Int displayHandle) { |
|
68 |
CallbackLookup* Display_GetCallbacks(UGL_Int displayHandle) { |
64 |
PUGL_Display display = UGL_DISPLAY(displayHandle); |
|
69 |
PUGL_Display display = UGL_DISPLAY(displayHandle); |
65 |
return display->callback_lookup; |
|
70 |
return display->callback_lookup; |
66 |
} |
|
71 |
} |
67 |
//======================================================================================== |
|
72 |
//======================================================================================== |
68 |
|
|
73 |
|
69 |
void Display_SetCallbacks(UGL_Int displayHandle, CallbackLookup* callbacks) { |
|
74 |
void Display_SetCallbacks(UGL_Int displayHandle, CallbackLookup* callbacks) { |
70 |
PUGL_Display display = UGL_DISPLAY(displayHandle); |
|
75 |
PUGL_Display display = UGL_DISPLAY(displayHandle); |
71 |
display->callback_lookup = callbacks; |
|
76 |
display->callback_lookup = callbacks; |
72 |
} |
|
77 |
} |
73 |
|
|
78 |
|
74 |
//======================================================================================== |
|
79 |
//======================================================================================== |
75 |
|
|
80 |
|
76 |
void Display_StartTimer(UGL_Int handle, UGL_Int milliseconds, UGL_Int timerId, UGL_Error uglError) { |
|
81 |
void Display_StartTimer(UGL_Int handle, UGL_Int milliseconds, UGL_Int timerId, UGL_Error uglError) { |
77 |
PUGL_Display ugl_display = UGL_DISPLAY(handle); |
|
82 |
PUGL_Display ugl_display = UGL_DISPLAY(handle); |
78 |
|
|
83 |
|
79 |
// Although the MSDN documentation does not mention this, SetTimer will fail on |
|
84 |
// Although the MSDN documentation does not mention this, SetTimer will fail on |
80 |
// PocketPC when a timerId of 0 is used. Bumping the timerId by 1 will avoid the |
|
85 |
// PocketPC when a timerId of 0 is used. Bumping the timerId by 1 will avoid the |
81 |
// failure, but it is important that the 1 be subtracted from the id before being |
|
86 |
// failure, but it is important that the 1 be subtracted from the id before being |
82 |
// sent back to Java. See _Timer_Proc to see the id being bumped down. |
|
87 |
// sent back to Java. See _Timer_Proc to see the id being bumped down. |
83 |
int newTimer = SetTimer(ugl_display->creation_hWnd, timerId+1, milliseconds, _Timer_Proc); |
|
88 |
int newTimer = SetTimer(ugl_display->creation_hWnd, timerId+1, milliseconds, _Timer_Proc); |
84 |
if (newTimer == 0) { |
|
89 |
if (newTimer == 0) { |
85 |
Win32Error_SetError(uglError, GetLastError(), _T("Failed to create timer")); |
|
90 |
Win32Error_SetError(uglError, GetLastError(), _T("Failed to create timer")); |
86 |
} |
|
91 |
} |
87 |
} |
|
92 |
} |
88 |
|
|
93 |
|
89 |
//======================================================================================== |
|
94 |
//======================================================================================== |
90 |
|
|
95 |
|
91 |
UGL_Int Display_New(UGL_Error uglError) { |
|
96 |
UGL_Int Display_New(UGL_Error uglError) { |
92 |
PUGL_Device ugl_device; |
|
97 |
PUGL_Device ugl_device; |
93 |
PUGL_Display ugl_display = NULL; |
|
98 |
PUGL_Display ugl_display = NULL; |
94 |
|
|
99 |
|
95 |
WNDCLASS staticClass; |
|
100 |
WNDCLASS staticClass; |
96 |
WNDCLASS wndClass; |
|
101 |
WNDCLASS wndClass; |
97 |
HWND creation_hWnd = NULL; |
|
102 |
HWND creation_hWnd = NULL; |
|
|
-+ |
103 |
#ifdef _WIN32_WCE |
|
|
|
104 |
TCHAR oemInfo[256]; |
|
|
|
105 |
#endif // #ifdef _WIN32_WCE |
98 |
|
= |
106 |
|
99 |
if (GetClassInfo(g_hInstance, _T("STATIC"), &staticClass) == FALSE) { |
|
107 |
if (GetClassInfo(g_hInstance, _T("STATIC"), &staticClass) == FALSE) { |
100 |
Win32Error_SetError(uglError, GetLastError(), _T("Unable get \"STATIC\" class data")); |
|
108 |
Win32Error_SetError(uglError, GetLastError(), _T("Unable get \"STATIC\" class data")); |
101 |
return 0; |
|
109 |
return 0; |
102 |
} |
|
110 |
} |
103 |
|
|
111 |
|
104 |
memset(&wndClass, 0, sizeof(WNDCLASS)); |
|
112 |
memset(&wndClass, 0, sizeof(WNDCLASS)); |
105 |
|
|
113 |
|
106 |
wndClass.hInstance = g_hInstance; |
|
114 |
wndClass.hInstance = g_hInstance; |
107 |
wndClass.lpfnWndProc = (WNDPROC)DefWindowProc; |
|
115 |
wndClass.lpfnWndProc = (WNDPROC)DefWindowProc; |
108 |
#ifdef _WIN32_WCE |
|
116 |
#ifdef _WIN32_WCE |
109 |
wndClass.style = CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW; |
|
117 |
wndClass.style = CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW; |
110 |
#else |
|
118 |
#else |
111 |
wndClass.style = CS_BYTEALIGNWINDOW | CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW; |
|
119 |
wndClass.style = CS_BYTEALIGNWINDOW | CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW; |
112 |
#endif |
|
120 |
#endif |
113 |
wndClass.hCursor = staticClass.hCursor; |
|
121 |
wndClass.hCursor = staticClass.hCursor; |
114 |
wndClass.lpszClassName = WINDOW_CLASS_NAME; |
|
122 |
wndClass.lpszClassName = WINDOW_CLASS_NAME; |
115 |
wndClass.hbrBackground = staticClass.hbrBackground; |
|
123 |
wndClass.hbrBackground = staticClass.hbrBackground; |
116 |
RegisterClass (&wndClass); |
|
124 |
RegisterClass (&wndClass); |
117 |
|
|
125 |
|
118 |
|
|
126 |
|
119 |
ugl_display = UGL_DISPLAY(calloc(sizeof(UGL_Display), 1)); |
|
127 |
ugl_display = UGL_DISPLAY(calloc(sizeof(UGL_Display), 1)); |
120 |
|
|
128 |
|
121 |
ugl_device = UGL_DEVICE(ugl_display); |
|
129 |
ugl_device = UGL_DEVICE(ugl_display); |
122 |
ugl_device->device_dispose = _Dispose_Display; |
|
130 |
ugl_device->device_dispose = _Dispose_Display; |
123 |
|
|
131 |
|
124 |
// message only window that will be called to create UI on the display thread |
|
132 |
// message only window that will be called to create UI on the display thread |
125 |
creation_hWnd = CreateWindowEx(0, WINDOW_CLASS_NAME, NULL, WS_OVERLAPPED, 0, 0, 0, 0, 0, NULL, g_hInstance, NULL); |
|
133 |
creation_hWnd = CreateWindowEx(0, WINDOW_CLASS_NAME, NULL, WS_OVERLAPPED, 0, 0, 0, 0, 0, NULL, g_hInstance, NULL); |
126 |
if (!creation_hWnd) { |
|
134 |
if (!creation_hWnd) { |
127 |
free(ugl_display); |
|
135 |
free(ugl_display); |
128 |
Win32Error_SetError(uglError, GetLastError(), _T("Unable to create message/creation window")); |
|
136 |
Win32Error_SetError(uglError, GetLastError(), _T("Unable to create message/creation window")); |
129 |
return NULL_HANDLE; |
|
137 |
return NULL_HANDLE; |
130 |
} |
|
138 |
} |
131 |
|
|
139 |
|
132 |
SetWindowLong(creation_hWnd, GWL_WNDPROC, (LONG)creationProc); |
|
140 |
SetWindowLong(creation_hWnd, GWL_WNDPROC, (LONG)creationProc); |
133 |
SetWindowLong(creation_hWnd, GWL_USERDATA, (LONG)ugl_display); |
|
141 |
SetWindowLong(creation_hWnd, GWL_USERDATA, (LONG)ugl_display); |
134 |
|
|
142 |
|
135 |
ugl_display->callback_lookup = NULL; |
|
143 |
ugl_display->callback_lookup = NULL; |
136 |
ugl_display->creation_hWnd = creation_hWnd; |
|
144 |
ugl_display->creation_hWnd = creation_hWnd; |
137 |
ugl_display->processID = GetCurrentProcessId(); |
|
145 |
ugl_display->processID = GetCurrentProcessId(); |
138 |
ugl_display->threadID = GetCurrentThreadId(); |
|
146 |
ugl_display->threadID = GetCurrentThreadId(); |
139 |
ugl_display->hInstance = g_hInstance; |
|
147 |
ugl_display->hInstance = g_hInstance; |
140 |
|
|
148 |
|
141 |
ugl_display->menuItemsLength = 0; |
|
149 |
ugl_display->menuItemsLength = 0; |
142 |
ugl_display->menuItemCount = 0; |
|
150 |
ugl_display->menuItemCount = 0; |
143 |
ugl_display->menuItems = NULL; |
|
151 |
ugl_display->menuItems = NULL; |
|
|
<> |
152 |
|
|
|
|
153 |
ugl_display->isEmulator = FALSE; |
|
|
|
154 |
|
|
|
|
155 |
#ifdef _WIN32_WCE |
|
|
|
156 |
// now check to see if we are running on the emulator |
|
|
|
157 |
SystemParametersInfo(SPI_GETOEMINFO, 256, oemInfo, 0); |
|
|
|
158 |
if(_tcsicmp(oemInfo, L"Microsoft DeviceEmulator") == 0) { |
|
|
|
159 |
ugl_display->isEmulator = TRUE; |
|
|
|
160 |
} |
|
|
|
161 |
#endif // #ifdef _WIN32_WCE |
144 |
|
= |
162 |
|
145 |
return (UGL_Int)ugl_display; |
|
163 |
return (UGL_Int)ugl_display; |
146 |
} |
|
164 |
} |
147 |
void _Display_AddMenu(PUGL_Display display, UGL_Int menuHandle, HMENU hMenu, UGL_Error uglError) { |
|
165 |
void _Display_AddMenu(PUGL_Display display, UGL_Int menuHandle, HMENU hMenu, UGL_Error uglError) { |
148 |
PMenuList menuList, endMenuList; |
|
166 |
PMenuList menuList, endMenuList; |
149 |
if (display->menus == NULL) { |
|
167 |
if (display->menus == NULL) { |
150 |
menuList = (PMenuList)calloc(sizeof(MenuList), 1); |
|
168 |
menuList = (PMenuList)calloc(sizeof(MenuList), 1); |
151 |
display->menus = menuList; |
|
169 |
display->menus = menuList; |
152 |
} else { |
|
170 |
} else { |
153 |
menuList = display->menus; |
|
171 |
menuList = display->menus; |
154 |
while (menuList != NULL) { |
|
172 |
while (menuList != NULL) { |
155 |
endMenuList = menuList; |
|
173 |
endMenuList = menuList; |
156 |
menuList = menuList->next; |
|
174 |
menuList = menuList->next; |
157 |
} |
|
175 |
} |
158 |
menuList = (PMenuList)calloc(sizeof(MenuList), 1); |
|
176 |
menuList = (PMenuList)calloc(sizeof(MenuList), 1); |
159 |
endMenuList->next = menuList; |
|
177 |
endMenuList->next = menuList; |
160 |
} |
|
178 |
} |
161 |
menuList->menuHandle = menuHandle; |
|
179 |
menuList->menuHandle = menuHandle; |
162 |
menuList->hMenu = hMenu; |
|
180 |
menuList->hMenu = hMenu; |
163 |
} |
|
181 |
} |
164 |
void _Display_RemoveMenu(PUGL_Display display, UGL_Int menuHandle, UGL_Error uglError) { |
|
182 |
void _Display_RemoveMenu(PUGL_Display display, UGL_Int menuHandle, UGL_Error uglError) { |
165 |
PMenuList menuList = display->menus; |
|
183 |
PMenuList menuList = display->menus; |
166 |
PMenuList prevMenu; |
|
184 |
PMenuList prevMenu; |
167 |
if (menuList->menuHandle == menuHandle) { |
|
185 |
if (menuList->menuHandle == menuHandle) { |
168 |
display->menus = menuList->next; |
|
186 |
display->menus = menuList->next; |
169 |
} else { |
|
187 |
} else { |
170 |
prevMenu = menuList; |
|
188 |
prevMenu = menuList; |
171 |
menuList = menuList->next; |
|
189 |
menuList = menuList->next; |
172 |
while (menuList != NULL) { |
|
190 |
while (menuList != NULL) { |
173 |
if (menuList->menuHandle == menuHandle) break; |
|
191 |
if (menuList->menuHandle == menuHandle) break; |
174 |
prevMenu = menuList; |
|
192 |
prevMenu = menuList; |
175 |
menuList = menuList->next; |
|
193 |
menuList = menuList->next; |
176 |
} |
|
194 |
} |
177 |
if (menuList == NULL) return; |
|
195 |
if (menuList == NULL) return; |
178 |
prevMenu->next = menuList->next; |
|
196 |
prevMenu->next = menuList->next; |
179 |
} |
|
197 |
} |
180 |
free(menuList); |
|
198 |
free(menuList); |
181 |
} |
|
199 |
} |
182 |
UGL_Int _Display_FindMenu(PUGL_Display display, HMENU hMenu) { |
|
200 |
UGL_Int _Display_FindMenu(PUGL_Display display, HMENU hMenu) { |
183 |
PMenuList menuList = display->menus; |
|
201 |
PMenuList menuList = display->menus; |
184 |
while (menuList != NULL) { |
|
202 |
while (menuList != NULL) { |
185 |
if (menuList->hMenu == hMenu) return menuList->menuHandle; |
|
203 |
if (menuList->hMenu == hMenu) return menuList->menuHandle; |
186 |
menuList = menuList->next; |
|
204 |
menuList = menuList->next; |
187 |
} |
|
205 |
} |
188 |
return 0; |
|
206 |
return 0; |
189 |
} |
|
207 |
} |
190 |
PUGL_Shell _Display_FindClosestShell(HWND child) { |
|
208 |
PUGL_Shell _Display_FindClosestShell(HWND child) { |
191 |
while (child != NULL) { |
|
209 |
while (child != NULL) { |
192 |
LONG style = GetWindowLong(child, GWL_STYLE); |
|
210 |
LONG style = GetWindowLong(child, GWL_STYLE); |
193 |
if ((style & WS_CHILD) != WS_CHILD) { |
|
211 |
if ((style & WS_CHILD) != WS_CHILD) { |
194 |
PUGL_Shell shell = (PUGL_Shell)GetWindowLong(child, GWL_USERDATA); |
|
212 |
PUGL_Shell shell = (PUGL_Shell)GetWindowLong(child, GWL_USERDATA); |
195 |
return shell; |
|
213 |
return shell; |
196 |
} |
|
214 |
} |
197 |
child = GetParent(child); |
|
215 |
child = GetParent(child); |
198 |
} |
|
216 |
} |
199 |
return NULL; |
|
217 |
return NULL; |
200 |
} |
|
218 |
} |
201 |
int _Display_GetComCtrlMajorVersion(PUGL_Display display, UGL_Error uglError) { |
|
219 |
int _Display_GetComCtrlMajorVersion(PUGL_Display display, UGL_Error uglError) { |
202 |
HINSTANCE library; |
|
220 |
HINSTANCE library; |
203 |
DLLVERSIONINFO dvi; |
|
221 |
DLLVERSIONINFO dvi; |
204 |
|
|
222 |
|
205 |
if (display->comCtrl32Major != 0) return display->comCtrl32Major; |
|
223 |
if (display->comCtrl32Major != 0) return display->comCtrl32Major; |
206 |
library = LoadLibrary(_T("comctl32.dll")); |
|
224 |
library = LoadLibrary(_T("comctl32.dll")); |
207 |
if (library == NULL) { |
|
225 |
if (library == NULL) { |
208 |
Win32Error_SetError(uglError, UGL_ERROR_OTHER, _T("Failed to load comctl32.dll")); |
|
226 |
Win32Error_SetError(uglError, UGL_ERROR_OTHER, _T("Failed to load comctl32.dll")); |
209 |
return 0; |
|
227 |
return 0; |
210 |
} else { |
|
228 |
} else { |
211 |
DLLGETVERSIONPROC pDllGetVersion = (DLLGETVERSIONPROC)GetProcAddress(library, "DllGetVersion"); |
|
229 |
DLLGETVERSIONPROC pDllGetVersion = (DLLGETVERSIONPROC)GetProcAddress(library, "DllGetVersion"); |
212 |
if (pDllGetVersion != NULL) { |
|
230 |
if (pDllGetVersion != NULL) { |
213 |
HRESULT result; |
|
231 |
HRESULT result; |
214 |
dvi.cbSize = sizeof(dvi); |
|
232 |
dvi.cbSize = sizeof(dvi); |
215 |
result = pDllGetVersion(&dvi); |
|
233 |
result = pDllGetVersion(&dvi); |
216 |
if(result == S_OK) { |
|
234 |
if(result == S_OK) { |
217 |
display->comCtrl32Major = dvi.dwMajorVersion; |
|
235 |
display->comCtrl32Major = dvi.dwMajorVersion; |
218 |
display->comCtrl32Minor = dvi.dwMinorVersion; |
|
236 |
display->comCtrl32Minor = dvi.dwMinorVersion; |
219 |
FreeLibrary(library); |
|
237 |
FreeLibrary(library); |
220 |
return dvi.dwMajorVersion; |
|
238 |
return dvi.dwMajorVersion; |
221 |
} |
|
239 |
} |
222 |
} |
|
240 |
} |
223 |
Win32Error_SetError(uglError, GetLastError(), _T("Unable to get comctrl version")); |
|
241 |
Win32Error_SetError(uglError, GetLastError(), _T("Unable to get comctrl version")); |
224 |
FreeLibrary(library); |
|
242 |
FreeLibrary(library); |
225 |
} |
|
243 |
} |
226 |
return 0; |
|
244 |
return 0; |
227 |
} |
|
245 |
} |
228 |
|
|
246 |
|
229 |
BOOL _Display_FilterMessage(PUGL_Display display, LPMSG msg) { |
|
247 |
BOOL _Display_FilterMessage(PUGL_Display display, LPMSG msg) { |
230 |
/* |
|
248 |
/* |
231 |
* Although the MSDN documentation for TranslateAccelerator says that |
|
249 |
* Although the MSDN documentation for TranslateAccelerator says that |
232 |
* only WM_KEYDOWN/KEYUP/SYSKEYDOWN/SYSKEYUP messages are translated, |
|
250 |
* only WM_KEYDOWN/KEYUP/SYSKEYDOWN/SYSKEYUP messages are translated, |
233 |
* accelerators were not dispatched correctly unless ALL key messages were |
|
251 |
* accelerators were not dispatched correctly unless ALL key messages were |
234 |
* handled |
|
252 |
* handled |
235 |
*/ |
|
253 |
*/ |
236 |
if ((msg->message >= WM_KEYFIRST) && (msg->message <= WM_KEYLAST)) { |
|
254 |
if ((msg->message >= WM_KEYFIRST) && (msg->message <= WM_KEYLAST)) { |
237 |
PUGL_Shell shell = _Display_FindClosestShell(msg->hwnd); |
|
255 |
PUGL_Shell shell = _Display_FindClosestShell(msg->hwnd); |
238 |
if (shell != NULL) { |
|
256 |
if (shell != NULL) { |
239 |
HACCEL table = _Shell_GetAcceleratorTable(shell); |
|
257 |
HACCEL table = _Shell_GetAcceleratorTable(shell); |
240 |
if (table != 0) { |
|
258 |
if (table != 0) { |
241 |
if (TranslateAccelerator(shell->scrollable.control.hWnd, table, msg) != 0) { |
|
259 |
if (TranslateAccelerator(shell->scrollable.control.hWnd, table, msg) != 0) { |
242 |
return TRUE; |
|
260 |
return TRUE; |
243 |
} |
|
261 |
} |
244 |
} |
|
262 |
} |
245 |
} |
|
263 |
} |
246 |
} |
|
264 |
} |
247 |
return FALSE; |
|
265 |
return FALSE; |
248 |
} |
|
266 |
} |
249 |
|
|
267 |
|
250 |
//======================================================================================== |
|
268 |
//======================================================================================== |
251 |
|
|
269 |
|
252 |
UGL_Boolean Display_ReadAndDispatch(UGL_Int handle, UGL_Error uglError) { |
|
270 |
UGL_Boolean Display_ReadAndDispatch(UGL_Int handle, UGL_Error uglError) { |
253 |
PUGL_Display display = UGL_DISPLAY(handle); |
|
271 |
PUGL_Display display = UGL_DISPLAY(handle); |
254 |
MSG msg; |
|
272 |
MSG msg; |
255 |
|
|
273 |
|
256 |
if (PeekMessage (&msg, 0, 0, 0, PM_REMOVE)) { |
|
274 |
if (PeekMessage (&msg, 0, 0, 0, PM_REMOVE)) { |
257 |
if (_Display_FilterMessage(display, &msg) == TRUE) return TRUE; |
|
275 |
if (_Display_FilterMessage(display, &msg) == TRUE) return TRUE; |
|
|
<> |
276 |
|
|
|
|
277 |
#ifdef _WIN32_WCE |
|
|
|
278 |
if (display->isEmulator) { |
|
|
|
279 |
// please see http://msdn.microsoft.com/en-us/library/aa912145.aspx |
|
|
|
280 |
// for information on this code: |
|
|
|
281 |
// "Although the IMM sets the virtual key value to VK_PROCESSKEY when |
|
|
|
282 |
// the IME processes a given virtual key, an application can recover |
|
|
|
283 |
// the original virtual key value with the ImmGetVirtualKey function. |
|
|
|
284 |
// This function is only used for key input messages containing the |
|
|
|
285 |
// VK_PROCESSKEY value. Applications can only get the original virtual |
|
|
|
286 |
// key by using this function after receiving the WM_KEYDOWN (VK_PROCESSKEY) |
|
|
|
287 |
// message, and before TranslateMessage is called in its own message loop." |
|
|
|
288 |
// |
|
|
|
289 |
// For some reason the emulator gets screwed up and stops properly sending virtual |
|
|
|
290 |
// keys. For instance, if you type in 0000 and then hit TAB, the keycode comes in |
|
|
|
291 |
// as VK_PROCESSKEY for WM_KeyDown but there is never a corresponding KeyDown |
|
|
|
292 |
// or KeyChar for the actual TAB character. This hack tries and fixes it. |
|
|
|
293 |
if (msg.message == WM_KEYDOWN || msg.message == WM_KEYUP) |
|
|
|
294 |
{ |
|
|
|
295 |
if (msg.wParam == VK_PROCESSKEY) |
|
|
|
296 |
{ |
|
|
|
297 |
msg.wParam = ImmGetVirtualKey(msg.hwnd); |
|
|
|
298 |
} |
|
|
|
299 |
} |
|
|
|
300 |
} |
|
|
|
301 |
#endif |
|
|
|
302 |
|
258 |
TranslateMessage (&msg); |
|
303 |
TranslateMessage (&msg); |
259 |
DispatchMessage (&msg); |
= |
304 |
DispatchMessage (&msg); |
260 |
return TRUE; |
|
305 |
return TRUE; |
261 |
} |
|
306 |
} |
262 |
return FALSE; |
|
307 |
return FALSE; |
263 |
} |
|
308 |
} |
264 |
//======================================================================================== |
|
309 |
//======================================================================================== |
265 |
|
|
310 |
|
266 |
void Display_Sleep(UGL_Int handle, UGL_Error uglError) { |
|
311 |
void Display_Sleep(UGL_Int handle, UGL_Error uglError) { |
267 |
#ifdef _WIN32_WCE |
|
312 |
#ifdef _WIN32_WCE |
268 |
MsgWaitForMultipleObjectsEx (0, 0, INFINITE, QS_ALLINPUT, MWMO_INPUTAVAILABLE); |
|
313 |
MsgWaitForMultipleObjectsEx (0, 0, INFINITE, QS_ALLINPUT, MWMO_INPUTAVAILABLE); |
269 |
#else |
|
314 |
#else |
270 |
MSG msg; |
|
315 |
MSG msg; |
271 |
|
|
316 |
|
272 |
// According to MSDN, WaitMessage will not return immediately if |
|
317 |
// According to MSDN, WaitMessage will not return immediately if |
273 |
// there is a message already on the queue. In PersonalProfile that is not a |
|
318 |
// there is a message already on the queue. In PersonalProfile that is not a |
274 |
// problem because the event loop is not controled by the user, but in eSWT |
|
319 |
// problem because the event loop is not controled by the user, but in eSWT |
275 |
// it is possible to write an incorrect event loop. |
|
320 |
// it is possible to write an incorrect event loop. |
276 |
// |
|
321 |
// |
277 |
// If event loop sleeps after every event is read and dispatched then some |
|
322 |
// If event loop sleeps after every event is read and dispatched then some |
278 |
// events can be queued up and only processed after a new event comes in. |
|
323 |
// events can be queued up and only processed after a new event comes in. |
279 |
// |
|
324 |
// |
280 |
// Checking for a pre-existing message will fix this problem |
|
325 |
// Checking for a pre-existing message will fix this problem |
281 |
if (PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE) != 0) return; |
|
326 |
if (PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE) != 0) return; |
282 |
WaitMessage(); |
|
327 |
WaitMessage(); |
283 |
#endif |
|
328 |
#endif |
284 |
} |
|
329 |
} |
285 |
//======================================================================================== |
|
330 |
//======================================================================================== |
286 |
|
|
331 |
|
287 |
void Display_Wake(UGL_Int handle, UGL_Error uglError) { |
|
332 |
void Display_Wake(UGL_Int handle, UGL_Error uglError) { |
288 |
PUGL_Display ugl_display = UGL_DISPLAY(handle); |
|
333 |
PUGL_Display ugl_display = UGL_DISPLAY(handle); |
289 |
#ifdef _WIN32_WCE |
|
334 |
#ifdef _WIN32_WCE |
290 |
PostMessage (ugl_display->creation_hWnd, WM_NULL, 0, 0); |
|
335 |
PostMessage (ugl_display->creation_hWnd, WM_NULL, 0, 0); |
291 |
#else |
|
336 |
#else |
292 |
PostThreadMessage(ugl_display->threadID, WM_NULL, 0, 0); |
|
337 |
PostThreadMessage(ugl_display->threadID, WM_NULL, 0, 0); |
293 |
#endif |
|
338 |
#endif |
294 |
} |
|
339 |
} |
295 |
//======================================================================================== |
|
340 |
//======================================================================================== |
296 |
|
|
341 |
|
297 |
UGL_Boolean Display_PostKeyEvent(UGL_Int handle, UGL_Int keyEventType, UGL_Int keyCode, UGL_Char character, UGL_Error uglError) { |
|
342 |
UGL_Boolean Display_PostKeyEvent(UGL_Int handle, UGL_Int keyEventType, UGL_Int keyCode, UGL_Char character, UGL_Error uglError) { |
298 |
|
|
343 |
|
299 |
/* |
|
344 |
/* |
300 |
* This function doesn't work quite like one would imagine. For example, if I send a |
|
345 |
* This function doesn't work quite like one would imagine. For example, if I send a |
301 |
* shift down event followed by a key down event with the 's' key, I don't get the 'S' |
|
346 |
* shift down event followed by a key down event with the 's' key, I don't get the 'S' |
302 |
* char in the generated event, but another unrecognized character. This is the exact same |
|
347 |
* char in the generated event, but another unrecognized character. This is the exact same |
303 |
* behavior as SWT though. |
|
348 |
* behavior as SWT though. |
304 |
* Also note that whether the upper- or lower-case keycode for a character is passed, |
|
349 |
* Also note that whether the upper- or lower-case keycode for a character is passed, |
305 |
* the keybd_event() function will only take the keycode of the upper-case character, and |
|
350 |
* the keybd_event() function will only take the keycode of the upper-case character, and |
306 |
* the generated event will always have the keycode of the lower-case character. |
|
351 |
* the generated event will always have the keycode of the lower-case character. |
307 |
*/ |
|
352 |
*/ |
308 |
|
|
353 |
|
309 |
if (keyCode > 96 && keyCode < 123) keyCode = keyCode - 32; |
|
354 |
if (keyCode > 96 && keyCode < 123) keyCode = keyCode - 32; |
310 |
|
|
355 |
|
311 |
else { |
|
356 |
else { |
312 |
keyCode = KeyUtils_ConvertToNativeKeycode(keyCode); |
|
357 |
keyCode = KeyUtils_ConvertToNativeKeycode(keyCode); |
313 |
} |
|
358 |
} |
314 |
|
|
359 |
|
315 |
if (keyEventType == UGL_EVENT_KEY_DOWN) { |
|
360 |
if (keyEventType == UGL_EVENT_KEY_DOWN) { |
316 |
keybd_event( keyCode, 0, KEYEVENTF_EXTENDEDKEY | 0, 0 ); |
|
361 |
keybd_event( keyCode, 0, KEYEVENTF_EXTENDEDKEY | 0, 0 ); |
317 |
} |
|
362 |
} |
318 |
else { |
|
363 |
else { |
319 |
keybd_event( keyCode, 0, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0 ); |
|
364 |
keybd_event( keyCode, 0, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0 ); |
320 |
} |
|
365 |
} |
321 |
|
|
366 |
|
322 |
return TRUE; |
|
367 |
return TRUE; |
323 |
|
|
368 |
|
324 |
|
|
369 |
|
325 |
} |
|
370 |
} |
326 |
//======================================================================================== |
|
371 |
//======================================================================================== |
327 |
|
|
372 |
|
328 |
LRESULT CALLBACK creationProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { |
|
373 |
LRESULT CALLBACK creationProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { |
329 |
if (message >= WM_USER) { |
|
374 |
if (message >= WM_USER) { |
330 |
|
|
375 |
|
331 |
switch (message) { |
|
376 |
switch (message) { |
332 |
case UI_NOTIFY_TRAY: { |
|
377 |
case UI_NOTIFY_TRAY: { |
333 |
if(lParam == WM_LBUTTONUP) { |
|
378 |
if(lParam == WM_LBUTTONUP) { |
334 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
|
379 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
335 |
PUGL_TrayItem ugl_trayitem = Tray_GetTrayItem(ugl_display, (UINT)wParam); |
|
380 |
PUGL_TrayItem ugl_trayitem = Tray_GetTrayItem(ugl_display, (UINT)wParam); |
336 |
#ifndef _WIN32_WCE |
|
381 |
#ifndef _WIN32_WCE |
337 |
POINT point; |
|
382 |
POINT point; |
338 |
GetCursorPos(&point); |
|
383 |
GetCursorPos(&point); |
339 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_SELECTION, point.x, point.y); |
|
384 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_SELECTION, point.x, point.y); |
340 |
#else |
|
385 |
#else |
341 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_SELECTION, 0, 0); |
|
386 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_SELECTION, 0, 0); |
342 |
#endif |
|
387 |
#endif |
343 |
} else if(lParam == WM_LBUTTONDBLCLK) { |
|
388 |
} else if(lParam == WM_LBUTTONDBLCLK) { |
344 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
|
389 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
345 |
PUGL_TrayItem ugl_trayitem = Tray_GetTrayItem(ugl_display, (UINT)wParam); |
|
390 |
PUGL_TrayItem ugl_trayitem = Tray_GetTrayItem(ugl_display, (UINT)wParam); |
346 |
#ifndef _WIN32_WCE |
|
391 |
#ifndef _WIN32_WCE |
347 |
POINT point; |
|
392 |
POINT point; |
348 |
GetCursorPos(&point); |
|
393 |
GetCursorPos(&point); |
349 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_DEFAULT_SELECTION, point.x, point.y); |
|
394 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_DEFAULT_SELECTION, point.x, point.y); |
350 |
#else |
|
395 |
#else |
351 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_DEFAULT_SELECTION, 0, 0); |
|
396 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_DEFAULT_SELECTION, 0, 0); |
352 |
#endif |
|
397 |
#endif |
353 |
#ifndef _WIN32_WCE |
|
398 |
#ifndef _WIN32_WCE |
354 |
} else if(lParam == WM_RBUTTONUP) { |
|
399 |
} else if(lParam == WM_RBUTTONUP) { |
355 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
|
400 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
356 |
PUGL_TrayItem ugl_trayitem = Tray_GetTrayItem(ugl_display, (UINT)wParam); |
|
401 |
PUGL_TrayItem ugl_trayitem = Tray_GetTrayItem(ugl_display, (UINT)wParam); |
357 |
POINT point; |
|
402 |
POINT point; |
358 |
GetCursorPos(&point); |
|
403 |
GetCursorPos(&point); |
359 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_MENU_DETECT, point.x, point.y); |
|
404 |
TrayItemCallback(UGL_WIDGET(ugl_trayitem)->callback_target, TRAYITEM_MENU_DETECT, point.x, point.y); |
360 |
#endif |
|
405 |
#endif |
361 |
} |
|
406 |
} |
362 |
} break; |
|
407 |
} break; |
363 |
case UI_CREATE_MENUBAR: { |
|
408 |
case UI_CREATE_MENUBAR: { |
364 |
UGL_Error* error = (UGL_Error*)lParam; |
|
409 |
UGL_Error* error = (UGL_Error*)lParam; |
365 |
return (LRESULT)_MenuBar_New((PUGL_Control)wParam, *error); |
|
410 |
return (LRESULT)_MenuBar_New((PUGL_Control)wParam, *error); |
366 |
} |
|
411 |
} |
367 |
case UI_CREATE_POPUP: { |
|
412 |
case UI_CREATE_POPUP: { |
368 |
UGL_Error* error = (UGL_Error*)lParam; |
|
413 |
UGL_Error* error = (UGL_Error*)lParam; |
369 |
return _PopupMenu_New(wParam, *error); |
|
414 |
return _PopupMenu_New(wParam, *error); |
370 |
} |
|
415 |
} |
371 |
|
|
416 |
|
372 |
case UI_DESTROY_WINDOW: { |
|
417 |
case UI_DESTROY_WINDOW: { |
373 |
return DestroyWindow((HWND)wParam); |
|
418 |
return DestroyWindow((HWND)wParam); |
374 |
} |
|
419 |
} |
375 |
// ---------------------------------------------------- |
|
420 |
// ---------------------------------------------------- |
376 |
// we only have two possible messages defined. Create either a shell, or create |
|
421 |
// we only have two possible messages defined. Create either a shell, or create |
377 |
// a control. |
|
422 |
// a control. |
378 |
case UI_CREATE_SHELL: { |
|
423 |
case UI_CREATE_SHELL: { |
379 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
|
424 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hWnd, GWL_USERDATA)); |
380 |
UGL_Int *args = (UGL_Int *)lParam; |
|
425 |
UGL_Int *args = (UGL_Int *)lParam; |
381 |
UGL_Int parent_handle = args[0]; |
|
426 |
UGL_Int parent_handle = args[0]; |
382 |
UGL_Error uglError = (UGL_Error)args[1]; |
|
427 |
UGL_Error uglError = (UGL_Error)args[1]; |
383 |
UGL_Int ugl_style = (UGL_Int)wParam; |
|
428 |
UGL_Int ugl_style = (UGL_Int)wParam; |
384 |
|
|
429 |
|
385 |
UGL_Int shell_handle = 0; |
|
430 |
UGL_Int shell_handle = 0; |
386 |
if (parent_handle == 0) shell_handle = Shell_New((UGL_Int)ugl_display, ugl_style, uglError); |
|
431 |
if (parent_handle == 0) shell_handle = Shell_New((UGL_Int)ugl_display, ugl_style, uglError); |
387 |
else shell_handle = Shell_NewChild(parent_handle, ugl_style, uglError); |
|
432 |
else shell_handle = Shell_NewChild(parent_handle, ugl_style, uglError); |
388 |
|
|
433 |
|
389 |
#ifdef _WIN32_WCE |
|
434 |
#ifdef _WIN32_WCE |
390 |
return (LRESULT)shell_handle; |
|
435 |
return (LRESULT)shell_handle; |
391 |
#else |
|
436 |
#else |
392 |
ReplyMessage(shell_handle); |
|
437 |
ReplyMessage(shell_handle); |
393 |
#endif |
|
438 |
#endif |
394 |
|
|
439 |
|
395 |
} break; |
|
440 |
} break; |
396 |
|
|
441 |
|
397 |
// create a control |
|
442 |
// create a control |
398 |
case UI_CREATE_CONTROL: { |
|
443 |
case UI_CREATE_CONTROL: { |
399 |
UGL_Int *args = (UGL_Int *)lParam; |
|
444 |
UGL_Int *args = (UGL_Int *)lParam; |
400 |
UGL_Int parentHandle = (UGL_Int)wParam; |
|
445 |
UGL_Int parentHandle = (UGL_Int)wParam; |
401 |
UGL_String control_class = (UGL_String)args[0]; |
|
446 |
UGL_String control_class = (UGL_String)args[0]; |
402 |
UGL_Int struct_size = args[1]; |
|
447 |
UGL_Int struct_size = args[1]; |
403 |
WNDPROC Control_Proc = (WNDPROC)args[2]; |
|
448 |
WNDPROC Control_Proc = (WNDPROC)args[2]; |
404 |
UGL_Int ugl_style = args[3]; |
|
449 |
UGL_Int ugl_style = args[3]; |
405 |
UGL_Int style = args[4]; |
|
450 |
UGL_Int style = args[4]; |
406 |
UGL_Int extended_style = args[5]; |
|
451 |
UGL_Int extended_style = args[5]; |
407 |
UGL_Error uglError = (UGL_Error)args[6]; |
|
452 |
UGL_Error uglError = (UGL_Error)args[6]; |
408 |
|
|
453 |
|
409 |
PUGL_Control ugl_handle = _Control_New(control_class, struct_size, Control_Proc, parentHandle, ugl_style, style, extended_style, uglError); |
|
454 |
PUGL_Control ugl_handle = _Control_New(control_class, struct_size, Control_Proc, parentHandle, ugl_style, style, extended_style, uglError); |
410 |
#ifdef _WIN32_WCE |
|
455 |
#ifdef _WIN32_WCE |
411 |
return (LRESULT)ugl_handle; |
|
456 |
return (LRESULT)ugl_handle; |
412 |
#else |
|
457 |
#else |
413 |
ReplyMessage((LRESULT)ugl_handle); |
|
458 |
ReplyMessage((LRESULT)ugl_handle); |
414 |
#endif |
|
459 |
#endif |
415 |
} break; |
|
460 |
} break; |
416 |
|
|
461 |
|
417 |
case UI_SETCALLBACKTARGET: { |
|
462 |
case UI_SETCALLBACKTARGET: { |
418 |
// Please see Widget_SetCallbackTarget for |
|
463 |
// Please see Widget_SetCallbackTarget for |
419 |
// a detailed description of why this |
|
464 |
// a detailed description of why this |
420 |
// must be done in the display thread |
|
465 |
// must be done in the display thread |
421 |
PUGL_Widget widget = UGL_WIDGET(wParam); |
|
466 |
PUGL_Widget widget = UGL_WIDGET(wParam); |
422 |
CallbackTarget* newTarget = (CallbackTarget*)lParam; |
|
467 |
CallbackTarget* newTarget = (CallbackTarget*)lParam; |
423 |
CallbackTarget* old_target = widget->callback_target; |
|
468 |
CallbackTarget* old_target = widget->callback_target; |
424 |
widget->callback_target = newTarget; |
|
469 |
widget->callback_target = newTarget; |
425 |
return (LRESULT)old_target; |
|
470 |
return (LRESULT)old_target; |
426 |
} |
|
471 |
} |
427 |
|
|
472 |
|
428 |
} |
|
473 |
} |
429 |
return 1; |
|
474 |
return 1; |
430 |
} else { |
|
475 |
} else { |
431 |
return DefWindowProc(hWnd, message, wParam, lParam); |
|
476 |
return DefWindowProc(hWnd, message, wParam, lParam); |
432 |
} |
|
477 |
} |
433 |
} |
|
478 |
} |
434 |
//======================================================================================== |
|
479 |
//======================================================================================== |
435 |
|
|
480 |
|
436 |
UGL_Boolean Display_PostPointerEvent(UGL_Int handle, UGL_Int type, UGL_Int button, UGL_Error uglError) { |
|
481 |
UGL_Boolean Display_PostPointerEvent(UGL_Int handle, UGL_Int type, UGL_Int button, UGL_Error uglError) { |
437 |
INPUT inputs; |
|
482 |
INPUT inputs; |
438 |
UINT result; |
|
483 |
UINT result; |
439 |
ZeroMemory(&inputs, sizeof(INPUT)); |
|
484 |
ZeroMemory(&inputs, sizeof(INPUT)); |
440 |
inputs.type = INPUT_MOUSE; |
|
485 |
inputs.type = INPUT_MOUSE; |
441 |
|
|
486 |
|
442 |
switch (button) { |
|
487 |
switch (button) { |
443 |
case UGL_POINTER_MASK_BUTTON1: { |
|
488 |
case UGL_POINTER_MASK_BUTTON1: { |
444 |
if (type == UGL_EVENT_POINTER_DOWN) inputs.mi.dwFlags = MOUSEEVENTF_LEFTDOWN; |
|
489 |
if (type == UGL_EVENT_POINTER_DOWN) inputs.mi.dwFlags = MOUSEEVENTF_LEFTDOWN; |
445 |
else inputs.mi.dwFlags = MOUSEEVENTF_LEFTUP; |
|
490 |
else inputs.mi.dwFlags = MOUSEEVENTF_LEFTUP; |
446 |
} break; |
|
491 |
} break; |
447 |
case UGL_POINTER_MASK_BUTTON2: { |
|
492 |
case UGL_POINTER_MASK_BUTTON2: { |
448 |
if (type == UGL_EVENT_POINTER_DOWN) inputs.mi.dwFlags = MOUSEEVENTF_MIDDLEDOWN; |
|
493 |
if (type == UGL_EVENT_POINTER_DOWN) inputs.mi.dwFlags = MOUSEEVENTF_MIDDLEDOWN; |
449 |
else inputs.mi.dwFlags = MOUSEEVENTF_MIDDLEUP; |
|
494 |
else inputs.mi.dwFlags = MOUSEEVENTF_MIDDLEUP; |
450 |
} break; |
|
495 |
} break; |
451 |
case UGL_POINTER_MASK_BUTTON3: { |
|
496 |
case UGL_POINTER_MASK_BUTTON3: { |
452 |
if (type == UGL_EVENT_POINTER_DOWN) inputs.mi.dwFlags = MOUSEEVENTF_RIGHTDOWN; |
|
497 |
if (type == UGL_EVENT_POINTER_DOWN) inputs.mi.dwFlags = MOUSEEVENTF_RIGHTDOWN; |
453 |
else inputs.mi.dwFlags = MOUSEEVENTF_RIGHTUP; |
|
498 |
else inputs.mi.dwFlags = MOUSEEVENTF_RIGHTUP; |
454 |
} break; |
|
499 |
} break; |
455 |
default: return FALSE; |
|
500 |
default: return FALSE; |
456 |
} |
|
501 |
} |
457 |
result = SendInput(1, &inputs, sizeof(INPUT)); |
|
502 |
result = SendInput(1, &inputs, sizeof(INPUT)); |
458 |
return result != 0; |
|
503 |
return result != 0; |
459 |
} |
|
504 |
} |
460 |
//======================================================================================== |
|
505 |
//======================================================================================== |
461 |
|
|
506 |
|
462 |
UGL_Boolean Display_PostPointerMoveEvent(UGL_Int handle, UGL_Int x, UGL_Int y, UGL_Error uglError) { |
|
507 |
UGL_Boolean Display_PostPointerMoveEvent(UGL_Int handle, UGL_Int x, UGL_Int y, UGL_Error uglError) { |
463 |
INPUT inputs; |
|
508 |
INPUT inputs; |
464 |
UINT result; |
|
509 |
UINT result; |
465 |
int screenWidth = GetSystemMetrics(SM_CXSCREEN) - 1; |
|
510 |
int screenWidth = GetSystemMetrics(SM_CXSCREEN) - 1; |
466 |
int screenHeight = GetSystemMetrics(SM_CYSCREEN) - 1; |
|
511 |
int screenHeight = GetSystemMetrics(SM_CYSCREEN) - 1; |
467 |
|
|
512 |
|
468 |
ZeroMemory(&inputs, sizeof(INPUT)); |
|
513 |
ZeroMemory(&inputs, sizeof(INPUT)); |
469 |
inputs.type = INPUT_MOUSE; |
|
514 |
inputs.type = INPUT_MOUSE; |
470 |
inputs.mi.dwFlags = MOUSEEVENTF_MOVE | MOUSEEVENTF_ABSOLUTE; |
|
515 |
inputs.mi.dwFlags = MOUSEEVENTF_MOVE | MOUSEEVENTF_ABSOLUTE; |
471 |
inputs.mi.dx = (x * 65535) / screenWidth; |
|
516 |
inputs.mi.dx = (x * 65535) / screenWidth; |
472 |
inputs.mi.dy = (y * 65535) / screenHeight; |
|
517 |
inputs.mi.dy = (y * 65535) / screenHeight; |
473 |
|
|
518 |
|
474 |
result = SendInput(1, &inputs, sizeof(INPUT)); |
|
519 |
result = SendInput(1, &inputs, sizeof(INPUT)); |
475 |
return result != 0; |
|
520 |
return result != 0; |
476 |
} |
|
521 |
} |
477 |
|
|
522 |
|
478 |
|
|
523 |
|
479 |
//======================================================================================== |
|
524 |
//======================================================================================== |
480 |
void Display_Beep(UGL_Int handle, UGL_Error uglError) { |
|
525 |
void Display_Beep(UGL_Int handle, UGL_Error uglError) { |
481 |
MessageBeep(MB_OK); |
|
526 |
MessageBeep(MB_OK); |
482 |
} |
|
527 |
} |
483 |
|
|
528 |
|
484 |
//======================================================================================== |
|
529 |
//======================================================================================== |
485 |
|
|
530 |
|
486 |
UGL_Int Display_GetSystemColor(UGL_Int handle, UGL_Int id, UGL_Error uglError) { |
|
531 |
UGL_Int Display_GetSystemColor(UGL_Int handle, UGL_Int id, UGL_Error uglError) { |
487 |
int pixel = 0x02000000; |
|
532 |
int pixel = 0x02000000; |
488 |
UGL_Int ugl_color = 0; |
|
533 |
UGL_Int ugl_color = 0; |
489 |
|
|
534 |
|
490 |
switch (id) { |
|
535 |
switch (id) { |
491 |
case UGL_COLOR_CONTROL_SHADOW_DARK: pixel = GetSysColor (COLOR_3DDKSHADOW); break; |
|
536 |
case UGL_COLOR_CONTROL_SHADOW_DARK: pixel = GetSysColor (COLOR_3DDKSHADOW); break; |
492 |
case UGL_COLOR_CONTROL_SHADOW_NORMAL: pixel = GetSysColor(COLOR_3DSHADOW); break; |
|
537 |
case UGL_COLOR_CONTROL_SHADOW_NORMAL: pixel = GetSysColor(COLOR_3DSHADOW); break; |
493 |
case UGL_COLOR_CONTROL_HIGHLIGHT_NORMAL: pixel = GetSysColor(COLOR_3DLIGHT); break; |
|
538 |
case UGL_COLOR_CONTROL_HIGHLIGHT_NORMAL: pixel = GetSysColor(COLOR_3DLIGHT); break; |
494 |
case UGL_COLOR_CONTROL_BACKGROUND: pixel = GetSysColor(COLOR_3DFACE); break; |
|
539 |
case UGL_COLOR_CONTROL_BACKGROUND: pixel = GetSysColor(COLOR_3DFACE); break; |
495 |
case UGL_COLOR_CONTROL_FOREGROUND: pixel = GetSysColor(COLOR_WINDOWTEXT); break; |
|
540 |
case UGL_COLOR_CONTROL_FOREGROUND: pixel = GetSysColor(COLOR_WINDOWTEXT); break; |
496 |
|
|
541 |
|
497 |
|
|
542 |
|
498 |
case UGL_COLOR_TEXT_HIGHLIGHT_BACKGROUND: pixel = GetSysColor(COLOR_HIGHLIGHT); break; |
|
543 |
case UGL_COLOR_TEXT_HIGHLIGHT_BACKGROUND: pixel = GetSysColor(COLOR_HIGHLIGHT); break; |
499 |
case UGL_COLOR_TEXT_HIGHLIGHT_FOREGROUND: pixel = GetSysColor(COLOR_HIGHLIGHTTEXT); break; |
|
544 |
case UGL_COLOR_TEXT_HIGHLIGHT_FOREGROUND: pixel = GetSysColor(COLOR_HIGHLIGHTTEXT); break; |
500 |
|
|
545 |
|
501 |
case UGL_COLOR_TITLE_BACKGROUND: pixel = GetSysColor(COLOR_ACTIVECAPTION); break; |
|
546 |
case UGL_COLOR_TITLE_BACKGROUND: pixel = GetSysColor(COLOR_ACTIVECAPTION); break; |
502 |
case UGL_COLOR_TITLE_FOREGROUND: pixel = GetSysColor(COLOR_CAPTIONTEXT); break; |
|
547 |
case UGL_COLOR_TITLE_FOREGROUND: pixel = GetSysColor(COLOR_CAPTIONTEXT); break; |
503 |
|
|
548 |
|
504 |
case UGL_COLOR_INFO_FOREGROUND: pixel = GetSysColor(COLOR_INFOTEXT); break; |
|
549 |
case UGL_COLOR_INFO_FOREGROUND: pixel = GetSysColor(COLOR_INFOTEXT); break; |
505 |
case UGL_COLOR_INFO_BACKGROUND: pixel = GetSysColor(COLOR_INFOBK); break; |
|
550 |
case UGL_COLOR_INFO_BACKGROUND: pixel = GetSysColor(COLOR_INFOBK); break; |
506 |
|
|
551 |
|
507 |
case UGL_COLOR_INACTIVE_CAPTION_FOREGROUND: pixel = GetSysColor(COLOR_INACTIVECAPTIONTEXT); break; |
|
552 |
case UGL_COLOR_INACTIVE_CAPTION_FOREGROUND: pixel = GetSysColor(COLOR_INACTIVECAPTIONTEXT); break; |
508 |
case UGL_COLOR_INACTIVE_CAPTION_BACKGROUND: pixel = GetSysColor(COLOR_INACTIVECAPTION); break; |
|
553 |
case UGL_COLOR_INACTIVE_CAPTION_BACKGROUND: pixel = GetSysColor(COLOR_INACTIVECAPTION); break; |
509 |
default: { |
|
554 |
default: { |
510 |
Win32Error_SetError(uglError, UGL_ERROR_OTHER, _T("Unrecognized color ID")); |
|
555 |
Win32Error_SetError(uglError, UGL_ERROR_OTHER, _T("Unrecognized color ID")); |
511 |
return NULL_HANDLE; |
|
556 |
return NULL_HANDLE; |
512 |
} break; |
|
557 |
} break; |
513 |
|
|
558 |
|
514 |
} |
|
559 |
} |
515 |
|
|
560 |
|
516 |
ugl_color = Color_New(handle, GetRValue(pixel), GetGValue(pixel), GetBValue(pixel), uglError); |
|
561 |
ugl_color = Color_New(handle, GetRValue(pixel), GetGValue(pixel), GetBValue(pixel), uglError); |
517 |
return ugl_color; |
|
562 |
return ugl_color; |
518 |
} |
|
563 |
} |
519 |
|
|
564 |
|
520 |
//======================================================================================== |
|
565 |
//======================================================================================== |
521 |
|
|
566 |
|
522 |
/** |
|
567 |
/** |
523 |
* Adds a control to the list of controls. |
|
568 |
* Adds a control to the list of controls. |
524 |
*/ |
|
569 |
*/ |
525 |
BOOL ControlList_AddControl(PControlList* list, struct UGL_Control* control) { |
|
570 |
BOOL ControlList_AddControl(PControlList* list, struct UGL_Control* control) { |
526 |
// It is important that new controls be added to the front of the list so that |
|
571 |
// It is important that new controls be added to the front of the list so that |
527 |
// the topmost control is always in the front of the list. |
|
572 |
// the topmost control is always in the front of the list. |
528 |
PControlList element; |
|
573 |
PControlList element; |
529 |
for (element = *list; element != NULL; element = element->next) { |
|
574 |
for (element = *list; element != NULL; element = element->next) { |
530 |
// It is possible that the control is already in the list and it |
|
575 |
// It is possible that the control is already in the list and it |
531 |
// should not be added twice |
|
576 |
// should not be added twice |
532 |
if (element->control == control) return TRUE; |
|
577 |
if (element->control == control) return TRUE; |
533 |
} |
|
578 |
} |
534 |
|
|
579 |
|
535 |
element = (PControlList)calloc(sizeof(ControlList), 1); |
|
580 |
element = (PControlList)calloc(sizeof(ControlList), 1); |
536 |
if (element == NULL) return FALSE; |
|
581 |
if (element == NULL) return FALSE; |
537 |
element->control = control; |
|
582 |
element->control = control; |
538 |
element->next = *list; |
|
583 |
element->next = *list; |
539 |
|
|
584 |
|
540 |
*list = element; |
|
585 |
*list = element; |
541 |
return TRUE; |
|
586 |
return TRUE; |
542 |
} |
|
587 |
} |
543 |
|
|
588 |
|
544 |
BOOL ControlList_RemoveControl(PControlList* list, struct UGL_Control* control) { |
|
589 |
BOOL ControlList_RemoveControl(PControlList* list, struct UGL_Control* control) { |
545 |
if (*list == NULL) { |
|
590 |
if (*list == NULL) { |
546 |
return FALSE; // The control is not in the empty list |
|
591 |
return FALSE; // The control is not in the empty list |
547 |
} |
|
592 |
} |
548 |
|
|
593 |
|
549 |
if ((*list)->control == control) { |
|
594 |
if ((*list)->control == control) { |
550 |
PControlList nextList = (*list)->next; |
|
595 |
PControlList nextList = (*list)->next; |
551 |
free(*list); |
|
596 |
free(*list); |
552 |
*list = nextList; |
|
597 |
*list = nextList; |
553 |
return TRUE; |
|
598 |
return TRUE; |
554 |
} else { |
|
599 |
} else { |
555 |
return ControlList_RemoveControl(&((*list)->next), control); |
|
600 |
return ControlList_RemoveControl(&((*list)->next), control); |
556 |
} |
|
601 |
} |
557 |
} |
|
602 |
} |
558 |
|
|
603 |
|
559 |
BOOL IsChildOfShell(struct UGL_Control* shell, struct UGL_Control* child) { |
|
604 |
BOOL IsChildOfShell(struct UGL_Control* shell, struct UGL_Control* child) { |
560 |
// If there is a modal dialog currently displayed then |
|
605 |
// If there is a modal dialog currently displayed then |
561 |
// we need to ignore all mouse events on windows that are |
|
606 |
// we need to ignore all mouse events on windows that are |
562 |
// not owned by that dialog |
|
607 |
// not owned by that dialog |
563 |
struct UGL_Control* test = child; |
|
608 |
struct UGL_Control* test = child; |
564 |
|
|
609 |
|
565 |
// In PPro it is possible for a modal dialog to open other |
|
610 |
// In PPro it is possible for a modal dialog to open other |
566 |
// windows which should still be usable. The solution it to |
|
611 |
// windows which should still be usable. The solution it to |
567 |
// walk the whole list of shells until the top-most shell checking |
|
612 |
// walk the whole list of shells until the top-most shell checking |
568 |
// if any are the modal dialog |
|
613 |
// if any are the modal dialog |
569 |
while (test != shell) { |
|
614 |
while (test != shell) { |
570 |
if (test == NULL) return FALSE; // None of the parents were the modal dialog |
|
615 |
if (test == NULL) return FALSE; // None of the parents were the modal dialog |
571 |
test = test->parent; |
|
616 |
test = test->parent; |
572 |
}; |
|
617 |
}; |
573 |
|
|
618 |
|
574 |
return TRUE; |
|
619 |
return TRUE; |
575 |
} |
|
620 |
} |
576 |
|
|
621 |
|
577 |
/** |
|
622 |
/** |
578 |
* Run through the list of shell's that want to be enable and adjust their |
|
623 |
* Run through the list of shell's that want to be enable and adjust their |
579 |
* enabled status based on the current modal dialog. |
|
624 |
* enabled status based on the current modal dialog. |
580 |
*/ |
|
625 |
*/ |
581 |
void UpdateEnabledShells(PUGL_Display display) { |
|
626 |
void UpdateEnabledShells(PUGL_Display display) { |
582 |
struct UGL_Control* topmostModalShell = display->modalShells == NULL ? NULL : display->modalShells->control; |
|
627 |
struct UGL_Control* topmostModalShell = display->modalShells == NULL ? NULL : display->modalShells->control; |
583 |
|
|
628 |
|
584 |
PControlList element; |
|
629 |
PControlList element; |
585 |
for (element = display->enabledShells; element != NULL; element = element->next) { |
|
630 |
for (element = display->enabledShells; element != NULL; element = element->next) { |
586 |
BOOL enabled; |
|
631 |
BOOL enabled; |
587 |
struct UGL_Control* shell = element->control; |
|
632 |
struct UGL_Control* shell = element->control; |
588 |
|
|
633 |
|
589 |
// Shells that are children of the modal shell do not need to be |
|
634 |
// Shells that are children of the modal shell do not need to be |
590 |
// disabled when the modal shell is shown. |
|
635 |
// disabled when the modal shell is shown. |
591 |
if ((topmostModalShell == NULL) || IsChildOfShell(topmostModalShell, shell)) { |
|
636 |
if ((topmostModalShell == NULL) || IsChildOfShell(topmostModalShell, shell)) { |
592 |
enabled = TRUE; |
|
637 |
enabled = TRUE; |
593 |
} else { |
|
638 |
} else { |
594 |
enabled = FALSE; |
|
639 |
enabled = FALSE; |
595 |
} |
|
640 |
} |
596 |
|
|
641 |
|
597 |
// It is important that we don't call Control_SetEnabled() to do the work because |
|
642 |
// It is important that we don't call Control_SetEnabled() to do the work because |
598 |
// that will result in the shell being removed from the list of shells that would |
|
643 |
// that will result in the shell being removed from the list of shells that would |
599 |
// prefer to be enabled |
|
644 |
// prefer to be enabled |
600 |
EnableWindow(shell->hWnd, enabled); |
|
645 |
EnableWindow(shell->hWnd, enabled); |
601 |
} |
|
646 |
} |
602 |
} |
|
647 |
} |
603 |
|
|
648 |
|
604 |
/** |
|
649 |
/** |
605 |
* When a modal shell is added to the display all other visible shell's are disabled. When |
|
650 |
* When a modal shell is added to the display all other visible shell's are disabled. When |
606 |
* the last modal shell is removed from the display all shells that want to be enabled |
|
651 |
* the last modal shell is removed from the display all shells that want to be enabled |
607 |
* will be re-enabled |
|
652 |
* will be re-enabled |
608 |
*/ |
|
653 |
*/ |
609 |
void Display_UpdateModalShellVisibility(PUGL_Display display, struct UGL_Control* modalShell, BOOL visible, UGL_Error error) { |
|
654 |
void Display_UpdateModalShellVisibility(PUGL_Display display, struct UGL_Control* modalShell, BOOL visible, UGL_Error error) { |
610 |
if (visible) { |
|
655 |
if (visible) { |
611 |
ControlList_AddControl(&(display->modalShells), modalShell); |
|
656 |
ControlList_AddControl(&(display->modalShells), modalShell); |
612 |
} else { |
|
657 |
} else { |
613 |
ControlList_RemoveControl(&(display->modalShells), modalShell); |
|
658 |
ControlList_RemoveControl(&(display->modalShells), modalShell); |
614 |
} |
|
659 |
} |
615 |
UpdateEnabledShells(display); |
|
660 |
UpdateEnabledShells(display); |
616 |
} |
|
661 |
} |
617 |
|
|
662 |
|
618 |
/** |
|
663 |
/** |
619 |
* This method will track the new shell and manage it's enabled state |
|
664 |
* This method will track the new shell and manage it's enabled state |
620 |
* based on the current modal shell. |
|
665 |
* based on the current modal shell. |
621 |
*/ |
|
666 |
*/ |
622 |
void Display_AddShell(PUGL_Display display, struct UGL_Control* shell, UGL_Error error) { |
|
667 |
void Display_AddShell(PUGL_Display display, struct UGL_Control* shell, UGL_Error error) { |
623 |
// Only shells that are enabled need to be tracked, if the shell |
|
668 |
// Only shells that are enabled need to be tracked, if the shell |
624 |
// become enabled in the future it will go through Display_EnableShell |
|
669 |
// become enabled in the future it will go through Display_EnableShell |
625 |
// and be added to the list then. |
|
670 |
// and be added to the list then. |
626 |
if (IsWindowEnabled(shell->hWnd)) { |
|
671 |
if (IsWindowEnabled(shell->hWnd)) { |
627 |
if (ControlList_AddControl(&(display->enabledShells), shell)) { |
|
672 |
if (ControlList_AddControl(&(display->enabledShells), shell)) { |
628 |
// If there is a current modal shell and the new shell is not a child of |
|
673 |
// If there is a current modal shell and the new shell is not a child of |
629 |
// that shell then it needs to be disabled to reflect the modal status. |
|
674 |
// that shell then it needs to be disabled to reflect the modal status. |
630 |
if ((display->modalShells != NULL) && !IsChildOfShell(display->modalShells->control, shell)) { |
|
675 |
if ((display->modalShells != NULL) && !IsChildOfShell(display->modalShells->control, shell)) { |
631 |
// It is important that we don't call Control_SetEnabled() to do the work because |
|
676 |
// It is important that we don't call Control_SetEnabled() to do the work because |
632 |
// that will result in the shell being removed from the list of shells that would |
|
677 |
// that will result in the shell being removed from the list of shells that would |
633 |
// prefer to be enabled |
|
678 |
// prefer to be enabled |
634 |
EnableWindow(shell->hWnd, FALSE); |
|
679 |
EnableWindow(shell->hWnd, FALSE); |
635 |
} |
|
680 |
} |
636 |
} else { |
|
681 |
} else { |
637 |
Win32Error_SetError(error, UGL_ERROR_OTHER, _T("Could not add control to control list")); |
|
682 |
Win32Error_SetError(error, UGL_ERROR_OTHER, _T("Could not add control to control list")); |
638 |
} |
|
683 |
} |
639 |
} |
|
684 |
} |
640 |
} |
|
685 |
} |
641 |
|
|
686 |
|
642 |
/** |
|
687 |
/** |
643 |
* Stops tracking the specified shell. This should only be called |
|
688 |
* Stops tracking the specified shell. This should only be called |
644 |
* when a shell is being disposed. |
|
689 |
* when a shell is being disposed. |
645 |
*/ |
|
690 |
*/ |
646 |
void Display_RemoveShell(PUGL_Display display, struct UGL_Control* shell) { |
|
691 |
void Display_RemoveShell(PUGL_Display display, struct UGL_Control* shell) { |
647 |
ControlList_RemoveControl(&(display->enabledShells), shell); |
|
692 |
ControlList_RemoveControl(&(display->enabledShells), shell); |
648 |
} |
|
693 |
} |
649 |
|
|
694 |
|
650 |
/** |
|
695 |
/** |
651 |
* Returns TRUE if the shell needs to be updated with the new |
|
696 |
* Returns TRUE if the shell needs to be updated with the new |
652 |
* enabled status. It will return FALSE if the shell already has the |
|
697 |
* enabled status. It will return FALSE if the shell already has the |
653 |
* style specified. For example, If the this method is called to enable a shell while |
|
698 |
* style specified. For example, If the this method is called to enable a shell while |
654 |
* a modal shell is visible it will return FALSE, since the shell must remain |
|
699 |
* a modal shell is visible it will return FALSE, since the shell must remain |
655 |
* disabled while the dialog is visible, but when the modal shell is hidden the desired |
|
700 |
* disabled while the dialog is visible, but when the modal shell is hidden the desired |
656 |
* enabled state will be remembered and updated. |
|
701 |
* enabled state will be remembered and updated. |
657 |
*/ |
|
702 |
*/ |
658 |
BOOL Display_EnableShell(PUGL_Display display, struct UGL_Control* shell, BOOL enable) { |
|
703 |
BOOL Display_EnableShell(PUGL_Display display, struct UGL_Control* shell, BOOL enable) { |
659 |
if (enable) { |
|
704 |
if (enable) { |
660 |
ControlList_AddControl(&(display->enabledShells), shell); |
|
705 |
ControlList_AddControl(&(display->enabledShells), shell); |
661 |
} else { |
|
706 |
} else { |
662 |
ControlList_RemoveControl(&(display->enabledShells), shell); |
|
707 |
ControlList_RemoveControl(&(display->enabledShells), shell); |
663 |
} |
|
708 |
} |
664 |
|
|
709 |
|
665 |
if ((display->modalShells != NULL) && !IsChildOfShell(display->modalShells->control, shell)) { |
|
710 |
if ((display->modalShells != NULL) && !IsChildOfShell(display->modalShells->control, shell)) { |
666 |
// Since there is either no modal shell or the specified shell is a child of the modal shell |
|
711 |
// Since there is either no modal shell or the specified shell is a child of the modal shell |
667 |
// it can do whatever it would like. |
|
712 |
// it can do whatever it would like. |
668 |
return TRUE; |
|
713 |
return TRUE; |
669 |
} else { |
|
714 |
} else { |
670 |
return FALSE; |
|
715 |
return FALSE; |
671 |
} |
|
716 |
} |
672 |
} |
|
717 |
} |
673 |
|
|
718 |
|
674 |
|
|
719 |
|
675 |
void _Dispose_Display(UGL_Int handle, UGL_Error uglError) { |
|
720 |
void _Dispose_Display(UGL_Int handle, UGL_Error uglError) { |
676 |
PUGL_Display ugl_display = UGL_DISPLAY(handle); |
|
721 |
PUGL_Display ugl_display = UGL_DISPLAY(handle); |
677 |
|
|
722 |
|
678 |
// destroy creation window |
|
723 |
// destroy creation window |
679 |
|
|
724 |
|
680 |
if (ugl_display->defaultControlFont != NULL) { |
|
725 |
if (ugl_display->defaultControlFont != NULL) { |
681 |
Font_Dispose((UGL_Int)ugl_display->defaultControlFont, uglError); |
|
726 |
Font_Dispose((UGL_Int)ugl_display->defaultControlFont, uglError); |
682 |
} |
|
727 |
} |
683 |
|
|
728 |
|
684 |
DestroyWindow(ugl_display->creation_hWnd); |
|
729 |
DestroyWindow(ugl_display->creation_hWnd); |
685 |
|
|
730 |
|
686 |
if (!UnregisterClass(WINDOW_CLASS_NAME, ugl_display->hInstance)) { |
|
731 |
if (!UnregisterClass(WINDOW_CLASS_NAME, ugl_display->hInstance)) { |
687 |
free(ugl_display); |
|
732 |
free(ugl_display); |
688 |
// Win32Error_SetError(uglError, GetLastError(), _T("Unable to unregister class for device")); |
|
733 |
// Win32Error_SetError(uglError, GetLastError(), _T("Unable to unregister class for device")); |
689 |
return; |
|
734 |
return; |
690 |
} |
|
735 |
} |
691 |
|
|
736 |
|
692 |
ugl_display->callback_lookup = NULL; |
|
737 |
ugl_display->callback_lookup = NULL; |
693 |
|
|
738 |
|
694 |
if (ugl_display->menuItems != NULL) { |
|
739 |
if (ugl_display->menuItems != NULL) { |
695 |
free(ugl_display->menuItems); |
|
740 |
free(ugl_display->menuItems); |
696 |
} |
|
741 |
} |
697 |
|
|
742 |
|
698 |
free(ugl_display); |
|
743 |
free(ugl_display); |
699 |
} |
|
744 |
} |
700 |
|
|
745 |
|
701 |
|
|
746 |
|
702 |
|
|
747 |
|
703 |
//======================================================================================== |
|
748 |
//======================================================================================== |
704 |
|
|
749 |
|
705 |
void Display_GetIconSize(UGL_Int handle, UGL_Int* returnX, UGL_Int* returnY, UGL_Error uglError) { |
|
750 |
void Display_GetIconSize(UGL_Int handle, UGL_Int* returnX, UGL_Int* returnY, UGL_Error uglError) { |
706 |
*returnX = GetSystemMetrics(SM_CXICON); |
|
751 |
*returnX = GetSystemMetrics(SM_CXICON); |
707 |
*returnY = GetSystemMetrics(SM_CYICON); |
|
752 |
*returnY = GetSystemMetrics(SM_CYICON); |
708 |
} |
|
753 |
} |
709 |
//======================================================================================== |
|
754 |
//======================================================================================== |
710 |
|
|
755 |
|
711 |
UGL_Int Display_GetDoubleClickTime(UGL_Int handle, UGL_Error uglError) { |
|
756 |
UGL_Int Display_GetDoubleClickTime(UGL_Int handle, UGL_Error uglError) { |
712 |
return GetDoubleClickTime(); |
|
757 |
return GetDoubleClickTime(); |
713 |
} |
|
758 |
} |
714 |
//======================================================================================== |
|
759 |
//======================================================================================== |
715 |
|
|
760 |
|
716 |
void Display_SetAppName(UGL_String name, UGL_Error uglError) { |
|
761 |
void Display_SetAppName(UGL_String name, UGL_Error uglError) { |
717 |
// Nothing to do on Windows |
|
762 |
// Nothing to do on Windows |
718 |
} |
|
763 |
} |
719 |
|
|
764 |
|
720 |
//======================================================================================== |
|
765 |
//======================================================================================== |
721 |
|
|
766 |
|
722 |
void CALLBACK _Timer_Proc(HWND hwnd, UINT msg, UINT_PTR timer_ID, DWORD dwTime) { |
|
767 |
void CALLBACK _Timer_Proc(HWND hwnd, UINT msg, UINT_PTR timer_ID, DWORD dwTime) { |
723 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hwnd, GWL_USERDATA)); |
|
768 |
PUGL_Display ugl_display = UGL_DISPLAY(GetWindowLong(hwnd, GWL_USERDATA)); |
724 |
|
|
769 |
|
725 |
// Because of PocketPC not liking timerIds with a value of 0, the id that |
|
770 |
// Because of PocketPC not liking timerIds with a value of 0, the id that |
726 |
// Java is expecting will be 1 less then the one comming into this method. |
|
771 |
// Java is expecting will be 1 less then the one comming into this method. |
727 |
// See Display_StartTimer() for me details. |
|
772 |
// See Display_StartTimer() for me details. |
728 |
DisplayTimerCallback((UGL_Int)ugl_display, (UGL_Int)timer_ID-1); |
|
773 |
DisplayTimerCallback((UGL_Int)ugl_display, (UGL_Int)timer_ID-1); |
729 |
} |
|
774 |
} |
730 |
|
|
775 |
|
731 |
void Display_AddMenuItem(struct UGL_MenuItem *menuItem) { |
|
776 |
void Display_AddMenuItem(struct UGL_MenuItem *menuItem) { |
732 |
PUGL_Display display = UGL_WIDGET(menuItem)->display; |
|
777 |
PUGL_Display display = UGL_WIDGET(menuItem)->display; |
733 |
struct UGL_MenuItem **menuItems; |
|
778 |
struct UGL_MenuItem **menuItems; |
734 |
int index; |
|
779 |
int index; |
735 |
#ifdef _WIN32_WCE |
|
780 |
#ifdef _WIN32_WCE |
736 |
if (menuItem->parent_menu->hwndCB != 0) { |
|
781 |
if (menuItem->parent_menu->hwndCB != 0) { |
737 |
display->menuItemCount+=1; |
|
782 |
display->menuItemCount+=1; |
738 |
} |
|
783 |
} |
739 |
#endif |
|
784 |
#endif |
740 |
for (index = 0; index < display->menuItemsLength; index++) { |
|
785 |
for (index = 0; index < display->menuItemsLength; index++) { |
741 |
if (display->menuItems[index] == NULL) { |
|
786 |
if (display->menuItems[index] == NULL) { |
742 |
display->menuItems[index] = menuItem; |
|
787 |
display->menuItems[index] = menuItem; |
743 |
menuItem->id = index + MENU_ITEM_ID_OFFSET; |
|
788 |
menuItem->id = index + MENU_ITEM_ID_OFFSET; |
744 |
return; |
|
789 |
return; |
745 |
} |
|
790 |
} |
746 |
} |
|
791 |
} |
747 |
menuItems = display->menuItems; |
|
792 |
menuItems = display->menuItems; |
748 |
display->menuItems = calloc(display->menuItemsLength + MENU_ITEMS_INCREMENT, sizeof(PUGL_MenuItem)); |
|
793 |
display->menuItems = calloc(display->menuItemsLength + MENU_ITEMS_INCREMENT, sizeof(PUGL_MenuItem)); |
749 |
memcpy(display->menuItems, menuItems, display->menuItemsLength * sizeof(PUGL_MenuItem)); |
|
794 |
memcpy(display->menuItems, menuItems, display->menuItemsLength * sizeof(PUGL_MenuItem)); |
750 |
if (menuItems != NULL) { |
|
795 |
if (menuItems != NULL) { |
751 |
free(menuItems); |
|
796 |
free(menuItems); |
752 |
} |
|
797 |
} |
753 |
display->menuItems[display->menuItemsLength] = menuItem; |
|
798 |
display->menuItems[display->menuItemsLength] = menuItem; |
754 |
menuItem->id = display->menuItemsLength + MENU_ITEM_ID_OFFSET; |
|
799 |
menuItem->id = display->menuItemsLength + MENU_ITEM_ID_OFFSET; |
755 |
display->menuItemsLength += MENU_ITEMS_INCREMENT; |
|
800 |
display->menuItemsLength += MENU_ITEMS_INCREMENT; |
756 |
} |
|
801 |
} |
757 |
|
|
802 |
|
758 |
PUGL_MenuItem Display_GetMenuItem(PUGL_Display display, int id) { |
|
803 |
PUGL_MenuItem Display_GetMenuItem(PUGL_Display display, int id) { |
759 |
PUGL_MenuItem menuItem = NULL; |
|
804 |
PUGL_MenuItem menuItem = NULL; |
760 |
int index = id - MENU_ITEM_ID_OFFSET; |
|
805 |
int index = id - MENU_ITEM_ID_OFFSET; |
761 |
|
|
806 |
|
762 |
if (index >= 0 && index < display->menuItemsLength) { |
|
807 |
if (index >= 0 && index < display->menuItemsLength) { |
763 |
menuItem = display->menuItems[index]; |
|
808 |
menuItem = display->menuItems[index]; |
764 |
} |
|
809 |
} |
765 |
return menuItem; |
|
810 |
return menuItem; |
766 |
} |
|
811 |
} |
767 |
|
|
812 |
|
768 |
void Display_RemoveMenuItem(struct UGL_MenuItem *menuItem) { |
|
813 |
void Display_RemoveMenuItem(struct UGL_MenuItem *menuItem) { |
769 |
PUGL_Display display = UGL_WIDGET(menuItem)->display; |
|
814 |
PUGL_Display display = UGL_WIDGET(menuItem)->display; |
770 |
int menuItemIndex = menuItem->id - MENU_ITEM_ID_OFFSET; |
|
815 |
int menuItemIndex = menuItem->id - MENU_ITEM_ID_OFFSET; |
771 |
|
|
816 |
|
772 |
if (menuItemIndex >= 0 && menuItemIndex < display->menuItemsLength) { |
|
817 |
if (menuItemIndex >= 0 && menuItemIndex < display->menuItemsLength) { |
773 |
display->menuItems[menuItemIndex] = NULL; |
|
818 |
display->menuItems[menuItemIndex] = NULL; |
774 |
menuItemIndex = -1; |
|
819 |
menuItemIndex = -1; |
775 |
} |
|
820 |
} |
776 |
#ifdef _WIN32_WCE |
|
821 |
#ifdef _WIN32_WCE |
777 |
if (menuItem->parent_menu->hwndCB != 0) { |
|
822 |
if (menuItem->parent_menu->hwndCB != 0) { |
778 |
display->menuItemCount -= 1; |
|
823 |
display->menuItemCount -= 1; |
779 |
} |
|
824 |
} |
780 |
#endif |
|
825 |
#endif |
781 |
} |
|
826 |
} |
782 |
|
|
827 |
|
783 |
#ifdef _WIN32_WCE |
|
828 |
#ifdef _WIN32_WCE |
784 |
// this function finds the menuitem in the main menu (top level menu) at index (index) |
|
829 |
// this function finds the menuitem in the main menu (top level menu) at index (index) |
785 |
/* |
|
830 |
/* |
786 |
PUGL_MenuItem Display_FindMenuItem(PUGL_Display display, int index) { |
|
831 |
PUGL_MenuItem Display_FindMenuItem(PUGL_Display display, int index) { |
787 |
int i; |
|
832 |
int i; |
788 |
|
|
833 |
|
789 |
for(i=0; i<display->menuItemsLength; i++){ |
|
834 |
for(i=0; i<display->menuItemsLength; i++){ |
790 |
if(display->menuItems[i] != NULL){ |
|
835 |
if(display->menuItems[i] != NULL){ |
791 |
if(display->menuItems[i]->index == index){ |
|
836 |
if(display->menuItems[i]->index == index){ |
792 |
if(display->menuItems[i]->parent_menu->hwndCB != 0) { |
|
837 |
if(display->menuItems[i]->parent_menu->hwndCB != 0) { |
793 |
return display->menuItems[i]; |
|
838 |
return display->menuItems[i]; |
794 |
} |
|
839 |
} |
795 |
} |
|
840 |
} |
796 |
} |
|
841 |
} |
797 |
} |
|
842 |
} |
798 |
|
|
843 |
|
799 |
return NULL; |
|
844 |
return NULL; |
800 |
} |
|
845 |
} |
801 |
*/ |
|
846 |
*/ |
802 |
|
|
847 |
|
803 |
PUGL_MenuItem Display_FindMenuItem(PUGL_Display display, HWND hwndCB, int index) { |
|
848 |
PUGL_MenuItem Display_FindMenuItem(PUGL_Display display, HWND hwndCB, int index) { |
804 |
int i; |
|
849 |
int i; |
805 |
for(i=0; i<display->menuItemsLength; i++){ |
|
850 |
for(i=0; i<display->menuItemsLength; i++){ |
806 |
if(display->menuItems[i] != NULL){ |
|
851 |
if(display->menuItems[i] != NULL){ |
807 |
if (display->menuItems[i]->parent_menu->hwndCB != hwndCB) continue; |
|
852 |
if (display->menuItems[i]->parent_menu->hwndCB != hwndCB) continue; |
808 |
if(display->menuItems[i]->index == index){ |
|
853 |
if(display->menuItems[i]->index == index){ |
809 |
if(display->menuItems[i]->parent_menu->hwndCB != 0) { |
|
854 |
if(display->menuItems[i]->parent_menu->hwndCB != 0) { |
810 |
return display->menuItems[i]; |
|
855 |
return display->menuItems[i]; |
811 |
} |
|
856 |
} |
812 |
} |
|
857 |
} |
813 |
} |
|
858 |
} |
814 |
} |
|
859 |
} |
815 |
return NULL; |
|
860 |
return NULL; |
816 |
} |
|
861 |
} |
817 |
|
|
862 |
|
818 |
|
|
863 |
|
819 |
// this function decrements the index of menuitems in the main menu (top level menu) starting at index (start) |
|
864 |
// this function decrements the index of menuitems in the main menu (top level menu) starting at index (start) |
820 |
// for example, when we remove menuItem index 3 we would wish to decrement the index of all menuitems greater than 3 by one |
|
865 |
// for example, when we remove menuItem index 3 we would wish to decrement the index of all menuitems greater than 3 by one |
821 |
/* |
|
866 |
/* |
822 |
void Display_DecMenuItemIndex(PUGL_Display display, HWND hwndCB, int start){ |
|
867 |
void Display_DecMenuItemIndex(PUGL_Display display, HWND hwndCB, int start){ |
823 |
// new for softkey, maintain the menuitem order |
|
868 |
// new for softkey, maintain the menuitem order |
824 |
int index; |
|
869 |
int index; |
825 |
for (index = 0; index < display->menuItemsLength; index++) { |
|
870 |
for (index = 0; index < display->menuItemsLength; index++) { |
826 |
|
|
871 |
|
827 |
if (display->menuItems[index] != NULL) { |
|
872 |
if (display->menuItems[index] != NULL) { |
828 |
if(display->menuItems[index]->parent_menu->hwndCB != 0){ |
|
873 |
if(display->menuItems[index]->parent_menu->hwndCB != 0){ |
829 |
//Fix duplicate menuItem problem. |
|
874 |
//Fix duplicate menuItem problem. |
830 |
if(start == display->menuItems[index]->index) { |
|
875 |
if(start == display->menuItems[index]->index) { |
831 |
display->menuItems[index]->index = -1 ; |
|
876 |
display->menuItems[index]->index = -1 ; |
832 |
} |
|
877 |
} |
833 |
if(start < display->menuItems[index]->index){ |
|
878 |
if(start < display->menuItems[index]->index){ |
834 |
display->menuItems[index]->index--; |
|
879 |
display->menuItems[index]->index--; |
835 |
} |
|
880 |
} |
836 |
} |
|
881 |
} |
837 |
} |
|
882 |
} |
838 |
} |
|
883 |
} |
839 |
} |
|
884 |
} |
840 |
*/ |
|
885 |
*/ |
841 |
|
|
886 |
|
842 |
|
|
887 |
|
843 |
void Display_DecMenuItemIndex(PUGL_Display display, HWND hwndCB, int start){ |
|
888 |
void Display_DecMenuItemIndex(PUGL_Display display, HWND hwndCB, int start){ |
844 |
// new for softkey, maintain the menuitem order |
|
889 |
// new for softkey, maintain the menuitem order |
845 |
int index; |
|
890 |
int index; |
846 |
for (index = 0; index < display->menuItemsLength; index++) { |
|
891 |
for (index = 0; index < display->menuItemsLength; index++) { |
847 |
if (display->menuItems[index] != NULL) { |
|
892 |
if (display->menuItems[index] != NULL) { |
848 |
if (display->menuItems[index]->parent_menu->hwndCB != hwndCB) continue; |
|
893 |
if (display->menuItems[index]->parent_menu->hwndCB != hwndCB) continue; |
849 |
if(display->menuItems[index]->parent_menu->hwndCB != 0){ |
|
894 |
if(display->menuItems[index]->parent_menu->hwndCB != 0){ |
850 |
//Fix duplicate menuItem problem. |
|
895 |
//Fix duplicate menuItem problem. |
851 |
if(start == display->menuItems[index]->index) { |
|
896 |
if(start == display->menuItems[index]->index) { |
852 |
display->menuItems[index]->index = -1 ; |
|
897 |
display->menuItems[index]->index = -1 ; |
853 |
} |
|
898 |
} |
854 |
if(start < display->menuItems[index]->index){ |
|
899 |
if(start < display->menuItems[index]->index){ |
855 |
display->menuItems[index]->index--; |
|
900 |
display->menuItems[index]->index--; |
856 |
} |
|
901 |
} |
857 |
} |
|
902 |
} |
858 |
} |
|
903 |
} |
859 |
} |
|
904 |
} |
860 |
} |
|
905 |
} |
861 |
|
|
906 |
|
862 |
// this function increments the index of menuitems in the main menu (top level menu) starting at index (start) |
|
907 |
// this function increments the index of menuitems in the main menu (top level menu) starting at index (start) |
863 |
// for example, when we add menuItem index 3 we would wish to increment the index of all menuitems greater than or equal to 3 by one |
|
908 |
// for example, when we add menuItem index 3 we would wish to increment the index of all menuitems greater than or equal to 3 by one |
864 |
void Display_IncMenuItemIndex(PUGL_Display display, HWND hwndCB, int start){ |
|
909 |
void Display_IncMenuItemIndex(PUGL_Display display, HWND hwndCB, int start){ |
865 |
// new for softkey, maintain the menuitem order |
|
910 |
// new for softkey, maintain the menuitem order |
866 |
int index; |
|
911 |
int index; |
867 |
FILE * pFile; |
|
912 |
FILE * pFile; |
868 |
for (index = 0; index < display->menuItemsLength; index++) { |
|
913 |
for (index = 0; index < display->menuItemsLength; index++) { |
869 |
if (display->menuItems[index] != NULL) { |
|
914 |
if (display->menuItems[index] != NULL) { |
870 |
if (display->menuItems[index]->parent_menu->hwndCB != hwndCB) continue; |
|
915 |
if (display->menuItems[index]->parent_menu->hwndCB != hwndCB) continue; |
871 |
if(display->menuItems[index]->parent_menu->hwndCB != 0){ |
|
916 |
if(display->menuItems[index]->parent_menu->hwndCB != 0){ |
872 |
if(start <= display->menuItems[index]->index){ |
|
917 |
if(start <= display->menuItems[index]->index){ |
873 |
display->menuItems[index]->index++; |
|
918 |
display->menuItems[index]->index++; |
874 |
} |
|
919 |
} |
875 |
} |
|
920 |
} |
876 |
} |
|
921 |
} |
877 |
} |
|
922 |
} |
878 |
} |
|
923 |
} |
879 |
|
|
924 |
|
880 |
// this function returns the menuitem count associated with specific menu hwndCB |
|
925 |
// this function returns the menuitem count associated with specific menu hwndCB |
881 |
int Display_MenuItemCount(PUGL_Display display, HWND hwndCB){ |
|
926 |
int Display_MenuItemCount(PUGL_Display display, HWND hwndCB){ |
882 |
int index; |
|
927 |
int index; |
883 |
int count=0; |
|
928 |
int count=0; |
884 |
for (index = 0; index < display->menuItemsLength; index++) { |
|
929 |
for (index = 0; index < display->menuItemsLength; index++) { |
885 |
if (display->menuItems[index] == NULL) continue; |
|
930 |
if (display->menuItems[index] == NULL) continue; |
886 |
if (display->menuItems[index]->parent_menu->hwndCB != hwndCB) continue; |
|
931 |
if (display->menuItems[index]->parent_menu->hwndCB != hwndCB) continue; |
887 |
count ++; |
|
932 |
count ++; |
888 |
} |
|
933 |
} |
889 |
return count; |
|
934 |
return count; |
890 |
} |
|
935 |
} |
891 |
|
|
936 |
|
892 |
#endif |
|
937 |
#endif |
893 |
|
|
938 |
|
894 |
//======================================================================================== |
|
939 |
//======================================================================================== |
895 |
|
|
940 |
|
896 |
/** |
|
941 |
/** |
897 |
* Returns the insets of the display identified by <code>handle</code>. |
|
942 |
* Returns the insets of the display identified by <code>handle</code>. |
898 |
* This is the portion of the screen that is unusable for drawing, |
|
943 |
* This is the portion of the screen that is unusable for drawing, |
899 |
* such as a task bar. |
|
944 |
* such as a task bar. |
900 |
* |
|
945 |
* |
901 |
* @ingroup Display |
|
946 |
* @ingroup Display |
902 |
* |
|
947 |
* |
903 |
* @param handle the display handle |
|
948 |
* @param handle the display handle |
904 |
* @param returnLeft (out) the left inset |
|
949 |
* @param returnLeft (out) the left inset |
905 |
* @param returnTop (out) the top inset |
|
950 |
* @param returnTop (out) the top inset |
906 |
* @param returnRight (out) the right inset |
|
951 |
* @param returnRight (out) the right inset |
907 |
* @param returnBottom (out) the bottom inset |
|
952 |
* @param returnBottom (out) the bottom inset |
908 |
* @param error the error status of the call |
|
953 |
* @param error the error status of the call |
909 |
*/ |
|
954 |
*/ |
910 |
void Display_GetInsets(UGL_Int handle, UGL_Int* returnLeft, UGL_Int* returnTop, UGL_Int* returnRight, UGL_Int* returnBottom, UGL_Error error) { |
|
955 |
void Display_GetInsets(UGL_Int handle, UGL_Int* returnLeft, UGL_Int* returnTop, UGL_Int* returnRight, UGL_Int* returnBottom, UGL_Error error) { |
911 |
int left = 0; |
|
956 |
int left = 0; |
912 |
int top = 0; |
|
957 |
int top = 0; |
913 |
int right = 0; |
|
958 |
int right = 0; |
914 |
int bottom = 0; |
|
959 |
int bottom = 0; |
915 |
|
|
960 |
|
916 |
RECT workarea; |
|
961 |
RECT workarea; |
917 |
int boundsX, boundsY, boundsWidth, boundsHeight; |
|
962 |
int boundsX, boundsY, boundsWidth, boundsHeight; |
918 |
|
|
963 |
|
919 |
SystemParametersInfo (SPI_GETWORKAREA, 0, &workarea, 0); |
|
964 |
SystemParametersInfo (SPI_GETWORKAREA, 0, &workarea, 0); |
920 |
Device_GetBounds(handle, &boundsX, &boundsY, &boundsWidth, &boundsHeight, error); |
|
965 |
Device_GetBounds(handle, &boundsX, &boundsY, &boundsWidth, &boundsHeight, error); |
921 |
|
|
966 |
|
922 |
*returnLeft = workarea.left - boundsX; |
|
967 |
*returnLeft = workarea.left - boundsX; |
923 |
*returnTop = workarea.top - boundsY; |
|
968 |
*returnTop = workarea.top - boundsY; |
924 |
*returnRight = boundsX + boundsWidth - workarea.right; |
|
969 |
*returnRight = boundsX + boundsWidth - workarea.right; |
925 |
*returnBottom = boundsY + boundsHeight - workarea.bottom; |
|
970 |
*returnBottom = boundsY + boundsHeight - workarea.bottom; |
926 |
} |
|
971 |
} |
927 |
|
|
972 |
|