home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / palette.zip / PALETTE.C next >
Text File  |  1998-04-20  |  42KB  |  1,012 lines

  1. /*+--------------------------------------------------------------------------+*/
  2. /*|                                                                          |*/
  3. /*| PROGRAM NAME: PALETTE                                                    |*/
  4. /*| -------------                                                            |*/
  5. /*|  A PM program demonstrating vector fonts, palette manager APIs, and IPF  |*/
  6. /*|  help.                                                                   |*/
  7. /*|                                                                          |*/
  8. /*| COPYRIGHT:                                                               |*/
  9. /*| ----------                                                               |*/
  10. /*|  Copyright (C) International Business Machines Corp., 1992, 1996         |*/
  11. /*|                                                                          |*/
  12. /*| DISCLAIMER OF WARRANTIES:                                                |*/
  13. /*| -------------------------                                                |*/
  14. /*|  The following [enclosed] code is sample code created by IBM Corporation.|*/
  15. /*|  This sample code is not part of any standard IBM product and is provided|*/
  16. /*|  to you solely for the purpose of assisting you in the development of    |*/
  17. /*|  your applications.  The code is provided "AS IS", without warranty of   |*/
  18. /*|  any kind.  IBM shall not be liable for any damages arising out of your  |*/
  19. /*|  use of the sample code, even if they have been advised of the           |*/
  20. /*|  possibility of such damages.                                            |*/
  21. /*|                                                                          |*/
  22. /*| REVISION LEVEL: 1.0                                                      |*/
  23. /*| ---------------                                                          |*/
  24. /*|                                                                          |*/
  25. /*| WHAT THIS PROGRAM DOES:                                                  |*/
  26. /*| -----------------------                                                  |*/
  27. /*|  This program displays a standard window and then draws the IBM logo     |*/
  28. /*|  in the window.  The logo is done using a vector font.  Then a palette   |*/
  29. /*|  is created and rotated in another thread.                               |*/
  30. /*|                                                                          |*/
  31. /*| WHAT THIS PROGRAM DEMONSTRATES:                                          |*/
  32. /*| -------------------------------                                          |*/
  33. /*|  This program demonstrates how to create and display a standard window,  |*/
  34. /*|  use switched menus, use a second thread for drawing, modify a palette   |*/
  35. /*|  using some basic GPI calls, and display vectored fonts.                 |*/
  36. /*|                                                                          |*/
  37. /*| APIs CALLED:                                                             |*/
  38. /*| ------------                                                             |*/
  39. /*|    WinInitialize                                                         |*/
  40. /*|    WinCreateMsgQueue                                                     |*/
  41. /*|    WinRegisterClass                                                      |*/
  42. /*|    WinCreateHelpInstance                                                 |*/
  43. /*|    WinDestroyHelpInstance                                                |*/
  44. /*|    WinCreateStdWindow                                                    |*/
  45. /*|    WinGetLastError                                                       |*/
  46. /*|    WinShowWindow                                                         |*/
  47. /*|    WinAssociateHelpInstance                                              |*/
  48. /*|    WinGetMsg                                                             |*/
  49. /*|    WinDispatchMsg                                                        |*/
  50. /*|    WinReleasePS                                                          |*/
  51. /*|    WinDestroyHelpInstance                                                |*/
  52. /*|    WinDestroyWindow                                                      |*/
  53. /*|    WinDestroyMsgQueue                                                    |*/
  54. /*|    WinTerminate                                                          |*/
  55. /*|    WinRequestMutexSem                                                    |*/
  56. /*|    WinRealizePalette                                                     |*/
  57. /*|    DosReleaseMutexSem                                                    |*/
  58. /*|    DosCreateMutexSem                                                     |*/
  59. /*|    WinOpenWindowDC                                                       |*/
  60. /*|    GpiCreatePS                                                           |*/
  61. /*|    DevQueryCaps                                                          |*/
  62. /*|    DosCreateThread                                                       |*/
  63. /*|    WinQueryWindowRect                                                    |*/
  64. /*|    WinPostMsg                                                            |*/
  65. /*|    WinWindowFromID                                                       |*/
  66. /*|    WinSetMenuItemText                                                    |*/
  67. /*|    WinInvalidateRect                                                     |*/
  68. /*|    WinDlgBox                                                             |*/
  69. /*|    WinSendMsg                                                            |*/
  70. /*|    WinBeginPaint                                                         |*/
  71. /*|    WinFillRect                                                           |*/
  72. /*|    GpiQueryFonts                                                         |*/
  73. /*|    GpiCreateLogFont                                                      |*/
  74. /*|    GpiSetCharSet                                                         |*/
  75. /*|    GpiSetCharBox                                                         |*/
  76. /*|    GpiQueryTextBox                                                       |*/
  77. /*|    GpiBeginPath                                                          |*/
  78. /*|    GpiMove                                                               |*/
  79. /*|    GpiCharString                                                         |*/
  80. /*|    GpiEndPath                                                            |*/
  81. /*|    GpiSetClipPath                                                        |*/
  82. /*|    WinEndPaint                                                           |*/
  83. /*|    WinDefWindowProc                                                      |*/
  84. /*|    WinDismissDlg                                                         |*/
  85. /*|    WinDefDlgProc                                                         |*/
  86. /*|    GpiCreatePalette                                                      |*/
  87. /*|    GpiSelectPalette                                                      |*/
  88. /*|    GpiSetColor                                                           |*/
  89. /*|    GpiLine                                                               |*/
  90. /*|    DosSleep                                                              |*/
  91. /*|    GpiAnimatePalette                                                     |*/
  92. /*|    GpiDeletePalette                                                      |*/
  93. /*|    DosExit                                                               |*/
  94. /*|    WinAlarm                                                              |*/
  95. /*|    WinMessageBox                                                         |*/
  96. /*|                                                                          |*/
  97. /*|                                                                          |*/
  98. /*| WHAT YOU NEED TO COMPILE THIS PROGRAM:                                   |*/
  99. /*| --------------------------------------                                   |*/
  100. /*|                                                                          |*/
  101. /*|  REQUIRED FILES:                                                         |*/
  102. /*|  ---------------                                                         |*/
  103. /*|                                                                          |*/
  104. /*|    PALETTE.C      - Source code                                          |*/
  105. /*|    PALETTE.MAK    - Make file for this program                           |*/
  106. /*|    PALETTE.DEP    - Dependency file for this program                     |*/
  107. /*|    PALETTE.DEF    - Module definition file                               |*/
  108. /*|    PALETTE.H      - Application header file                              |*/
  109. /*|    PALETTE.ICO    - Icon file                                            |*/
  110. /*|    PALETTE.RC     - Resource file                                        |*/
  111. /*|    PALETTE.IPF    - Documentation file for this program                  |*/
  112. /*|    PALETTE.DLG    - Dialog file                                          |*/
  113. /*|                                                                          |*/
  114. /*|    OS2.H          - Presentation Manager include file                    |*/
  115. /*|    STDLIB.H       - Standard library function declarations               |*/
  116. /*|    ...                                                                   |*/
  117. /*|                                                                          |*/
  118. /*|  REQUIRED LIBRARIES:                                                     |*/
  119. /*|  -------------------                                                     |*/
  120. /*|                                                                          |*/
  121. /*|    OS2386.LIB     - OS/2 API Library                                     |*/
  122. /*|                                                                          |*/
  123. /*|  REQUIRED PROGRAMS:                                                      |*/
  124. /*|  ------------------                                                      |*/
  125. /*|                                                                          |*/
  126. /*|    IBM C Set/2 Compiler (icc.exe    )                                    |*/
  127. /*|    IBM Linker           (ilink.exe  )                                    |*/
  128. /*|    Resource Compiler    (rc.exe     )                                    |*/
  129. /*|    Help Compiler        (ipfc.exe   )                                    |*/
  130. /*|                                                                          |*/
  131. /*+--------------------------------------------------------------------------+*/
  132.  
  133. /*+--------------------------------------------------------------------------+*/
  134. /*| System and library header files.                                         |*/
  135. /*+--------------------------------------------------------------------------+*/
  136.  
  137. #define INCL_WINWINDOWMGR
  138. #define INCL_WINMESSAGEMGR
  139. #define INCL_WINHELP
  140. #define INCL_WINFRAMEMGR
  141. #define INCL_WINERRORS
  142. #define INCL_WINPALETTE
  143. #define INCL_GPICONTROL
  144. #define INCL_WINMENUS
  145. #define INCL_WINDIALOGS
  146. #define INCL_GPILCIDS
  147. #define INCL_GPIPRIMITIVES
  148. #define INCL_GPIPATHS
  149. #define INCL_GPILOGCOLORTABLE
  150. #define INCL_DOSSEMAPHORES
  151. #define INCL_DOSPROCESS
  152. #define INCL_DEV
  153. #include <os2.h>
  154.  
  155. #include <string.h>
  156. #include <stdlib.h>
  157. #include <stdio.h>
  158. #include <stdarg.h>
  159. #include "palette.h"
  160.  
  161. /*
  162.  * Globals
  163.  */
  164.  
  165. HAB     hab;
  166. HPAL    hPal = NULLHANDLE;
  167. HRGN    hrgn = NULLHANDLE;
  168. HDC     hdc =  NULLHANDLE;
  169. HMQ     hmqPalette;
  170. HWND    hwndPalette;
  171. HWND    hwndPaletteFrame;
  172. CHAR    szClassName[]   = "Palette";
  173. CHAR    szMessage[]     = "Palette Manager Sample";
  174.  
  175.  
  176. /*
  177.  * Status Flags For the options menu
  178.  */
  179.  
  180. #define SLOW_VALUE    100LU
  181. #define MEDIUM_VALUE  10LU                  /* Set speed constants            */
  182. #define FAST_VALUE     0LU
  183.  
  184. BOOL  speedSlow      = FALSE;
  185. BOOL  speedMedium    = TRUE;                /* Initial Speed                  */
  186. BOOL  speedFast      = FALSE;
  187. ULONG animationSpeed = MEDIUM_VALUE;
  188.  
  189. BOOL  logoIBM        = FALSE;               /* Initial Text                   */
  190. BOOL  logoOS2        = TRUE;
  191.  
  192. /*
  193.  * Palette Drawing Thread Globals
  194.  */
  195.  
  196. static LONG    lMessageCount = 0L;
  197. static BOOL    fPaletteCaps = TRUE;    /* Palette Manager capabilities?  */
  198. static SHORT   cxClient, cyClient;     /* client window X and Y size     */
  199. static USHORT  threadRun = FALSE;      /* non-zero means draw lines      */
  200. static HMTX    hmtxPS    = NULLHANDLE; /* PS access semaphore            */
  201. static HPS     hpsBuffer = NULLHANDLE; /* Pres. space for memory buffer  */
  202.  
  203. #define PAL_COUNT 128L       /* For the purposes of this example we will be   */
  204. ULONG alTable[PAL_COUNT];    /*        using 128 palette entries.             */
  205.  
  206. #define MSG_BOX_ID     256                  /* error message box id           */
  207.  
  208.  
  209. /*
  210.  * Required IPF Structure Declarations
  211.  */
  212.  
  213. HELPINIT hmiHelpData;                       /* Help initialization structure  */
  214. HWND     hwndHelpInstance;                  /* Handle to Help window          */
  215.  
  216.  
  217. /*
  218.  * Main routine...initializes window and message queue
  219.  */
  220. int main( )
  221. {
  222.    QMSG qmsg;
  223.    ULONG ctldata;
  224.  
  225.    /*
  226.     * Create your hab, hmq, and register a class.
  227.     */
  228.  
  229.    hab = WinInitialize(0LU);
  230.  
  231.    hmqPalette = WinCreateMsgQueue(hab, 0L);
  232.  
  233.    WinRegisterClass( hab,
  234.                      (PSZ)szClassName,
  235.                      (PFNWP)PaletteWndProc,
  236.                      CS_SIZEREDRAW,
  237.                      0LU);
  238.  
  239.    /*+-----------------------------------------+*/
  240.    /*| IPF Initialization Structure            |*/
  241.    /*+-----------------------------------------+*/
  242.  
  243.    hmiHelpData.cb                       = sizeof(HELPINIT);
  244.    hmiHelpData.ulReturnCode             = 0LU;
  245.    hmiHelpData.pszTutorialName          = (PSZ)NULL;
  246.    hmiHelpData.phtHelpTable  = (PHELPTABLE)MAKELONG(MAIN_HELPTABLE, 0xFFFF);
  247.    hmiHelpData.hmodAccelActionBarModule = NULLHANDLE;
  248.    hmiHelpData.idAccelTable             = 0;
  249.    hmiHelpData.idActionBar              = 0;
  250.    hmiHelpData.pszHelpWindowTitle       = "Palette Help";
  251.    hmiHelpData.hmodHelpTableModule      = NULLHANDLE;
  252.    hmiHelpData.fShowPanelId             = CMIC_HIDE_PANEL_ID;
  253.    hmiHelpData.pszHelpLibraryName       = "PALETTE.HLP";
  254.  
  255.  
  256.    /*+------------------------------------------+*/
  257.    /*| Create Instance of IPF                   |*/
  258.    /*|                                          |*/
  259.    /*| pass Anchor Block handle and address of  |*/
  260.    /*| IPF initialization structure, and check  |*/
  261.    /*| that creation was successful.            |*/
  262.    /*+------------------------------------------+*/
  263.  
  264.    if((hwndHelpInstance = WinCreateHelpInstance(hab, &hmiHelpData))==NULLHANDLE)
  265.       mprintf("Help Creation Error");
  266.  
  267.    else if (hmiHelpData.ulReturnCode)
  268.    {
  269.       mprintf("Help ended because of error %ld", hmiHelpData.ulReturnCode);
  270.       WinDestroyHelpInstance(hwndHelpInstance);
  271.    }
  272.  
  273.  
  274.    /*
  275.     * Create a standard pm window and check
  276.     * that creation was successful.
  277.     */
  278.    ctldata = FCF_STANDARD;
  279.  
  280.    hwndPaletteFrame = WinCreateStdWindow( HWND_DESKTOP,
  281.                                           WS_VISIBLE,
  282.                                           &ctldata,
  283.                                           szClassName,
  284.                                           szMessage,
  285.                                           0LU,
  286.                                           NULLHANDLE,
  287.                                           ID_WINDOW,
  288.                                           &hwndPalette );
  289.    if (hwndPaletteFrame == NULLHANDLE)
  290.    {
  291.       mprintf("WinCreateStdWindow error: 0x%04x", WinGetLastError(hab));
  292.       return 0;
  293.    }
  294.    WinShowWindow( hwndPaletteFrame, TRUE );
  295.  
  296.  
  297.    /*+-----------------------------------------+*/
  298.    /*| Associate Instance of IPF               |*/
  299.    /*|                                         |*/
  300.    /*| pass handle to Help Window and handle   |*/
  301.    /*| to frame window with which Help is      |*/
  302.    /*| to be associated.                       |*/
  303.    /*+-----------------------------------------+*/
  304.  
  305.    if (hwndHelpInstance)
  306.       WinAssociateHelpInstance(hwndHelpInstance, hwndPaletteFrame);
  307.  
  308.  
  309.    /*
  310.     * Poll messages from event queue
  311.     */
  312.    while( WinGetMsg( hab, (PQMSG)&qmsg, (HWND)NULLHANDLE, 0LU, 0LU ) )
  313.       WinDispatchMsg( hab, (PQMSG)&qmsg );
  314.  
  315.  
  316.    /*
  317.     * Clean up
  318.     */
  319.  
  320.    if(hpsBuffer)
  321.       WinReleasePS( hpsBuffer );
  322.    if(hwndHelpInstance)
  323.       WinDestroyHelpInstance( hwndHelpInstance );
  324.    if(hwndPaletteFrame)
  325.       WinDestroyWindow( hwndPaletteFrame );
  326.    if(hmqPalette)
  327.       WinDestroyMsgQueue( hmqPalette );
  328.    WinTerminate( hab );
  329.    return 0;
  330. } /*  end of main()  */
  331.  
  332.  
  333. /*
  334.  * This routine processes WM_COMMAND, WM_PAINT.  It passes
  335.  * everything else to the Default Window Procedure.
  336.  */
  337. MRESULT PaletteWndProc(
  338.    HWND   hwnd,
  339.    ULONG  msg,
  340.    MPARAM mp1,
  341.    MPARAM mp2 )
  342. {
  343.    static  RECTL  rctlClient, rctlSize;       /* client rectl's               */
  344.    TID     tidDrawing;                        /* drawing thread identifier    */
  345.    ULONG   cclr;
  346.    HPS     hps;
  347.    HWND    hwndMenu;                          /* Handle for the Menu bar      */
  348.  
  349.    switch (msg)
  350.    {
  351.  
  352.       /*+-----------------------------------------------------------------+*/
  353.       /*| In this example, the WinRealizePalette call is issued in        |*/
  354.       /*| response to a WM_REALIZEPALETTE. This ensures that the palette  |*/
  355.       /*| is appropriately realized for all drawing operations.           |*/
  356.       /*+-----------------------------------------------------------------+*/
  357.  
  358.    case WM_REALIZEPALETTE:
  359.          WinRequestMutexSem( hmtxPS, SEM_INDEFINITE_WAIT );
  360.          WinRealizePalette(hwnd, hpsBuffer, &cclr);
  361.          DosReleaseMutexSem( hmtxPS );
  362.       break;
  363.  
  364.  
  365.    case WM_CREATE:
  366.    {
  367.       SIZEL sizl = { 0L, 0L };
  368.       LONG  alCaps[CAPS_PHYS_COLORS];
  369.       LONG lCount = CAPS_PHYS_COLORS;
  370.       LONG lStart = CAPS_FAMILY;
  371.  
  372.       /*+-----------------------------------------------------------------+*/
  373.       /*| The client window is being created.  Create the semaphore to    |*/
  374.       /*| control access to the presentation space.  Then create the      |*/
  375.       /*| thread that will draw the lines.                                |*/
  376.       /*+-----------------------------------------------------------------+*/
  377.  
  378.       DosCreateMutexSem( (PSZ)NULL, &hmtxPS, 0UL, FALSE );
  379.  
  380.       hdc = WinOpenWindowDC(hwnd);
  381.  
  382.       /*+-----------------------------------------------------------------+*/
  383.       /*| Create a non-cached presentation space.  We will not release    |*/
  384.       /*| this PS, as we will be selecting a Palette to this PS and then  |*/
  385.       /*| animating the palette.  Upon releasing a PS the palette is no   |*/
  386.       /*| longer selected for obvious reasons.                            |*/
  387.       /*+-----------------------------------------------------------------+*/
  388.  
  389.       hpsBuffer = GpiCreatePS( hab,
  390.                                hdc,
  391.                                &sizl,
  392.                                PU_PELS | GPIF_DEFAULT |
  393.                                GPIT_MICRO | GPIA_ASSOC );
  394.  
  395.       DevQueryCaps( hdc, lStart, lCount, alCaps );
  396.       fPaletteCaps = alCaps[CAPS_ADDITIONAL_GRAPHICS] & CAPS_PALETTE_MANAGER;
  397.  
  398.       hwndPalette = hwnd;
  399.       if ( PaletteInit() )
  400.          break;
  401.  
  402.       threadRun = TRUE;
  403.  
  404.       DosCreateThread( &tidDrawing,
  405.                        (PFNTHREAD) DrawingThread,
  406.                        0UL,
  407.                        0UL,
  408.                        8192UL );
  409.  
  410.       break;
  411.    }
  412.  
  413.    case WM_SIZE:
  414.       /*+-----------------------------------------------------------------+*/
  415.       /*| Window is being resized so get new client window size and       |*/
  416.       /*| recompute the end points for the lines.                         |*/
  417.       /*+-----------------------------------------------------------------+*/
  418.  
  419.       WinQueryWindowRect(hwnd,&rctlSize);
  420.  
  421.       cxClient = SHORT1FROMMP( mp2 );       /* Get new client window size     */
  422.       cyClient = SHORT2FROMMP( mp2 );
  423.       break;
  424.  
  425.    case WM_SHOW:
  426.       if ( (lMessageCount == 0L) && !fPaletteCaps )
  427.       {
  428.          lMessageCount +=
  429.          mprintf("Palette animation is not supported on this display.");
  430.       }
  431.       break;
  432.  
  433.    case WM_INITMENU:
  434.       switch (LOUSHORT(mp1))
  435.       {
  436.          case IDM_OPTIONS:
  437.             hwndMenu = WinWindowFromID( hwndPaletteFrame, /* Get Menu Handle  */
  438.                                         FID_MENU );
  439.             WinEnableMenuItem(hwndMenu, IDM_SPEED,     fPaletteCaps);
  440.             WinEnableMenuItem(hwndMenu, IDM_STARTSTOP, fPaletteCaps);
  441.             break;
  442.  
  443.          case IDM_SPEED:
  444.             SetPulldownState(hwndPaletteFrame, IDM_SPEEDSLOW  , speedSlow);
  445.             SetPulldownState(hwndPaletteFrame, IDM_SPEEDMEDIUM, speedMedium);
  446.             SetPulldownState(hwndPaletteFrame, IDM_SPEEDFAST  , speedFast);
  447.             break;
  448.  
  449.          case IDM_LOGO:
  450.             SetPulldownState(hwndPaletteFrame, IDM_LOGOIBM    , logoIBM);
  451.             SetPulldownState(hwndPaletteFrame, IDM_LOGOOS2    , logoOS2);
  452.             break;
  453.       }
  454.       break;
  455.  
  456.  
  457.    case WM_COMMAND:
  458.       switch (LOUSHORT(mp1))
  459.       {
  460.          case IDM_EXIT:
  461.             WinPostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
  462.             break;
  463.  
  464.          case IDM_STARTSTOP:
  465.             hwndMenu = WinWindowFromID( hwndPaletteFrame, /* Get Menu Handle  */
  466.                                         FID_MENU );
  467.  
  468.             if ( speedSlow || speedMedium || speedFast  ) /* If running->stop */
  469.             {
  470.                speedSlow   = FALSE;
  471.                speedMedium = FALSE;                       /* Set no speed     */
  472.                speedFast   = FALSE;
  473.  
  474.                WinSetMenuItemText( hwndMenu,              /* Change Menu Text */
  475.                                    IDM_STARTSTOP,         /* ID# for old text */
  476.                                    "Start" );             /* 'Change To' text */
  477.             }
  478.             else                                     /* If stopped then start */
  479.             {
  480.                if ( animationSpeed == SLOW_VALUE )
  481.                     speedSlow   = TRUE;
  482.                if ( animationSpeed == MEDIUM_VALUE )      /* Reset proper flag */
  483.                     speedMedium = TRUE;
  484.                if ( animationSpeed == FAST_VALUE )
  485.                     speedFast   = TRUE;
  486.  
  487.                WinSetMenuItemText( hwndMenu,              /* Change Menu Text */
  488.                                    IDM_STARTSTOP,         /* ID# for old text */
  489.                                    "Stop" );              /* 'Change To' text */
  490.             }
  491.             break;
  492.  
  493.  
  494.          case IDM_SPEEDSLOW:
  495.             speedSlow   = TRUE;
  496.             speedMedium = FALSE;
  497.             speedFast   = FALSE;
  498.             animationSpeed = SLOW_VALUE;
  499.             break;
  500.  
  501.          case IDM_SPEEDMEDIUM:
  502.             speedSlow   = FALSE;
  503.             speedMedium = TRUE;
  504.             speedFast   = FALSE;
  505.             animationSpeed = MEDIUM_VALUE;
  506.             break;
  507.  
  508.          case IDM_SPEEDFAST:
  509.             speedSlow   = FALSE;
  510.             speedMedium = FALSE;
  511.             speedFast   = TRUE;
  512.             animationSpeed = FAST_VALUE;
  513.             break;
  514.  
  515.          case IDM_LOGOIBM:
  516.             logoIBM = TRUE;
  517.             logoOS2 = FALSE;
  518.             WinInvalidateRect(hwnd, &rctlSize, FALSE);
  519.             break;
  520.  
  521.          case IDM_LOGOOS2:
  522.             logoIBM = FALSE;
  523.             logoOS2 = TRUE;
  524.             WinInvalidateRect(hwnd, &rctlSize, FALSE);
  525.             break;
  526.  
  527.          case IDM_HELPABOUT:               /* DISPLAY HELP ABOUT DIALOG       */
  528.             WinDlgBox(HWND_DESKTOP,        /* MAKE THE DESKTOP THE PARENT     */
  529.                       hwnd,                /* OWNED BY THE CLIENT WINDOW      */
  530.                       (PFNWP) AboutDlgProc,/* ADDRESS OF THE DIALOG PROCEDURE */
  531.                       NULLHANDLE,          /* MODULE HANDLE                   */
  532.                       IDD_PRODUCTINFO,     /* DIALOG IDENTIFIER IN RESOURCE   */
  533.                       (PVOID)NULL);        /* INITIALIZATION DATA             */
  534.  
  535.             WinInvalidateRect(hwnd, &rctlSize, FALSE);      /* Refresh Window */
  536.             break;
  537.  
  538.          case IDM_HELPFORHELP:
  539.             if (hwndHelpInstance)
  540.             {
  541.                WinSendMsg( hwndHelpInstance, HM_DISPLAY_HELP, MPVOID, MPVOID);
  542.             }
  543.            break;
  544.  
  545.          case IDM_HELP_INDEX:
  546.             if (hwndHelpInstance)
  547.             {
  548.                WinSendMsg(hwndHelpInstance, HM_HELP_CONTENTS, MPVOID, MPVOID);
  549.             }
  550.             break;
  551.  
  552.          case IDM_EXTENDED_HELP:
  553.             if (hwndHelpInstance)
  554.             {
  555.                WinSendMsg(hwndHelpInstance, HM_DISPLAY_HELP,
  556.                MPFROMSHORT(IDM_EXTENDED_HELP), HM_RESOURCEID);
  557.             }
  558.             break;
  559.  
  560.          case IDM_KEYS_HELP:
  561.             if (hwndHelpInstance)
  562.             {
  563.                WinSendMsg( hwndHelpInstance,
  564.                            HM_DISPLAY_HELP,
  565.                            MPFROM2SHORT(IDM_KEYS_HELP, 0),
  566.                            MPFROMSHORT(HM_RESOURCEID));
  567.             }
  568.             break;
  569.  
  570.          default:
  571.             break;
  572.  
  573.       } /* end of switch within case WM_COMMAND */
  574.       break;
  575.  
  576.    case WM_PAINT:
  577.  
  578.       /*+------------------------------------------------------+*/
  579.       /*| Since there will be two threads painting on the same |*/
  580.       /*| frame we will use a semaphore to resolve contention. |*/
  581.       /*+------------------------------------------------------+*/
  582.  
  583.       WinRequestMutexSem( hmtxPS, SEM_INDEFINITE_WAIT );
  584.  
  585.       /*
  586.        * Get a cached micro presentation space.
  587.        */
  588.       hps = WinBeginPaint( hwnd, NULLHANDLE, &rctlClient );
  589.  
  590.       /*
  591.        * Fill the rectangle with the backgound color.
  592.        */
  593.       WinFillRect( hps, &rctlClient, CLR_BLACK );
  594.  
  595.       /*+-------------------------------------------------+*/
  596.       /*| The following code segment loads a vector font  |*/
  597.       /*| scales it to fit in the window and draws it     |*/
  598.       /*| vertically and horizontally centered.           |*/
  599.       /*+-------------------------------------------------+*/
  600.       {
  601.          POINTL       ptl;
  602.          SIZEF        sizfx;
  603.          FATTRS       fattrs;
  604.          LONG         cFonts, lTemp = 0L;
  605.          PFONTMETRICS pfm;
  606.          LONG         lcid = 1L;
  607.          CHAR         fontName[25],outText[25];
  608.          USHORT       codePage;
  609.          ULONG        min = (cxClient<cyClient) ? cxClient : cyClient;
  610.  
  611.          min /= 3;
  612.  
  613.          if(logoIBM)
  614.          {
  615.             strcpy(fontName,"Symbol Set");
  616.             codePage = 65400;
  617.             strcpy(outText,"Ä");
  618.          }
  619.          else
  620.          {
  621.             /*+-------------------------------------------+*/
  622.             /*| Define "Helvetica Bold" vector font,      |*/
  623.             /*| "Courier Bold" and "Times New Roman Bold" |*/
  624.             /*| are examples of other vector fonts.       |*/
  625.             /*+-------------------------------------------+*/
  626.             strcpy(fontName,"Helvetica Bold");
  627.             codePage = 850;
  628.             strcpy(outText,"OS/2");
  629.          }
  630.  
  631.          cFonts = GpiQueryFonts(hpsBuffer, QF_PUBLIC, fontName, &lTemp,
  632.              (LONG) sizeof(FONTMETRICS), (PFONTMETRICS)NULL);
  633.  
  634.          if(cFonts > 0L)
  635.          {
  636.             pfm = malloc(sizeof(FONTMETRICS) * cFonts);
  637.             GpiQueryFonts(hpsBuffer, QF_PUBLIC, fontName, &cFonts,
  638.                           (LONG) sizeof(FONTMETRICS), pfm);
  639.             fattrs.lMatch          = pfm[0].lMatch;
  640.             strcpy(fattrs.szFacename, pfm[0].szFacename);
  641.          }
  642.          else
  643.          {
  644.             fattrs.lMatch = 0L;
  645.             strcpy(fattrs.szFacename, "");
  646.          }
  647.  
  648.          fattrs.usRecordLength  = sizeof(FATTRS);
  649.          fattrs.fsSelection     = FATTR_SEL_OUTLINE;
  650.          fattrs.idRegistry      = 0;
  651.          fattrs.usCodePage      = codePage;
  652.          fattrs.lMaxBaselineExt = 0L;
  653.          fattrs.lAveCharWidth   = 0L;
  654.          fattrs.fsType          = 0;
  655.          fattrs.fsFontUse       = FATTR_FONTUSE_OUTLINE;
  656.  
  657.          GpiCreateLogFont(hpsBuffer, (PSTR8)NULL, lcid, &fattrs);
  658.          GpiSetCharSet(hpsBuffer, lcid);
  659.  
  660.          sizfx.cx = MAKEFIXED(min, 0);
  661.          sizfx.cy = MAKEFIXED(min, 0);
  662.          GpiSetCharBox(hpsBuffer, &sizfx);
  663.  
  664.          /*+------------------------------------------------+*/
  665.          /*| CALCULATE THE POINT TO START THE CENTERED TEXT |*/
  666.          /*+------------------------------------------------+*/
  667.          {
  668.             POINTL aptl[TXTBOX_COUNT];
  669.  
  670.             GpiQueryTextBox(hpsBuffer,
  671.                             strlen(outText),
  672.                             outText,
  673.                             TXTBOX_COUNT,      /* return maximum information  */
  674.                             aptl);             /* array of coordinates points */
  675.                                                /* in world coordinates.       */
  676.  
  677.  
  678.             ptl.x = (cxClient - aptl[TXTBOX_TOPRIGHT].x) / 2;
  679.             ptl.y = (cyClient - aptl[TXTBOX_TOPRIGHT].y) / 2;
  680.  
  681.          }
  682.  
  683.  
  684.          /*+-------------------------------------------+*/
  685.          /*| Now that we have our vector font and      |*/
  686.          /*| location to place on the screen, let's    |*/
  687.          /*| create a Path using the outline font.     |*/
  688.          /*+-------------------------------------------+*/
  689.  
  690.          GpiBeginPath(hpsBuffer,1L);
  691.  
  692.          GpiMove(hpsBuffer,&ptl);
  693.          GpiCharString(hpsBuffer, strlen(outText), outText);
  694.  
  695.          GpiEndPath(hpsBuffer);
  696.  
  697.          /*+-----------------------------------------+*/
  698.          /*| Next let's erase the current clip path  |*/
  699.          /*| and assign the above outline font path  |*/
  700.          /*| as a clip path to the current hps.      |*/
  701.          /*+-----------------------------------------+*/
  702.  
  703.          GpiSetClipPath(hpsBuffer,
  704.                 0L,
  705.                 FPATH_ALTERNATE);
  706.  
  707.          GpiSetClipPath(hpsBuffer,
  708.                 1L,
  709.                 FPATH_ALTERNATE | SCP_AND);
  710.  
  711.  
  712.          /*+-------------------------------------------+*/
  713.          /*| Lastly draw a series of lines which will  |*/
  714.          /*| be clipped to attached clip path.         |*/
  715.          /*| *Draw on the Char Box                     |*/
  716.          /*+-------------------------------------------+*/
  717.  
  718.          DrawPaletteLines(rctlSize,
  719.                           PAL_COUNT,
  720.                           hpsBuffer);
  721.  
  722.          if(pfm)
  723.             free(pfm);
  724.       }
  725.  
  726.  
  727.       /*
  728.        * Release the cached micro presentation space.
  729.        */
  730.       WinEndPaint( hps );
  731.  
  732.       /*+------------------------------------------------------+*/
  733.       /*| Release the semaphore, thereby allowing the other    |*/
  734.       /*| thread to paint.                                     |*/
  735.       /*+------------------------------------------------------+*/
  736.  
  737.       DosReleaseMutexSem( hmtxPS );
  738.       break;
  739.  
  740.    default:
  741.       return WinDefWindowProc(hwnd, msg, mp1, mp2);
  742.  
  743.    }
  744.    return MRFROMLONG(0L);
  745. }   /*  end of PaletteWndProc()  */
  746.  
  747.  
  748.  
  749. /*+--------------------------------------------------------------------------+*/
  750. /*| AboutDlgProc - Help About Dialog Procedure                               |*/
  751. /*+--------------------------------------------------------------------------+*/
  752. MRESULT AboutDlgProc( HWND hwndDlg, ULONG msg, MPARAM mp1, MPARAM mp2)
  753. {
  754.    switch( msg )
  755.    {
  756.    case WM_COMMAND:          /* DISMISS DIALOG */
  757.       WinDismissDlg( hwndDlg, TRUE );
  758.       break;
  759.  
  760.    default:
  761.       return (WinDefDlgProc( hwndDlg, msg, mp1, mp2 ));
  762.    }
  763.    return MRFROMLONG(0L);
  764. }  /*  end of AboutDlgProc()  */
  765.  
  766.  
  767.  
  768. /*+--------------------------------------------------------------------------+*/
  769. /*| PaletteInit - Initializes the palette in the client window.              |*/
  770. /*+--------------------------------------------------------------------------+*/
  771. LONG PaletteInit()
  772. {
  773.    LONG    i;
  774.    LONG    ret = 0L;
  775.    ULONG   cclr;
  776.  
  777.    WinRequestMutexSem( hmtxPS, SEM_INDEFINITE_WAIT );
  778.  
  779.    /*+--------------------------------------------------------------+*/
  780.    /*| Create entry with shades of blue if animation is supported,  |*/
  781.    /*| solid blue otherwise.                                        |*/
  782.    /*+--------------------------------------------------------------+*/
  783.  
  784.    for (i = 0L; (ULONG)i < PAL_COUNT; i++)
  785.    {
  786.       LONG index = 222L;    /*  use if no animation  */
  787.  
  788.       /*+----------------------------------------------------+*/
  789.       /*| INDEX = 128 POINTS EVENLY SPACED BETWEEN 1 AND 255 |*/
  790.       /*+----------------------------------------------------+*/
  791.       if(fPaletteCaps)
  792.          index = ((float) (i + 1L) * 255.0) / (float) PAL_COUNT;
  793.  
  794.       alTable[i] = PC_RESERVED * 16777216 + LONGFromRGB(0, 0, index); /* BLUE */
  795.  
  796.    }
  797.  
  798.    hPal = GpiCreatePalette( hab,
  799.                             (ULONG) LCOL_PURECOLOR,
  800.                             (ULONG) LCOLF_CONSECRGB,
  801.                             PAL_COUNT,
  802.                             alTable );
  803.  
  804.    if( hPal == NULLHANDLE || hPal == GPI_ERROR)
  805.    {
  806.       DosReleaseMutexSem( hmtxPS );
  807.       mprintf("GpiCreatePalette Error 0x%04x",ret = WinGetLastError(hab));
  808.    }
  809.  
  810.    else if(GpiSelectPalette(hpsBuffer, hPal ) == PAL_ERROR)
  811.    {
  812.       DosReleaseMutexSem( hmtxPS );
  813.       mprintf("GpiSelectPalette Error 0x%04x", ret = WinGetLastError(hab));
  814.    }
  815.  
  816.    else if( WinRealizePalette(hwndPalette,hpsBuffer,&cclr) == PAL_ERROR)
  817.    {
  818.       DosReleaseMutexSem( hmtxPS );
  819.       mprintf("WinRealizePalette Error 0x%04x", ret = WinGetLastError(hab));
  820.    }
  821.  
  822.    else
  823.    {
  824.       DosReleaseMutexSem( hmtxPS );
  825.    }
  826.  
  827.    return ret;
  828. }  /*  end of PaletteInit()  */
  829.  
  830.  
  831. /*+--------------------------------------------------------------------------+*/
  832. /*| DrawPaletteLines - Procedure that draws the lines in the passed box.     |*/
  833. /*+--------------------------------------------------------------------------+*/
  834. VOID DrawPaletteLines(RECTL  rctl,
  835.                       ULONG ulPalCount,
  836.                       HPS hps)
  837. {
  838.    LONG  color = 0L;                 /* foreground (line) color      */
  839.    POINTL ptl1,ptl2;
  840.  
  841.    ptl1.x = rctl.xLeft;
  842.    ptl1.y = rctl.yTop;
  843.    ptl2.x = rctl.xLeft;
  844.    ptl2.y = rctl.yBottom;
  845.  
  846.    while(ptl1.x <= rctl.xRight)
  847.    {
  848.       if ( (ULONG) color >= ulPalCount )
  849.          color = 0L;
  850.       else
  851.          color++;                   /* Increment foreground color   */
  852.  
  853.       ptl1.x ++;
  854.       ptl2.x ++;
  855.  
  856.       GpiSetColor( hps, color );
  857.       GpiMove( hps, &ptl1 );         /* Move to start point          */
  858.       GpiLine( hps, &ptl2 );         /* Draw new line                */
  859.     }
  860. }  /*  end of DrawPaletteLines()  */
  861.  
  862.  
  863.  
  864. /*+--------------------------------------------------------------------------+*/
  865. /*| DrawingThread - Procedure that animates the palette in the client window.|*/
  866. /*+--------------------------------------------------------------------------+*/
  867. static void DrawingThread( ULONG ulThreadArg )
  868. {
  869.    int   i;
  870.  
  871.    HAB habThread2 = WinInitialize( 0LU );                  /* Anchor block handle for thread */ 
  872.    HAB hmqThread2 = WinCreateMsgQueue( habThread2, 0L );   /* Queue handle for thread        */ 
  873.  
  874.    while ( threadRun )
  875.    {
  876.       LONG temp;
  877.  
  878.  
  879. /*+--------------------------------------------------------------------------+*/
  880. /*|     The following if clause puts this thread to sleep as long as there   |*/
  881. /*| is no speed flag set, i.e. the animation is 'Stop'ed.                    |*/
  882. /*|     The else clause continues rotating the palette.                      |*/
  883. /*+--------------------------------------------------------------------------+*/
  884.       if (!speedSlow && !speedMedium && !speedFast )
  885.       {
  886.          DosSleep(500LU);
  887.       }
  888.       else
  889.       {
  890.          /*+-----------------------------------------------------------+*/
  891.          /*| Request PS semaphore so that main thread does NOT use it. |*/
  892.          /*+-----------------------------------------------------------+*/
  893.  
  894.          WinRequestMutexSem( hmtxPS, SEM_INDEFINITE_WAIT );
  895.  
  896.          temp = alTable[ 0 ];
  897.          for(i = 0; (ULONG) i < PAL_COUNT - 1; i++)
  898.          {
  899.             alTable[ i ] = alTable[ i + 1 ];
  900.          }
  901.          alTable[ PAL_COUNT - 1 ] = temp;
  902.  
  903.          GpiAnimatePalette( hPal,
  904.                             LCOLF_CONSECRGB,
  905.                             0LU,
  906.                             PAL_COUNT,
  907.                             alTable);
  908.  
  909.          /*+-----------------------+*/
  910.          /*| Release PS semaphore. |*/
  911.          /*+-----------------------+*/
  912.  
  913.          DosReleaseMutexSem( hmtxPS );
  914.  
  915.          /*+---------------------------------------------+*/
  916.          /* Surrender rest of timeslice to other threads. */
  917.          /* Never do a DosSleep(0) as this will not give  */
  918.          /* lower priority threads a time slice           */
  919.          /*+---------------------------------------------+*/
  920.  
  921.          if(animationSpeed) DosSleep( animationSpeed );
  922.       }
  923.    }
  924.  
  925.  
  926.    /*+----------------------------------------+*/
  927.    /*| Clean up and terminate drawing thread. |*/
  928.    /*+----------------------------------------+*/
  929.  
  930.    if(hPal)
  931.       GpiDeletePalette( hPal );
  932.    if(hmqThread2)
  933.       WinDestroyMsgQueue( hmqThread2 );
  934.    WinTerminate( habThread2 );
  935.    DosExit( EXIT_THREAD, 0LU );
  936. }     /*  end of DrawingThread()  */
  937.  
  938.  
  939.  
  940. /*+--------------------------------------------------------------------------+*/
  941. /*|                                                                          |*/
  942. /*| FUNCTION NAME: mprintf                                                   |*/
  943. /*| --------------                                                           |*/
  944. /*|  A PM function for displaying a message box with a printf type format.   |*/
  945. /*|                                                                          |*/
  946. /*| EXPECTED INPUT:                                                          |*/
  947. /*| ---------------                                                          |*/
  948. /*|  See the definition of printf.                                           |*/
  949. /*|                                                                          |*/
  950. /*| EXPECTED OUTPUT:                                                         |*/
  951. /*| ----------------                                                         |*/
  952. /*|  Message Box                                                             |*/
  953. /*|                                                                          |*/
  954. /*| NOTES                                                                    |*/
  955. /*| ----------------                                                         |*/
  956. /*|  One must be careful not to call this within a paint routine, because    |*/
  957. /*|  the closing of the message box will generate another paint message.     |*/
  958. /*|                                                                          |*/
  959. /*+--------------------------------------------------------------------------+*/
  960. LONG mprintf(PSZ format, ...)
  961. {
  962.    va_list pArg;
  963.    PSZ     buffer;
  964.    LONG    lCount;
  965.  
  966.    WinAlarm( HWND_DESKTOP, WA_ERROR );
  967.  
  968.    if(!(buffer = malloc(513)))
  969.       return 0L;
  970.  
  971.    va_start(pArg, format);
  972.  
  973.    lCount = vsprintf(buffer, format, pArg);
  974.  
  975.    WinMessageBox( HWND_DESKTOP,       /* parent window handle    */
  976.                   HWND_DESKTOP,       /* owner window handle     */
  977.                   buffer,             /* pointer to message text */
  978.                   szClassName,        /* pointer to title text   */
  979.                   MSG_BOX_ID,         /* message box identifier  */
  980.                   MB_OK | MB_ERROR ); /* message box style       */
  981.  
  982.    free(buffer);
  983.    
  984.    return lCount;
  985. }   /*  end of mprintf()  */
  986.  
  987.  
  988.  
  989. /*+--------------------------------------------------------------------------+*/
  990. /*|                                                                          |*/
  991. /*| FUNCTION NAME: SetPulldownState                                          |*/
  992. /*| --------------                                                           |*/
  993. /*|  A PM function for setting the check mark status of a menu item.         |*/
  994. /*|                                                                          |*/
  995. /*| EXPECTED INPUT:                                                          |*/
  996. /*| ---------------                                                          |*/
  997. /*|  Handle to the window containing the menu.                               |*/
  998. /*|  Item id within the menu to check.                                       |*/
  999. /*|  BOOL indicating state to set:  TRUE=CHECKED FALSE=UNCHECKED             |*/
  1000. /*|                                                                          |*/
  1001. /*| EXPECTED OUTPUT:                                                         |*/
  1002. /*| ----------------                                                         |*/
  1003. /*|  None                                                                    |*/
  1004. /*+--------------------------------------------------------------------------+*/
  1005. void SetPulldownState( HWND hwnd, USHORT item, BOOL state)
  1006. {
  1007.    WinCheckMenuItem(WinWindowFromID(hwnd, FID_MENU), item, state);
  1008. } /*  end of SetPulldownState()  */
  1009. /**************************  end of palette.c   *******************************/
  1010.  
  1011.  
  1012.