- color and font dialogs now actually do something interesting,
[wine.git] / programs / cmdlgtst / cmdlgtst.c
blob673b1e6c5181abd42da89419c500067fe9a78f97
1 // (c) 1999 Eric Williams. Rights as specified under the WINE
2 // License. Don't hoard code; share it!
4 //
5 // One might call this a Commdlg test jig. Its sole function in life
6 // is to call the Commdlg Common Dialogs; at present it doesn't even
7 // do anything horribly interesting with the results.
9 // Ideally it would also do event logging and be a bit less stupid
10 // about displaying the results of the various requesters. But hey,
11 // it's only a first step. :-)
13 #include <windows.h>
14 #include <commdlg.h>
15 #include <stdio.h>
16 #include "cmdlgr.h"
18 // This structure is to set up flag / control associations for the custom
19 // requesters. The ft_id is the id for the control (usually generated
20 // by the system) and the ft_bit is the flag bit which goes into the
21 // settings longword for the various Commdlg structures. It is assumed
22 // that all flags fit in an unsigned long and that all bits are in fact
23 // one bit.
25 // The array of entries is terminated by {IDOK, 0}; the assumption is that
26 // IDOK would never be associated with a dialogbox control (since it's
27 // usually the ID of the OK button}.
29 struct FlagTableEntry {
30 int ft_id;
31 unsigned long ft_bit;
34 // #ifdef __WINE_WINDOWS_H
35 // #define EXPORT
36 // #define HWND HWND32
37 // int ctx_debug = 0;
38 // #else
39 // #define EXPORT _export
40 // #endif
42 //#define FAR
43 #define EXPORT
45 static char menuName[] = "TestCommdlgMenu";
46 static char className[] = "TestCommdlg";
47 static char windowName[] = "TestCommdlg Window";
49 // global hInstance variable. This makes the code non-threadable,
50 // but wotthehell; this is Win32 anyway! (Though it does work
51 // under Win16, if one doesn't run more than one copy at a time.)
53 static HINSTANCE g_hInstance;
55 // global CommDlg data structures for modals. These are placed here
56 // so that the custom dialog boxes can get at them.
58 static PRINTDLG pd;
59 static COLORREF cc_cr[16];
60 static CHOOSECOLOR cc;
61 static LOGFONT cf_lf;
62 static CHOOSEFONT cf;
63 static char ofn_filepat[] = "All Files (*.*)\0*.*\0Only Text Files (*.txt)\0*.txt\0";
64 static char ofn_result[1024];
65 static OPENFILENAME ofn;
67 // Stuff for find and replace. These are modeless, so I have to put them here.
69 static HWND findDialogBox = 0;
70 static UINT findMessageId = 0;
72 static int findDialogBoxInit = 0;
73 static int findDialogStructInit = 0;
74 static FINDREPLACE frS;
75 static char fromstring[1024], tostring[1024];
77 // Stuff for the drawing of the window(s). I put them here for convenience.
79 static COLORREF fgColor = RGB(0, 0, 0); // not settable
80 static COLORREF bgColor = RGB(255, 255, 255);
81 static COLORREF txtColor = RGB(0, 0, 0);
83 // Utility routines. Currently there is only one, and it's a nasty
84 // reminder that I'm not done yet.
86 void nyi(HWND hWnd)
88 MessageBox(hWnd, "Not yet implemented!", "NYI", MB_ICONEXCLAMATION | MB_OK);
92 // Initial initialization code. This code simply shoves in predefined
93 // data into the COMMDLG data structures; in the future, I might use
94 // a series of loadable resources, or static initializers; of course,
95 // if Microsoft decides to change the field ordering, I'd be screwed.
97 void mwi_Print(HWND hWnd)
99 pd.lStructSize = sizeof(PRINTDLG);
100 pd.hwndOwner = hWnd;
101 pd.hDevMode = 0;
102 pd.hDevNames = 0;
103 pd.hDC = 0;
104 pd.Flags = 0;
105 pd.nMinPage = 1;
106 pd.nMaxPage = 100;
107 pd.hInstance = 0;
108 pd.lCustData = 0;
109 pd.lpfnPrintHook = 0;
110 pd.lpfnSetupHook = 0;
111 pd.lpPrintTemplateName = 0;
112 pd.lpSetupTemplateName = 0;
113 pd.hPrintTemplate = 0;
114 pd.hSetupTemplate = 0;
118 void mwi_Color(HWND hWnd)
120 int i;
122 // there's probably an init call for this, somewhere.
124 for(i=0;i<16;i++)
125 cc_cr[i] = RGB(0,0,0);
127 cc.lStructSize = sizeof(CHOOSECOLOR);
128 cc.hwndOwner = hWnd;
129 cc.hInstance = 0;
130 cc.rgbResult = RGB(0,0,0);
131 cc.lpCustColors = cc_cr;
132 cc.Flags = 0;
133 cc.lCustData = 0;
134 cc.lpfnHook = 0;
135 cc.lpTemplateName = 0;
138 void mwi_Font(HWND hWnd)
140 cf.lStructSize = sizeof(CHOOSEFONT);
141 cf.hwndOwner = hWnd;
142 cf.hDC = 0;
143 cf.lpLogFont = &cf_lf;
144 cf.Flags = 0;
145 cf.rgbColors = RGB(0,0,0); // what is *this* doing here??
146 cf.lCustData = 0;
147 cf.lpfnHook = 0;
148 cf.lpTemplateName = 0;
149 cf.hInstance = 0;
150 cf.lpszStyle = 0;
151 cf.nFontType = 0;
152 cf.nSizeMin = 8;
153 cf.nSizeMax = 72;
156 void mwi_File(HWND hWnd)
158 ofn.lStructSize = sizeof(OPENFILENAME);
159 ofn.hwndOwner = hWnd;
160 ofn.hInstance = 0;
161 ofn.lpstrFilter = (LPSTR) ofn_filepat;
162 ofn.lpstrCustomFilter = 0;
163 ofn.nMaxCustFilter = 0;
164 ofn.nFilterIndex = 0;
165 ofn.lpstrFile = ofn_result;
166 ofn.nMaxFile = sizeof(ofn_result);
167 ofn.lpstrFileTitle = 0;
168 ofn.nMaxFileTitle = 0;
169 ofn.lpstrInitialDir = 0;
170 ofn.lpstrTitle = "Open File";
171 ofn.Flags = 0;
172 ofn.nFileOffset = 0;
173 ofn.nFileExtension = 0;
174 ofn.lpstrDefExt = "*";
175 ofn.lCustData = 0;
176 ofn.lpfnHook = 0;
177 ofn.lpTemplateName = 0;
179 ofn_result[0] = '\0';
182 void mwi_FindReplace(HWND hWnd)
184 frS.lStructSize = sizeof(FINDREPLACE);
185 frS.hwndOwner = hWnd;
186 frS.hInstance = 0;
187 frS.Flags = FR_DOWN;
188 frS.lpstrFindWhat = fromstring;
189 frS.lpstrReplaceWith = tostring;
190 frS.wFindWhatLen = sizeof(fromstring);
191 frS.wReplaceWithLen = sizeof(tostring);
192 frS.lCustData = 0;
193 frS.lpfnHook = 0;
194 frS.lpTemplateName = 0;
196 fromstring[0] = '\0';
197 tostring[0] = '\0';
198 findMessageId = RegisterWindowMessage(FINDMSGSTRING);
201 void mwi_InitAll(HWND hWnd)
203 mwi_Print(hWnd);
204 mwi_Font(hWnd);
205 mwi_Color(hWnd);
206 mwi_File(hWnd);
207 mwi_FindReplace(hWnd);
210 // Various configurations for the window. Ideally, this
211 // would be stored with the window itself, but then, this
212 // isn't the brightest of apps. Wouldn't be hard to set up,
213 // though -- one of the neater functions of Windows, but if
214 // someone decides to load the windows themselves from resources,
215 // there might be a problem.
217 void paintMainWindow(HWND hWnd, UINT iMessage, WPARAM wParam, LPARAM lParam)
219 PAINTSTRUCT ps;
220 RECT rect;
221 HPEN pen;
222 HFONT font;
223 HBRUSH brush;
225 // Commence painting!
227 BeginPaint(hWnd, &ps);
228 GetClientRect(hWnd, (LPRECT) &rect);
230 pen = (HPEN) SelectObject(ps.hdc, CreatePen(0, 0, fgColor));
231 brush = (HBRUSH) SelectObject(ps.hdc, CreateSolidBrush(bgColor));
232 font = (HFONT) SelectObject(ps.hdc, CreateFontIndirect(&cf_lf));
234 // only need to draw the exposed bit.
235 Rectangle(ps.hdc, ps.rcPaint.left, ps.rcPaint.top, ps.rcPaint.right, ps.rcPaint.bottom);
237 // now draw a couple of lines, just for giggles.
239 MoveToEx(ps.hdc, rect.left, rect.top, (POINT FAR *) 0);
240 LineTo(ps.hdc, rect.right, rect.bottom);
241 MoveToEx(ps.hdc, rect.left, rect.bottom, (POINT FAR *) 0);
242 LineTo(ps.hdc, rect.right, rect.top);
244 // draw some text
246 SetTextAlign(ps.hdc, TA_CENTER|TA_BASELINE);
247 SetTextColor(ps.hdc, txtColor);
248 TextOut(ps.hdc, (rect.left+rect.right)/2, (rect.top+rect.bottom)/2, "Common Dialog Test Page", 23);
250 SetTextAlign(ps.hdc, TA_LEFT|TA_TOP);
251 TextOut(ps.hdc, rect.left, rect.top, ofn_result, strlen(ofn_result));
253 // set the HDC back to the old pen and brush,
254 // and delete the newly created objects.
256 pen = (HPEN) SelectObject(ps.hdc, pen);
257 DeleteObject(pen);
258 brush = (HBRUSH) SelectObject(ps.hdc, brush);
259 DeleteObject(brush);
260 font = (HFONT) SelectObject(ps.hdc, font);
261 DeleteObject(font);
263 EndPaint(hWnd, &ps);
266 // This function simply returns an error indication. Naturally,
267 // I do not (yet) see an elegant method by which one can convert
268 // the CDERR_xxx return values into something resembling usable text;
269 // consult cderr.h to see what was returned.
271 void mw_checkError(HWND hWnd, BOOL explicitcancel)
273 DWORD errval = CommDlgExtendedError();
274 if(errval) {
275 char errbuf[80];
277 sprintf(errbuf, "CommDlgExtendedError(): error code %ld (0x%lx)", errval, errval);
278 MessageBox(hWnd, errbuf, "Error", MB_ICONEXCLAMATION | MB_OK);
280 else {
281 if(explicitcancel) MessageBox(hWnd, "Nope, user canceled it.", "No", MB_OK);
285 // The actual dialog function calls. These merely wrap the Commdlg
286 // calls, and do something (not so) intelligent with the result.
287 // Ideally, the main window would refresh and take into account the
288 // various values specified in the dialog.
290 void mw_ColorSetup(HWND hWnd)
292 if(ChooseColor(&cc)) {
293 RECT rect;
295 GetClientRect(hWnd, (LPRECT) &rect);
296 InvalidateRect(hWnd, (LPRECT) &rect, FALSE);
297 bgColor = cc.rgbResult;
299 else mw_checkError(hWnd, FALSE);
302 void mw_FontSetup(HWND hWnd)
304 if(ChooseFont(&cf)) {
305 RECT rect;
306 GetClientRect(hWnd, (LPRECT) &rect);
307 InvalidateRect(hWnd, (LPRECT) &rect, FALSE);
308 txtColor = cf.rgbColors;
310 else mw_checkError(hWnd, FALSE);
313 void mw_FindSetup(HWND hWnd)
315 if(findDialogBox == 0) {
316 findDialogBox = FindText(&frS);
317 if(findDialogBox==0) mw_checkError(hWnd,TRUE);
321 void mw_ReplaceSetup(HWND hWnd)
323 if(findDialogBox == 0) {
324 findDialogBox = ReplaceText(&frS);
325 if(findDialogBox==0) mw_checkError(hWnd,TRUE);
329 void mw_OpenSetup(HWND hWnd)
331 if(GetOpenFileName(&ofn)) {
332 RECT rect;
333 GetClientRect(hWnd, (LPRECT) &rect);
334 InvalidateRect(hWnd, (LPRECT) &rect, FALSE);
336 else mw_checkError(hWnd,FALSE);
339 void mw_SaveSetup(HWND hWnd)
341 if(GetSaveFileName(&ofn)) {
342 RECT rect;
343 GetClientRect(hWnd, (LPRECT) &rect);
344 InvalidateRect(hWnd, (LPRECT) &rect, FALSE);
346 else mw_checkError(hWnd,FALSE);
349 // Can't find documentation in Borland for this one. Does it
350 // exist at all, or is it merely a subdialog of Print?
352 void mw_PSetupSetup(HWND hWnd)
354 nyi(hWnd);
357 void mw_PrintSetup(HWND hWnd)
359 if(PrintDlg(&pd)) {
360 // the following are suggested in the Borland documentation,
361 // but aren't that useful until WinE starts to actually
362 // function with respect to printing.
364 // Escape(tmp.hDC, STARTDOC, 8, "Test-Doc", NULL);
366 /* Print text and rectangle */
368 // TextOut(tmp.hDC, 50, 50, "Common Dialog Test Page", 23);
370 // Rectangle(tmp.hDC, 50, 90, 625, 105);
371 // Escape(tmp.hDC, NEWFRAME, 0, NULL, NULL);
372 // Escape(tmp.hDC, ENDDOC, 0, NULL, NULL);
373 // DeleteDC(tmp.hDC);
374 if (pd.hDevMode != NULL)
375 GlobalFree(pd.hDevMode);
376 if (pd.hDevNames != NULL)
377 GlobalFree(pd.hDevNames);
379 pd.hDevMode = 0;
380 pd.hDevNames = 0;
382 MessageBox(hWnd, "Success.", "Yes", MB_OK);
384 else mw_checkError(hWnd,TRUE);
387 // Some support functions for the custom dialog box handlers.
388 // In particular, we have to set things properly, and get the flags back.
390 void mwcd_SetFlags(HWND hWnd, struct FlagTableEntry *table, unsigned long flags)
392 int i;
394 for(i=0; table[i].ft_id != IDOK; i++)
396 CheckDlgButton(hWnd, table[i].ft_id,(table[i].ft_bit & flags) ? 1 : 0);
400 unsigned long mwcd_GetFlags(HWND hWnd, struct FlagTableEntry * table)
402 int i;
403 unsigned long l = 0;
405 for(i=0; table[i].ft_id != IDOK; i++)
407 if(IsDlgButtonChecked(hWnd, table[i].ft_id) == 1)
408 l |= table[i].ft_bit;
411 return l;
414 // These functions are the custom dialog box handlers.
415 // The division of labor may be a tad peculiar; in particular,
416 // the flag tables should probably be in the main functions,
417 // not the handlers. I'll fix that later; this works as of right now.
419 BOOL mwcd_Setup(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam,
420 struct FlagTableEntry * table, unsigned long * flags)
422 switch(uMsg)
424 case WM_INITDIALOG:
425 // Set the controls properly.
427 mwcd_SetFlags(hWnd, table, *flags);
429 return TRUE; // I would return FALSE if I explicitly called SetFocus().
430 // As usual, Windows is weird.
432 case WM_COMMAND:
433 switch(wParam) {
434 case IDOK:
435 *flags = mwcd_GetFlags(hWnd, table);
436 EndDialog(hWnd,1);
437 break;
439 case IDCANCEL:
440 EndDialog(hWnd,0);
441 break;
443 case CM_R_HELP:
444 break; // help? We don't need no steenkin help!
446 default:
447 break; // eat the message
449 return TRUE;
451 default:
452 return FALSE; // since I don't process this particular message
456 BOOL CALLBACK mwcd_ColorSetup(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
458 static struct FlagTableEntry flagTable[] = {
459 {I_CC_RGBINIT, CC_RGBINIT},
460 {I_CC_SHOWHELP, CC_SHOWHELP},
461 {I_CC_PREVENTFULLOPEN, CC_PREVENTFULLOPEN},
462 {I_CC_FULLOPEN, CC_FULLOPEN},
463 {I_CC_ENABLETEMPLATEHANDLE, CC_ENABLETEMPLATEHANDLE},
464 {I_CC_ENABLETEMPLATE, CC_ENABLETEMPLATE},
465 {I_CC_ENABLEHOOK, CC_ENABLEHOOK},
466 {IDOK, 0},
469 return mwcd_Setup(hWnd, uMsg, wParam, lParam, flagTable, &cc.Flags);
472 BOOL CALLBACK mwcd_FontSetup(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
474 static struct FlagTableEntry flagTable[] = {
475 {I_CF_APPLY, CF_APPLY},
476 {I_CF_ANSIONLY, CF_ANSIONLY},
477 {I_CF_BOTH, CF_BOTH},
478 {I_CF_TTONLY, CF_TTONLY},
479 {I_CF_EFFECTS, CF_EFFECTS},
480 {I_CF_ENABLEHOOK, CF_ENABLEHOOK},
481 {I_CF_ENABLETEMPLATE, CF_ENABLETEMPLATE},
482 {I_CF_ENABLETEMPLATEHANDLE, CF_ENABLETEMPLATEHANDLE},
483 {I_CF_FIXEDPITCHONLY, CF_FIXEDPITCHONLY},
484 {I_CF_INITTOLOGFONTSTRUCT, CF_INITTOLOGFONTSTRUCT},
485 {I_CF_LIMITSIZE, CF_LIMITSIZE},
486 {I_CF_NOFACESEL, CF_NOFACESEL},
487 {I_CF_USESTYLE, CF_USESTYLE},
488 {I_CF_WYSIWYG, CF_WYSIWYG},
489 {I_CF_SHOWHELP, CF_SHOWHELP},
490 {I_CF_SCREENFONTS, CF_SCREENFONTS},
491 {I_CF_SCALABLEONLY, CF_SCALABLEONLY},
492 {I_CF_PRINTERFONTS, CF_PRINTERFONTS},
493 {I_CF_NOVECTORFONTS, CF_NOVECTORFONTS},
494 {I_CF_NOSTYLESEL, CF_NOSTYLESEL},
495 {I_CF_NOSIZESEL, CF_NOSIZESEL},
496 {I_CF_NOOEMFONTS, CF_NOOEMFONTS},
497 {IDOK, 0},
500 return mwcd_Setup(hWnd, uMsg, wParam, lParam, flagTable, &cf.Flags);
503 BOOL CALLBACK mwcd_FindSetup(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
506 static struct FlagTableEntry flagTable[] = {
507 {I_FR_DIALOGTERM, FR_DIALOGTERM},
508 {I_FR_DOWN, FR_DOWN},
509 {I_FR_ENABLEHOOK, FR_ENABLEHOOK},
510 {I_FR_ENABLETEMPLATE, FR_ENABLETEMPLATE},
511 {I_FR_ENABLETEMPLATEHANDLE, FR_ENABLETEMPLATEHANDLE},
512 {I_FR_FINDNEXT, FR_FINDNEXT},
513 {I_FR_HIDEMATCHCASE, FR_HIDEMATCHCASE},
514 {I_FR_HIDEWHOLEWORD, FR_HIDEWHOLEWORD},
515 {I_FR_HIDEUPDOWN, FR_HIDEUPDOWN},
516 {I_FR_MATCHCASE, FR_MATCHCASE},
517 {I_FR_NOMATCHCASE, FR_NOMATCHCASE},
518 {I_FR_NOUPDOWN, FR_NOUPDOWN},
519 {I_FR_NOWHOLEWORD, FR_NOWHOLEWORD},
520 {I_FR_REPLACE, FR_REPLACE},
521 {I_FR_REPLACEALL, FR_REPLACEALL},
522 {I_FR_SHOWHELP, FR_SHOWHELP},
523 {I_FR_WHOLEWORD, FR_WHOLEWORD},
524 {IDOK, 0},
527 return mwcd_Setup(hWnd, uMsg, wParam, lParam, flagTable, &frS.Flags);
530 BOOL CALLBACK mwcd_PrintSetup(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
532 static struct FlagTableEntry flagTable[] = {
533 {I_PD_ALLPAGES, PD_ALLPAGES},
534 {I_PD_COLLATE, PD_COLLATE},
535 {I_PD_DISABLEPRINTTOFILE, PD_DISABLEPRINTTOFILE},
536 {I_PD_ENABLEPRINTHOOK, PD_ENABLEPRINTHOOK},
537 {I_PD_ENABLEPRINTTEMPLATE, PD_ENABLEPRINTTEMPLATE},
538 {I_PD_ENABLEPRINTTEMPLATEHANDLE, PD_ENABLEPRINTTEMPLATEHANDLE},
539 {I_PD_ENABLESETUPHOOK, PD_ENABLESETUPHOOK},
540 {I_PD_ENABLESETUPTEMPLATE, PD_ENABLESETUPTEMPLATE},
541 {I_PD_ENABLESETUPTEMPLATEHANDLE, PD_ENABLESETUPTEMPLATEHANDLE},
542 {I_PD_HIDEPRINTTOFILE, PD_HIDEPRINTTOFILE},
543 {I_PD_NOPAGENUMS, PD_NOPAGENUMS},
544 {I_PD_NOSELECTION, PD_NOSELECTION},
545 {I_PD_NOWARNING, PD_NOWARNING},
546 {I_PD_PAGENUMS, PD_PAGENUMS},
547 {I_PD_PRINTSETUP, PD_PRINTSETUP},
548 {I_PD_PRINTTOFILE, PD_PRINTTOFILE},
549 {I_PD_RETURNDC, PD_RETURNDC},
550 {I_PD_RETURNDEFAULT, PD_RETURNDEFAULT},
551 {I_PD_RETURNIC, PD_RETURNIC},
552 {I_PD_SELECTION, PD_SELECTION},
553 {I_PD_SHOWHELP, PD_SHOWHELP},
554 {I_PD_USEDEVMODECOPIES, PD_USEDEVMODECOPIES},
555 {IDOK, 0},
558 return mwcd_Setup(hWnd, uMsg, wParam, lParam, flagTable, &pd.Flags);
561 BOOL CALLBACK mwcd_FileSetup(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
563 static struct FlagTableEntry flagTable[] = {
564 {I_OFN_ALLOWMULTISELECT, OFN_ALLOWMULTISELECT},
565 {I_OFN_CREATEPROMPT, OFN_CREATEPROMPT},
566 {I_OFN_ENABLEHOOK, OFN_ENABLEHOOK},
567 {I_OFN_ENABLETEMPLATE, OFN_ENABLETEMPLATE},
568 {I_OFN_ENABLETEMPLATEHANDLE, OFN_ENABLETEMPLATEHANDLE},
569 {I_OFN_EXTENSIONDIFFERENT, OFN_EXTENSIONDIFFERENT},
570 {I_OFN_FILEMUSTEXIST, OFN_FILEMUSTEXIST},
571 {I_OFN_HIDEREADONLY, OFN_HIDEREADONLY},
572 {I_OFN_NOCHANGEDIR, OFN_NOCHANGEDIR},
573 {I_OFN_NOREADONLYRETURN, OFN_NOREADONLYRETURN},
574 {I_OFN_NOTESTFILECREATE, OFN_NOTESTFILECREATE},
575 {I_OFN_NOVALIDATE, OFN_NOVALIDATE},
576 {I_OFN_OVERWRITEPROMPT, OFN_OVERWRITEPROMPT},
577 {I_OFN_PATHMUSTEXIST, OFN_PATHMUSTEXIST},
578 {I_OFN_READONLY, OFN_READONLY},
579 {I_OFN_SHAREAWARE, OFN_SHAREAWARE},
580 {I_OFN_SHOWHELP, OFN_SHOWHELP},
581 {IDOK, 0},
584 return mwcd_Setup(hWnd, uMsg, wParam, lParam, flagTable, &pd.Flags);
587 BOOL CALLBACK mwcd_About(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
589 switch(uMsg) {
590 case WM_INITDIALOG: return TRUE; // let WINDOWS set the focus.
591 case WM_COMMAND: EndDialog(hWnd, 0); return TRUE; // it's our OK button.
592 default: return FALSE; // it's something else, let Windows worry about it
597 // These functions call custom dialog boxes (resource-loaded, if I do this right).
598 // Right now they don't do a heck of a lot, but at some future time
599 // they will muck about with the flags (and be loaded from the flags) of
600 // the CommDlg structures initialized by the mwi_xxx() routines.
602 void mwc_ColorSetup(HWND hWnd)
604 int r = DialogBox(g_hInstance, "Color_Flags_Dialog", hWnd, (DLGPROC) mwcd_ColorSetup);
605 if(r < 0) { MessageBox(hWnd, "Failure opening Color_Flags_Dialog box", "Error", MB_ICONASTERISK|MB_OK); }
608 void mwc_FontSetup(HWND hWnd)
610 int r = DialogBox(g_hInstance, "Font_Flags_Dialog", hWnd, (DLGPROC) mwcd_FontSetup);
611 if(r < 0) { MessageBox(hWnd, "Failure opening Font_Flags_Dialog box", "Error", MB_ICONASTERISK|MB_OK); }
614 void mwc_FindReplaceSetup(HWND hWnd)
616 int r = DialogBox(g_hInstance, "Find_Flags_Dialog", hWnd, (DLGPROC) mwcd_FindSetup);
617 if(r < 0) { MessageBox(hWnd, "Failure opening Find_Flags_Dialog box", "Error", MB_ICONASTERISK|MB_OK); }
620 void mwc_PrintSetup(HWND hWnd)
622 int r = DialogBox(g_hInstance, "Print_Flags_Dialog", hWnd, (DLGPROC) mwcd_PrintSetup);
623 if(r < 0) { MessageBox(hWnd, "Failure opening Print_Flags_Dialog box", "Error", MB_ICONASTERISK|MB_OK); }
626 void mwc_FileSetup(HWND hWnd)
628 int r = DialogBox(g_hInstance, "File_Flags_Dialog", hWnd, (DLGPROC) mwcd_PrintSetup);
629 if(r < 0) { MessageBox(hWnd, "Failure opening File_Flags_Dialog box", "Error", MB_ICONASTERISK|MB_OK); }
632 // Main window message dispatcher. Here the messages get chewed up
633 // and spit out. Note the ugly hack for the modeless Find/Replace box;
634 // this looks like it was bolted on with hexhead screws and is now
635 // dangling from Windows like a loose muffler. Sigh.
637 LRESULT CALLBACK EXPORT mainWindowDispatcher(
638 HWND hWnd,
639 UINT uMsg,
640 WPARAM wParam,
641 LPARAM lParam
645 if(uMsg == findMessageId) {
646 FINDREPLACE FAR* lpfr = (FINDREPLACE FAR*) lParam;
647 if(lpfr->Flags & FR_DIALOGTERM) {
648 MessageBox(hWnd, "User closing us down.", "Down", MB_OK);
649 findDialogBox = 0;
651 else if (lpfr->Flags & FR_FINDNEXT) {
652 MessageBox(hWnd, "Finding next occurrence.", "Findnext", MB_OK);
654 else if (lpfr->Flags & FR_REPLACE) {
655 MessageBox(hWnd, "Replacing next occurence.", "Replace", MB_OK);
657 else if (lpfr->Flags & FR_REPLACEALL) {
658 MessageBox(hWnd, "Replacing all occurrences.", "Replace All", MB_OK);
660 else {
661 MessageBox(hWnd, "Eh?", "Eh?", MB_OK);
663 return 1;
665 else switch(uMsg) {
666 case WM_CREATE:
667 // this is always the first message...at least as far as
668 // we are concerned.
669 mwi_InitAll(hWnd);
670 break;
672 case WM_PAINT:
673 // Well, draw something!
674 paintMainWindow(hWnd, uMsg, wParam, lParam);
675 break;
677 case WM_DESTROY:
678 // Uh oh. Eject! Eject! Eject!
679 PostQuitMessage(0);
680 break;
682 case WM_COMMAND:
683 // menu or accelerator pressed; do something.
685 switch(wParam) {
686 case CM_U_EXIT:
687 // Uh oh. Eject! Eject! Eject!
688 PostQuitMessage(0);
689 break;
691 // these actually call the Common Dialogs.
693 case CM_U_COLOR:
694 mw_ColorSetup(hWnd); return 1;
696 case CM_U_FONT:
697 mw_FontSetup(hWnd); return 1;
699 case CM_U_FIND:
700 mw_FindSetup(hWnd); return 1;
702 case CM_U_REPLACE:
703 mw_ReplaceSetup(hWnd); return 1;
705 case CM_U_OPEN:
706 mw_OpenSetup(hWnd); return 1;
708 case CM_U_SAVE:
709 mw_SaveSetup(hWnd); return 1;
711 case CM_U_PSETUP:
712 mw_PSetupSetup(hWnd); return 1;
714 case CM_U_PRINT:
715 mw_PrintSetup(hWnd); return 1;
717 // these set up various flags and values in the Common Dialog
718 // data structures, which are currently stored in static memory.
719 // The control dialogs themselves are resources as well.
721 case CM_F_FILE:
722 mwc_FileSetup(hWnd); return 1;
724 case CM_F_COLOR:
725 mwc_ColorSetup(hWnd); return 1;
727 case CM_F_FONT:
728 mwc_FontSetup(hWnd); return 1;
730 case CM_F_FINDREPLACE:
731 mwc_FindReplaceSetup(hWnd); return 1;
733 case CM_F_PRINT:
734 mwc_PrintSetup(hWnd); return 1;
736 case CM_H_ABOUT:
737 DialogBox(g_hInstance, "AboutDialog", hWnd, (DLGPROC) mwcd_About);
738 case CM_H_USAGE:
739 DialogBox(g_hInstance, "UsageDialog", hWnd, (DLGPROC) mwcd_About);
740 // return value? *What* return value?
741 return 1;
743 default:
744 nyi(hWnd); return 1;
746 break;
748 default:
749 return DefWindowProc(hWnd, uMsg, wParam, lParam);
751 return 0;
754 // Class registration. One might call this a Windowsism.
756 int registerMainWindowClass(HINSTANCE hInstance)
758 WNDCLASS wndClass;
760 wndClass.style = CS_HREDRAW|CS_VREDRAW;
761 wndClass.lpfnWndProc = mainWindowDispatcher;
762 wndClass.cbClsExtra = 0;
763 wndClass.cbWndExtra = 0;
764 wndClass.hInstance = hInstance;
765 //wndClass.hIcon = LoadIcon(hInstance, "whello");
766 //wndClass.hCursor = LoadCursor(hInstance, IDC_ARROW);
767 wndClass.hIcon = 0;
768 wndClass.hCursor = 0;
769 wndClass.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH);
770 wndClass.lpszMenuName = menuName;
771 wndClass.lpszClassName = className;
773 return RegisterClass(&wndClass);
776 // Another Windowsism; this one's not too bad, as it compares
777 // favorably with CreateWindow() in X (mucking about with X Visuals
778 // can get messy; at least here we don't have to worry about that).
780 HWND createMainWindow(HINSTANCE hInstance, int show)
782 HWND hWnd;
784 hWnd = CreateWindow(
785 className, // classname
786 windowName, // windowname/title
787 WS_OVERLAPPEDWINDOW, // dwStyle
788 0, //x
789 0, //y
790 CW_USEDEFAULT, //width
791 CW_USEDEFAULT, //height
792 0, // parent window
793 0, // menu
794 hInstance, // instance
795 0 // passthrough for MDI
798 if(hWnd==0) return 0;
800 ShowWindow(hWnd, show);
801 UpdateWindow(hWnd);
803 return hWnd;
806 int messageLoop(HINSTANCE hInstance, HWND hWnd)
809 MSG msg;
811 while(GetMessage(&msg, 0, 0, 0)) {
812 TranslateMessage(&msg);
813 DispatchMessage(&msg);
816 return msg.wParam;
819 // Oh, did we tell you that main() isn't the name of the
820 // thing called in a Win16/Win32 app? And then there are
821 // the lack of argument lists, the necessity (at least in Win16)
822 // of having to deal with class registration exactly once (as the
823 // app may be run again), and some other bizarre holdovers from
824 // Windows 3.x days. But hey, Solitaire still works.
826 int PASCAL WinMain(
827 HINSTANCE hInstance, HINSTANCE hPrevInstance,
828 LPSTR lpszCmdLine, int nCmdShow
831 HWND hWnd;
833 strcpy(ofn_result, "--- not yet set ---");
835 if(hPrevInstance==0) {
836 if(!registerMainWindowClass(hInstance))
837 return -1;
840 g_hInstance = hInstance;
842 hWnd = createMainWindow(hInstance,nCmdShow);
843 if(hWnd == 0)
844 return -1;
847 return messageLoop(hInstance, hWnd);
850 // And now the end of the program. Enjoy.
852 // (c) 1999 Eric Williams. Rights as specified under the WINE
853 // License. Don't hoard code; share it!