1 /*
2 vfdguiopen.c
3
4 Virtual Floppy Drive for Windows
5 Driver control library
6 Open image GUI utility function
7
8 Copyright (c) 2003-2005 Ken Kato
9 */
10
11 #ifdef __cplusplus
12 #pragma message(__FILE__": Compiled as C++ for testing purpose.")
13 #endif // __cplusplus
14
15 #define WIN32_LEAN_AND_MEAN
16 #include <windows.h>
17 #if !defined(__REACTOS__) || defined(_MSC_VER)
18 #pragma warning(push,3)
19 #endif
20 #include <commdlg.h>
21 #if !defined(__REACTOS__) || defined(_MSC_VER)
22 #pragma warning(pop)
23 #endif
24
25 #include "vfdtypes.h"
26 #include "vfdapi.h"
27 #include "vfdlib.h"
28 #ifndef __REACTOS__
29 #include "vfdmsg.h"
30 #else
31 #include "vfdmsg_lib.h"
32 #endif
33 #include "vfdguirc.h"
34
35 //
36 // String constants
37 //
38
39 #define FALLBACK_IMAGE_FILTER \
40 "Common image files (bin,dat,fdd,flp,ima,img,vfd)\0" \
41 "*.bin;*.dat;*.fdd;*.flp;*.ima;*.img;*.vfd\0" \
42 "Zip compressed image (imz,zip)\0*.imz;*.zip\0" \
43 "All files (*.*)\0*.*\0"
44
45 #define FALLBACK_IMAGE_TITLE "Open Virtual Floppy Image"
46
47 //
48 // local functions
49 //
50 #ifndef __REACTOS__
51 static INT CALLBACK OpenDialogProc(
52 #else
53 static INT_PTR CALLBACK OpenDialogProc(
54 #endif
55 HWND hDlg,
56 UINT uMsg,
57 WPARAM wParam,
58 LPARAM lParam);
59
60 static void OnInit(HWND hDlg, ULONG nDevice);
61 static void OnImage(HWND hDlg, HWND hEdit);
62 static void OnBrowse(HWND hDlg);
63 static void OnDiskType(HWND hDlg, HWND hRadio);
64 static void OnMediaType(HWND hDlg, HWND hCombo);
65 static void OnProtect(HWND hDlg, HWND hCheck);
66 static DWORD OnOK(HWND hDlg);
67
68 //
69 // Show Open Image dialog box
70 //
VfdGuiOpen(HWND hParent,ULONG nDevice)71 DWORD WINAPI VfdGuiOpen(
72 HWND hParent,
73 ULONG nDevice)
74 {
75 switch (DialogBoxParam(
76 g_hDllModule,
77 MAKEINTRESOURCE(IDD_OPENDIALOG),
78 hParent,
79 OpenDialogProc,
80 nDevice))
81 {
82 case IDOK:
83 return ERROR_SUCCESS;
84
85 case IDCANCEL:
86 return ERROR_CANCELLED;
87
88 default:
89 return GetLastError();
90 }
91 }
92
93 //
94 // Open image dialog procedure
95 //
96 #ifndef __REACTOS__
OpenDialogProc(HWND hDlg,UINT uMsg,WPARAM wParam,LPARAM lParam)97 INT CALLBACK OpenDialogProc(
98 #else
99 INT_PTR CALLBACK OpenDialogProc(
100 #endif
101 HWND hDlg,
102 UINT uMsg,
103 WPARAM wParam,
104 LPARAM lParam)
105 {
106 switch (uMsg) {
107 case WM_INITDIALOG:
108 OnInit(hDlg, lParam);
109 return TRUE;
110
111 case WM_COMMAND:
112 switch (wParam) {
113 case MAKELONG(IDC_IMAGEFILE, EN_CHANGE):
114 OnImage(hDlg, (HWND)lParam);
115 return TRUE;
116
117 case IDC_BROWSE:
118 OnBrowse(hDlg);
119 return TRUE;
120
121 case IDC_DISKTYPE_FILE:
122 case IDC_DISKTYPE_RAM:
123 OnDiskType(hDlg, (HWND)lParam);
124 return TRUE;
125
126 case MAKELONG(IDC_MEDIATYPE, CBN_SELCHANGE):
127 OnMediaType(hDlg, (HWND)lParam);
128 return TRUE;
129
130 case IDC_OPEN_PROTECTED:
131 OnProtect(hDlg, (HWND)lParam);
132 return TRUE;
133
134 case IDOK:
135 if (OnOK(hDlg) == ERROR_SUCCESS) {
136 EndDialog(hDlg, IDOK);
137 }
138 return TRUE;
139
140 case IDCANCEL:
141 EndDialog(hDlg, IDCANCEL);
142 return TRUE;
143 }
144 break;
145
146 case WM_CONTEXTMENU:
147 ShowContextMenu(hDlg, (HWND)wParam, lParam);
148 break;
149
150 case WM_HELP:
151 {
152 LPHELPINFO info = (LPHELPINFO)lParam;
153
154 if (info->iContextType == HELPINFO_WINDOW) {
155 ShowHelpWindow(hDlg, info->iCtrlId);
156 }
157 }
158 return TRUE;
159 }
160
161 return FALSE;
162 }
163
164 //
165 // Initialize the Open Image dialog
166 //
OnInit(HWND hDlg,ULONG nDevice)167 void OnInit(
168 HWND hDlg,
169 ULONG nDevice)
170 {
171 VFD_MEDIA i;
172
173 // Store the device number
174
175 SetWindowLong(hDlg, GWL_USERDATA, nDevice);
176
177 // Store default file size
178
179 SetWindowLong(hDlg, DWL_USER, INVALID_FILE_SIZE);
180
181 // Set dialog window title
182
183 SetControlText(hDlg, 0, MSG_OPEN_TITLE);
184
185 // Set control captions
186
187 SetControlText(hDlg, IDC_IMAGEFILE_LABEL, MSG_IMAGEFILE_ACCEL);
188 SetControlText(hDlg, IDC_IMAGEDESC_LABEL, MSG_DESCRIPTION_LABEL);
189 SetControlText(hDlg, IDC_BROWSE, MSG_BROWSE_BUTTON);
190 SetControlText(hDlg, IDC_DISKTYPE_LABEL, MSG_DISKTYPE_LABEL);
191 SetControlText(hDlg, IDC_MEDIATYPE_LABEL, MSG_MEDIATYPE_ACCEL);
192 SetControlText(hDlg, IDC_OPEN_PROTECTED, MSG_MENU_PROTECT);
193 SetControlText(hDlg, IDOK, MSG_CREATE_BUTTON);
194 SetControlText(hDlg, IDCANCEL, MSG_CANCEL_BUTTON);
195
196 // select RAM disk as default
197
198 CheckRadioButton(hDlg, IDC_DISKTYPE_FILE,
199 IDC_DISKTYPE_RAM, IDC_DISKTYPE_RAM);
200
201 // setup media type combo list
202
203 for (i = 1; i < VFD_MEDIA_MAX; i++) {
204 SendDlgItemMessage(hDlg, IDC_MEDIATYPE,
205 CB_ADDSTRING, 0, (LPARAM)VfdMediaTypeName(i));
206 }
207
208 // select 1.44MB as the default
209
210 SendDlgItemMessage(hDlg, IDC_MEDIATYPE, CB_SELECTSTRING,
211 (WPARAM)-1, (LPARAM)VfdMediaTypeName(VFD_MEDIA_F3_1P4));
212
213 // set up other controls
214
215 OnImage(hDlg, GetDlgItem(hDlg, IDC_IMAGEFILE));
216 }
217
218 //
219 // Path is changed -- check if the file exists
220 //
OnImage(HWND hDlg,HWND hEdit)221 void OnImage(
222 HWND hDlg,
223 HWND hEdit)
224 {
225 CHAR buf[MAX_PATH];
226 DWORD file_attr;
227 ULONG image_size;
228 VFD_FILETYPE file_type;
229 VFD_MEDIA media_type;
230
231 DWORD ret = ERROR_SUCCESS;
232
233 // Store default file size
234
235 SetWindowLong(hDlg, DWL_USER, INVALID_FILE_SIZE);
236
237 // get currently selected media type
238
239 media_type = (VFD_MEDIA)(SendDlgItemMessage(
240 hDlg, IDC_MEDIATYPE, CB_GETCURSEL, 0, 0) + 1);
241
242 // clear hint and description text
243
244 SetDlgItemText(hDlg, IDC_IMAGEFILE_DESC, NULL);
245 SetDlgItemText(hDlg, IDC_IMAGEFILE_HINT, NULL);
246
247 // get file name and file information
248
249 if (GetWindowText(hEdit, buf, sizeof(buf))) {
250
251 ret = VfdCheckImageFile(
252 buf, &file_attr, &file_type, &image_size);
253
254 if (ret == ERROR_SUCCESS) {
255
256 // use media type from image size
257
258 media_type = VfdLookupMedia(image_size);
259 }
260 else if (ret == ERROR_FILE_NOT_FOUND) {
261
262 // new file
263 // use the parent directory attributes
264
265 PSTR p;
266
267 if ((p = strrchr(buf, '\\')) != NULL) {
268 *p = '\0';
269 }
270
271 file_attr = GetFileAttributes(buf);
272
273 if (file_attr == INVALID_FILE_ATTRIBUTES) {
274 // directory access error
275 EnableWindow(GetDlgItem(hDlg, IDOK), FALSE);
276 SetDlgItemText(hDlg, IDC_IMAGEFILE_DESC, SystemMessage(ret));
277 return;
278 }
279
280 file_attr &= ~(FILE_ATTRIBUTE_READONLY | FILE_ATTRIBUTE_DIRECTORY);
281 image_size = INVALID_FILE_SIZE;
282 file_type = VFD_FILETYPE_RAW;
283 }
284 else {
285 // file access error
286 EnableWindow(GetDlgItem(hDlg, IDOK), FALSE);
287 SetDlgItemText(hDlg, IDC_IMAGEFILE_DESC, SystemMessage(ret));
288 return;
289 }
290
291 // make file description text
292
293 VfdMakeFileDesc(buf, sizeof(buf),
294 file_type, image_size, file_attr);
295
296 // set file description
297
298 SetDlgItemText(hDlg, IDC_IMAGEFILE_DESC, buf);
299 }
300 else {
301
302 // filename is empty - RAM disk
303
304 file_attr = 0;
305 image_size = INVALID_FILE_SIZE;
306 file_type = VFD_FILETYPE_NONE;
307
308 SetDlgItemText(hDlg, IDC_IMAGEFILE_DESC, "RAM");
309 }
310
311 // store the image size
312
313 SetWindowLong(hDlg, DWL_USER, image_size);
314
315 // setup disktype controls
316
317 if (file_type != VFD_FILETYPE_RAW ||
318 (file_attr & (FILE_ATTRIBUTE_READONLY | FILE_ATTRIBUTE_COMPRESSED | FILE_ATTRIBUTE_ENCRYPTED))) {
319
320 // file cannot be opened directly -- RAM mode is forced
321
322 CheckRadioButton(hDlg, IDC_DISKTYPE_FILE,
323 IDC_DISKTYPE_RAM, IDC_DISKTYPE_RAM);
324
325 EnableWindow(GetDlgItem(hDlg, IDC_DISKTYPE_FILE), FALSE);
326 }
327 else {
328 EnableWindow(GetDlgItem(hDlg, IDC_DISKTYPE_FILE), TRUE);
329 }
330
331 // set OK button text
332
333 if (image_size == INVALID_FILE_SIZE) {
334 // file does not exist - OK button is "Create"
335
336 SetControlText(hDlg, IDOK, MSG_CREATE_BUTTON);
337 }
338 else {
339 // file exists - OK button is "Open"
340
341 SetControlText(hDlg, IDOK, MSG_OPEN_BUTTON);
342 }
343
344 // select media type
345
346 SendDlgItemMessage(hDlg, IDC_MEDIATYPE,
347 CB_SETCURSEL, media_type - 1, 0);
348
349 OnMediaType(hDlg, GetDlgItem(hDlg, IDC_MEDIATYPE));
350 }
351
352 //
353 // Show open file dialog box
354 //
OnBrowse(HWND hDlg)355 void OnBrowse(
356 HWND hDlg)
357 {
358 OPENFILENAME ofn;
359 PSTR title;
360 PSTR filter;
361 CHAR file[MAX_PATH];
362 CHAR dir[MAX_PATH];
363 DWORD len;
364
365 // prepare title and filter text
366
367 title = ModuleMessage(MSG_OPEN_TITLE);
368
369 filter = ModuleMessage(MSG_OPEN_FILTER);
370
371 if (filter) {
372 PSTR p = filter;
373
374 do {
375 if (*p == '|') {
376 *p = '\0';
377 }
378 }
379 while (*(++p));
380 }
381
382 // get current file name from the control
383
384 ZeroMemory(file, sizeof(file));
385 ZeroMemory(dir, sizeof(dir));
386
387 len = GetDlgItemText(hDlg, IDC_IMAGEFILE, file, sizeof(file));
388
389 if (len && file[len - 1] == '\\') {
390 strcpy(dir, file);
391 ZeroMemory(file, sizeof(file));
392 }
393
394 // prepare OPENFILENAME structure
395
396 ZeroMemory(&ofn, sizeof(ofn));
397
398 ofn.lStructSize = IS_WINDOWS_NT() ?
399 OPENFILENAME_SIZE_VERSION_400 : sizeof(ofn);
400
401 ofn.hwndOwner = hDlg;
402 ofn.lpstrFilter = filter ? filter : FALLBACK_IMAGE_FILTER;
403 ofn.lpstrFile = file;
404 ofn.nMaxFile = sizeof(file);
405 ofn.lpstrInitialDir = dir;
406 ofn.lpstrTitle = title ? title : FALLBACK_IMAGE_TITLE;
407 #ifndef __REACTOS__
408 ofn.Flags = OFN_ENABLESIZING | OFN_HIDEREADONLY | OFN_PATHMUSTEXIST;
409 #else
410 ofn.Flags = OFN_EXPLORER | OFN_ENABLESIZING | OFN_HIDEREADONLY | OFN_PATHMUSTEXIST;
411 #endif
412
413 // show the open file dialog box
414
415 if (GetOpenFileName(&ofn)) {
416 SetDlgItemText(hDlg, IDC_IMAGEFILE, file);
417 SetFocus(GetDlgItem(hDlg, IDC_IMAGEFILE));
418 }
419
420 // release text buffers
421
422 if (filter) {
423 LocalFree(filter);
424 }
425
426 if (title) {
427 LocalFree(title);
428 }
429 }
430
431 //
432 // Disk type is changed
433 //
OnDiskType(HWND hDlg,HWND hRadio)434 void OnDiskType(
435 HWND hDlg,
436 HWND hRadio)
437 {
438 UNREFERENCED_PARAMETER(hDlg);
439 UNREFERENCED_PARAMETER(hRadio);
440 }
441
442 //
443 // Media type is changed
444 //
OnMediaType(HWND hDlg,HWND hCombo)445 void OnMediaType(
446 HWND hDlg,
447 HWND hCombo)
448 {
449 VFD_MEDIA media_type;
450 ULONG media_size;
451 ULONG image_size;
452
453 image_size = GetWindowLong(hDlg, DWL_USER);
454
455 if (image_size == INVALID_FILE_SIZE) {
456 return;
457 }
458
459 media_type = (VFD_MEDIA)(SendMessage(
460 hCombo, CB_GETCURSEL, 0, 0) + 1);
461
462 if (media_type == 0) {
463 return;
464 }
465
466 media_size = VfdGetMediaSize(media_type);
467
468 if (media_size > image_size) {
469 // selected media is too large
470 SetControlText(hDlg, IDC_IMAGEFILE_HINT, MSG_FILE_TOO_SMALL);
471 EnableWindow(GetDlgItem(hDlg, IDOK), FALSE);
472 return;
473 }
474 else if (media_size < image_size) {
475 SetControlText(hDlg, IDC_IMAGEFILE_HINT, MSG_SIZE_MISMATCH);
476 }
477 else {
478 SetDlgItemText(hDlg, IDC_IMAGEFILE_HINT, NULL);
479 }
480
481 EnableWindow(GetDlgItem(hDlg, IDOK), TRUE);
482 }
483
484 //
485 // Write Protect check box is clicked
486 //
OnProtect(HWND hDlg,HWND hCheck)487 void OnProtect(
488 HWND hDlg,
489 HWND hCheck)
490 {
491 UNREFERENCED_PARAMETER(hDlg);
492 UNREFERENCED_PARAMETER(hCheck);
493 }
494
495 //
496 // Create / open an image
497 //
OnOK(HWND hDlg)498 DWORD OnOK(
499 HWND hDlg)
500 {
501 CHAR file_name[MAX_PATH];
502 VFD_DISKTYPE disk_type;
503 VFD_MEDIA media_type;
504 VFD_FLAGS image_flags;
505 HANDLE hDevice;
506 DWORD ret;
507
508 // get the disk type
509
510 if (IsDlgButtonChecked(hDlg, IDC_DISKTYPE_FILE) == BST_CHECKED) {
511 disk_type = VFD_DISKTYPE_FILE;
512 }
513 else {
514 disk_type = VFD_DISKTYPE_RAM;
515 }
516
517 // get the media type
518
519 media_type = (VFD_MEDIA)(SendDlgItemMessage(
520 hDlg, IDC_MEDIATYPE, CB_GETCURSEL, 0, 0) + 1);
521
522 // get the protect flag
523
524 if (IsDlgButtonChecked(hDlg, IDC_OPEN_PROTECTED) == BST_CHECKED) {
525 image_flags = VFD_FLAG_WRITE_PROTECTED;
526 }
527 else {
528 image_flags = 0;
529 }
530
531 // get the image name to create
532
533 if (GetDlgItemText(hDlg, IDC_IMAGEFILE, file_name, sizeof(file_name))) {
534
535 // file is specified
536
537 if (GetWindowLong(hDlg, DWL_USER) == INVALID_FILE_SIZE) {
538
539 // create a new image
540
541 ret = VfdCreateImageFile(
542 file_name, media_type, VFD_FILETYPE_RAW, FALSE);
543
544 if (ret != ERROR_SUCCESS) {
545 goto exit_func;
546 }
547 }
548 }
549
550 // open the image
551
552 hDevice = VfdOpenDevice(GetWindowLong(hDlg, GWL_USERDATA));
553
554 if (hDevice == INVALID_HANDLE_VALUE) {
555 ret = GetLastError();
556 goto exit_func;
557 }
558
559 ret = VfdOpenImage(
560 hDevice, file_name, disk_type, media_type, image_flags);
561
562 CloseHandle(hDevice);
563
564 exit_func:
565 if (ret != ERROR_SUCCESS) {
566
567 // show error message
568
569 MessageBox(hDlg, SystemMessage(ret),
570 VFD_MSGBOX_TITLE, MB_ICONSTOP);
571 }
572
573 return ret;
574 }
575