home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / bmp1.zip / BmpWnd.C < prev    next >
C/C++ Source or Header  |  1995-10-25  |  26KB  |  796 lines

  1. #pragma    title("View Bitmap  --  Version 1  --  (BmpWnd.C)")
  2. #pragma    subtitle("   Main Client Window - Interface Definitions")
  3.  
  4. #define    INCL_GPI           /* Include OS/2 PM GPI Interface    */
  5. #define    INCL_WIN           /* Include OS/2 PM Windows Interface    */
  6.  
  7. #include <malloc.h>
  8. #include <os2.h>
  9. #include <string.h>
  10.  
  11. #include "appdefs.h"
  12. #include "viewbmp.h"
  13.  
  14. /* This    module contains    routine    used to    handle the main    application    */
  15. /* window.                                */
  16.  
  17. /* Filename:   BmpWnd.C                            */
  18.  
  19. /*  Version:   1                            */
  20. /*  Created:   1995-07-05                        */
  21. /*  Revised:   1995-07-22                        */
  22.  
  23. /* Routines:   static VOID SizeBitmap(HWND hWnd);            */
  24. /*           static VOID SizeBitmapStack(HWND    hWnd);            */
  25. /*           MRESULT EXPENTRY    BitmapViewerWndProc(HWND hWnd,        */
  26. /*                            ULONG msg,        */
  27. /*                            MPARAM mp1,        */
  28. /*                            MPARAM mp2);    */
  29.  
  30.  
  31. /************************************************************************/
  32. /************************************************************************/
  33. /************************************************************************/
  34. /* DISCLAIMER OF WARRANTIES:                        */
  35. /* -------------------------                        */
  36. /* The following [enclosed] code is sample code    created    by IBM        */
  37. /* Corporation and Prominare Inc.  This    sample code is not part    of any    */
  38. /* standard IBM    product    and is provided    to you solely for the purpose    */
  39. /* of assisting    you in the development of your applications.  The code    */
  40. /* is provided "AS IS",    without    warranty of any    kind.  Neither IBM nor    */
  41. /* Prominare shall be liable for any damages arising out of your    */
  42. /* use of the sample code, even    if they    have been advised of the    */
  43. /* possibility of such damages.                        */
  44. /************************************************************************/
  45. /************************************************************************/
  46. /************************************************************************/
  47. /*               D I S C L A I M E R                */
  48. /* This    code is    provided on an as is basis with    no implied support.    */
  49. /* It should be    considered freeware that cannot    be rebundled as        */
  50. /* part    of a larger "*ware" offering without our consent.        */
  51. /************************************************************************/
  52. /************************************************************************/
  53. /************************************************************************/
  54.  
  55. /* Copyright ╕ International Business Machines Corp., 1995.        */
  56. /* Copyright ╕ 1995  Prominare Inc.  All Rights    Reserved.        */
  57.  
  58. /* --------------------------------------------------------------------    */
  59.  
  60. HBITMAP    hbmView    = 0;           /* Bitmap Handle            */
  61. LONG    lScale = 100L;           /* Scale Factor            */
  62. RECTL    rclDest;           /* Destination Rectangle        */
  63. RECTL    rclImage;           /* Image Rectangle            */
  64. POINTL    aptlArea[8];           /* Shadow Points            */
  65.  
  66. LONG    iImage;               /* Bitmap Image Index        */
  67.  
  68. static VOID SizeBitmap(HWND hWnd);
  69. static VOID SizeBitmapStack(HWND hWnd);
  70.  
  71. #pragma    subtitle("   Client Window - Bitmap Sizing Function")
  72. #pragma    page( )
  73.  
  74. /* --- SizeBitmap -------------------------------------    [ Private ] ---    */
  75. /*                                    */
  76. /*     This function is    used to    size the scaled    bitmap for the window.    */
  77. /*                                    */
  78. /*     Upon Entry:                            */
  79. /*                                    */
  80. /*     HWND hWnd; = Window Handle                    */
  81. /*                                    */
  82. /*     Upon Exit:                            */
  83. /*                                    */
  84. /*     Nothing                                */
  85. /*                                    */
  86. /* --------------------------------------------------------------------    */
  87.  
  88. static VOID SizeBitmap(HWND hWnd)
  89.  
  90. {
  91. BITMAPINFOHEADER bmp;           /* Bitmap Information Header        */
  92. RECTL         rcl;           /* Window Rectangle            */
  93. LONG         cx;           /* Bitmap Width            */
  94. LONG         cy;           /* Bitmap Height            */
  95.  
  96. WinQueryWindowRect(hWnd, &rcl);
  97.  
  98. GpiQueryBitmapParameters(hbmView, &bmp);
  99.  
  100. cx = (bmp.cx * lScale) / 100L;
  101. cy = (bmp.cy * lScale) / 100L;
  102.  
  103. rclDest.xRight = (rclDest.xLeft      = ((rcl.xRight - rcl.xLeft) /    2L) - (cx / 2L)) + cx;
  104. rclDest.yTop   = (rclDest.yBottom = ((rcl.yTop - rcl.yBottom) /    2L) - (cy / 2L)) + cy;
  105.  
  106. rclImage.xRight    = (rclImage.xLeft   = ((rcl.xRight - rcl.xLeft)    / 2L) -    (bmp.cx    * 4L)) + bmp.cx    * 8L;
  107. rclImage.yTop    = (rclImage.yBottom = ((rcl.yTop - rcl.yBottom)    / 2L) -    (bmp.cy    * 4L)) + bmp.cy    * 8L;
  108.  
  109. rclImage.xLeft     -= 3L;
  110. rclImage.yBottom -= 3L;
  111. rclImage.xRight     += 3L;
  112. rclImage.yTop     += 3L;
  113.  
  114.                /* Form the final boundary points        */
  115.  
  116. aptlArea[0].x =    rclDest.xLeft  - 2L;
  117. aptlArea[0].y =    rclDest.yTop   + 2L;
  118. aptlArea[1].x =    rclDest.xRight + 2L;
  119. aptlArea[1].y =    rclDest.yTop   + 2L;
  120.  
  121. aptlArea[2].x =    rclDest.xRight    + 2L;
  122. aptlArea[2].y =    rclDest.yBottom    - 2L;
  123. aptlArea[3].x =    rclDest.xLeft    - 2L;
  124. aptlArea[3].y =    rclDest.yBottom    - 2L;
  125.  
  126. aptlArea[4].x =    rclDest.xLeft  - 1L;
  127. aptlArea[4].y =    rclDest.yTop   + 1L;
  128. aptlArea[5].x =    rclDest.xRight + 1L;
  129. aptlArea[5].y =    rclDest.yTop   + 1L;
  130.  
  131. aptlArea[6].x =    rclDest.xRight    + 1L;
  132. aptlArea[6].y =    rclDest.yBottom    - 1L;
  133. aptlArea[7].x =    rclDest.xLeft    - 1L;
  134. aptlArea[7].y =    rclDest.yBottom    - 1L;
  135. }
  136. #pragma    subtitle("   Client Window - Bitmap Stack Sizing Function")
  137. #pragma    page( )
  138.  
  139. /* --- SizeBitmapStack --------------------------------    [ Private ] ---    */
  140. /*                                    */
  141. /*     This function is    used to    calculate the size and position    of    */
  142. /*     the bitmaps from    the bitmap array for the window.        */
  143. /*                                    */
  144. /*     Upon Entry:                            */
  145. /*                                    */
  146. /*     HWND hWnd; = Window Handle                    */
  147. /*                                    */
  148. /*     Upon Exit:                            */
  149. /*                                    */
  150. /*     Nothing                                */
  151. /*                                    */
  152. /* --------------------------------------------------------------------    */
  153.  
  154. static VOID SizeBitmapStack(HWND hWnd)
  155.  
  156. {
  157. BITMAPINFOHEADER bmp;           /* Bitmap Information Header        */
  158. RECTL         rcl;           /* Window Rectangle            */
  159. LONG         cx;           /* Bitmap Width            */
  160. LONG         cy;           /* Bitmap Height            */
  161. LONG         xImage;       /* Image Starting Point        */
  162. register INT i;               /* Loop Counter            */
  163.  
  164.  
  165. WinQueryWindowRect(hWnd, &rcl);
  166.     
  167. for ( i    = 0, cx    = 10 * (cBitmaps - 1), cy = 0L;    i < cBitmaps; i++ )
  168.    {
  169.    GpiQueryBitmapParameters(abm[i].hbm,    &bmp);
  170.  
  171.    cx += bmp.cx;
  172.    if (    bmp.cy > cy )
  173.        cy = bmp.cy;
  174.    }
  175.  
  176. rclImage.xRight    = (rclImage.xLeft   = ((rcl.xRight - rcl.xLeft)    / 2L) -    (cx / 2L)) + cx;
  177. rclImage.yTop    = (rclImage.yBottom = ((rcl.yTop - rcl.yBottom)    / 2L) -    (cy / 2L)) + cy;
  178.  
  179. xImage = rclImage.xLeft;
  180.  
  181. rclImage.xLeft     -= 3L;
  182. rclImage.yBottom -= 3L;
  183. rclImage.xRight     += 3L;
  184. rclImage.yTop     += 3L;
  185.  
  186. for ( i    = 0; i < cBitmaps; i++ )
  187.    {
  188.    GpiQueryBitmapParameters(abm[i].hbm,    &bmp);
  189.  
  190.    abm[i].rclDest.xRight = (abm[i].rclDest.xLeft   = xImage) + bmp.cx;
  191.    abm[i].rclDest.yTop     = (abm[i].rclDest.yBottom = ((rcl.yTop    - rcl.yBottom) / 2L) - (bmp.cy / 2L)) +    bmp.cy;
  192.  
  193.                /* Form the final boundary points        */
  194.  
  195.    abm[i].aptlArea[0].x    = abm[i].rclDest.xLeft    - 2L;
  196.    abm[i].aptlArea[0].y    = abm[i].rclDest.yTop    + 2L;
  197.    abm[i].aptlArea[1].x    = abm[i].rclDest.xRight    + 2L;
  198.    abm[i].aptlArea[1].y    = abm[i].rclDest.yTop    + 2L;
  199.  
  200.    abm[i].aptlArea[2].x    = abm[i].rclDest.xRight     + 2L;
  201.    abm[i].aptlArea[2].y    = abm[i].rclDest.yBottom - 2L;
  202.    abm[i].aptlArea[3].x    = abm[i].rclDest.xLeft     - 2L;
  203.    abm[i].aptlArea[3].y    = abm[i].rclDest.yBottom - 2L;
  204.  
  205.    abm[i].aptlArea[4].x    = abm[i].rclDest.xLeft    - 1L;
  206.    abm[i].aptlArea[4].y    = abm[i].rclDest.yTop    + 1L;
  207.    abm[i].aptlArea[5].x    = abm[i].rclDest.xRight    + 1L;
  208.    abm[i].aptlArea[5].y    = abm[i].rclDest.yTop    + 1L;
  209.  
  210.    abm[i].aptlArea[6].x    = abm[i].rclDest.xRight     + 1L;
  211.    abm[i].aptlArea[6].y    = abm[i].rclDest.yBottom - 1L;
  212.    abm[i].aptlArea[7].x    = abm[i].rclDest.xLeft     - 1L;
  213.    abm[i].aptlArea[7].y    = abm[i].rclDest.yBottom - 1L;
  214.  
  215.    xImage += (bmp.cx + 10L);
  216.    }
  217. }
  218. #pragma    subtitle("   Client Window - Bitmap Viewer Window Procedure")
  219. #pragma    page( )
  220.  
  221. /* --- BitmapViewerWndProc ----------------------------- [ Public ] ---    */
  222. /*                                    */
  223. /*     This function is    used to    process    the messages sent to the    */
  224. /*     applications client window.                    */
  225. /*                                    */
  226. /*     Upon Entry:                            */
  227. /*                                    */
  228. /*     HWND   hWnd; = Window Handle                    */
  229. /*     ULONG  msg;  = PM Message                    */
  230. /*     MPARAM mp1;  = Message Parameter    1                */
  231. /*     MPARAM mp2;  = Message Parameter    2                */
  232. /*                                    */
  233. /*     Upon Exit:                            */
  234. /*                                    */
  235. /*     BitmapViewerWndProc = Message Handling Result            */
  236. /*                                    */
  237. /* --------------------------------------------------------------------    */
  238.  
  239. MRESULT    EXPENTRY BitmapViewerWndProc(HWND hWnd,    ULONG msg, MPARAM mp1, MPARAM mp2)
  240.  
  241. {
  242. CHAR            szTitle[300];  /* Title    Bar Text        */
  243. HPS            hPS;       /* Presentation Space Handle        */
  244. LONG            lClrBack;  /* Colour Holder            */
  245. LONG            lClrFore;  /* Colour Holder            */
  246. PBITMAPARRAYFILEHEADER    pbafh;       /* Bitmap Array File    Header Pointer    */
  247. PBITMAPARRAYFILEHEADER2    pbafh2;       /* Bitmap Array File    Header Pointer    */
  248. PBITMAPFILEHEADER    pbfh;       /* Bitmap File Header Pointer    */
  249. PBITMAPFILEHEADER2    pbfh2;       /* Bitmap File Header Pointer    */
  250. PBITMAPINFO        pbmi;       /* Bitmap Info Pointer        */
  251. PBITMAPINFO2        pbmi2;       /* Bitmap Info Pointer        */
  252. PBYTE            pbData;       /* Byte Pointer            */
  253. POINTL            ptl;       /* Pointer Position            */
  254. RECTL            rcl;       /* Window Rectangle            */
  255. register INT i,    n;           /* Index                */
  256.  
  257. switch ( msg )
  258.    {
  259. /************************************************************************/
  260. /* Window being    created, perform window    initialization            */
  261. /************************************************************************/
  262.  
  263.    case    WM_CREATE :
  264.  
  265.        hptrWait     = WinQuerySysPointer(HWND_DESKTOP, SPTR_WAIT,    FALSE);
  266.        hptrArrow = WinQuerySysPointer(HWND_DESKTOP, SPTR_ARROW,    FALSE);
  267.  
  268.        cxScreen    = WinQuerySysValue(HWND_DESKTOP, SV_CXSCREEN);
  269.  
  270.        hmenuViewBmp = WinWindowFromID(WinQueryWindow(hWnd, QW_PARENT), FID_MENU);
  271.  
  272.                /************************************************/
  273.                /* PDSGetTemplate is used to allow controls in  */
  274.                /* windows.  Do not remove this function    if you */
  275.                /* intend to include controls within the    window.*/
  276.                /************************************************/
  277.  
  278.        PDSGetTemplate(hWnd, WIN_BITMAPVIEWER);
  279.        break;
  280.  
  281. /************************************************************************/
  282. /* Window being    sized                            */
  283. /************************************************************************/
  284.  
  285.    case    WM_SIZE    :
  286.        if ( lScale )
  287.        {
  288.        if (    hbmView    )
  289.            SizeBitmap(hWnd);
  290.        }
  291.        else
  292.        if (    cBitmaps )
  293.            SizeBitmapStack(hWnd);
  294.        break;
  295.  
  296. /************************************************************************/
  297. /* Perform menu    initialization                        */
  298. /************************************************************************/
  299.  
  300.    case    WM_INITMENU :
  301.        switch (    SHORT1FROMMP(mp1) )
  302.        {
  303.        case    IDM_FILE :
  304.            break;
  305.  
  306.        case    IDM_SCALE :
  307.            switch (    lScale )
  308.            {
  309.            case    25 :
  310.                i = IDM_25PERCENT;
  311.                break;
  312.            case    50 :
  313.                i = IDM_50PERCENT;
  314.                break;
  315.            case    75 :
  316.                i = IDM_75PERCENT;
  317.                break;
  318.            case    100 :
  319.                i = IDM_100PERCENT;
  320.                break;
  321.            case    200 :
  322.                i = IDM_200PERCENT;
  323.                break;
  324.            case    400 :
  325.                i = IDM_400PERCENT;
  326.                break;
  327.            case    800 :
  328.                i = IDM_800PERCENT;
  329.                break;
  330.            default :
  331.                i = IDM_SHOWALL;
  332.                break;
  333.            }
  334.  
  335.            for ( n = IDM_25PERCENT;    n <= IDM_SHOWALL; n++ )
  336.            WinSendMsg(hmenuViewBmp, MM_SETITEMATTR, MPFROM2SHORT(n, TRUE),
  337.                   MPFROM2SHORT(MIA_CHECKED,    (i == n) ? MIA_CHECKED : 0));
  338.            break;
  339.  
  340.        case    IDM_EFFECTS :
  341.            WinSendMsg(hmenuViewBmp,    MM_SETITEMATTR,    MPFROM2SHORT(IDM_FLIPCOLOURTABLE, TRUE),
  342.               MPFROM2SHORT(MIA_DISABLED, cBitmaps && lScale    ? 0 : MIA_DISABLED));
  343.            break;
  344.        }
  345.        break;
  346.  
  347. /************************************************************************/
  348. /* Process key press from keyboard                    */
  349. /************************************************************************/
  350.  
  351.    case    WM_CHAR    :
  352.                /************************************************/
  353.                /* PDSKeyProc is    used to    allow controls in      */
  354.                /* windows.  Do not remove this function    if you */
  355.                /* intend to include controls within the    window.*/
  356.                /************************************************/
  357.  
  358.        return(PDSKeyProc(hWnd, msg, mp1, mp2));
  359.  
  360.    case    WM_BUTTON2CLICK    :
  361.  
  362. /************************************************************************/
  363. /* Button 2 clicked                            */
  364. /************************************************************************/
  365.  
  366.        if ( !lScale && cBitmaps    )
  367.        {
  368.        ptl.x = (LONG)(SHORT)SHORT1FROMMP(mp1);
  369.        ptl.y = (LONG)(SHORT)SHORT2FROMMP(mp1);
  370.        for ( i = 0;    i < cBitmaps; i++ )
  371.            if ( WinPtInRect(hAB, &abm[i].rclDest, &ptl) )
  372.            {
  373.            iImage = i;
  374.            if (    hmenuPopup )
  375.                WinDestroyWindow(hmenuPopup);
  376.            hmenuPopup =    WinLoadMenu(hWnd, (HMODULE)NULL, (cBitmaps > 1)    ? IDM_POPUP : IDM_POPUPSINGLE);
  377.            WinPopupMenu(hWnd, hWnd, hmenuPopup,    SHORT1FROMMP(mp1), SHORT2FROMMP(mp1), IDM_BITMAPARRAYFILEHEADER,
  378.                 PU_KEYBOARD | PU_MOUSEBUTTON1 |    PU_VCONSTRAIN |    PU_HCONSTRAIN);
  379.            }
  380.        }
  381.        else
  382.        if (    hbmView    )
  383.            {
  384.            ptl.x = (LONG)(SHORT)SHORT1FROMMP(mp1);
  385.            ptl.y = (LONG)(SHORT)SHORT2FROMMP(mp1);
  386.            if ( WinPtInRect(hAB, &rclDest, &ptl) )
  387.            {
  388.            iImage = iBitmap;
  389.            if (    hmenuPopup )
  390.                WinDestroyWindow(hmenuPopup);
  391.            hmenuPopup =    WinLoadMenu(hWnd, (HMODULE)NULL, (cBitmaps > 1)    ? IDM_POPUP : IDM_POPUPSINGLE);
  392.            WinPopupMenu(hWnd, hWnd, hmenuPopup,    SHORT1FROMMP(mp1), SHORT2FROMMP(mp1), IDM_BITMAPARRAYFILEHEADER,
  393.                 PU_KEYBOARD | PU_MOUSEBUTTON1 |    PU_VCONSTRAIN |    PU_HCONSTRAIN);
  394.            }
  395.            }
  396.  
  397.        break;
  398.  
  399. /************************************************************************/
  400. /* Process control selections                        */
  401. /************************************************************************/
  402.  
  403.    case    WM_COMMAND :
  404.        switch (    SHORT1FROMMP(mp1) )
  405.        {
  406.        case    IDM_OPEN :
  407.            if ( WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)OpenBitmapDlgProc,
  408.                   (HMODULE)NULL, DLG_OPENBITMAP, NULL) )
  409.            {
  410.            hbmView = hbmGetBitmap(szBitmapFile);
  411.            SizeBitmap(hWnd);
  412.            WinInvalidateRect(hWnd, NULL, FALSE);
  413.            strcat(memcpy(szTitle, "Bitmap Viewer - ", 17), szBitmapFile);
  414.            if (    fWindowsBitmap )
  415.                strcat(szTitle, " [Windows 3.x format]");
  416.            else
  417.                if ( f20Bitmap )
  418.                strcat(szTitle, " [OS/2 2.x format]");
  419.                else
  420.                strcat(szTitle, " [OS/2 1.x format]");
  421.            WinSetWindowText(hwndViewBmpFrame, szTitle);
  422.            }
  423.            break;
  424.  
  425.        case    IDM_VIEWSYSTEMINFO :
  426.            WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewSystemBitmapInfoDlgProc,
  427.              (HMODULE)NULL,    DLG_VIEWBITMAPSYSINO, NULL);
  428.            break;
  429.  
  430.        case    IDM_25PERCENT :
  431.            lScale =    25L;
  432.            SizeBitmap(hWnd);
  433.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  434.            break;
  435.  
  436.        case    IDM_50PERCENT :
  437.            lScale =    50L;
  438.            SizeBitmap(hWnd);
  439.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  440.            break;
  441.  
  442.        case    IDM_75PERCENT :
  443.            lScale =    75L;
  444.            SizeBitmap(hWnd);
  445.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  446.            break;
  447.  
  448.        case    IDM_100PERCENT :
  449.            lScale =    100L;
  450.            SizeBitmap(hWnd);
  451.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  452.            break;
  453.  
  454.        case    IDM_200PERCENT :
  455.            lScale =    200L;
  456.            SizeBitmap(hWnd);
  457.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  458.            break;
  459.  
  460.        case    IDM_400PERCENT :
  461.            lScale =    400L;
  462.            SizeBitmap(hWnd);
  463.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  464.            break;
  465.  
  466.        case    IDM_800PERCENT :
  467.            lScale =    800L;
  468.            SizeBitmap(hWnd);
  469.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  470.            break;
  471.  
  472.        case    IDM_SHOWALL :
  473.            lScale =    0L;
  474.            SizeBitmapStack(hWnd);
  475.            WinInvalidateRect(hWnd, NULL, FALSE);
  476.            break;
  477.  
  478.        case    IDM_BITMAPARRAYFILEHEADER :
  479.            if ( f20Bitmap )
  480.            WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewBITMAPARRAYFILEHEADER2DlgProc,
  481.                  (HMODULE)NULL, DLG_VIEWBITMAPARRAYFILEHEADER2, (PVOID)iImage);
  482.            else
  483.            WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewBITMAPARRAYFILEHEADERDlgProc,
  484.                  (HMODULE)NULL, DLG_VIEWBITMAPARRAYFILEHEADER, (PVOID)iImage);
  485.            break;
  486.  
  487.        case    IDM_BITMAPFILEHEADER :
  488.            if ( f20Bitmap )
  489.            {
  490.            if (    (cBitmaps == 1)    && !fBitmapArray )
  491.                pbData =    abm[iBitmapSelected = iImage].pb;
  492.            else
  493.                {
  494.                pbafh2 =    (PBITMAPARRAYFILEHEADER2)abm[iBitmapSelected = iImage].pb;
  495.                pbData =    (PBYTE)&pbafh2->bfh2;
  496.                }
  497.            WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewBITMAPFILEHEADER2DlgProc,
  498.                  (HMODULE)NULL, DLG_VIEWBITMAPFILEHEADER2, (PVOID)pbData);
  499.            }
  500.            else
  501.            {
  502.            if (    (cBitmaps == 1)    && !fBitmapArray )
  503.                pbData =    abm[iBitmapSelected = iImage].pb;
  504.            else
  505.                {
  506.                pbafh = (PBITMAPARRAYFILEHEADER)abm[iBitmapSelected = iImage].pb;
  507.                pbData =    (PBYTE)&pbafh->bfh;
  508.                }
  509.            WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewBITMAPFILEHEADERDlgProc,
  510.                  (HMODULE)NULL, DLG_VIEWBITMAPFILEHEADER, (PVOID)pbData);
  511.            }
  512.            break;
  513.  
  514.        case    IDM_BITMAPINFOHEADER :
  515.            if ( f20Bitmap )
  516.            {
  517.            if (    (cBitmaps == 1)    && !fBitmapArray )
  518.                {
  519.                pbfh2 = (PBITMAPFILEHEADER2)abm[iBitmapSelected = iImage].pb;
  520.                pbData =    (PBYTE)&pbfh2->bmp2;
  521.                }
  522.            else
  523.                {
  524.                pbafh2 =    (PBITMAPARRAYFILEHEADER2)abm[iBitmapSelected = iImage].pb;
  525.                pbData =    (PBYTE)&pbafh2->bfh2.bmp2;
  526.                }
  527.            WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewBITMAPINFOHEADER2DlgProc,
  528.                  (HMODULE)NULL, DLG_VIEWBITMAPINFOHEADER2, (PVOID)pbData);
  529.            }
  530.            else
  531.            {
  532.            if (    (cBitmaps == 1)    && !fBitmapArray )
  533.                {
  534.                pbfh = (PBITMAPFILEHEADER)abm[iBitmapSelected = iImage].pb;
  535.                pbData =    (PBYTE)&pbfh->bmp;
  536.                }
  537.            else
  538.                {
  539.                pbafh = (PBITMAPARRAYFILEHEADER)abm[iBitmapSelected = iImage].pb;
  540.                pbData =    (PBYTE)&pbafh->bfh.bmp;
  541.                }
  542.            WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewBITMAPINFOHEADERDlgProc,
  543.                  (HMODULE)NULL, DLG_VIEWBITMAPINFOHEADER, (PVOID)pbData);
  544.            }
  545.            break;
  546.  
  547.        case    IDM_COLOURTABLE    :
  548.            if ( f20Bitmap )
  549.            {
  550.            if (    (cBitmaps == 1)    && !fBitmapArray )
  551.                {
  552.                pbfh2 = (PBITMAPFILEHEADER2)abm[iBitmapSelected = iImage].pb;
  553.                pbmi2 = (PBITMAPINFO2)&pbfh2->bmp2;
  554.                }
  555.            else
  556.                {
  557.                pbafh2 =    (PBITMAPARRAYFILEHEADER2)abm[iBitmapSelected = iImage].pb;
  558.                pbmi2 = (PBITMAPINFO2)&pbafh2->bfh2.bmp2;
  559.                }
  560.            pbData = (PBYTE)&pbmi2->argbColor;
  561.            }
  562.            else
  563.            {
  564.            if (    (cBitmaps == 1)    && !fBitmapArray )
  565.                {
  566.                pbfh = (PBITMAPFILEHEADER)abm[iBitmapSelected = iImage].pb;
  567.                pbmi = (PBITMAPINFO)&pbfh->bmp;
  568.                }
  569.            else
  570.                {
  571.                pbafh = (PBITMAPARRAYFILEHEADER)abm[iBitmapSelected = iImage].pb;
  572.                pbmi = (PBITMAPINFO)&pbafh->bfh.bmp;
  573.                }
  574.            pbData = (PBYTE)&pbmi->argbColor;
  575.            }
  576.            if ( WinDlgBox(HWND_DESKTOP, hwndViewBmpFrame, (PFNWP)ViewColourTableDlgProc,
  577.                   (HMODULE)NULL, abm[iImage].cColours == 2L    ? DLG_VIEW2COLOURTABLE : DLG_VIEWCOLOURTABLE, (PVOID)pbData) )
  578.            {
  579.            hbmView = hbmRefreshBitmap(iImage);
  580.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  581.            }
  582.            break;
  583.  
  584.        case    IDM_FLIPCOLOURTABLE :
  585.            hbmView = hbmFlipColourTable(iImage);
  586.            WinInvalidateRect(hWnd, &rclImage, FALSE);
  587.            break;
  588.        }
  589.        break;
  590.  
  591. /************************************************************************/
  592. /* Erase window    background                        */
  593. /************************************************************************/
  594.  
  595.    case    WM_ERASEBACKGROUND :
  596.        WinQueryWindowRect(hWnd,    &rcl);
  597.        WinFillRect((HPS)LONGFROMMP(mp1), &rcl, CLR_PALEGRAY);
  598.        break;
  599.  
  600. /************************************************************************/
  601. /* Paint client    window                            */
  602. /************************************************************************/
  603.  
  604.    case    WM_PAINT :
  605.        GpiCreateLogColorTable(hPS = WinBeginPaint(hWnd,    (HPS)NULL, &rcl), 0UL, LCOLF_RGB, 0L, 0L, (PLONG)NULL);
  606.        WinFillRect(hPS,    &rcl, RGBCLR_PALEGRAY);
  607.  
  608.                /* Check    to see if image    being scaled otherwise    */
  609.                /* are showing complete bitmap array        */
  610.        if ( lScale )
  611.        {
  612.                /* Check    to see if the image is a 2-colour which    */
  613.                /* menas    that the colours have to be set        */
  614.                /* explicitely                    */
  615.  
  616.        if (    abm[iImage].cColours ==    2L )
  617.            {
  618.            lClrBack    = lClrFore = 0L;
  619.  
  620.                /* Check    to see if a 2.x    format bitmap since the    */
  621.                /* the structures are slightly different        */
  622.  
  623.            if ( f20Bitmap )
  624.            {
  625.                /* Locate the bitmap information    structure    */
  626.  
  627.            if (    (cBitmaps == 1)    && !fBitmapArray )
  628.                {
  629.                pbfh2 = (PBITMAPFILEHEADER2)abm[iImage].pb;
  630.                pbmi2 = (PBITMAPINFO2)&pbfh2->bmp2;
  631.                }
  632.            else
  633.                {
  634.                pbafh2 =    (PBITMAPARRAYFILEHEADER2)abm[iImage].pb;
  635.                pbmi2 = (PBITMAPINFO2)&pbafh2->bfh2.bmp2;
  636.                }
  637.                /* Transfer the RGB info to the colour    */
  638.                /* holders                    */
  639.  
  640.            memcpy(&lClrBack, &pbmi2->argbColor[0], 3);
  641.            memcpy(&lClrFore, &pbmi2->argbColor[1], 3);
  642.            }
  643.            else
  644.            {
  645.                /* Locate the bitmap information    structure    */
  646.  
  647.            if (    (cBitmaps == 1)    && !fBitmapArray )
  648.                {
  649.                pbfh = (PBITMAPFILEHEADER)abm[iImage].pb;
  650.                pbmi = (PBITMAPINFO)&pbfh->bmp;
  651.                }
  652.            else
  653.                {
  654.                pbafh = (PBITMAPARRAYFILEHEADER)abm[iImage].pb;
  655.                pbmi = (PBITMAPINFO)&pbafh->bfh.bmp;
  656.                }
  657.                /* Transfer the RGB info to the colour    */
  658.                /* holders                    */
  659.  
  660.            memcpy(&lClrBack, &pbmi->argbColor[0], 3);
  661.            memcpy(&lClrFore, &pbmi->argbColor[1], 3);
  662.            }
  663.                /* Draw the 2-colour    bitmap using the    */
  664.                /* provided colours from the    bitmap        */
  665.  
  666.            WinDrawBitmap(hPS, hbmView, (PRECTL)NULL, (PPOINTL)(PVOID)&rclDest,
  667.                  lClrFore, lClrBack, DBM_NORMAL | DBM_STRETCH);
  668.            }
  669.        else
  670.                /* Normal bitmap, draw stretched        */
  671.            WinDrawBitmap(hPS, hbmView, (PRECTL)NULL, (PPOINTL)(PVOID)&rclDest,
  672.                  0L, 0L, DBM_NORMAL    | DBM_STRETCH);
  673.  
  674.                /* Draw the 3-D frame around    the image    */
  675.  
  676.        GpiSetColor(hPS, RGBCLR_SHADOW);
  677.        GpiMove(hPS,    &aptlArea[7]);
  678.        GpiPolyLine(hPS, 2L,    &aptlArea[4]);
  679.  
  680.        GpiSetColor(hPS, RGB_WHITE);
  681.        GpiPolyLine(hPS, 2L,    &aptlArea[6]);
  682.  
  683.        GpiSetColor(hPS, RGB_BLACK);
  684.        GpiMove(hPS,    &aptlArea[3]);
  685.        GpiPolyLine(hPS, 2L,    &aptlArea[0]);
  686.  
  687.        GpiSetColor(hPS, RGBCLR_PALEGRAY);
  688.        GpiPolyLine(hPS, 2L,    &aptlArea[2]);
  689.        }
  690.        else
  691.                /* Display the bitmap array images side-by-side    */
  692.  
  693.        for ( i = 0;    i < cBitmaps; i++ )
  694.            {
  695.                /* Check    to see if the image is a 2-colour which    */
  696.                /* menas    that the colours have to be set        */
  697.                /* explicitely                    */
  698.  
  699.            if ( abm[i].cColours == 2L )
  700.            {
  701.            lClrBack = lClrFore = 0L;
  702.  
  703.                /* Check    to see if a 2.x    format bitmap since the    */
  704.                /* the structures are slightly different        */
  705.  
  706.            if (    f20Bitmap )
  707.                {
  708.                /* Locate the bitmap information    structure    */
  709.  
  710.                if ( (cBitmaps == 1) && !fBitmapArray )
  711.                {
  712.                pbfh2 = (PBITMAPFILEHEADER2)abm[i].pb;
  713.                pbmi2 = (PBITMAPINFO2)&pbfh2->bmp2;
  714.                }
  715.                else
  716.                {
  717.                pbafh2 = (PBITMAPARRAYFILEHEADER2)abm[i].pb;
  718.                pbmi2 = (PBITMAPINFO2)&pbafh2->bfh2.bmp2;
  719.                }
  720.                /* Transfer the RGB info    to the colour holders    */
  721.  
  722.                memcpy(&lClrBack, &pbmi2->argbColor[0], 3);
  723.                memcpy(&lClrFore, &pbmi2->argbColor[1], 3);
  724.                }
  725.            else
  726.                {
  727.                /* Locate the bitmap information    structure    */
  728.  
  729.                if ( (cBitmaps == 1) && !fBitmapArray )
  730.                {
  731.                pbfh    = (PBITMAPFILEHEADER)abm[i].pb;
  732.                pbmi    = (PBITMAPINFO)&pbfh->bmp;
  733.                }
  734.                else
  735.                {
  736.                pbafh = (PBITMAPARRAYFILEHEADER)abm[i].pb;
  737.                pbmi    = (PBITMAPINFO)&pbafh->bfh.bmp;
  738.                }
  739.                /* Transfer the RGB info    to the colour holders    */
  740.  
  741.                memcpy(&lClrBack, &pbmi->argbColor[0], 3);
  742.                memcpy(&lClrFore, &pbmi->argbColor[1], 3);
  743.                }
  744.                /* Draw the 2-colour bitmap using the        */
  745.                /* provided colours from    the bitmap        */
  746.  
  747.            WinDrawBitmap(hPS, abm[i].hbm, (PRECTL)NULL,    (PPOINTL)(PVOID)&abm[i].rclDest,
  748.                  lClrFore, lClrBack, DBM_NORMAL);
  749.            }
  750.            else
  751.                /* Draw the bitmap from the array        */
  752.  
  753.            WinDrawBitmap(hPS, abm[i].hbm, (PRECTL)NULL,    (PPOINTL)(PVOID)&abm[i].rclDest,
  754.                  RGB_WHITE, RGB_BLACK, DBM_NORMAL);
  755.  
  756.                /* Draw the 3-D frame around the    image        */
  757.  
  758.            GpiSetColor(hPS,    RGBCLR_SHADOW);
  759.            GpiMove(hPS, &abm[i].aptlArea[7]);
  760.            GpiPolyLine(hPS,    2L, &abm[i].aptlArea[4]);
  761.  
  762.            GpiSetColor(hPS,    RGB_WHITE);
  763.            GpiPolyLine(hPS,    2L, &abm[i].aptlArea[6]);
  764.  
  765.            GpiSetColor(hPS,    RGB_BLACK);
  766.            GpiMove(hPS, &abm[i].aptlArea[3]);
  767.            GpiPolyLine(hPS,    2L, &abm[i].aptlArea[0]);
  768.  
  769.            GpiSetColor(hPS,    RGBCLR_PALEGRAY);
  770.            GpiPolyLine(hPS,    2L, &abm[i].aptlArea[2]);
  771.            }
  772.        WinEndPaint(hPS);
  773.        break;
  774.  
  775. /************************************************************************/
  776. /* Window being    destroyed, perform clean-up operations            */
  777. /************************************************************************/
  778.  
  779.    case    WM_DESTROY :
  780.        for ( i = 0; i <    cBitmaps; i++ )
  781.        GpiDeleteBitmap(abm[i].hbm);
  782.  
  783.        if ( hmenuPopup )
  784.        WinDestroyWindow(hmenuPopup);
  785.  
  786.        if ( pb )
  787.        free(pb);
  788.        break;
  789.  
  790.                /* Default message processing            */
  791.    default :
  792.        return(WinDefWindowProc(hWnd, msg, mp1, mp2));
  793.    }
  794. return(0L);
  795. }
  796.