823b9004 |
1 | #include <windows.h>\r |
2 | #include <commdlg.h>\r |
3 | #include <stdio.h>\r |
4 | \r |
5 | #include "../../pico/pico.h"\r |
6 | #include "../common/readpng.h"\r |
7 | #include "../common/config.h"\r |
8 | #include "../common/lprintf.h"\r |
9 | #include "../common/emu.h"\r |
10 | #include "../common/menu.h"\r |
11 | #include "../common/input.h"\r |
12 | #include "../common/plat.h"\r |
13 | #include "version.h"\r |
14 | #include "direct.h"\r |
15 | #include "in_vk.h"\r |
16 | \r |
17 | char *romname=NULL;\r |
18 | HWND FrameWnd=NULL;\r |
19 | RECT FrameRectMy;\r |
20 | RECT EmuScreenRect = { 0, 0, 320, 224 };\r |
21 | int lock_to_1_1 = 1;\r |
22 | static HWND PicoSwWnd=NULL, PicoPadWnd=NULL;\r |
23 | \r |
24 | static HMENU mmain = 0, mdisplay = 0, mpicohw = 0;\r |
25 | static HBITMAP ppad_bmp = 0;\r |
26 | static HBITMAP ppage_bmps[7] = { 0, };\r |
27 | static char rom_name[0x20*3+1];\r |
28 | static int main_wnd_as_pad = 0;\r |
29 | \r |
30 | static HANDLE loop_enter_event, loop_end_event;\r |
31 | \r |
32 | void error(char *text)\r |
33 | {\r |
34 | MessageBox(FrameWnd, text, "Error", 0);\r |
35 | }\r |
36 | \r |
37 | static void UpdateRect(void)\r |
38 | {\r |
39 | WINDOWINFO wi;\r |
40 | memset(&wi, 0, sizeof(wi));\r |
41 | wi.cbSize = sizeof(wi);\r |
42 | GetWindowInfo(FrameWnd, &wi);\r |
43 | FrameRectMy = wi.rcClient;\r |
44 | }\r |
45 | \r |
46 | static int extract_rom_name(char *dest, const unsigned char *src, int len)\r |
47 | {\r |
48 | char *p = dest, s_old = 0x20;\r |
49 | int i;\r |
50 | \r |
51 | for (i = len - 1; i >= 0; i--)\r |
52 | {\r |
53 | if (src[i^1] != ' ') break;\r |
54 | }\r |
55 | len = i + 1;\r |
56 | \r |
57 | for (i = 0; i < len; i++)\r |
58 | {\r |
59 | unsigned char s = src[i^1];\r |
60 | if (s == 0x20 && s_old == 0x20) continue;\r |
61 | else if (s >= 0x20 && s < 0x7f && s != '%')\r |
62 | {\r |
63 | *p++ = s;\r |
64 | }\r |
65 | else\r |
66 | {\r |
67 | sprintf(p, "%%%02x", s);\r |
68 | p += 3;\r |
69 | }\r |
70 | s_old = s;\r |
71 | }\r |
72 | *p = 0;\r |
73 | \r |
74 | return p - dest;\r |
75 | }\r |
76 | \r |
77 | static void check_name_alias(const char *afname)\r |
78 | {\r |
79 | char buff[256], *var, *val;\r |
80 | FILE *f;\r |
81 | int ret;\r |
82 | \r |
83 | f = fopen(afname, "r");\r |
84 | if (f == NULL) return;\r |
85 | \r |
86 | while (1)\r |
87 | {\r |
88 | ret = config_get_var_val(f, buff, sizeof(buff), &var, &val);\r |
89 | if (ret == 0) break;\r |
90 | if (ret == -1) continue;\r |
91 | \r |
92 | if (strcmp(rom_name, var) == 0) {\r |
93 | lprintf("rom aliased: \"%s\" -> \"%s\"\n", rom_name, val);\r |
94 | strncpy(rom_name, val, sizeof(rom_name));\r |
95 | break;\r |
96 | }\r |
97 | }\r |
98 | fclose(f);\r |
99 | }\r |
100 | \r |
101 | static HBITMAP png2hb(const char *fname, int is_480)\r |
102 | {\r |
103 | BITMAPINFOHEADER bih;\r |
104 | HBITMAP bmp;\r |
105 | void *bmem;\r |
106 | int ret;\r |
107 | \r |
108 | bmem = calloc(1, is_480 ? 480*240*3 : 320*240*3);\r |
109 | if (bmem == NULL) return NULL;\r |
110 | ret = readpng(bmem, fname, is_480 ? READPNG_480_24 : READPNG_320_24);\r |
111 | if (ret != 0) {\r |
112 | free(bmem);\r |
113 | return NULL;\r |
114 | }\r |
115 | \r |
116 | memset(&bih, 0, sizeof(bih));\r |
117 | bih.biSize = sizeof(bih);\r |
118 | bih.biWidth = is_480 ? 480 : 320;\r |
119 | bih.biHeight = -240;\r |
120 | bih.biPlanes = 1;\r |
121 | bih.biBitCount = 24;\r |
122 | bih.biCompression = BI_RGB;\r |
123 | bmp = CreateDIBitmap(GetDC(FrameWnd), &bih, CBM_INIT, bmem, (BITMAPINFO *)&bih, 0);\r |
124 | if (bmp == NULL)\r |
125 | lprintf("CreateDIBitmap failed with %i", GetLastError());\r |
126 | \r |
127 | free(bmem);\r |
128 | return bmp;\r |
129 | }\r |
130 | \r |
131 | static void PrepareForROM(void)\r |
132 | {\r |
133 | unsigned char *rom_data = NULL;\r |
134 | int i, ret, show = PicoAHW & PAHW_PICO;\r |
135 | \r |
136 | PicoGetInternal(PI_ROM, (pint_ret_t *) &rom_data);\r |
137 | EnableMenuItem(mmain, 2, MF_BYPOSITION|(show ? MF_ENABLED : MF_GRAYED));\r |
138 | ShowWindow(PicoPadWnd, show ? SW_SHOWNA : SW_HIDE);\r |
139 | ShowWindow(PicoSwWnd, show ? SW_SHOWNA : SW_HIDE);\r |
140 | CheckMenuItem(mpicohw, 1210, show ? MF_CHECKED : MF_UNCHECKED);\r |
141 | CheckMenuItem(mpicohw, 1211, show ? MF_CHECKED : MF_UNCHECKED);\r |
142 | PostMessage(FrameWnd, WM_COMMAND, 1220 + PicoPicohw.page, 0);\r |
143 | DrawMenuBar(FrameWnd);\r |
144 | InvalidateRect(PicoSwWnd, NULL, 1);\r |
145 | \r |
146 | PicoPicohw.pen_pos[0] =\r |
147 | PicoPicohw.pen_pos[1] = 0x8000;\r |
148 | in_vk_add_pl12 = 0;\r |
149 | \r |
150 | ret = extract_rom_name(rom_name, rom_data + 0x150, 0x20);\r |
151 | if (ret == 0)\r |
152 | extract_rom_name(rom_name, rom_data + 0x130, 0x20);\r |
153 | \r |
154 | if (show)\r |
155 | {\r |
156 | char path[MAX_PATH], *p;\r |
157 | GetModuleFileName(NULL, path, sizeof(path) - 32);\r |
158 | p = strrchr(path, '\\');\r |
159 | if (p == NULL) p = path;\r |
160 | else p++;\r |
161 | if (ppad_bmp == NULL) {\r |
162 | strcpy(p, "pico\\pad.png");\r |
163 | ppad_bmp = png2hb(path, 0);\r |
164 | }\r |
165 | \r |
166 | strcpy(p, "pico\\alias.txt");\r |
167 | check_name_alias(path);\r |
168 | \r |
169 | for (i = 0; i < 7; i++) {\r |
170 | if (ppage_bmps[i] != NULL) DeleteObject(ppage_bmps[i]);\r |
171 | sprintf(p, "pico\\%s_%i.png", rom_name, i);\r |
172 | ppage_bmps[i] = png2hb(path, 1);\r |
173 | }\r |
174 | // games usually don't have page 6, so just duplicate page 5.\r |
175 | if (ppage_bmps[6] == NULL && ppage_bmps[5] != NULL) {\r |
176 | sprintf(p, "pico\\%s_5.png", rom_name);\r |
177 | ppage_bmps[6] = png2hb(path, 1);\r |
178 | }\r |
179 | }\r |
180 | }\r |
181 | \r |
182 | static void LoadROM(const char *cmdpath)\r |
183 | {\r |
184 | char rompath[MAX_PATH];\r |
185 | int ret;\r |
186 | \r |
187 | if (cmdpath != NULL && strlen(cmdpath)) {\r |
188 | strcpy(rompath, cmdpath + (cmdpath[0] == '\"' ? 1 : 0));\r |
189 | if (rompath[strlen(rompath)-1] == '\"')\r |
190 | rompath[strlen(rompath)-1] = 0;\r |
191 | }\r |
192 | else {\r |
193 | OPENFILENAME of; ZeroMemory(&of, sizeof(of));\r |
194 | rompath[sizeof(rompath) - 1] = 0;\r |
195 | strncpy(rompath, rom_fname_loaded, sizeof(rompath) - 1);\r |
196 | of.lStructSize = sizeof(of);\r |
197 | of.lpstrFilter = "ROMs, CD images\0*.smd;*.bin;*.gen;*.zip;*.32x;*.sms;*.iso;*.cso;*.cue\0"\r |
198 | "whatever\0*.*\0";\r |
199 | of.lpstrFile = rompath;\r |
200 | of.nMaxFile = MAX_PATH;\r |
201 | of.Flags = OFN_FILEMUSTEXIST|OFN_HIDEREADONLY;\r |
202 | of.hwndOwner = FrameWnd;\r |
203 | if (!GetOpenFileName(&of))\r |
204 | return;\r |
205 | }\r |
206 | \r |
207 | if (engineState == PGS_Running) {\r |
208 | engineState = PGS_Paused;\r |
209 | WaitForSingleObject(loop_end_event, 5000);\r |
210 | }\r |
211 | \r |
212 | ret = emu_reload_rom(rompath);\r |
213 | if (ret == 0) {\r |
214 | extern char menu_error_msg[]; // HACK..\r |
215 | error(menu_error_msg);\r |
216 | return;\r |
217 | }\r |
218 | \r |
219 | PrepareForROM();\r |
220 | engineState = PGS_Running;\r |
221 | SetEvent(loop_enter_event);\r |
222 | }\r |
223 | \r |
224 | static const int rect_widths[4] = { 320, 256, 640, 512 };\r |
225 | static const int rect_heights[4] = { 224, 224, 448, 448 };\r |
226 | \r |
227 | // Window proc for the frame window:\r |
228 | static LRESULT CALLBACK WndProc(HWND hwnd,UINT msg,WPARAM wparam,LPARAM lparam)\r |
229 | {\r |
230 | POINT pt;\r |
231 | RECT rc;\r |
232 | int i;\r |
233 | switch (msg)\r |
234 | {\r |
235 | case WM_CLOSE:\r |
236 | PostQuitMessage(0);\r |
237 | return 0;\r |
238 | case WM_DESTROY:\r |
239 | FrameWnd = NULL; // Blank the handle\r |
240 | break;\r |
241 | case WM_SIZE:\r |
242 | case WM_MOVE:\r |
243 | case WM_SIZING:\r |
244 | UpdateRect();\r |
245 | if (lock_to_1_1 && FrameRectMy.right - FrameRectMy.left != 0 &&\r |
246 | (FrameRectMy.right - FrameRectMy.left != EmuScreenRect.right - EmuScreenRect.left ||\r |
247 | FrameRectMy.bottom - FrameRectMy.top != EmuScreenRect.bottom - EmuScreenRect.top)) {\r |
248 | lock_to_1_1 = 0;\r |
249 | CheckMenuItem(mdisplay, 1104, MF_UNCHECKED);\r |
250 | }\r |
251 | break;\r |
252 | case WM_COMMAND:\r |
253 | switch (LOWORD(wparam))\r |
254 | {\r |
255 | case 1000:\r |
256 | LoadROM(NULL);\r |
257 | break;\r |
258 | case 1001:\r |
259 | emu_reset_game();\r |
260 | return 0;\r |
261 | case 1002:\r |
262 | PostQuitMessage(0);\r |
263 | return 0;\r |
264 | case 1100:\r |
265 | case 1101:\r |
266 | case 1102:\r |
267 | case 1103:\r |
268 | // LoopWait=1; // another sync hack\r |
269 | // for (i = 0; !LoopWaiting && i < 10; i++) Sleep(10);\r |
270 | FrameRectMy.right = FrameRectMy.left + rect_widths[wparam&3];\r |
271 | FrameRectMy.bottom = FrameRectMy.top + rect_heights[wparam&3];\r |
272 | AdjustWindowRect(&FrameRectMy, WS_OVERLAPPEDWINDOW, 1);\r |
273 | MoveWindow(hwnd, FrameRectMy.left, FrameRectMy.top,\r |
274 | FrameRectMy.right-FrameRectMy.left, FrameRectMy.bottom-FrameRectMy.top, 1);\r |
275 | UpdateRect();\r |
276 | lock_to_1_1 = 0;\r |
277 | CheckMenuItem(mdisplay, 1104, MF_UNCHECKED);\r |
278 | // if (rom_loaded) LoopWait=0;\r |
279 | return 0;\r |
280 | case 1104:\r |
281 | lock_to_1_1 = !lock_to_1_1;\r |
282 | CheckMenuItem(mdisplay, 1104, lock_to_1_1 ? MF_CHECKED : MF_UNCHECKED);\r |
283 | /* FALLTHROUGH */\r |
284 | case 2000: // EmuScreenRect/FrameRectMy sync request\r |
285 | if (!lock_to_1_1)\r |
286 | return 0;\r |
287 | FrameRectMy.right = FrameRectMy.left + (EmuScreenRect.right - EmuScreenRect.left);\r |
288 | FrameRectMy.bottom = FrameRectMy.top + (EmuScreenRect.bottom - EmuScreenRect.top);\r |
289 | AdjustWindowRect(&FrameRectMy, WS_OVERLAPPEDWINDOW, 1);\r |
290 | MoveWindow(hwnd, FrameRectMy.left, FrameRectMy.top,\r |
291 | FrameRectMy.right-FrameRectMy.left, FrameRectMy.bottom-FrameRectMy.top, 1);\r |
292 | UpdateRect();\r |
293 | return 0;\r |
294 | case 1210:\r |
295 | case 1211:\r |
296 | i = IsWindowVisible((LOWORD(wparam)&1) ? PicoPadWnd : PicoSwWnd);\r |
297 | i = !i;\r |
298 | ShowWindow((LOWORD(wparam)&1) ? PicoPadWnd : PicoSwWnd, i ? SW_SHOWNA : SW_HIDE);\r |
299 | CheckMenuItem(mpicohw, LOWORD(wparam), i ? MF_CHECKED : MF_UNCHECKED);\r |
300 | return 0;\r |
301 | case 1212:\r |
302 | main_wnd_as_pad = !main_wnd_as_pad;\r |
303 | CheckMenuItem(mpicohw, 1212, main_wnd_as_pad ? MF_CHECKED : MF_UNCHECKED);\r |
304 | return 0;\r |
305 | case 1220:\r |
306 | case 1221:\r |
307 | case 1222:\r |
308 | case 1223:\r |
309 | case 1224:\r |
310 | case 1225:\r |
311 | case 1226:\r |
312 | PicoPicohw.page = LOWORD(wparam) % 10;\r |
313 | for (i = 0; i < 7; i++)\r |
314 | CheckMenuItem(mpicohw, 1220 + i, MF_UNCHECKED);\r |
315 | CheckMenuItem(mpicohw, 1220 + PicoPicohw.page, MF_CHECKED);\r |
316 | InvalidateRect(PicoSwWnd, NULL, 1);\r |
317 | return 0;\r |
318 | case 1300:\r |
319 | MessageBox(FrameWnd, plat_get_credits(), "About", 0);\r |
320 | return 0;\r |
321 | }\r |
322 | break;\r |
323 | case WM_TIMER:\r |
324 | GetCursorPos(&pt);\r |
325 | GetWindowRect(PicoSwWnd, &rc);\r |
326 | if (PtInRect(&rc, pt)) break;\r |
327 | GetWindowRect(PicoPadWnd, &rc);\r |
328 | if (PtInRect(&rc, pt)) break;\r |
329 | PicoPicohw.pen_pos[0] |= 0x8000;\r |
330 | PicoPicohw.pen_pos[1] |= 0x8000;\r |
331 | in_vk_add_pl12 = 0;\r |
332 | break;\r |
333 | case WM_LBUTTONDOWN: in_vk_add_pl12 |= 0x20; return 0;\r |
334 | case WM_LBUTTONUP: in_vk_add_pl12 &= ~0x20; return 0;\r |
335 | case WM_MOUSEMOVE:\r |
336 | if (!main_wnd_as_pad) break;\r |
337 | PicoPicohw.pen_pos[0] = 0x03c + (320 * LOWORD(lparam) / (FrameRectMy.right - FrameRectMy.left));\r |
338 | PicoPicohw.pen_pos[1] = 0x1fc + (232 * HIWORD(lparam) / (FrameRectMy.bottom - FrameRectMy.top));\r |
339 | SetTimer(FrameWnd, 100, 1000, NULL);\r |
340 | break;\r |
341 | case WM_KEYDOWN:\r |
342 | if (wparam == VK_TAB) {\r |
343 | emu_reset_game();\r |
344 | break;\r |
345 | }\r |
346 | if (wparam == VK_ESCAPE) {\r |
347 | LoadROM(NULL);\r |
348 | break;\r |
349 | }\r |
350 | in_vk_keydown(wparam);\r |
351 | break;\r |
352 | case WM_KEYUP:\r |
353 | in_vk_keyup(wparam);\r |
354 | break;\r |
355 | }\r |
356 | \r |
357 | return DefWindowProc(hwnd,msg,wparam,lparam);\r |
358 | }\r |
359 | \r |
360 | static LRESULT CALLBACK PicoSwWndProc(HWND hwnd,UINT msg,WPARAM wparam,LPARAM lparam)\r |
361 | {\r |
362 | PAINTSTRUCT ps;\r |
363 | HDC hdc, hdc2;\r |
364 | \r |
365 | switch (msg)\r |
366 | {\r |
367 | case WM_DESTROY: PicoSwWnd=NULL; break;\r |
368 | case WM_LBUTTONDOWN: in_vk_add_pl12 |= 0x20; return 0;\r |
369 | case WM_LBUTTONUP: in_vk_add_pl12 &= ~0x20; return 0;\r |
370 | case WM_MOUSEMOVE:\r |
371 | if (HIWORD(lparam) < 0x20) break;\r |
372 | PicoPicohw.pen_pos[0] = 0x03c + LOWORD(lparam) * 2/3;\r |
373 | PicoPicohw.pen_pos[1] = 0x2f8 + HIWORD(lparam) - 0x20;\r |
374 | SetTimer(FrameWnd, 100, 1000, NULL);\r |
375 | break;\r |
376 | case WM_KEYDOWN: in_vk_keydown(wparam); break;\r |
377 | case WM_KEYUP: in_vk_keyup(wparam); break;\r |
378 | case WM_PAINT:\r |
379 | hdc = BeginPaint(hwnd, &ps);\r |
380 | if (ppage_bmps[PicoPicohw.page] == NULL)\r |
381 | {\r |
382 | SelectObject(hdc, GetStockObject(DEFAULT_GUI_FONT));\r |
383 | SetTextColor(hdc, RGB(255, 255, 255));\r |
384 | SetBkColor(hdc, RGB(0, 0, 0));\r |
385 | TextOut(hdc, 2, 2, "missing PNGs for", 16);\r |
386 | TextOut(hdc, 2, 18, rom_name, strlen(rom_name));\r |
387 | }\r |
388 | else\r |
389 | {\r |
390 | hdc2 = CreateCompatibleDC(GetDC(FrameWnd));\r |
391 | SelectObject(hdc2, ppage_bmps[PicoPicohw.page]);\r |
392 | BitBlt(hdc, 0, 0, 480, 240, hdc2, 0, 0, SRCCOPY);\r |
393 | DeleteDC(hdc2);\r |
394 | }\r |
395 | EndPaint(hwnd, &ps);\r |
396 | return 0;\r |
397 | case WM_CLOSE:\r |
398 | ShowWindow(hwnd, SW_HIDE);\r |
399 | CheckMenuItem(mpicohw, 1210, MF_UNCHECKED);\r |
400 | return 0;\r |
401 | }\r |
402 | \r |
403 | return DefWindowProc(hwnd,msg,wparam,lparam);\r |
404 | }\r |
405 | \r |
406 | static LRESULT CALLBACK PicoPadWndProc(HWND hwnd,UINT msg,WPARAM wparam,LPARAM lparam)\r |
407 | {\r |
408 | PAINTSTRUCT ps;\r |
409 | HDC hdc, hdc2;\r |
410 | \r |
411 | switch (msg)\r |
412 | {\r |
413 | case WM_DESTROY: PicoPadWnd=NULL; break;\r |
414 | case WM_LBUTTONDOWN: in_vk_add_pl12 |= 0x20; return 0;\r |
415 | case WM_LBUTTONUP: in_vk_add_pl12 &= ~0x20; return 0;\r |
416 | case WM_MOUSEMOVE:\r |
417 | PicoPicohw.pen_pos[0] = 0x03c + LOWORD(lparam);\r |
418 | PicoPicohw.pen_pos[1] = 0x1fc + HIWORD(lparam);\r |
419 | SetTimer(FrameWnd, 100, 1000, NULL);\r |
420 | break;\r |
421 | case WM_KEYDOWN: in_vk_keydown(wparam); break;\r |
422 | case WM_KEYUP: in_vk_keyup(wparam); break;\r |
423 | case WM_PAINT:\r |
424 | if (ppad_bmp == NULL) break;\r |
425 | hdc = BeginPaint(hwnd, &ps);\r |
426 | hdc2 = CreateCompatibleDC(GetDC(FrameWnd));\r |
427 | SelectObject(hdc2, ppad_bmp);\r |
428 | BitBlt(hdc, 0, 0, 320, 240, hdc2, 0, 0, SRCCOPY);\r |
429 | EndPaint(hwnd, &ps);\r |
430 | DeleteDC(hdc2);\r |
431 | return 0;\r |
432 | case WM_CLOSE:\r |
433 | ShowWindow(hwnd, SW_HIDE);\r |
434 | CheckMenuItem(mpicohw, 1211, MF_UNCHECKED);\r |
435 | return 0;\r |
436 | }\r |
437 | \r |
438 | return DefWindowProc(hwnd,msg,wparam,lparam);\r |
439 | }\r |
440 | \r |
441 | \r |
442 | static int FrameInit()\r |
443 | {\r |
444 | WNDCLASS wc;\r |
445 | RECT rect={0,0,0,0};\r |
446 | HMENU mfile;\r |
447 | int style=0;\r |
448 | int left=0,top=0,width=0,height=0;\r |
449 | \r |
450 | memset(&wc,0,sizeof(wc));\r |
451 | \r |
452 | // Register the window class:\r |
453 | wc.lpfnWndProc=WndProc;\r |
454 | wc.hInstance=GetModuleHandle(NULL);\r |
455 | wc.hCursor=LoadCursor(NULL,IDC_ARROW);\r |
456 | wc.hbrBackground=CreateSolidBrush(0);\r |
457 | wc.lpszClassName="PicoMainFrame";\r |
458 | RegisterClass(&wc);\r |
459 | \r |
460 | wc.lpszClassName="PicoSwWnd";\r |
461 | wc.lpfnWndProc=PicoSwWndProc;\r |
462 | RegisterClass(&wc);\r |
463 | \r |
464 | wc.lpszClassName="PicoPadWnd";\r |
465 | wc.lpfnWndProc=PicoPadWndProc;\r |
466 | RegisterClass(&wc);\r |
467 | \r |
468 | rect.right =320;\r |
469 | rect.bottom=224;\r |
470 | \r |
471 | // Adjust size of windows based on borders:\r |
472 | style=WS_OVERLAPPEDWINDOW;\r |
473 | AdjustWindowRect(&rect,style,1);\r |
474 | width =rect.right-rect.left;\r |
475 | height=rect.bottom-rect.top;\r |
476 | \r |
477 | // Place window in the centre of the screen:\r |
478 | SystemParametersInfo(SPI_GETWORKAREA,0,&rect,0);\r |
479 | left=rect.left+rect.right;\r |
480 | top=rect.top+rect.bottom;\r |
481 | \r |
482 | left-=width; left>>=1;\r |
483 | top-=height; top>>=1;\r |
484 | \r |
485 | // Create menu:\r |
486 | mfile = CreateMenu();\r |
487 | InsertMenu(mfile, -1, MF_BYPOSITION|MF_STRING, 1000, "&Load ROM");\r |
488 | InsertMenu(mfile, -1, MF_BYPOSITION|MF_STRING, 1001, "&Reset");\r |
489 | InsertMenu(mfile, -1, MF_BYPOSITION|MF_STRING, 1002, "E&xit");\r |
490 | mdisplay = CreateMenu();\r |
491 | InsertMenu(mdisplay, -1, MF_BYPOSITION|MF_STRING, 1100, "320x224");\r |
492 | InsertMenu(mdisplay, -1, MF_BYPOSITION|MF_STRING, 1101, "256x224");\r |
493 | InsertMenu(mdisplay, -1, MF_BYPOSITION|MF_STRING, 1102, "640x448");\r |
494 | InsertMenu(mdisplay, -1, MF_BYPOSITION|MF_STRING, 1103, "512x448");\r |
495 | InsertMenu(mdisplay, -1, MF_BYPOSITION|MF_STRING, 1104, "Lock to 1:1");\r |
496 | mpicohw = CreateMenu();\r |
497 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1210, "Show &Storyware");\r |
498 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1211, "Show &Drawing pad");\r |
499 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1212, "&Main window as pad");\r |
500 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_SEPARATOR, 0, NULL);\r |
501 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1220, "Title page (&0)");\r |
502 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1221, "Page &1");\r |
503 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1222, "Page &2");\r |
504 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1223, "Page &3");\r |
505 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1224, "Page &4");\r |
506 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1225, "Page &5");\r |
507 | InsertMenu(mpicohw, -1, MF_BYPOSITION|MF_STRING, 1226, "Page &6");\r |
508 | mmain = CreateMenu();\r |
509 | InsertMenu(mmain, -1, MF_BYPOSITION|MF_STRING|MF_POPUP, (UINT_PTR) mfile, "&File");\r |
510 | InsertMenu(mmain, -1, MF_BYPOSITION|MF_STRING|MF_POPUP, (UINT_PTR) mdisplay, "&Display");\r |
511 | InsertMenu(mmain, -1, MF_BYPOSITION|MF_STRING|MF_POPUP, (UINT_PTR) mpicohw, "&Pico");\r |
512 | EnableMenuItem(mmain, 2, MF_BYPOSITION|MF_GRAYED);\r |
513 | // InsertMenu(mmain, -1, MF_BYPOSITION|MF_STRING|MF_POPUP, 1200, "&Config");\r |
514 | InsertMenu(mmain, -1, MF_BYPOSITION|MF_STRING, 1300, "&About");\r |
515 | \r |
516 | // Create the window:\r |
517 | FrameWnd=CreateWindow("PicoMainFrame","PicoDrive " VERSION,style|WS_VISIBLE,\r |
518 | left,top,width,height,NULL,mmain,NULL,NULL);\r |
519 | \r |
520 | CheckMenuItem(mdisplay, 1104, lock_to_1_1 ? MF_CHECKED : MF_UNCHECKED);\r |
521 | ShowWindow(FrameWnd, SW_NORMAL);\r |
522 | UpdateWindow(FrameWnd);\r |
523 | UpdateRect();\r |
524 | \r |
525 | // create Pico windows\r |
526 | style = WS_OVERLAPPED|WS_CAPTION|WS_BORDER|WS_SYSMENU;\r |
527 | rect.left=rect.top=0;\r |
528 | rect.right =320;\r |
529 | rect.bottom=224;\r |
530 | \r |
531 | AdjustWindowRect(&rect,style,1);\r |
532 | width =rect.right-rect.left;\r |
533 | height=rect.bottom-rect.top;\r |
534 | \r |
535 | left += 326;\r |
536 | PicoSwWnd=CreateWindow("PicoSwWnd","Storyware",style,\r |
537 | left,top,width+160,height,FrameWnd,NULL,NULL,NULL);\r |
538 | \r |
539 | top += 266;\r |
540 | PicoPadWnd=CreateWindow("PicoPadWnd","Drawing Pad",style,\r |
541 | left,top,width,height,FrameWnd,NULL,NULL,NULL);\r |
542 | \r |
543 | return 0;\r |
544 | }\r |
545 | \r |
546 | // --------------------\r |
547 | \r |
548 | static DWORD WINAPI work_thread(void *x)\r |
549 | {\r |
550 | while (engineState != PGS_Quit) {\r |
551 | WaitForSingleObject(loop_enter_event, INFINITE);\r |
552 | if (engineState != PGS_Running)\r |
553 | continue;\r |
554 | \r |
555 | printf("loop..\n");\r |
556 | emu_loop();\r |
557 | SetEvent(loop_end_event);\r |
558 | }\r |
559 | \r |
560 | return 0;\r |
561 | }\r |
562 | \r |
563 | // XXX: use main.c\r |
564 | void xxinit(void)\r |
565 | {\r |
566 | /* in_init() must go before config, config accesses in_ fwk */\r |
567 | in_init();\r |
568 | pemu_prep_defconfig();\r |
569 | emu_read_config(0, 0);\r |
570 | config_readlrom(PicoConfigFile);\r |
571 | \r |
572 | plat_init();\r |
573 | in_probe();\r |
574 | \r |
575 | emu_init();\r |
576 | menu_init();\r |
577 | }\r |
578 | \r |
579 | \r |
580 | int WINAPI WinMain(HINSTANCE p1, HINSTANCE p2, LPSTR cmdline, int p4)\r |
581 | {\r |
582 | MSG msg;\r |
583 | DWORD tid = 0;\r |
584 | HANDLE thread;\r |
585 | int ret;\r |
586 | \r |
587 | xxinit();\r |
588 | FrameInit();\r |
589 | ret = DirectInit();\r |
590 | if (ret)\r |
591 | goto end0;\r |
592 | \r |
593 | loop_enter_event = CreateEvent(NULL, 0, 0, NULL);\r |
594 | if (loop_enter_event == NULL)\r |
595 | goto end0;\r |
596 | \r |
597 | loop_end_event = CreateEvent(NULL, 0, 0, NULL);\r |
598 | if (loop_end_event == NULL)\r |
599 | goto end0;\r |
600 | \r |
601 | thread = CreateThread(NULL, 0, work_thread, NULL, 0, &tid);\r |
602 | if (thread == NULL)\r |
603 | goto end0;\r |
604 | \r |
605 | LoadROM(cmdline);\r |
606 | \r |
607 | // Main window loop:\r |
608 | for (;;)\r |
609 | {\r |
610 | GetMessage(&msg,NULL,0,0);\r |
611 | if (msg.message==WM_QUIT) break;\r |
612 | \r |
613 | TranslateMessage(&msg);\r |
614 | DispatchMessage(&msg);\r |
615 | }\r |
616 | \r |
617 | // Signal thread to quit and wait for it to exit:\r |
618 | if (engineState == PGS_Running) {\r |
619 | engineState = PGS_Quit;\r |
620 | WaitForSingleObject(loop_end_event, 5000);\r |
621 | }\r |
622 | CloseHandle(thread); thread=NULL;\r |
623 | \r |
624 | emu_write_config(0);\r |
625 | emu_finish();\r |
626 | //plat_finish();\r |
627 | \r |
628 | end0:\r |
629 | DirectExit();\r |
630 | DestroyWindow(FrameWnd);\r |
631 | \r |
632 | // _CrtDumpMemoryLeaks();\r |
633 | return 0;\r |
634 | }\r |
635 | \r |