home *** CD-ROM | disk | FTP | other *** search
/ Liren Large Software Subsidy 7 / 07.iso / c / c480 / 19.ddi / SAMPLES / DEFPROCS / DEFDLG.C_ / DEFDLG.C
Encoding:
Text File  |  1993-02-08  |  9.2 KB  |  266 lines

  1. /*--------------------------------------------------------------------------*/
  2. /*                                                                          */
  3. /*  DefDlgProc() -                                                          */
  4. /*                                                                          */
  5. /*--------------------------------------------------------------------------*/
  6.  
  7. LRESULT API IDefDlgProc(HWND hwnd, WORD message, WPARAM wParam, LPARAM lParam)
  8. {
  9.     HWND hwndT1;
  10.     HWND hwndT2;
  11.     BOOL result;
  12.  
  13.     ((PDLG)hwnd)->resultWP = 0L;
  14.     result = FALSE;
  15.     //
  16.     // Call the dialog proc if it exists
  17.     //
  18.     if (((PDLG)hwnd)->lpfnDlg == NULL ||
  19.             !(result = CallDlgProc(hwnd, message, wParam, lParam)))
  20.         {
  21.  
  22.         // Make sure window still exists.
  23.         if (!IsWindow(hwnd))
  24.         {
  25.             DebugErr(DBF_ERROR, "Dialog window destroyed in dialog callback");
  26.             goto ReturnIt;
  27.         }
  28.  
  29.         switch (message)
  30.         {
  31.         case WM_ERASEBKGND:
  32.             FillWindow(hwnd, hwnd, (HDC)wParam, (HBRUSH)CTLCOLOR_DLG);
  33.             return((LRESULT)(LONG)TRUE);
  34.  
  35.         case WM_SHOWWINDOW:
  36.             // If hiding the window, save the focus. If showing the window
  37.             // by means of a SW_* command and the fEnd bit is set, do not
  38.             // pass to DWP so it won't get shown.
  39.             //
  40.             if (!wParam)
  41.                 SaveDlgFocus(hwnd);
  42.             else if (LOWORD(lParam) && pdlg->fEnd)
  43.                 break;
  44.             return(DefWindowProc(hwnd, message, wParam, lParam));
  45.  
  46.         case WM_SYSCOMMAND:
  47.             //
  48.             // If we're minimizing and a dialog control has the focus,
  49.             // save the hwnd for that control
  50.             //
  51.             if ((int) wParam == SC_MINIMIZE)
  52.                 SaveDlgFocus(hwnd);
  53.             return(DefWindowProc(hwnd, message, wParam, lParam));
  54.  
  55.         case WM_ACTIVATE:
  56.             if (fDialog = (wParam != 0))
  57.                 RestoreDlgFocus(hwnd);
  58.             else
  59.                 SaveDlgFocus(hwnd);
  60.             break;
  61.  
  62.         case WM_SETFOCUS:
  63.             if (!pdlg->fEnd && !RestoreDlgFocus(hwnd))
  64.                 DlgSetFocus(GetFirstTab(hwnd));
  65.             break;
  66.  
  67.         case WM_CLOSE:
  68.             // Make sure cancel button is not disabled before sending the
  69.             // IDCANCEL.  Note that we need to do this as a message instead
  70.             // of directly calling the dlg proc so that any dialog box
  71.             // filters get this.
  72.             //
  73.             hwndT1 = GetDlgItem(hwnd, IDCANCEL);
  74.             if (hwndT1 && TestWF(hwndT1, WFDISABLED))
  75.                 MessageBeep(0);
  76.             else
  77.                 PostMessage(hwnd, WM_COMMAND, (WPARAM)IDCANCEL, MAKELPARAM(hwndT1, BN_CLICKED));
  78.             break;
  79.  
  80.         case WM_NCDESTROY:
  81.             fDialog = FALSE;      /* clear this flag */
  82.  
  83.             // Make sure we are going to terminate the mode loop, in case
  84.             // DestroyWindow was called instead of EndDialog.  We'll RIP
  85.             // in DialogBox2.
  86.             //
  87.             ((PDLG)hwnd)->fEnd = TRUE;
  88.  
  89.             if (!(hwnd->style & DS_LOCALEDIT))
  90.             {
  91.                 if (((PDLG)hwnd)->hData)
  92.                 {
  93.  
  94.                     GlobalUnlock(((PDLG)hwnd)->hData);
  95.  
  96.                     ReleaseEditDS(((PDLG)hwnd)->hData);
  97.                     ((PDLG)hwnd)->hData = NULL;
  98.                 }
  99.             }
  100.  
  101.             // Delete the user defined font if any
  102.             if (((PDLG)hwnd)->hUserFont)
  103.             {
  104.                 DeleteObject((HANDLE)((PDLG)hwnd)->hUserFont);
  105.                 ((PDLG)hwnd)->hUserFont = NULL;
  106.             }
  107.  
  108.             // Always let DefWindowProc do its thing to ensure that
  109.             // everything associated with the window is freed up.
  110.             //
  111.             DefWindowProc(hwnd, message, wParam, lParam);
  112.             break;
  113.  
  114.         case DM_SETDEFID:
  115.             if (!(((PDLG)hwnd)->fEnd))
  116.             {
  117.                 // Make sure that the new default button has the highlight.
  118.                 // We need to ignore this if we are ending the dialog box
  119.                 // because hwnd->result is no longer a default window id but
  120.                 // rather the return value of the dialog box.
  121.                 //
  122.                 // Catch the case of setting the defid to null or setting
  123.                 // the defid to something else when it was initially null.
  124.                 //
  125.                 CheckDefPushButton(hwnd,
  126.                      (((PDLG)hwnd)->result ? GetDlgItem(hwnd, ((PDLG)hwnd)->result) : NULL),
  127.                      (wParam               ? GetDlgItem(hwnd, (int) wParam        ) : NULL) );
  128.                 ((PDLG)hwnd)->result = (int)wParam;
  129.             }
  130.             return((LRESULT)(DWORD)TRUE);
  131.  
  132.         case DM_GETDEFID:
  133.             if (!((PDLG)hwnd)->fEnd && ((PDLG)hwnd)->result)
  134.                 return(MAKELRESULT(((PDLG)hwnd)->result, DC_HASDEFID));
  135.             else
  136.                 return(0L);
  137.  
  138.         case WM_NEXTDLGCTL:
  139.             // This message is so TAB-like operations can be properly handled
  140.             // (simple SetFocus won't do the default button stuff)
  141.             //
  142.             hwndT2 = hwndFocus;
  143.             if (LOWORD(lParam))
  144.             {
  145.                 if (hwndT2 == NULL)
  146.                     hwndT2 = hwnd;
  147.  
  148.                 // wParam contains the hwnd of the ctl to set focus to
  149.                 hwndT1 = (HWND)wParam;
  150.             }
  151.             else
  152.             {
  153.                 if (hwndT2 == NULL)
  154.                 {
  155.                     // Set focus to the first tab item.
  156.                     hwndT1 = GetFirstTab(hwnd);
  157.                     hwndT2 = hwnd;
  158.                 }
  159.                 else
  160.                 {
  161.                     // If window with focus not a dlg ctl, ignore message.
  162.                     if (!IsChild(hwnd, hwndT2))
  163.                         return((LRESULT)(LONG)TRUE);
  164.  
  165.                     // wParam = TRUE for previous, FALSE for next
  166.                     hwndT1 = GetNextDlgTabItem(hwnd, hwndT2, (BOOL)wParam);
  167.                 }
  168.             }
  169.             DlgSetFocus(hwndT1);
  170.             CheckDefPushButton(hwnd, hwndT2, hwndT1);
  171.             return((LRESULT)(LONG)TRUE);
  172.  
  173.         case WM_ENTERMENULOOP:
  174.         case WM_LBUTTONDOWN:
  175.         case WM_NCLBUTTONDOWN:
  176.             //
  177.             // PLEASE NOTE: The following code is a VERY UGLY compatibility
  178.             // hack.  NEVER write code that looks at the window proc address
  179.             // in order to determine the window type.  The following code will
  180.             // not work with subclassed combo or edit controls.
  181.             //
  182.             if (hwndT1 = hwndFocus)
  183.             {
  184.                 if (hwndT1->pcls->lpfnWndProc == ComboBoxCtlWndProc)
  185.                 {
  186.                     // If user clicks anywhere in dialog box and a combo box (or
  187.                     // the editcontrol of a combo box) has the focus, then hide
  188.                     // it's listbox.
  189.                     //
  190.                     SendMessage(hwndT1, CB_SHOWDROPDOWN, FALSE, 0L);
  191.                 }
  192.                 else
  193.                 {
  194.                     if (hwndT1->pcls->lpfnWndProc == EditWndProc &&
  195.                         hwndT1->hwndParent->pcls->lpfnWndProc==ComboBoxCtlWndProc)
  196.                     {
  197.                         SendMessage(hwndT1->hwndParent,CB_SHOWDROPDOWN, FALSE, 0L);
  198.                     }
  199.                 }
  200.             }
  201.             return(DefWindowProc(hwnd, message, wParam, lParam));
  202.  
  203.         case WM_GETFONT:
  204.             return (LRESULT)(DWORD)(WORD)((PDLG)hwnd)->hUserFont;
  205.  
  206.         // We don't want to pass the following messages to DefWindowProc:
  207.         // instead, return the value returned by the dialog proc (FALSE)
  208.         //
  209.         case WM_VKEYTOITEM:
  210.         case WM_COMPAREITEM:
  211.         case WM_CHARTOITEM:
  212.         case WM_INITDIALOG:
  213.             break;
  214.  
  215.         default:
  216.             return(DefWindowProc(hwnd, message, wParam, lParam));
  217.         }
  218.     }
  219.  
  220. ReturnIt:
  221.     // These messages are special cased in an unusual way: the return value
  222.     // of the dialog function is not BOOL fProcessed, but instead it's the
  223.     // return value of these messages.
  224.     //
  225.     if (message == WM_CTLCOLOR ||
  226.         message == WM_COMPAREITEM ||
  227.         message == WM_VKEYTOITEM ||
  228.         message == WM_CHARTOITEM ||
  229.         message == WM_QUERYDRAGICON ||
  230.         message == WM_INITDIALOG)
  231.     {
  232.         return((LRESULT)(DWORD)result);
  233.     }
  234.  
  235.     return(((PDLG)hwnd)->resultWP);
  236. }
  237.  
  238. BOOL SaveDlgFocus(HWND hwnd)
  239. {
  240.     if (hwndFocus && IsChild(hwnd, hwndFocus) && !((PDLG)hwnd)->hwndFocusSave)
  241.     {
  242.         ((PDLG)hwnd)->hwndFocusSave = hwndFocus;
  243.         RemoveDefaultButton(hwnd, hwndFocus);
  244.         return(TRUE);
  245.     }
  246.     return(FALSE);
  247. }
  248.  
  249. BOOL RestoreDlgFocus(HWND hwnd)
  250. {
  251.     BOOL fRestored = FALSE;
  252.  
  253.     if (((PDLG)hwnd)->hwndFocusSave && !TestWF(hwnd, WFMINIMIZED))
  254.     {
  255.         if (IsWindow(((PDLG)hwnd)->hwndFocusSave))
  256.         {
  257.             CheckDefPushButton(hwnd, hwndFocus, ((PDLG)hwnd)->hwndFocusSave);
  258.             SetFocus(((PDLG)hwnd)->hwndFocusSave);
  259.             fRestored = TRUE;
  260.         }
  261.  
  262.         ((PDLG)hwnd)->hwndFocusSave = NULL;
  263.     }
  264.     return(fRestored);
  265. }
  266.