home *** CD-ROM | disk | FTP | other *** search
/ Tricks of the Windows Gam…ming Gurus (2nd Edition) / Disc2.iso / msdn_vcb / samples / vc98 / sdk / com / inole2 / chap12 / cocosmo / cocosmo.cpp < prev    next >
C/C++ Source or Header  |  1995-05-03  |  15KB  |  684 lines

  1. /*
  2.  * COCOSMO.CPP
  3.  * Component Cosmo Chapter 12
  4.  *
  5.  * WinMain and CCosmoFrame implementations.
  6.  *
  7.  * Copyright (c)1993-1995 Microsoft Corporation, All Rights Reserved
  8.  *
  9.  * Kraig Brockschmidt, Microsoft
  10.  * Internet  :  kraigb@microsoft.com
  11.  * Compuserve:  >INTERNET:kraigb@microsoft.com
  12.  */
  13.  
  14.  
  15. #define INITGUIDS
  16. #include "cocosmo.h"
  17.  
  18.  
  19. /*
  20.  * WinMain
  21.  *
  22.  * Purpose:
  23.  *  Main entry point of application.  Should register the app class
  24.  *  if a previous instance has not done so and do any other one-time
  25.  *  initializations.
  26.  */
  27.  
  28. int PASCAL WinMain (HINSTANCE hInst, HINSTANCE hPrev
  29.     , LPSTR pszCmdLine, int nCmdShow)
  30.     {
  31.     PCCosmoFrame    pFR;
  32.     FRAMEINIT       fi;
  33.     WPARAM          wRet;
  34.  
  35.     //Attempt to allocate and initialize the application
  36.     pFR=new CCosmoFrame(hInst, hPrev, pszCmdLine, nCmdShow);
  37.  
  38.     if (NULL==pFR)
  39.         return -1;
  40.  
  41.     fi.idsMin=IDS_FRAMEMIN;
  42.     fi.idsMax=IDS_FRAMEMAX;
  43.     fi.idsStatMin=IDS_STATMESSAGEMIN;
  44.     fi.idsStatMax=IDS_STATMESSAGEMAX;
  45.     fi.idStatMenuMin=ID_MENUFILE;
  46.     fi.idStatMenuMax=ID_MENUHELP;
  47.     fi.iPosWindowMenu=WINDOW_MENU;
  48.     fi.cMenus=CMENUS;
  49.  
  50.     fi.x=CW_USEDEFAULT;
  51.     fi.y=CW_USEDEFAULT;
  52.     fi.cx=440;
  53.     fi.cy=460;
  54.  
  55.     //If we can initialize pFR, start chugging messages
  56.     if (pFR->Init(&fi))
  57.         wRet=pFR->MessageLoop();
  58.  
  59.     delete pFR;
  60.     return wRet;
  61.     }
  62.  
  63.  
  64.  
  65.  
  66. /*
  67.  * CCosmoFrame::CCosmoFrame
  68.  * CCosmoFrame::~CCosmoFrame
  69.  *
  70.  * Constructor Parameters:
  71.  *  hInst           HINSTANCE from WinMain
  72.  *  hInstPrev       HINSTANCE from WinMain
  73.  *  pszCmdLine      LPSTR from WinMain
  74.  *  nCmdShow        int from WInMain
  75.  */
  76.  
  77. CCosmoFrame::CCosmoFrame(HINSTANCE hInst, HINSTANCE hInstPrev
  78.     , LPSTR pszCmdLine, int nCmdShow)
  79.     : CFrame(hInst, hInstPrev, pszCmdLine, nCmdShow)
  80.     {
  81.     UINT        i;
  82.  
  83.     for (i=0; i<5; i++)
  84.         m_hBmpLines[i]=NULL;
  85.  
  86.     m_uIDCurLine=0;
  87.     m_fInitialized=FALSE;
  88.     return;
  89.     }
  90.  
  91.  
  92. CCosmoFrame::~CCosmoFrame(void)
  93.     {
  94.     UINT        i;
  95.  
  96.     for (i=0; i<5; i++)
  97.         {
  98.         if (NULL!=m_hBmpLines[i])
  99.             DeleteObject(m_hBmpLines[i]);
  100.         }
  101.  
  102.     //CHAPTER12MOD
  103.     if (m_fInitialized)
  104.         OleUninitialize();
  105.     //End CHAPTER12MOD
  106.  
  107.     return;
  108.     }
  109.  
  110.  
  111.  
  112.  
  113. /*
  114.  * CCosmoFrame::Init
  115.  *
  116.  * Purpose:
  117.  *  Call OleInitialize then calling down into the base class
  118.  *  initialization.
  119.  *
  120.  * Parameters:
  121.  *  pFI             PFRAMEINIT containing initialization
  122.  *                  parameters.
  123.  *
  124.  * Return Value:
  125.  *  BOOL            TRUE if initialization succeeded,
  126.  *                  FALSE otherwise.
  127.  */
  128.  
  129. BOOL CCosmoFrame::Init(PFRAMEINIT pFI)
  130.     {
  131.     //CHAPTER12MOD
  132.     CHECKVER_OLE;
  133.  
  134.     if (FAILED(OleInitialize(NULL)))
  135.         return FALSE;
  136.     //End CHAPTER12MOD
  137.  
  138.     m_fInitialized=TRUE;
  139.  
  140.     return CFrame::Init(pFI);
  141.     }
  142.  
  143.  
  144.  
  145.  
  146.  
  147. /*
  148.  * CCosmoFrame::CreateCClient
  149.  *
  150.  * Purpose:
  151.  *  Constructs a new client specific to the application.
  152.  *
  153.  * Parameters:
  154.  *  None
  155.  *
  156.  * Return Value:
  157.  *  PCClient        Pointer to the new client object.
  158.  */
  159.  
  160. PCClient CCosmoFrame::CreateCClient(void)
  161.     {
  162.     return (PCClient)(new CCosmoClient(m_hInst, this));
  163.     }
  164.  
  165.  
  166.  
  167.  
  168.  
  169.  
  170.  
  171.  
  172. /*
  173.  * CCosmoFrame::RegisterAllClasses
  174.  *
  175.  * Purpose:
  176.  *  Registers all classes used in this application.
  177.  *
  178.  * Parameters:
  179.  *  None
  180.  *
  181.  * Return Value:
  182.  *  BOOL            TRUE if registration succeeded, FALSE otherwise.
  183.  */
  184.  
  185. BOOL CCosmoFrame::RegisterAllClasses(void)
  186.     {
  187.     WNDCLASS        wc;
  188.  
  189.     //First let the standard frame do its thing
  190.     if (!CFrame::RegisterAllClasses())
  191.         return FALSE;
  192.  
  193.     /*
  194.      * We want a different background color for the document
  195.      * because the Polyline we put in the document will paint
  196.      * with COLOR_WINDOW which by default which is CLASSLIB's
  197.      * default document color.
  198.      */
  199.  
  200.     GetClassInfo(m_hInst, SZCLASSDOCUMENT, &wc);
  201.     UnregisterClass(SZCLASSDOCUMENT, m_hInst);
  202.  
  203.     wc.hbrBackground=(HBRUSH)(COLOR_APPWORKSPACE+1);
  204.  
  205.     if (!RegisterClass(&wc))
  206.         return FALSE;
  207.  
  208.     //No need to register the Polyline window now...
  209.  
  210.     return TRUE;
  211.     }
  212.  
  213.  
  214.  
  215. /*
  216.  * CCosmoFrame::PreShowInit
  217.  *
  218.  * Purpose:
  219.  *  Called from Init before intially showing the window.  We do
  220.  *  whatever else we want here, modifying nCmdShow as necessary
  221.  *  which affects ShowWindow in Init.
  222.  *
  223.  * Parameters:
  224.  *  None
  225.  *
  226.  * Return Value:
  227.  *  BOOL            TRUE if this initialization succeeded,
  228.  *                  FALSE otherwise.
  229.  */
  230.  
  231. BOOL CCosmoFrame::PreShowInit(void)
  232.     {
  233.     CreateLineMenu();
  234.     CheckLineSelection(IDM_LINESOLID);
  235.     return TRUE;
  236.     }
  237.  
  238.  
  239.  
  240.  
  241.  
  242.  
  243. /*
  244.  * CCosmoFrame::CreateLineMenu
  245.  *
  246.  * Purpose:
  247.  *  Initializes the bitmaps used to create the Line menu and
  248.  *  replaces the text items defined in the application resources
  249.  *  with these bitmaps.  Note that the contents of m_hBmpLines
  250.  *  must be cleaned up when the application terminates.
  251.  *
  252.  * Parameters:
  253.  *  None
  254.  *
  255.  * Return Value:
  256.  *  None
  257.  */
  258.  
  259. void CCosmoFrame::CreateLineMenu(void)
  260.     {
  261.     HMENU       hMenu;
  262.     HDC         hDC, hMemDC;
  263.     HPEN        hPen;
  264.     HGDIOBJ     hObj;
  265.     TEXTMETRIC  tm;
  266.     UINT        i, cx, cy;
  267.  
  268.  
  269.     hMenu=GetSubMenu(GetMenu(m_hWnd), 3);   //Line menu.
  270.     hDC=GetDC(m_hWnd);
  271.  
  272.     //Create each line in a menu item 8 chars wide, one char high.
  273.     GetTextMetrics(hDC, &tm);
  274.     cx=tm.tmAveCharWidth*8;
  275.     cy=tm.tmHeight;
  276.  
  277.     /*
  278.      * Create a memory DC in which to draw lines, and bitmaps
  279.      * for each line.
  280.      */
  281.     hMemDC=CreateCompatibleDC(hDC);
  282.     ReleaseDC(m_hWnd, hDC);
  283.  
  284.     for (i=0; i<5; i++)
  285.         {
  286.         m_hBmpLines[i]=CreateCompatibleBitmap(hMemDC, cx, cy);
  287.         SelectObject(hMemDC, m_hBmpLines[i]);
  288.  
  289.         PatBlt(hMemDC, 0, 0, cx, cy, WHITENESS);
  290.  
  291.         hPen=CreatePen(i, 1, 0L);       //i=line style like PS_SOLID
  292.         hObj=SelectObject(hMemDC, hPen);
  293.  
  294.         MoveToEx(hMemDC, 0, cy/2, NULL);
  295.         LineTo(hMemDC, cx, cy/2);
  296.  
  297.         ModifyMenu(hMenu, IDM_LINEMIN+i, MF_BYCOMMAND | MF_BITMAP
  298.             , IDM_LINEMIN+i, (LPTSTR)(LONG)(UINT)m_hBmpLines[i]);
  299.  
  300.         SelectObject(hMemDC, hObj);
  301.         DeleteObject(hPen);
  302.         }
  303.  
  304.     CheckMenuItem(hMenu, IDM_LINESOLID, MF_CHECKED);
  305.     DeleteDC(hMemDC);
  306.  
  307.     return;
  308.     }
  309.  
  310.  
  311.  
  312.  
  313. /*
  314.  * CCosmoFrame::CreateToolbar
  315.  *
  316.  * Purpose:
  317.  *  Procedure to create all the necessary toolbar buttons.
  318.  *
  319.  * Parameters:
  320.  *  None
  321.  *
  322.  * Return Value:
  323.  *  UINT            Number of tools added to the bar.
  324.  */
  325.  
  326. UINT CCosmoFrame::CreateToolbar(void)
  327.     {
  328.     UINT            iLast;
  329.     UINT            uState=GIZMO_NORMAL;
  330.     UINT            utCmd =GIZMOTYPE_BUTTONCOMMAND;
  331.     UINT            utEx  =GIZMOTYPE_BUTTONATTRIBUTEEX;
  332.  
  333.     //Insert the standard ones.
  334.     iLast=CFrame::CreateToolbar();
  335.  
  336.     /*
  337.      * Insert File Import in the 5th position and account for
  338.      * it in iLast.
  339.      */
  340.     m_pTB->Add(utCmd, 4, IDM_FILEIMPORT, m_dxB, m_dyB
  341.         , NULL, m_hBmp, 2, uState);
  342.     iLast++;
  343.  
  344.     //Separator
  345.     m_pTB->Add(GIZMOTYPE_SEPARATOR, iLast++, 0, 6, m_dyB
  346.         , NULL, NULL, 0, uState);
  347.  
  348.     /*
  349.      * For the Background bitmap, preserve our use of black
  350.      * (part of the image)
  351.      */
  352.     m_pTB->Add(utCmd, iLast++, IDM_COLORBACKGROUND, m_dxB, m_dyB
  353.         , NULL, m_hBmp, 3, GIZMO_NORMAL | PRESERVE_BLACK);
  354.  
  355.     m_pTB->Add(utCmd, iLast++, IDM_COLORLINE, m_dxB, m_dyB
  356.         , NULL, m_hBmp, 4, uState);
  357.  
  358.     //Separator
  359.     m_pTB->Add(GIZMOTYPE_SEPARATOR, iLast++, 0, 6, m_dyB
  360.         , NULL, NULL, 0, uState);
  361.  
  362.     //Line styles.
  363.     m_pTB->Add(utEx, iLast++, IDM_LINESOLID, m_dxB, m_dyB
  364.         , NULL, m_hBmp, 5, uState);
  365.     m_pTB->Add(utEx, iLast++, IDM_LINEDASH, m_dxB, m_dyB
  366.         , NULL, m_hBmp, 6, uState);
  367.     m_pTB->Add(utEx, iLast++, IDM_LINEDOT, m_dxB, m_dyB
  368.         , NULL, m_hBmp, 7, uState);
  369.     m_pTB->Add(utEx, iLast++, IDM_LINEDASHDOT, m_dxB, m_dyB
  370.         , NULL, m_hBmp, 8, uState);
  371.     m_pTB->Add(utEx, iLast++, IDM_LINEDASHDOTDOT, m_dxB, m_dyB
  372.         , NULL, m_hBmp, 9, uState);
  373.  
  374.     return iLast;
  375.     }
  376.  
  377.  
  378.  
  379.  
  380.  
  381.  
  382.  
  383.  
  384. /*
  385.  * CCosmoFrame::OnCommand
  386.  *
  387.  * Purpose:
  388.  *  WM_COMMAND handler for the Cosmo frame window that just
  389.  *  processes the line menu and the color menu leaving the
  390.  *  CFrame to do everything else.
  391.  *
  392.  * Parameters:
  393.  *  hWnd            HWND of the frame window.
  394.  *  wParam          WPARAM of the message.
  395.  *  lParam          LPARAM of the message.
  396.  *
  397.  * Return Value:
  398.  *  LRESULT         Return value for the message.
  399.  */
  400.  
  401. LRESULT CCosmoFrame::OnCommand(HWND hWnd, WPARAM wParam
  402.     , LPARAM lParam)
  403.     {
  404.     PCCosmoDoc      pDoc;
  405.     TCHAR           szFile[CCHPATHMAX];
  406.     BOOL            fOK;
  407.     UINT            i, uTemp;
  408.     COLORREF        rgColors[16];
  409.     CHOOSECOLOR     cc;
  410.  
  411.     COMMANDPARAMS(wID, wCode, hWndMsg);
  412.  
  413.     /*
  414.      * Don't bother with anything during first initialization,
  415.      * skipping many toolbar notifications.
  416.      */
  417.     if (m_fInit)
  418.         return 0L;
  419.  
  420.     pDoc=(PCCosmoDoc)m_pCL->ActiveDocument();
  421.  
  422.     /*
  423.      * Check for the line style commands which are
  424.      * IDM_LINEMIN+<style>.  We handle this by changing the menu
  425.      * and toolbar, then we pass it to the document for real
  426.      * processing.
  427.      */
  428.     if (NULL!=pDoc && IDM_LINEMIN <= wID && IDM_LINEMAX >=wID)
  429.         {
  430.         CheckLineSelection(wID);
  431.         pDoc->LineStyleSet(wID-IDM_LINEMIN);
  432.         return 0L;
  433.         }
  434.  
  435.     switch (wID)
  436.         {
  437.         case IDM_FILEIMPORT:
  438.             szFile[0]=0;
  439.             fOK=SaveOpenDialog(szFile, CCHPATHMAX, IDS_FILEIMPORT
  440.                 , TRUE, &i);
  441.  
  442.             if (fOK)
  443.                 {
  444.                 uTemp=pDoc->Load(FALSE, szFile);
  445.                 pDoc->ErrorMessage(uTemp);
  446.                 }
  447.  
  448.             return (LRESULT)fOK;
  449.  
  450.  
  451.         case IDM_COLORBACKGROUND:
  452.         case IDM_COLORLINE:
  453.             //Invoke the color chooser for either color
  454.             uTemp=(IDM_COLORBACKGROUND==wID)
  455.                 ? DOCCOLOR_BACKGROUND : DOCCOLOR_LINE;
  456.  
  457.             for (i=0; i<16; i++)
  458.                 rgColors[i]=RGB(0, 0, i*16);
  459.  
  460.             memset(&cc, 0, sizeof(CHOOSECOLOR));
  461.             cc.lStructSize=sizeof(CHOOSECOLOR);
  462.             cc.lpCustColors=rgColors;
  463.             cc.hwndOwner=hWnd;
  464.             cc.Flags=CC_RGBINIT;
  465.             cc.rgbResult=pDoc->ColorGet(uTemp);
  466.  
  467.             if (ChooseColor(&cc))
  468.                 pDoc->ColorSet(uTemp, cc.rgbResult);
  469.  
  470.             break;
  471.  
  472.  
  473.         default:
  474.            CFrame::OnCommand(hWnd, wParam, lParam);
  475.         }
  476.  
  477.     return 0L;
  478.     }
  479.  
  480.  
  481.  
  482.  
  483.  
  484.  
  485. /*
  486.  * CCosmoFrame::OnDocumentDataChange
  487.  *
  488.  * Purpose:
  489.  *  Update the Line menu and toolbar if the style in the data
  490.  *  changes.
  491.  *
  492.  * Parameters:
  493.  *  pDoc            PCDocument notifying the sink.
  494.  *
  495.  * Return Value:
  496.  *  None
  497.  */
  498.  
  499. void CCosmoFrame::OnDocumentDataChange(PCDocument pDoc)
  500.     {
  501.     CheckLineSelection(IDM_LINEMIN
  502.         +((PCCosmoDoc)pDoc)->LineStyleGet());
  503.     return;
  504.     }
  505.  
  506.  
  507.  
  508.  
  509. /*
  510.  * CCosmoFrame::OnDocumentActivate
  511.  *
  512.  * Purpose:
  513.  *  Informs us that document activation changed, so update the UI
  514.  *  for that new document.
  515.  *
  516.  * Parameters:
  517.  *  pDoc            PCDocument notifying the sink.
  518.  *
  519.  * Return Value:
  520.  *  None
  521.  */
  522.  
  523. void CCosmoFrame::OnDocumentActivate(PCDocument pDoc)
  524.     {
  525.     CheckLineSelection(IDM_LINEMIN
  526.         +((PCCosmoDoc)pDoc)->LineStyleGet());
  527.     return;
  528.     }
  529.  
  530.  
  531.  
  532.  
  533.  
  534.  
  535.  
  536. /*
  537.  * CCosmoFrame::UpdateMenus
  538.  *
  539.  * Purpose:
  540.  *  Handles the WM_INITMENU message for the frame window.  Depending
  541.  *  on the existence of an active window, menu items are selectively
  542.  *  enabled and disabled.
  543.  *
  544.  * Parameters:
  545.  *  hMenu           HMENU of the menu to intialize
  546.  *  iMenu           UINT position of the menu.
  547.  *
  548.  * Return Value:
  549.  *  None
  550.  */
  551.  
  552. void CCosmoFrame::UpdateMenus(HMENU hMenu, UINT iMenu)
  553.     {
  554.     PCDocument  pDoc;
  555.     BOOL        fOK=FALSE;
  556.     BOOL        fCallDefault=TRUE;
  557.     UINT        i;
  558.     UINT        uTemp;
  559.     UINT        uTempE;
  560.     UINT        uTempD;
  561.  
  562.     pDoc=m_pCL->ActiveDocument();
  563.  
  564.     uTempE=MF_ENABLED | MF_BYCOMMAND;
  565.     uTempD=MF_DISABLED | MF_GRAYED | MF_BYCOMMAND;
  566.     uTemp=((NULL!=pDoc) ? uTempE : uTempD);
  567.  
  568.     //File menu:  If there is document window, disable Import.
  569.     if (m_phMenu[0]==hMenu)
  570.         EnableMenuItem(hMenu, IDM_FILEIMPORT, uTemp);
  571.  
  572.     //Color menu:  no document, no commands
  573.     if (m_phMenu[2]==hMenu)
  574.         {
  575.         EnableMenuItem(hMenu, IDM_COLORBACKGROUND, uTemp);
  576.         EnableMenuItem(hMenu, IDM_COLORLINE,       uTemp);
  577.         fCallDefault=FALSE;
  578.         }
  579.  
  580.     //Line menu:  no document, no commands
  581.     if (m_phMenu[3]==hMenu)
  582.         {
  583.         for (i=IDM_LINEMIN; i<=IDM_LINEMAX; i++)
  584.             EnableMenuItem(hMenu, i, uTemp);
  585.  
  586.         fCallDefault=FALSE;
  587.         }
  588.  
  589.     if (fCallDefault)
  590.         CFrame::UpdateMenus(hMenu, iMenu);
  591.  
  592.     return;
  593.     }
  594.  
  595.  
  596.  
  597.  
  598.  
  599.  
  600. /*
  601.  * CCosmoFrame::UpdateToolbar
  602.  *
  603.  * Purpose:
  604.  *  Enables and disables tools depending on whether we have
  605.  *  a document or not.
  606.  *
  607.  * Parameters:
  608.  *  None
  609.  *
  610.  * Return Value:
  611.  *  None
  612.  */
  613.  
  614. void CCosmoFrame::UpdateToolbar(void)
  615.     {
  616.     BOOL        fLast;
  617.     UINT        i;
  618.  
  619.     //Save the last enabled state before CFrame changes it
  620.     fLast=m_fLastEnable;
  621.  
  622.     //Let the default hack on its tools
  623.     CFrame::UpdateToolbar();
  624.  
  625.     /*
  626.      * If CFrame::UpdateToolbar changed anything, then we need
  627.      * to change as well--if nothing changes, nothing to do.
  628.      */
  629.     if (fLast!=m_fLastEnable)
  630.         {
  631.         m_pTB->Enable(IDM_FILEIMPORT, m_fLastEnable);
  632.  
  633.         m_pTB->Enable(IDM_COLORBACKGROUND, m_fLastEnable);
  634.         m_pTB->Enable(IDM_COLORLINE,       m_fLastEnable);
  635.  
  636.         for (i=IDM_LINEMIN; i <= IDM_LINEMAX; i++)
  637.             m_pTB->Enable(i, m_fLastEnable);
  638.         }
  639.  
  640.     return;
  641.     }
  642.  
  643.  
  644.  
  645.  
  646.  
  647.  
  648. /*
  649.  * CCosmoFrame::CheckLineSelection
  650.  *
  651.  * Purpose:
  652.  *  Maintains the bitmap menu and the tools for the line selection.
  653.  *  Both are mutially exclusive option lists where a selection in
  654.  *  one has to affect the other.
  655.  *
  656.  * Parameters:
  657.  *  uID             UINT ID of the item to be selected
  658.  *
  659.  * Return Value:
  660.  *  None
  661.  */
  662.  
  663. void CCosmoFrame::CheckLineSelection(UINT uID)
  664.     {
  665.     UINT        i;
  666.     HMENU       hMenu;
  667.  
  668.     //Update menus and tools if the selection changed.
  669.     if (uID!=m_uIDCurLine)
  670.         {
  671.         m_uIDCurLine=uID;
  672.         hMenu=GetMenu(m_hWnd);
  673.  
  674.         //Uncheck all lines initially.
  675.         for (i=IDM_LINEMIN; i<=IDM_LINEMAX; i++)
  676.             CheckMenuItem(hMenu, i, MF_UNCHECKED | MF_BYCOMMAND);
  677.  
  678.         CheckMenuItem(hMenu, uID, MF_CHECKED | MF_BYCOMMAND);
  679.         m_pTB->Check(uID, TRUE);
  680.         }
  681.  
  682.     return;
  683.     }
  684.