source: trunk/src/comctl32/propsheet.c@ 91

Last change on this file since 91 was 60, checked in by achimha, 26 years ago

* empty log message *

File size: 38.1 KB
Line 
1/*
2 * Property Sheets
3 *
4 * Copyright 1998 Francis Beaudet
5 * Copyright 1999 Thuy Nguyen
6 * Copyright 1999 Achim Hasenmueller
7 *
8 * TODO:
9 * - Modeless mode
10 * - Wizard mode
11 * - Unicode property sheets
12 */
13
14#include <string.h>
15#include "winbase.h"
16#include "commctrl.h"
17#include "prsht.h"
18#include "winnls.h"
19#include "comctl32.h"
20
21
22/******************************************************************************
23 * Data structures
24 */
25typedef struct
26{
27 WORD dlgVer;
28 WORD signature;
29 DWORD helpID;
30 DWORD exStyle;
31 DWORD style;
32} MyDLGTEMPLATEEX;
33
34typedef struct tagPropPageInfo
35{
36 int index; /* corresponds to the index in ppshheader->ppsp */
37 HPROPSHEETPAGE hpage; /* to keep track of pages not passed to PropertySheet */
38 HWND hwndPage;
39 BOOL isDirty;
40 LPCWSTR pszText;
41 BOOL hasHelp;
42 BOOL useCallback;
43} PropPageInfo;
44
45typedef struct tagPropSheetInfo
46{
47 LPSTR strPropertiesFor;
48 int nPages;
49 int active_page;
50 LPCPROPSHEETHEADERA ppshheader;
51 BOOL isModeless;
52 BOOL hasHelp;
53 BOOL hasApply;
54 BOOL useCallback;
55 BOOL restartWindows;
56 BOOL rebootSystem;
57 PropPageInfo* proppage;
58 int x;
59 int y;
60 int width;
61 int height;
62} PropSheetInfo;
63
64typedef struct
65{
66 int x;
67 int y;
68} PADDING_INFO;
69
70/******************************************************************************
71 * Defines and global variables
72 */
73
74const char * PropSheetInfoStr = "PropertySheetInfo";
75
76#define MAX_CAPTION_LENGTH 255
77#define MAX_TABTEXT_LENGTH 255
78
79
80/******************************************************************************
81 * Prototypes
82 */
83static BOOL PROPSHEET_CreateDialog(PropSheetInfo* psInfo);
84static BOOL PROPSHEET_IsTooSmall(HWND hwndDlg, PropSheetInfo* psInfo);
85static BOOL PROPSHEET_AdjustSize(HWND hwndDlg, PropSheetInfo* psInfo);
86static BOOL PROPSHEET_AdjustButtons(HWND hwndParent, PropSheetInfo* psInfo);
87static BOOL PROPSHEET_CollectSheetInfo(LPCPROPSHEETHEADERA lppsh,
88 PropSheetInfo * psInfo);
89static BOOL PROPSHEET_CollectPageInfo(LPCPROPSHEETPAGEA lppsp,
90 PropSheetInfo * psInfo,
91 int index);
92static BOOL PROPSHEET_CreateTabControl(HWND hwndParent,
93 PropSheetInfo * psInfo);
94static int PROPSHEET_CreatePage(HWND hwndParent, int index,
95 const PropSheetInfo * psInfo,
96 LPCPROPSHEETPAGEA ppshpage,
97 BOOL showPage);
98static BOOL PROPSHEET_ShowPage(HWND hwndDlg, int index, PropSheetInfo * psInfo);
99static PADDING_INFO PROPSHEET_GetPaddingInfo(HWND hwndDlg);
100static BOOL PROPSHEET_Apply(HWND hwndDlg);
101static void PROPSHEET_Cancel(HWND hwndDlg);
102static void PROPSHEET_Help(HWND hwndDlg);
103static void PROPSHEET_Changed(HWND hwndDlg, HWND hwndDirtyPage);
104static void PROPSHEET_UnChanged(HWND hwndDlg, HWND hwndCleanPage);
105static void PROPSHEET_PressButton(HWND hwndDlg, int buttonID);
106static void PROPSHEET_SetTitleA(HWND hwndDlg, DWORD dwStyle, LPCSTR lpszText);
107static BOOL PROPSHEET_SetCurSel(HWND hwndDlg,
108 int index,
109 HPROPSHEETPAGE hpage);
110static LRESULT PROPSHEET_QuerySiblings(HWND hwndDlg,
111 WPARAM wParam, LPARAM lParam);
112static LPCPROPSHEETPAGEA PROPSHEET_GetPSPPage(const PropSheetInfo * psInfo,
113 int index);
114static BOOL PROPSHEET_AddPage(HWND hwndDlg,
115 HPROPSHEETPAGE hpage);
116
117static BOOL PROPSHEET_RemovePage(HWND hwndDlg,
118 int index,
119 HPROPSHEETPAGE hpage);
120static void PROPSHEET_CleanUp();
121static int PROPSHEET_GetPageIndex(HPROPSHEETPAGE hpage, PropSheetInfo* psInfo);
122
123BOOL WINAPI
124PROPSHEET_DialogProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
125
126
127/******************************************************************************
128 * PROPSHEET_CollectSheetInfo
129 *
130 * Collect relevant data.
131 */
132static BOOL PROPSHEET_CollectSheetInfo(LPCPROPSHEETHEADERA lppsh,
133 PropSheetInfo * psInfo)
134{
135 DWORD dwFlags = lppsh->dwFlags;
136
137 psInfo->hasHelp = dwFlags & PSH_HASHELP;
138 psInfo->hasApply = !(dwFlags & PSH_NOAPPLYNOW);
139 psInfo->useCallback = dwFlags & PSH_USECALLBACK;
140 psInfo->isModeless = dwFlags & PSH_MODELESS;
141 psInfo->ppshheader = lppsh;
142 psInfo->nPages = lppsh->nPages;
143
144 if (dwFlags & PSH_USEPSTARTPAGE)
145 {
146// TRACE(propsheet, "PSH_USEPSTARTPAGE is on");
147 psInfo->active_page = 0;
148 }
149 else
150 psInfo->active_page = lppsh->u2.nStartPage;
151
152 psInfo->restartWindows = FALSE;
153 psInfo->rebootSystem = FALSE;
154
155 return TRUE;
156}
157
158/******************************************************************************
159 * PROPSHEET_CollectPageInfo
160 *
161 * Collect property sheet data.
162 * With code taken from DIALOG_ParseTemplate32.
163 */
164BOOL PROPSHEET_CollectPageInfo(LPCPROPSHEETPAGEA lppsp,
165 PropSheetInfo * psInfo,
166 int index)
167{
168 DLGTEMPLATE* pTemplate;
169 const WORD* p;
170 DWORD dwFlags;
171 int width, height;
172
173 if (psInfo->ppshheader->dwFlags & PSH_PROPSHEETPAGE)
174 psInfo->proppage[index].hpage = 0;
175 psInfo->proppage[index].hwndPage = 0;
176 psInfo->proppage[index].isDirty = FALSE;
177
178 /*
179 * Process property page flags.
180 */
181 dwFlags = lppsp->dwFlags;
182 psInfo->proppage[index].useCallback = dwFlags & PSP_USECALLBACK;
183 psInfo->proppage[index].hasHelp = dwFlags & PSP_HASHELP;
184
185 /* as soon as we have a page with the help flag, set the sheet flag on */
186 if (psInfo->proppage[index].hasHelp)
187 psInfo->hasHelp = TRUE;
188
189 /*
190 * Process page template.
191 */
192 if (dwFlags & PSP_DLGINDIRECT)
193 pTemplate = (DLGTEMPLATE*)lppsp->u1.pResource;
194 else
195 {
196 HRSRC hResource = FindResourceA(lppsp->hInstance,
197 lppsp->u1.pszTemplate,
198 RT_DIALOGA);
199 HGLOBAL hTemplate = LoadResource(lppsp->hInstance,
200 hResource);
201 pTemplate = (LPDLGTEMPLATEA)LockResource(hTemplate);
202 }
203
204 /*
205 * Extract the size of the page and the caption.
206 */
207 p = (const WORD *)pTemplate;
208
209 if (((MyDLGTEMPLATEEX*)pTemplate)->signature == 0xFFFF)
210 {
211 /* DIALOGEX template */
212
213 p++; /* dlgVer */
214 p++; /* signature */
215 p += 2; /* help ID */
216 p += 2; /* ext style */
217 p += 2; /* style */
218 }
219 else
220 {
221 /* DIALOG template */
222
223 p += 2; /* style */
224 p += 2; /* ext style */
225 }
226
227 p++; /* nb items */
228 p++; /* x */
229 p++; /* y */
230 width = (WORD)*p; p++;
231 height = (WORD)*p; p++;
232
233 /* remember the largest width and height */
234 if (width > psInfo->width)
235 psInfo->width = width;
236
237 if (height > psInfo->height)
238 psInfo->height = height;
239
240 /* menu */
241 switch ((WORD)*p)
242 {
243 case 0x0000:
244 p++;
245 break;
246 case 0xffff:
247 p += 2;
248 break;
249 default:
250 p += lstrlenW( (LPCWSTR)p ) + 1;
251 break;
252 }
253
254 /* class */
255 switch ((WORD)*p)
256 {
257 case 0x0000:
258 p++;
259 break;
260 case 0xffff:
261 p += 2;
262 break;
263 default:
264 p += lstrlenW( (LPCWSTR)p ) + 1;
265 break;
266 }
267
268 /* Extract the caption */
269 psInfo->proppage[index].pszText = (LPCWSTR)p;
270// TRACE(propsheet, "Tab %d %s\n",index,debugstr_w((LPCWSTR)p));
271 p += lstrlenW((LPCWSTR)p) + 1;
272
273 return TRUE;
274}
275
276/******************************************************************************
277 * PROPSHEET_CreateDialog
278 *
279 * Creates the actual property sheet.
280 */
281BOOL PROPSHEET_CreateDialog(PropSheetInfo* psInfo)
282{
283 LRESULT ret;
284 LPCVOID template;
285 HRSRC hRes;
286
287 if(!(hRes = FindResourceA(COMCTL32_hModule,
288 MAKEINTRESOURCEA(IDD_PROPSHEET),
289 RT_DIALOGA)))
290 return FALSE;
291
292 if(!(template = (LPVOID)LoadResource(COMCTL32_hModule, hRes)))
293 return FALSE;
294
295 if (psInfo->useCallback)
296 (*(psInfo->ppshheader->pfnCallback))(0, PSCB_PRECREATE, (LPARAM)template);
297
298 if (psInfo->ppshheader->dwFlags & PSH_MODELESS)
299 ret = CreateDialogIndirectParamA(psInfo->ppshheader->hInstance,
300 (LPDLGTEMPLATEA) template,
301 psInfo->ppshheader->hwndParent,
302 (DLGPROC) PROPSHEET_DialogProc,
303 (LPARAM)psInfo);
304 else
305 ret = DialogBoxIndirectParamA(psInfo->ppshheader->hInstance,
306 (LPDLGTEMPLATEA) template,
307 psInfo->ppshheader->hwndParent,
308 (DLGPROC) PROPSHEET_DialogProc,
309 (LPARAM)psInfo);
310
311 return ret;
312}
313
314/******************************************************************************
315 * PROPSHEET_IsTooSmall
316 *
317 * Verify that the resource property sheet is big enough.
318 */
319static BOOL PROPSHEET_IsTooSmall(HWND hwndDlg, PropSheetInfo* psInfo)
320{
321 HWND hwndTabCtrl = GetDlgItem(hwndDlg, IDC_TABCONTROL);
322 RECT rcOrigTab, rcPage;
323
324 /*
325 * Original tab size.
326 */
327 GetClientRect(hwndTabCtrl, &rcOrigTab);
328// TRACE(propsheet, "orig tab %d %d %d %d\n", rcOrigTab.left, rcOrigTab.top,
329// rcOrigTab.right, rcOrigTab.bottom);
330
331 /*
332 * Biggest page size.
333 */
334 rcPage.left = psInfo->x;
335 rcPage.top = psInfo->y;
336 rcPage.right = psInfo->width;
337 rcPage.bottom = psInfo->height;
338
339 MapDialogRect(hwndDlg, &rcPage);
340// TRACE(propsheet, "biggest page %d %d %d %d\n", rcPage.left, rcPage.top,
341// rcPage.right, rcPage.bottom);
342
343 if (rcPage.right > rcOrigTab.right)
344 return TRUE;
345
346 if (rcPage.bottom > rcOrigTab.bottom)
347 return TRUE;
348
349 return FALSE;
350}
351
352/******************************************************************************
353 * PROPSHEET_AdjustSize
354 *
355 * Resizes the property sheet and the tab control to fit the largest page.
356 */
357static BOOL PROPSHEET_AdjustSize(HWND hwndDlg, PropSheetInfo* psInfo)
358{
359 HWND hwndTabCtrl = GetDlgItem(hwndDlg, IDC_TABCONTROL);
360 HWND hwndButton = GetDlgItem(hwndDlg, IDOK);
361 RECT rc;
362 int tabOffsetX, tabOffsetY, buttonHeight;
363 PADDING_INFO padding = PROPSHEET_GetPaddingInfo(hwndDlg);
364
365 /* Get the height of buttons */
366 GetClientRect(hwndButton, &rc);
367 buttonHeight = rc.bottom;
368
369 /*
370 * Biggest page size.
371 */
372 rc.left = psInfo->x;
373 rc.top = psInfo->y;
374 rc.right = psInfo->width;
375 rc.bottom = psInfo->height;
376
377 MapDialogRect(hwndDlg, &rc);
378
379 /*
380 * Resize the tab control.
381 */
382 SendMessageA(hwndTabCtrl, TCM_ADJUSTRECT, TRUE, (LPARAM)&rc);
383
384 tabOffsetX = -(rc.left);
385 tabOffsetY = -(rc.top);
386
387 rc.right -= rc.left;
388 rc.bottom -= rc.top;
389 SetWindowPos(hwndTabCtrl, 0, 0, 0, rc.right, rc.bottom,
390 SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE);
391
392 GetClientRect(hwndTabCtrl, &rc);
393
394// TRACE(propsheet, "tab client rc %d %d %d %d\n",
395// rc.left, rc.top, rc.right, rc.bottom);
396
397 rc.right += ((padding.x * 2) + tabOffsetX);
398 rc.bottom += (buttonHeight + (3 * padding.y) + tabOffsetY);
399
400 /*
401 * Resize the property sheet.
402 */
403 SetWindowPos(hwndDlg, 0, 0, 0, rc.right, rc.bottom,
404 SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE);
405
406 return TRUE;
407}
408
409/******************************************************************************
410 * PROPSHEET_AdjustButtons
411 *
412 * Adjusts the buttons' positions.
413 */
414static BOOL PROPSHEET_AdjustButtons(HWND hwndParent, PropSheetInfo* psInfo)
415{
416 HWND hwndButton = GetDlgItem(hwndParent, IDOK);
417 RECT rcSheet;
418 int x, y;
419 int num_buttons = 2;
420 int buttonWidth, buttonHeight;
421 PADDING_INFO padding = PROPSHEET_GetPaddingInfo(hwndParent);
422
423 if (psInfo->hasApply)
424 num_buttons++;
425
426 if (psInfo->hasHelp)
427 num_buttons++;
428
429 /*
430 * Obtain the size of the buttons.
431 */
432 GetClientRect(hwndButton, &rcSheet);
433 buttonWidth = rcSheet.right;
434 buttonHeight = rcSheet.bottom;
435
436 /*
437 * Get the size of the property sheet.
438 */
439 GetClientRect(hwndParent, &rcSheet);
440
441 /*
442 * All buttons will be at this y coordinate.
443 */
444 y = rcSheet.bottom - (padding.y + buttonHeight);
445
446 /*
447 * Position OK button.
448 */
449 hwndButton = GetDlgItem(hwndParent, IDOK);
450
451 x = rcSheet.right - ((padding.x + buttonWidth) * num_buttons);
452
453 SetWindowPos(hwndButton, 0, x, y, 0, 0,
454 SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE);
455
456 /*
457 * Position Cancel button.
458 */
459 hwndButton = GetDlgItem(hwndParent, IDCANCEL);
460
461 x = rcSheet.right - ((padding.x + buttonWidth) * (num_buttons - 1));
462
463 SetWindowPos(hwndButton, 0, x, y, 0, 0,
464 SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE);
465
466 /*
467 * Position Apply button.
468 */
469 hwndButton = GetDlgItem(hwndParent, IDC_APPLY_BUTTON);
470
471 if (psInfo->hasApply)
472 {
473 if (psInfo->hasHelp)
474 x = rcSheet.right - ((padding.x + buttonWidth) * 2);
475 else
476 x = rcSheet.right - (padding.x + buttonWidth);
477
478 SetWindowPos(hwndButton, 0, x, y, 0, 0,
479 SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE);
480
481 EnableWindow(hwndButton, FALSE);
482 }
483 else
484 ShowWindow(hwndButton, SW_HIDE);
485
486 /*
487 * Position Help button.
488 */
489 hwndButton = GetDlgItem(hwndParent, IDHELP);
490
491 if (psInfo->hasHelp)
492 {
493 x = rcSheet.right - (padding.x + buttonWidth);
494
495 SetWindowPos(hwndButton, 0, x, y, 0, 0,
496 SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE);
497 }
498 else
499 ShowWindow(hwndButton, SW_HIDE);
500
501 return TRUE;
502}
503
504/******************************************************************************
505 * PROPSHEET_GetPaddingInfo
506 *
507 * Returns the layout information.
508 */
509static PADDING_INFO PROPSHEET_GetPaddingInfo(HWND hwndDlg)
510{
511 HWND hwndTab = GetDlgItem(hwndDlg, IDC_TABCONTROL);
512 RECT rcTab;
513 POINT tl;
514 PADDING_INFO padding;
515
516 GetWindowRect(hwndTab, &rcTab);
517
518 tl.x = rcTab.left;
519 tl.y = rcTab.top;
520
521 ScreenToClient(hwndDlg, &tl);
522
523 padding.x = tl.x;
524 padding.y = tl.y;
525
526 return padding;
527}
528
529/******************************************************************************
530 * PROPSHEET_CreateTabControl
531 *
532 * Insert the tabs in the tab control.
533 */
534static BOOL PROPSHEET_CreateTabControl(HWND hwndParent,
535 PropSheetInfo * psInfo)
536{
537 HWND hwndTabCtrl = GetDlgItem(hwndParent, IDC_TABCONTROL);
538 TCITEMA item;
539 int i, nTabs;
540 char tabtext[MAX_TABTEXT_LENGTH] = "Tab text";
541
542 item.mask = TCIF_TEXT;
543 item.pszText = tabtext;
544 item.cchTextMax = MAX_TABTEXT_LENGTH;
545
546 nTabs = psInfo->ppshheader->nPages;
547
548 for (i = 0; i < nTabs; i++)
549 {
550 WideCharToMultiByte(CP_ACP, 0,
551 (LPCWSTR)psInfo->proppage[i].pszText,
552 -1, tabtext, MAX_TABTEXT_LENGTH, NULL, NULL);
553
554 SendMessageA(hwndTabCtrl, TCM_INSERTITEMA, (WPARAM)i, (LPARAM)&item);
555 }
556
557 return TRUE;
558}
559
560/******************************************************************************
561 * PROPSHEET_CreatePage
562 *
563 * Creates a page.
564 */
565static int PROPSHEET_CreatePage(HWND hwndParent,
566 int index,
567 const PropSheetInfo * psInfo,
568 LPCPROPSHEETPAGEA ppshpage,
569 BOOL showPage)
570{
571 DLGTEMPLATE* pTemplate;
572 HWND hwndPage;
573 RECT rc;
574 PropPageInfo* ppInfo = psInfo->proppage;
575 PADDING_INFO padding = PROPSHEET_GetPaddingInfo(hwndParent);
576 HWND hwndTabCtrl = GetDlgItem(hwndParent, IDC_TABCONTROL);
577
578// TRACE(propsheet, "index %d\n", index);
579
580 if (ppshpage->dwFlags & PSP_DLGINDIRECT)
581 pTemplate = (DLGTEMPLATE*)ppshpage->u1.pResource;
582 else
583 {
584 HRSRC hResource = FindResourceA(ppshpage->hInstance,
585 ppshpage->u1.pszTemplate,
586 RT_DIALOGA);
587 HGLOBAL hTemplate = LoadResource(ppshpage->hInstance, hResource);
588 pTemplate = (LPDLGTEMPLATEA)LockResource(hTemplate);
589 }
590
591 if (((MyDLGTEMPLATEEX*)pTemplate)->signature == 0xFFFF)
592 {
593 ((MyDLGTEMPLATEEX*)pTemplate)->style |= WS_CHILD;
594 ((MyDLGTEMPLATEEX*)pTemplate)->style &= ~DS_MODALFRAME;
595 ((MyDLGTEMPLATEEX*)pTemplate)->style &= ~WS_CAPTION;
596 ((MyDLGTEMPLATEEX*)pTemplate)->style &= ~WS_SYSMENU;
597 ((MyDLGTEMPLATEEX*)pTemplate)->style &= ~WS_POPUP;
598 }
599 else
600 {
601 pTemplate->style |= WS_CHILD;
602 pTemplate->style &= ~DS_MODALFRAME;
603 pTemplate->style &= ~WS_CAPTION;
604 pTemplate->style &= ~WS_SYSMENU;
605 pTemplate->style &= ~WS_POPUP;
606 }
607
608 if (psInfo->proppage[index].useCallback)
609 (*(ppshpage->pfnCallback))(hwndParent,
610 PSPCB_CREATE,
611 (LPPROPSHEETPAGEA)ppshpage);
612
613 hwndPage = CreateDialogIndirectParamA(ppshpage->hInstance,
614 pTemplate,
615 hwndParent,
616 ppshpage->pfnDlgProc,
617 (LPARAM)ppshpage);
618
619 ppInfo[index].hwndPage = hwndPage;
620
621 rc.left = psInfo->x;
622 rc.top = psInfo->y;
623 rc.right = psInfo->width;
624 rc.bottom = psInfo->height;
625
626 MapDialogRect(hwndParent, &rc);
627
628 /*
629 * Ask the Tab control to fit this page in.
630 */
631 SendMessageA(hwndTabCtrl, TCM_ADJUSTRECT, FALSE, (LPARAM)&rc);
632
633 SetWindowPos(hwndPage, HWND_TOP,
634 rc.left + padding.x,
635 rc.top + padding.y,
636 0, 0, SWP_NOSIZE);
637
638 if (showPage)
639 ShowWindow(hwndPage, SW_SHOW);
640 else
641 ShowWindow(hwndPage, SW_HIDE);
642
643 return TRUE;
644}
645
646/******************************************************************************
647 * PROPSHEET_ShowPage
648 *
649 * Displays or creates the specified page.
650 */
651static BOOL PROPSHEET_ShowPage(HWND hwndDlg, int index, PropSheetInfo * psInfo)
652{
653 if (index == psInfo->active_page)
654 return TRUE;
655
656 ShowWindow(psInfo->proppage[psInfo->active_page].hwndPage, SW_HIDE);
657
658 if (psInfo->proppage[index].hwndPage != 0)
659 ShowWindow(psInfo->proppage[index].hwndPage, SW_SHOW);
660 else
661 {
662 LPCPROPSHEETPAGEA ppshpage = PROPSHEET_GetPSPPage(psInfo, index);
663 PROPSHEET_CreatePage(hwndDlg, index, psInfo, ppshpage, TRUE);
664 }
665
666 psInfo->active_page = index;
667
668 return TRUE;
669}
670
671/******************************************************************************
672 * PROPSHEET_Apply
673 */
674static BOOL PROPSHEET_Apply(HWND hwndDlg)
675{
676 int i;
677 NMHDR hdr;
678 HWND hwndPage;
679 LRESULT msgResult;
680 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
681 PropSheetInfoStr);
682
683 hdr.hwndFrom = hwndDlg;
684
685 /*
686 * Send PSN_KILLACTIVE to the current page.
687 */
688 hdr.code = PSN_KILLACTIVE;
689
690 hwndPage = psInfo->proppage[psInfo->active_page].hwndPage;
691
692 if (SendMessageA(hwndPage, WM_NOTIFY, 0, (LPARAM) &hdr) != FALSE)
693 return FALSE;
694
695 /*
696 * Send PSN_APPLY to all pages.
697 */
698 hdr.code = PSN_APPLY;
699
700 for (i = 0; i < psInfo->nPages; i++)
701 {
702 hwndPage = psInfo->proppage[i].hwndPage;
703 msgResult = SendMessageA(hwndPage, WM_NOTIFY, 0, (LPARAM) &hdr);
704
705 if (msgResult == PSNRET_INVALID_NOCHANGEPAGE)
706 return FALSE;
707 }
708
709 return TRUE;
710}
711
712/******************************************************************************
713 * PROPSHEET_Cancel
714 */
715static void PROPSHEET_Cancel(HWND hwndDlg)
716{
717 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
718 PropSheetInfoStr);
719 HWND hwndPage = psInfo->proppage[psInfo->active_page].hwndPage;
720 NMHDR hdr;
721
722 hdr.hwndFrom = hwndDlg;
723 hdr.code = PSN_QUERYCANCEL;
724
725 if (SendMessageA(hwndPage, WM_NOTIFY, 0, (LPARAM) &hdr))
726 return;
727
728 hdr.code = PSN_RESET;
729
730 SendMessageA(hwndPage, WM_NOTIFY, 0, (LPARAM) &hdr);
731
732 if (psInfo->isModeless)
733 psInfo->active_page = -1; /* makes PSM_GETCURRENTPAGEHWND return NULL */
734 else
735 EndDialog(hwndDlg, FALSE);
736}
737
738/******************************************************************************
739 * PROPSHEET_Help
740 */
741static void PROPSHEET_Help(HWND hwndDlg)
742{
743 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
744 PropSheetInfoStr);
745 HWND hwndPage = psInfo->proppage[psInfo->active_page].hwndPage;
746 NMHDR hdr;
747
748 hdr.hwndFrom = hwndDlg;
749 hdr.code = PSN_HELP;
750
751 SendMessageA(hwndPage, WM_NOTIFY, 0, (LPARAM) &hdr);
752}
753
754/******************************************************************************
755 * PROPSHEET_Changed
756 */
757static void PROPSHEET_Changed(HWND hwndDlg, HWND hwndDirtyPage)
758{
759 int i;
760 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
761 PropSheetInfoStr);
762
763 /*
764 * Set the dirty flag of this page.
765 */
766 for (i = 0; i < psInfo->nPages; i++)
767 {
768 if (psInfo->proppage[i].hwndPage == hwndDirtyPage)
769 psInfo->proppage[i].isDirty = TRUE;
770 }
771
772 /*
773 * Enable the Apply button.
774 */
775 if (psInfo->hasApply)
776 {
777 HWND hwndApplyBtn = GetDlgItem(hwndDlg, IDC_APPLY_BUTTON);
778
779 EnableWindow(hwndApplyBtn, TRUE);
780 }
781}
782
783/******************************************************************************
784 * PROPSHEET_UnChanged
785 */
786static void PROPSHEET_UnChanged(HWND hwndDlg, HWND hwndCleanPage)
787{
788 int i;
789 BOOL noPageDirty = TRUE;
790 HWND hwndApplyBtn = GetDlgItem(hwndDlg, IDC_APPLY_BUTTON);
791 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
792 PropSheetInfoStr);
793
794 for (i = 0; i < psInfo->nPages; i++)
795 {
796 /* set the specified page as clean */
797 if (psInfo->proppage[i].hwndPage == hwndCleanPage)
798 psInfo->proppage[i].isDirty = FALSE;
799
800 /* look to see if there's any dirty pages */
801 if (psInfo->proppage[i].isDirty)
802 noPageDirty = FALSE;
803 }
804
805 /*
806 * Disable Apply button.
807 */
808 if (noPageDirty)
809 EnableWindow(hwndApplyBtn, FALSE);
810}
811
812/******************************************************************************
813 * PROPSHEET_PressButton
814 */
815static void PROPSHEET_PressButton(HWND hwndDlg, int buttonID)
816{
817 switch (buttonID)
818 {
819 case PSBTN_APPLYNOW:
820 SendMessageA(hwndDlg, WM_COMMAND, IDC_APPLY_BUTTON, 0);
821 break;
822 case PSBTN_BACK:
823// FIXME(propsheet, "Wizard mode not implemented.\n");
824 break;
825 case PSBTN_CANCEL:
826 SendMessageA(hwndDlg, WM_COMMAND, IDCANCEL, 0);
827 break;
828 case PSBTN_FINISH:
829// FIXME(propsheet, "Wizard mode not implemented.\n");
830 break;
831 case PSBTN_HELP:
832 SendMessageA(hwndDlg, WM_COMMAND, IDHELP, 0);
833 break;
834 case PSBTN_NEXT:
835// FIXME(propsheet, "Wizard mode not implemented.\n");
836 break;
837 case PSBTN_OK:
838 SendMessageA(hwndDlg, WM_COMMAND, IDOK, 0);
839 break;
840 default:
841// FIXME(propsheet, "Invalid button index %d\n", buttonID);
842 break;
843 }
844}
845
846/******************************************************************************
847 * PROPSHEET_SetCurSel
848 */
849static BOOL PROPSHEET_SetCurSel(HWND hwndDlg,
850 int index,
851 HPROPSHEETPAGE hpage)
852{
853 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
854 PropSheetInfoStr);
855 HWND hwndPage;
856 HWND hwndHelp = GetDlgItem(hwndDlg, IDHELP);
857 NMHDR hdr;
858
859 /*
860 * Notify the current page.
861 */
862 hwndPage = psInfo->proppage[psInfo->active_page].hwndPage;
863
864 hdr.hwndFrom = hwndDlg;
865 hdr.code = PSN_KILLACTIVE;
866
867 if (SendMessageA(hwndPage, WM_NOTIFY, 0, (LPARAM) &hdr))
868 return FALSE;
869
870// if (hpage != NULL)
871// FIXME(propsheet, "Implement HPROPSHEETPAGE!\n");
872// else
873 hwndPage = psInfo->proppage[index].hwndPage;
874
875 /*
876 * Notify the new page.
877 */
878 hdr.code = PSN_SETACTIVE;
879
880 SendMessageA(hwndPage, WM_NOTIFY, 0, (LPARAM) &hdr);
881
882 /*
883 * Display the new page.
884 */
885 PROPSHEET_ShowPage(hwndDlg, index, psInfo);
886
887 if (psInfo->proppage[index].hasHelp)
888 EnableWindow(hwndHelp, TRUE);
889 else
890 EnableWindow(hwndHelp, FALSE);
891
892 return TRUE;
893}
894
895/******************************************************************************
896 * PROPSHEET_SetTitleA
897 */
898static void PROPSHEET_SetTitleA(HWND hwndDlg, DWORD dwStyle, LPCSTR lpszText)
899{
900 if (dwStyle & PSH_PROPTITLE)
901 {
902 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
903 PropSheetInfoStr);
904 char* dest;
905 int lentitle = strlen(lpszText);
906 int lenprop = strlen(psInfo->strPropertiesFor);
907
908 dest = COMCTL32_Alloc(lentitle + lenprop + 1);
909 strcpy(dest, psInfo->strPropertiesFor);
910 strcat(dest, lpszText);
911
912 SetWindowTextA(hwndDlg, dest);
913 COMCTL32_Free(dest);
914 }
915 else
916 SetWindowTextA(hwndDlg, lpszText);
917}
918
919/******************************************************************************
920 * PROPSHEET_QuerySiblings
921 */
922static LRESULT PROPSHEET_QuerySiblings(HWND hwndDlg,
923 WPARAM wParam, LPARAM lParam)
924{
925 int i = 0;
926 HWND hwndPage;
927 LRESULT msgResult = 0;
928 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
929 PropSheetInfoStr);
930
931 while ((i < psInfo->nPages) && (msgResult == 0))
932 {
933 hwndPage = psInfo->proppage[i].hwndPage;
934 msgResult = SendMessageA(hwndPage, PSM_QUERYSIBLINGS, wParam, lParam);
935 i++;
936 }
937
938 return msgResult;
939}
940
941/******************************************************************************
942 * PROPSHEET_GetPSPPage
943 */
944static LPCPROPSHEETPAGEA PROPSHEET_GetPSPPage(const PropSheetInfo * psInfo,
945 int index)
946{
947 BOOL usePSP = psInfo->ppshheader->dwFlags & PSH_PROPSHEETPAGE;
948 LPCPROPSHEETPAGEA lppsp;
949 int realIndex = psInfo->proppage[index].index;
950
951 if (usePSP)
952 {
953 BYTE* pByte;
954
955 lppsp = psInfo->ppshheader->u3.ppsp;
956
957 pByte = (BYTE*) lppsp;
958
959 pByte += (lppsp->dwSize * realIndex);
960 lppsp = (LPCPROPSHEETPAGEA)pByte;
961 }
962 else
963 lppsp = (LPCPROPSHEETPAGEA) psInfo->ppshheader->u3.phpage[realIndex];
964
965 return lppsp;
966}
967
968/******************************************************************************
969 * PROPSHEET_AddPage
970 */
971static BOOL PROPSHEET_AddPage(HWND hwndDlg,
972 HPROPSHEETPAGE hpage)
973{
974 PropSheetInfo * psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
975 PropSheetInfoStr);
976 HWND hwndTabControl = GetDlgItem(hwndDlg, IDC_TABCONTROL);
977 TCITEMA item;
978 char tabtext[MAX_TABTEXT_LENGTH] = "Tab text";
979 LPCPROPSHEETPAGEA ppsp = (LPCPROPSHEETPAGEA)hpage;
980
981 /*
982 * Allocate and fill in a new PropPageInfo entry.
983 */
984 psInfo->proppage = (PropPageInfo*) COMCTL32_ReAlloc(psInfo->proppage,
985 sizeof(PropPageInfo) *
986 (psInfo->nPages + 1));
987
988 PROPSHEET_CollectPageInfo(ppsp, psInfo, psInfo->nPages);
989 psInfo->proppage[psInfo->nPages].index = -1;
990 psInfo->proppage[psInfo->nPages].hpage = hpage;
991
992 /*
993 * Create the page but don't show it.
994 */
995 PROPSHEET_CreatePage(hwndDlg, psInfo->nPages, psInfo, ppsp, FALSE);
996
997 /*
998 * Add a new tab to the tab control.
999 */
1000 item.mask = TCIF_TEXT;
1001 item.pszText = tabtext;
1002 item.cchTextMax = MAX_TABTEXT_LENGTH;
1003
1004 WideCharToMultiByte(CP_ACP, 0,
1005 (LPCWSTR)psInfo->proppage[psInfo->nPages].pszText,
1006 -1, tabtext, MAX_TABTEXT_LENGTH, NULL, NULL);
1007
1008 SendMessageA(hwndTabControl, TCM_INSERTITEMA, psInfo->nPages + 1,
1009 (LPARAM)&item);
1010
1011 psInfo->nPages++;
1012
1013 return FALSE;
1014}
1015
1016/******************************************************************************
1017 * PROPSHEET_RemovePage
1018 */
1019static BOOL PROPSHEET_RemovePage(HWND hwndDlg,
1020 int index,
1021 HPROPSHEETPAGE hpage)
1022{
1023 PropSheetInfo * psInfo = (PropSheetInfo*) GetPropA(hwndDlg,
1024 PropSheetInfoStr);
1025 HWND hwndTabControl = GetDlgItem(hwndDlg, IDC_TABCONTROL);
1026 PropPageInfo* oldPages = psInfo->proppage;
1027
1028 /*
1029 * hpage takes precedence over index.
1030 */
1031 if (hpage != 0)
1032 {
1033 index = PROPSHEET_GetPageIndex(hpage, psInfo);
1034
1035 if (index == -1)
1036 {
1037// TRACE(propsheet, "Could not find page to remove!\n");
1038 return FALSE;
1039 }
1040 }
1041
1042// TRACE(propsheet, "total pages %d removing page %d active page %d\n",
1043// psInfo->nPages, index, psInfo->active_page);
1044 /*
1045 * Check if we're removing the active page.
1046 */
1047 if (index == psInfo->active_page)
1048 {
1049 if (psInfo->nPages > 1)
1050 {
1051 if (index > 0)
1052 {
1053 /* activate previous page */
1054 PROPSHEET_ShowPage(hwndDlg, index - 1, psInfo);
1055 }
1056 else
1057 {
1058 /* activate the next page */
1059 PROPSHEET_ShowPage(hwndDlg, index + 1, psInfo);
1060 }
1061 }
1062 else
1063 {
1064// TRACE(propsheet, "Removing the only page, close the dialog!\n");
1065
1066 if (psInfo->isModeless)
1067 psInfo->active_page = -1;
1068 else
1069 EndDialog(hwndDlg, FALSE);
1070
1071 return TRUE;
1072 }
1073 }
1074
1075 if (index < psInfo->active_page)
1076 psInfo->active_page--;
1077
1078 /* Remove the tab */
1079 SendMessageA(hwndTabControl, TCM_DELETEITEM, index, 0);
1080
1081 psInfo->nPages--;
1082 psInfo->proppage = COMCTL32_Alloc(sizeof(PropPageInfo) * psInfo->nPages);
1083
1084 if (index > 0)
1085 memcpy(&psInfo->proppage[0], &oldPages[0], index * sizeof(PropPageInfo));
1086
1087 if (index < psInfo->nPages)
1088 memcpy(&psInfo->proppage[index], &oldPages[index + 1],
1089 (psInfo->nPages - index) * sizeof(PropPageInfo));
1090
1091 COMCTL32_Free(oldPages);
1092
1093 return FALSE;
1094}
1095
1096/******************************************************************************
1097 * PROPSHEET_GetPageIndex
1098 *
1099 * Given a HPROPSHEETPAGE, returns the index of the corresponding page from
1100 * the array of PropPageInfo.
1101 */
1102static int PROPSHEET_GetPageIndex(HPROPSHEETPAGE hpage, PropSheetInfo* psInfo)
1103{
1104 BOOL found = FALSE;
1105 int index = 0;
1106
1107 while ((index < psInfo->nPages) && (found == FALSE))
1108 {
1109 if (psInfo->proppage[index].hpage == hpage)
1110 found = TRUE;
1111 else
1112 index++;
1113 }
1114
1115 if (found == FALSE)
1116 index = -1;
1117
1118 return index;
1119}
1120
1121/******************************************************************************
1122 * PROPSHEET_CleanUp
1123 */
1124static void PROPSHEET_CleanUp(HWND hwndDlg)
1125{
1126 PropSheetInfo* psInfo = (PropSheetInfo*) RemovePropA(hwndDlg,
1127 PropSheetInfoStr);
1128 COMCTL32_Free(psInfo->proppage);
1129 COMCTL32_Free(psInfo->strPropertiesFor);
1130
1131 GlobalFree((HGLOBAL)psInfo);
1132}
1133
1134/******************************************************************************
1135 * PropertySheetA (COMCTL32.84)(COMCTL32.83)
1136 */
1137INT WINAPI PropertySheetA(LPCPROPSHEETHEADERA lppsh)
1138{
1139 int bRet = 0;
1140 PropSheetInfo* psInfo = (PropSheetInfo*) GlobalAlloc(GPTR,
1141 sizeof(PropSheetInfo));
1142 LPCPROPSHEETPAGEA lppsp;
1143 int i;
1144
1145 PROPSHEET_CollectSheetInfo(lppsh, psInfo);
1146
1147 psInfo->proppage = (PropPageInfo*) COMCTL32_Alloc(sizeof(PropPageInfo) *
1148 lppsh->nPages);
1149
1150 for (i = 0; i < lppsh->nPages; i++)
1151 {
1152 psInfo->proppage[i].index = i;
1153 if (!(lppsh->dwFlags & PSH_PROPSHEETPAGE))
1154 psInfo->proppage[i].hpage = psInfo->ppshheader->u3.phpage[i];
1155 lppsp = PROPSHEET_GetPSPPage(psInfo, i);
1156 PROPSHEET_CollectPageInfo(lppsp, psInfo, i);
1157 }
1158
1159 bRet = PROPSHEET_CreateDialog(psInfo);
1160
1161 return bRet;
1162}
1163
1164/******************************************************************************
1165 * PropertySheet32W (COMCTL32.85)
1166 */
1167INT WINAPI PropertySheetW(LPCPROPSHEETHEADERW propertySheetHeader)
1168{
1169// FIXME(propsheet, "(%p): stub\n", propertySheetHeader);
1170
1171 return -1;
1172}
1173
1174/******************************************************************************
1175 * CreatePropertySheetPageA (COMCTL32.19)(COMCTL32.18)
1176 */
1177HPROPSHEETPAGE WINAPI CreatePropertySheetPageA(
1178 LPCPROPSHEETPAGEA lpPropSheetPage)
1179{
1180 PROPSHEETPAGEA* ppsp = COMCTL32_Alloc(sizeof(PROPSHEETPAGEA));
1181
1182 *ppsp = *lpPropSheetPage;
1183
1184 return (HPROPSHEETPAGE)ppsp;
1185}
1186
1187/******************************************************************************
1188 * CreatePropertySheetPageW (COMCTL32.20)
1189 */
1190HPROPSHEETPAGE WINAPI CreatePropertySheetPageW(LPCPROPSHEETPAGEW lpPropSheetPage)
1191{
1192// FIXME(propsheet, "(%p): stub\n", lpPropSheetPage);
1193
1194 return 0;
1195}
1196
1197/******************************************************************************
1198 * DestroyPropertySheetPage (COMCTL32.24)
1199 */
1200BOOL WINAPI DestroyPropertySheetPage(HPROPSHEETPAGE hPropPage)
1201{
1202 COMCTL32_Free(hPropPage);
1203
1204 return TRUE;
1205}
1206
1207/******************************************************************************
1208 * PROPSHEET_DialogProc
1209 */
1210BOOL WINAPI
1211PROPSHEET_DialogProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
1212{
1213 switch (uMsg)
1214 {
1215 case WM_INITDIALOG:
1216 {
1217 PropSheetInfo* psInfo = (PropSheetInfo*) lParam;
1218 char* strCaption = (char*)COMCTL32_Alloc(MAX_CAPTION_LENGTH);
1219 HWND hwndTabCtrl = GetDlgItem(hwnd, IDC_TABCONTROL);
1220 LPCPROPSHEETPAGEA ppshpage;
1221
1222 psInfo->strPropertiesFor = strCaption;
1223
1224 GetWindowTextA(hwnd, psInfo->strPropertiesFor, MAX_CAPTION_LENGTH);
1225
1226 PROPSHEET_CreateTabControl(hwnd, psInfo);
1227
1228 if (PROPSHEET_IsTooSmall(hwnd, psInfo))
1229 {
1230 PROPSHEET_AdjustSize(hwnd, psInfo);
1231 PROPSHEET_AdjustButtons(hwnd, psInfo);
1232 }
1233
1234 ppshpage = PROPSHEET_GetPSPPage(psInfo, psInfo->active_page);
1235 PROPSHEET_CreatePage(hwnd, psInfo->active_page, psInfo, ppshpage, TRUE);
1236 SendMessageA(hwndTabCtrl, TCM_SETCURSEL, psInfo->active_page, 0);
1237
1238 SetPropA(hwnd, PropSheetInfoStr, (HANDLE)psInfo);
1239
1240 PROPSHEET_SetTitleA(hwnd,
1241 psInfo->ppshheader->dwFlags,
1242 psInfo->ppshheader->pszCaption);
1243
1244 return TRUE;
1245 }
1246
1247 case WM_DESTROY:
1248 PROPSHEET_CleanUp(hwnd);
1249 return TRUE;
1250
1251 case WM_CLOSE:
1252 PROPSHEET_Cancel(hwnd);
1253 return TRUE;
1254
1255 case WM_COMMAND:
1256 {
1257 WORD wID = LOWORD(wParam);
1258
1259 switch (wID)
1260 {
1261 case IDOK:
1262 case IDC_APPLY_BUTTON:
1263 {
1264 HWND hwndApplyBtn = GetDlgItem(hwnd, IDC_APPLY_BUTTON);
1265
1266 if (PROPSHEET_Apply(hwnd) == FALSE)
1267 break;
1268
1269 EnableWindow(hwndApplyBtn, FALSE);
1270
1271 if (wID == IDOK)
1272 {
1273 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwnd,
1274 PropSheetInfoStr);
1275 int result = TRUE;
1276
1277 if (psInfo->restartWindows)
1278 result = ID_PSRESTARTWINDOWS;
1279
1280 /* reboot system takes precedence over restart windows */
1281 if (psInfo->rebootSystem)
1282 result = ID_PSREBOOTSYSTEM;
1283
1284 if (psInfo->isModeless)
1285 psInfo->active_page = -1;
1286 else
1287 EndDialog(hwnd, result);
1288 }
1289
1290 break;
1291 }
1292
1293 case IDCANCEL:
1294 PROPSHEET_Cancel(hwnd);
1295 break;
1296
1297 case IDHELP:
1298 PROPSHEET_Help(hwnd);
1299 break;
1300 }
1301
1302 return TRUE;
1303 }
1304
1305 case WM_NOTIFY:
1306 {
1307 NMHDR* pnmh = (LPNMHDR) lParam;
1308
1309 if (pnmh->code == TCN_SELCHANGE)
1310 {
1311 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwnd,
1312 PropSheetInfoStr);
1313 int index = SendMessageA(pnmh->hwndFrom, TCM_GETCURSEL, 0, 0);
1314 HWND hwndHelp = GetDlgItem(hwnd, IDHELP);
1315
1316 PROPSHEET_ShowPage(hwnd, index, psInfo);
1317
1318 if (psInfo->proppage[index].hasHelp)
1319 EnableWindow(hwndHelp, TRUE);
1320 else
1321 EnableWindow(hwndHelp, FALSE);
1322 }
1323
1324 return 0;
1325 }
1326
1327 case PSM_GETCURRENTPAGEHWND:
1328 {
1329 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwnd,
1330 PropSheetInfoStr);
1331 HWND hwndPage = 0;
1332
1333 if (psInfo->active_page != -1)
1334 hwndPage = psInfo->proppage[psInfo->active_page].hwndPage;
1335
1336 SetWindowLongA(hwnd, DWL_MSGRESULT, hwndPage);
1337
1338 return TRUE;
1339 }
1340
1341 case PSM_CHANGED:
1342 PROPSHEET_Changed(hwnd, (HWND)wParam);
1343 return TRUE;
1344
1345 case PSM_UNCHANGED:
1346 PROPSHEET_UnChanged(hwnd, (HWND)wParam);
1347 return TRUE;
1348
1349 case PSM_GETTABCONTROL:
1350 {
1351 HWND hwndTabCtrl = GetDlgItem(hwnd, IDC_TABCONTROL);
1352
1353 SetWindowLongA(hwnd, DWL_MSGRESULT, hwndTabCtrl);
1354
1355 return TRUE;
1356 }
1357
1358 case PSM_SETCURSEL:
1359 {
1360 BOOL msgResult;
1361
1362 msgResult = PROPSHEET_SetCurSel(hwnd,
1363 (int)wParam,
1364 (HPROPSHEETPAGE)lParam);
1365
1366 SetWindowLongA(hwnd, DWL_MSGRESULT, msgResult);
1367
1368 return TRUE;
1369 }
1370
1371 case PSM_CANCELTOCLOSE:
1372 {
1373 HWND hwndOK = GetDlgItem(hwnd, IDOK);
1374 HWND hwndCancel = GetDlgItem(hwnd, IDCANCEL);
1375
1376 EnableWindow(hwndCancel, FALSE);
1377 SetWindowTextA(hwndOK, "Close"); /* FIXME: hardcoded string */
1378
1379 return TRUE;
1380 }
1381
1382 case PSM_RESTARTWINDOWS:
1383 {
1384 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwnd,
1385 PropSheetInfoStr);
1386
1387 psInfo->restartWindows = TRUE;
1388 return TRUE;
1389 }
1390
1391 case PSM_REBOOTSYSTEM:
1392 {
1393 PropSheetInfo* psInfo = (PropSheetInfo*) GetPropA(hwnd,
1394 PropSheetInfoStr);
1395
1396 psInfo->rebootSystem = TRUE;
1397 return TRUE;
1398 }
1399
1400 case PSM_SETTITLEA:
1401 PROPSHEET_SetTitleA(hwnd, (DWORD) wParam, (LPCSTR) lParam);
1402 return TRUE;
1403
1404 case PSM_APPLY:
1405 {
1406 BOOL msgResult = PROPSHEET_Apply(hwnd);
1407
1408 SetWindowLongA(hwnd, DWL_MSGRESULT, msgResult);
1409
1410 return TRUE;
1411 }
1412
1413 case PSM_QUERYSIBLINGS:
1414 {
1415 LRESULT msgResult = PROPSHEET_QuerySiblings(hwnd, wParam, lParam);
1416
1417 SetWindowLongA(hwnd, DWL_MSGRESULT, msgResult);
1418
1419 return TRUE;
1420 }
1421
1422 case PSM_ADDPAGE:
1423 PROPSHEET_AddPage(hwnd, (HPROPSHEETPAGE)lParam);
1424 return TRUE;
1425
1426 case PSM_REMOVEPAGE:
1427 PROPSHEET_RemovePage(hwnd, (int)wParam, (HPROPSHEETPAGE)lParam);
1428 return TRUE;
1429
1430 case PSM_ISDIALOGMESSAGE:
1431 {
1432// FIXME (propsheet, "Unimplemented msg PSM_ISDIALOGMESSAGE\n");
1433 return 0;
1434 }
1435
1436 case PSM_PRESSBUTTON:
1437 PROPSHEET_PressButton(hwnd, (int)wParam);
1438 return TRUE;
1439
1440 case PSM_SETTITLEW:
1441// FIXME (propsheet, "Unimplemented msg PSM_SETTITLE32W\n");
1442 return 0;
1443 case PSM_SETWIZBUTTONS:
1444// FIXME (propsheet, "Unimplemented msg PSM_SETWIZBUTTONS\n");
1445 return 0;
1446 case PSM_SETCURSELID:
1447// FIXME (propsheet, "Unimplemented msg PSM_SETCURSELID\n");
1448 return 0;
1449 case PSM_SETFINISHTEXTA:
1450// FIXME (propsheet, "Unimplemented msg PSM_SETFINISHTEXT32A\n");
1451 return 0;
1452 case PSM_SETFINISHTEXTW:
1453// FIXME (propsheet, "Unimplemented msg PSM_SETFINISHTEXT32W\n");
1454 return 0;
1455
1456 default:
1457 return FALSE;
1458 }
1459}
1460
Note: See TracBrowser for help on using the repository browser.