home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / sibdemo3.zip / SAMPLES.DAT / SAMPLES / DIVE / DIVEDEMO.PAS < prev    next >
Pascal/Delphi Source File  |  1997-08-20  |  41KB  |  1,292 lines

  1. /**************************************************************************
  2. * DIVE demo application. Taken from OS/2 Warp Toolkit.
  3. * Translation to Sibyl: 20-Aug-97, Joerg Pleumann
  4. *
  5. * Limitations: - No fullscreen support
  6. *              - No custom bitmaps can be specified.
  7. ****************************************************************************/
  8.  
  9. /**************************************************************************
  10. *
  11. * File Name        : DIVEDEMO.C
  12. *
  13. * Description      : This program provides the sample code of using DIVE APIs.
  14. *
  15. *                    Direct Interface Video Extension is developed for
  16. *                    the entertainment, education, and games software
  17. *                    to give the high-speed perforemance.
  18. *
  19. *
  20. *
  21. * Concepts         :
  22. *
  23. * Entry Points     : DirectMoveMem()
  24. *                    ReadFile()
  25. *                    Main()
  26. *                    MyWindowProc()
  27. *
  28. * DIVE API's       :
  29. *                    DiveSetSourcePalette
  30. *                    DiveBlitImage
  31. *                    DiveAllocImageBuffer
  32. *                    DiveBeginImageBufferAccess
  33. *                    DiveEndImageBufferAccess
  34. *                    DiveOpen
  35. *                    DiveSetDestinationPalette
  36. *                    DiveFreeImageBuffer
  37. *                    DiveClose
  38. *                    DiveSetupBlitter
  39. *
  40. * Copyright        : COPYRIGHT IBM CORPORATION, 1991, 1992, 1993
  41. *
  42. *        DISCLAIMER OF WARRANTIES.  The following [enclosed] code is
  43. *        sample code created by IBM Corporation. This sample code is not
  44. *        part of any standard or IBM product and is provided to you solely
  45. *        for  the purpose of assisting you in the development of your
  46. *        applications.  The code is provided "AS IS", without
  47. *        warranty of any kind.  IBM shall not be liable for any damages
  48. *        arising out of your use of the sample code, even if they have been
  49. *        advised of the possibility of such damages.
  50. *
  51. ****************************************************************************/
  52.  
  53. program DiveDemo;
  54.  
  55. uses
  56.   Dos, SysUtils, OS2Def, BseDos, PmGpi, PmWin, PmBitmap, Dive;
  57.  
  58. {$r DiveDemo.srf}
  59.  
  60. /*   Menu items definitions
  61. */
  62. const
  63.   ID_MAINWND    = 256;
  64.   ID_OPTIONS    = 257;
  65.   ID_SNAP       = 258;
  66.   ID_EXIT       = 259;
  67.   ID_NEWTEXT    = 260;
  68.   ID_QUERY      = 261;
  69.   ID_DIRECT     = 263;
  70.   ID_USEDIVE    = 264;
  71.   ID_FULLSCR    = 265;
  72.  
  73.   ID_DIALOG     = 262;
  74.   ID_EF_11      =  11;
  75.   ID_EF_12      =  12;
  76.   ID_EF_13      =  13;
  77.   ID_EF_14      =  14;
  78.   ID_EF_15      =  15;
  79.   ID_EF_16      =  16;
  80.   ID_EF_17      =  17;
  81.   ID_EF_18      =  18;
  82.   ID_EF_19      =  19;
  83.   ID_EF_20      =  20;
  84.  
  85.  
  86.   WM_GetVideoModeTable     = $04A2;
  87.   WM_SetVideoMode          = $04A0;
  88.   WM_NotifyVideoModeChange = $04A1;
  89.  
  90.  
  91. /*   Maximum number of files to support
  92. */
  93.   MAX_FILE = 14;                    /* Maximum number of bitmap files    */
  94.  
  95.  
  96.  
  97. /*   Windoe data structure
  98. */
  99. type
  100.   WINDATA = record
  101.     fStartBlit: BOOL;
  102.     fVrnDisabled: BOOL;             /* ????  Visual region enable/disable  */
  103.     fChgSrcPalette: BOOL;           /* Flag for change of source palette   */
  104.     fDataInProcess: BOOL;           /* ????  Visual region enable/disable  */
  105.     fDirect: BOOL;                  /* Indicates direct access or blit     */
  106.     hwndFrame: HWND;                /* Frame window handle                 */
  107.     hwndClient: HWND;               /* Client window handle                */
  108.     _hDive: HDIVE;                  /* DIVE handle                         */
  109.     ulnumColor: ULONG;              /* Number of colors in bitmaps         */
  110.     ulWidth: ULONG;                 /* Bitmap width in pels                */
  111.     ulHeight: ULONG;                /* Bitmap Height in pels               */
  112.     fccColorFormat: FOURCC;         /* Bitmap color format                 */
  113.     ulMaxFiles: ULONG;              /* Number of bimap files showing       */
  114.     tidBlitThread: TID;             /* Thread ID for blitting routine      */
  115.     ulSrcLineSizeBytes: ULONG;      /* source linesize                     */
  116.     cxWidthWindow: LONG;            /* Size of width of frame window       */
  117.     cyHeightWindow: LONG;           /* Size of height of frame window      */
  118.  
  119.     cxWidthBorder: LONG;            /* Size of width of vertical border    */
  120.     cyWidthBorder: LONG;            /* Size of width of horizontal border  */
  121.     cyTitleBar: LONG;               /* Size of title bar                   */
  122.     cyMenu: LONG;                   /* Size of menu                        */
  123.     cxWindowPos: LONG;              /* X position of frame window          */
  124.     cyWindowPos: LONG;              /* Y position of frmae window          */
  125.  
  126.     plWindowPos: POINTL;            /* Position of display window          */
  127.     rcls: array[0..49] of RECTL;    /* Visible region rectangles           */
  128.     ulNumRcls: ULONG;               /* Number of visible region rectangles */
  129.     ulLineSizeBytes: ULONG;         /* Size of scan line bounded by window */
  130.     ulColorSizeBytes: ULONG;        /* Number of bytes per pel             */
  131.  
  132.     _swp: SWP;                      /* Standard window position structure  */
  133.   end;
  134.   PWINDATA = ^WINDATA;
  135.  
  136.   PPBYTE = ^PBYTE;
  137.  
  138.   PFN = procedure;
  139.  
  140. const
  141.   WS_DesktopDive    = 0;   // Desktop dive window style
  142.   WS_MaxDesktopDive = 1;   // Maximized desktop dive window style
  143.   WS_FullScreenDive = 2;   // Full-screen 320x200x256 dive style
  144.  
  145.  
  146. // Function prototypes
  147.  
  148. function MyWindowProc(_hwnd: HWND; msg: ULONG; mp1, mp2: MPARAM): MRESULT; CDECL; forward;
  149. function MyDlgProc(hwndDlg: HWND; msg: ULONG; mp1, mp2: MPARAM): MRESULT; CDECL; forward;
  150.  
  151. // Missing APIs
  152.  
  153. imports
  154.   // ULONG APIENTRY WinQueryVisibleRegion( HWND hwnd,
  155.   //                                     HRGN hrgn);
  156.  
  157.   function WinQueryVisibleRegion(_hwnd: HWND; _hrgn: HRGN): ULONG;
  158.  
  159.            APIENTRY; 'PMWIN' index 1000;
  160.  
  161.   // BOOL APIENTRY WinSetVisibleRegionNotify( HWND hwnd,
  162.   //                                         BOOL fEnable);
  163.  
  164.   function WinSetVisibleRegionNotify(_hwnd: HWND; fEnable: BOOL): BOOL;
  165.  
  166.            APIENTRY; 'PMWIN' index 1001;
  167. end;
  168.  
  169. // Global definitions
  170.  
  171. const
  172.   pszMyWindow = 'MyWindow';             /* Window class name                 */
  173.   pszTitleText = 'DIVE SAMPLE';         /* Title bar text                    */
  174.  
  175. var
  176.   _hab: HAB;                                 /* PM anchor block handle            */
  177.   ulImage: array[0..MAX_FILE-1] of ULONG;    /* Image buffer numbers from Dive    */
  178.   pPalette: array[0..MAX_FILE-1] of Pointer; /* Pointer to bitmap palette area    */
  179.   ulToEnd: ULONG = 0;                        /*                                   */
  180.   DiveCaps: DIVE_CAPS;
  181.   fccFormats: array[0..99] of FOURCC;
  182.   ulFramesToTime: ULONG = 8;                 /* Interval of frames to get time    */
  183.   ulNumFrames: ULONG = 0;                    /* Frame counter                     */
  184.  
  185. //  Default bitmap file name definitions
  186. //       These files are used only when EXE is called without parameter.
  187.  
  188.   pszDefFile : array[0..15] of PSZ =
  189.     ('TPG20000.BMP',
  190.      'TPG20001.BMP',
  191.      'TPG20002.BMP',
  192.      'TPG20003.BMP',
  193.      'TPG20004.BMP',
  194.      'TPG20005.BMP',
  195.      'TPG20006.BMP',
  196.      'TPG20007.BMP',
  197.      'TPG20008.BMP',
  198.      'TPG20009.BMP',
  199.      'TPG20010.BMP',
  200.      'TPG20011.BMP',
  201.      'TPG20012.BMP',
  202.      'TPG20013.BMP',
  203.      'TPG20014.BMP',
  204.      'TPG20015.BMP');
  205.  
  206. //  It is the definition how many time draw each bitmap
  207.  
  208.   ulDrawCnt: array[0..15] of ULONG =
  209.     (
  210.       1,                                  /* For TPG20000.BMP  */
  211.       1,                                  /* For TPG20001.BMP  */
  212.       1,                                  /* For TPG20002.BMP  */
  213.       1,                                  /* For TPG20003.BMP  */
  214.       1,                                  /* For TPG20004.BMP  */
  215.       1,                                  /* For TPG20005.BMP  */
  216.       1,                                  /* For TPG20006.BMP  */
  217.       1,                                  /* For TPG20007.BMP  */
  218.       1,                                  /* For TPG20008.BMP  */
  219.       1,                                  /* For TPG20009.BMP  */
  220.       1,                                  /* For TPG20010.BMP  */
  221.       1,                                  /* For TPG20011.BMP  */
  222.       1,                                  /* For TPG20012.BMP  */
  223.       1,                                  /* For TPG20013.BMP  */
  224.       1,                                  /* For TPG20014.BMP  */
  225.       1);                                 /* For TPG20015.BMP  */
  226.  
  227. /****************************************************************************
  228.  *
  229.  * Name          : DirectMoveMem
  230.  *
  231.  * Description   : It is calling DIVE bitblt function periodically.
  232.  *                 And also it calculates how many frames per a second
  233.  *                 is able to be blit to the screen.
  234.  *
  235.  * Concepts      :
  236.  *
  237.  * Parameters    : Pointer to window data
  238.  *
  239.  * Return        : VOID
  240.  *
  241.  ****************************************************************************/
  242.  
  243. // VOID APIENTRY DirectMoveMem (ULONG parm1)
  244.  
  245. procedure DirectMoveMem(parm1: ULONG);
  246. var
  247.   ulTime0, ulTime1: ULONG;              /* output buffer for DosQierySysInfo      */
  248.   ulIndexImage: ULONG = 0;              /* Index of bitmap data                   */
  249.   achFrameRate: array[0..47] of CHAR;   /* string buffer for WinSetWindowText     */
  250.   tmpFrameRate: string;                 /* temp string buffer                     */
  251.   ulFirstTime: ULONG = 0;               /* very first time flag for DiveSetSour.. */
  252.  
  253.   _pwinData: PWINDATA;                  /* pointer to window data                 */
  254.   ulCount: ULONG = 0;                   /* Counter for each bitmap                */
  255.   b: Boolean;
  256.  
  257. begin
  258.   _pwinData := PWINDATA(parm1);
  259.  
  260.   while (ulToEnd = 0) do
  261.   begin
  262.  
  263.     /* Check if it's time to start the blit-time counter.
  264.     */
  265.     if (ulNumFrames = 0) then
  266.       DosQuerySysInfo (QSV_MS_COUNT, QSV_MS_COUNT, ulTime0, 4);
  267.  
  268.     Inc(ulNumFrames);
  269.  
  270.     /* Check if need to change the source palette.
  271.     **
  272.     ** In this sample case, this API should be called only once at
  273.     ** very first.  After this, it will not be called, because there is
  274.     ** assumption that all bitmap data have the sample palette.
  275.     */
  276.  
  277.     b := _pwinData^.fChgSrcPalette;
  278.     b := b or (ulFirstTime = 0) and (_pwinData^.ulnumColor = 256);
  279.  
  280.     if b then
  281.     begin
  282.       DiveSetSourcePalette (_pwinData^._hDive, 0,
  283.                             _pwinData^.ulnumColor,
  284.                             PBYTE(pPalette[ulIndexImage]));
  285.       ulFirstTime := $FFFF;
  286.     end;
  287.  
  288.     /* Blit the image.
  289.     */
  290.     DiveBlitImage (_pwinData^._hDive,
  291.                    ulImage[ulIndexImage],
  292.                    DIVE_BUFFER_SCREEN);
  293.  
  294.     /* Updated the index for the bitmap data to be drawn next.
  295.     */
  296.     Inc(ulCount);
  297.     if (ulCount >=  ulDrawCnt[ulIndexImage]) then
  298.     begin
  299.       Inc(ulIndexImage);
  300.       ulCount := 0;
  301.     end;
  302.  
  303.     if (ulIndexImage >= _pwinData^.ulMaxFiles) then
  304.       ulIndexImage := 0;
  305.  
  306.     /* Check to see if we have enough frames for a fairly accurate read.
  307.     */
  308.     if (ulNumFrames >= ulFramesToTime) then
  309.     begin
  310.       DosQuerySysInfo (QSV_MS_COUNT, QSV_MS_COUNT, ulTime1, 4);
  311.       ulTime1 := ulTime1 - ulTime0;
  312.       if (ulTime1 <> 0) then
  313.         FmtStr(tmpFrameRate, '%d: %d: %5.2f frames per second.',
  314.                [_pwinData^._hDive, ulFramesToTime,
  315.                  ulFramesToTime * 1000.0 / ulTime1])
  316.       else
  317.         FmtStr(tmpFrameRate, '%d: %d: Lots of frames per second.',
  318.                [_pwinData^._hDive, ulFramesToTime]);
  319.  
  320.       StrPCopy(@achFrameRate, tmpFrameRate);
  321.  
  322.       WinPostMsg (_pwinData^.hwndFrame, WM_COMMAND,
  323.                   ID_NEWTEXT, MPARAM(@achFrameRate));
  324.  
  325.       ulNumFrames := 0;
  326.  
  327.       /* Adjust number of frames to time based on last set.
  328.       */
  329.       if (ulTime1 < 250) then
  330.         ulFramesToTime := ulFramesToTime shl 1;
  331.       if (ulTime1 > 3000) then
  332.         ulFramesToTime := ulFramesToTime shr 1;
  333.     end;
  334.  
  335.     /* Let other threads and processes have some time.
  336.     */
  337.     DosSleep (0);
  338.   end;
  339. end;
  340.  
  341. /****************************************************************************
  342.  *
  343.  * Name          : ReadFile
  344.  *
  345.  * Description   : It opens the file, and reads bitmap header and bitmap
  346.  *                 palette, and reads image data to the buffer allocated
  347.  *                 by DIVE APIs.
  348.  *
  349.  * Concepts      :
  350.  *
  351.  * Parameters    : Index for the file to open
  352.  *                 Pointer to the file name to open
  353.  *                 Pointer to window data
  354.  *
  355.  * Return        : 0 - succeed
  356.  *                 1 - fail
  357.  *
  358.  ****************************************************************************/
  359.  
  360.  
  361. // unsigned long ReadFile (ULONG iFile, unsigned char *pszFile,
  362. //        PWINDATA _pwinData)
  363.  
  364. function ReadFile(iFile: ULONG; pszFile: PSZ; _pwinData: PWINDATA): ULONG;
  365. var
  366.   _hFile: HFILE;                        /* file handke                              */
  367.   ulNumBytes: ULONG;                    /* output for number of bytes actually read */
  368.   ulFileLength: ULONG;                  /* file length                              */
  369.   pbBuffer: PBYTE;                      /* pointer to the image/ temp. palette data */
  370.   ulScanLineBytes: ULONG;               /* output for number of bytes a scan line   */
  371.   ulScanLines: ULONG;                   /* output for height of the buffer          */
  372.   pImgHdr: PBITMAPFILEHEADER2;          /* pointer to bitmapheader                  */
  373.   i, j: ULONG;
  374.   pbTmpDst: PBYTE;                      /* temporaly destination pointer            */
  375.   pTmpLoad: Pointer;                    /* temporaly load pointer                   */
  376. begin
  377.   /* Attempt to open up the passed filename.
  378.   */
  379.   if (DosOpen (pszFile, _hFile, ulNumBytes, 0, FILE_NORMAL,
  380.        OPEN_ACTION_OPEN_IF_EXISTS or OPEN_ACTION_FAIL_IF_NEW,
  381.        OPEN_ACCESS_READONLY or OPEN_SHARE_DENYREADWRITE or
  382.        OPEN_FLAGS_SEQUENTIAL or OPEN_FLAGS_NO_CACHE, nil) <> 0) then
  383.   begin
  384.     Result := 1;
  385.     Exit;
  386.   end;
  387.  
  388.   /* Get the legnth of the file.
  389.   */
  390.   DosSetFilePtr (_hFile, 0, FILE_END, ulFileLength);
  391.   DosSetFilePtr (_hFile, 0, FILE_BEGIN, ulNumBytes);
  392.  
  393.                                       /* Allocate memory for bitmap file header
  394.   */
  395.   if (DosAllocMem (pImgHdr, SizeOf(BITMAPFILEHEADER2),
  396.        PAG_COMMIT or PAG_READ or PAG_WRITE) <> 0) then
  397.   begin
  398.     DosClose(_hFile);
  399.     Result := 1;
  400.     Exit;
  401.   end;
  402.  
  403.   /* Read from the beginning of the header to cbFix in BITMAPINFOHEADER
  404.   ** to know the length of the header.
  405.   */
  406.   if (DosRead (_hFile, pImgHdr^,
  407.        SizeOf(BITMAPFILEHEADER2) - SizeOf(BITMAPINFOHEADER2) +
  408.        SizeOf(ULONG),
  409.        ulNumBytes) <> 0) then
  410.   begin
  411.     DosFreeMem(pImgHdr);
  412.     DosClose(_hFile);
  413.     Result := 1;
  414.     Exit;
  415.   end;
  416.  
  417.   /* Read the rest of the header.
  418.   */
  419.   pTmpLoad := pImgHdr;
  420.   Inc(pTmpLoad, ulNumBytes);
  421.  
  422.   if (DosRead (_hFile, pTmpLoad^,
  423.        pImgHdr^.bmp2.cbFix - SizeOf(ULONG),
  424.        ulNumBytes) <> 0) then
  425.   begin
  426.     DosFreeMem(pImgHdr);
  427.     DosClose(_hFile);
  428.     Result := 1;
  429.     Exit;
  430.   end;
  431.  
  432.   _pwinData^.ulnumColor := 1;
  433.  
  434.   /* Check the bitmap header format --  new or old one.
  435.   */
  436.   if (pImgHdr^.bmp2.cbFix <> SizeOf(BITMAPINFOHEADER)) then
  437.   begin
  438.     /*  Bitmap has new format (BITMAPFILEHEADER2)
  439.     */
  440.  
  441.     /* Check bitmap header to see if it can support.
  442.     */
  443.  
  444.     /* Set how many color bitmap data is supporting
  445.     */
  446.     _pwinData^.ulnumColor := _pwinData^.ulnumColor shl pImgHdr^.bmp2.cBitCount;
  447.  
  448.     /* Set bitmap width and height in pels.
  449.     */
  450.     _pwinData^.ulWidth  := pImgHdr^.bmp2.cx;
  451.     _pwinData^.ulHeight := pImgHdr^.bmp2.cy;
  452.  
  453.     /* Calculate source line size.  It should be double word boundary.
  454.     */
  455.     _pwinData^.ulSrcLineSizeBytes := (((pImgHdr^.bmp2.cx *
  456.             (pImgHdr^.bmp2.cBitCount shr 3)) + 3) div 4) * 4;
  457.  
  458.     /* Set bitmap color format.
  459.     */
  460.     case pImgHdr^.bmp2.cBitCount of
  461.       8:
  462.       begin
  463.         _pwinData^.fccColorFormat := FOURCC_LUT8;
  464.         /* Alloate buffer for palette data in bitmap file.
  465.         */
  466.         if (DosAllocMem (pPalette[iFile],
  467.             _pwinData^.ulnumColor * SizeOf(ULONG),
  468.             PAG_COMMIT | PAG_READ | PAG_WRITE) <> 0) then
  469.         begin
  470.           DosFreeMem(pImgHdr);
  471.           DosClose(_hFile);
  472.           Result := 1;
  473.           Exit;
  474.         end;
  475.  
  476.         /* Read palette data.
  477.         */
  478.         if (DosRead (_hFile, pPalette[iFile]^,
  479.             _pwinData^.ulnumColor * SizeOf(ULONG),
  480.             ulNumBytes) <> 0) then
  481.         begin
  482.           DosFreeMem(pImgHdr);
  483.           DosFreeMem(pPalette[iFile]);
  484.           DosClose(_hFile);
  485.           Result := 1;
  486.           Exit;
  487.         end;
  488.       end;
  489.  
  490.       16:
  491.       begin
  492.         _pwinData^.fccColorFormat := FOURCC_R565;
  493.       end;
  494.  
  495.       24:
  496.       begin
  497.         _pwinData^.fccColorFormat := FOURCC_BGR3;
  498.       end;
  499.  
  500.     else
  501.       DosFreeMem(pImgHdr);
  502.       DosClose(_hFile);
  503.       Result := 1;
  504.       Exit;
  505.     end;                        /* endswitch */
  506.   end
  507.  
  508.   else
  509.  
  510.   begin
  511.     /*  Bitmap has old format (BITMAPFILEHEADER)
  512.     */
  513.  
  514.     /* Set how many color bitmap data is supporting
  515.     */
  516.     _pwinData^.ulnumColor := _pwinData^.ulnumColor shl PBITMAPFILEHEADER(pImgHdr)^.bmp.cBitCount;
  517.  
  518.     /* Set bitmap width and height in pels.
  519.     */
  520.     _pwinData^.ulWidth  := PBITMAPFILEHEADER(pImgHdr)^.bmp.cx;
  521.     _pwinData^.ulHeight := PBITMAPFILEHEADER(pImgHdr)^.bmp.cy;
  522.  
  523.     /* Calculate source line size.  It should be double word boundary.
  524.     */
  525.     _pwinData^.ulSrcLineSizeBytes := (((PBITMAPFILEHEADER(pImgHdr)^.bmp.cx *
  526.             PBITMAPFILEHEADER(pImgHdr)^.bmp.cBitCount shr 3) + 3) div 4) * 4;
  527.  
  528.     /* Set bitmap coclor format.
  529.     */
  530.     case PBITMAPFILEHEADER(pImgHdr)^.bmp.cBitCount of
  531.       8:
  532.       begin
  533.         _pwinData^.fccColorFormat := FOURCC_LUT8;
  534.         /* Alloate buffer for temporally palette data in bitmap file
  535.         */
  536.         if (DosAllocMem(pbBuffer,
  537.             _pwinData^.ulnumColor * SizeOf(RGB),
  538.             PAG_COMMIT | PAG_READ | PAG_WRITE) <> 0) then
  539.         begin
  540.           DosFreeMem(pImgHdr);
  541.           DosClose(_hFile);
  542.           Result := 1;
  543.           Exit;
  544.         end;
  545.  
  546.         if (DosAllocMem (pPalette[iFile],
  547.             _pwinData^.ulnumColor * SizeOf(ULONG),
  548.             PAG_COMMIT | PAG_READ | PAG_WRITE) <> 0) then
  549.         begin
  550.           DosFreeMem(pImgHdr);
  551.           DosFreeMem(pbBuffer);
  552.           DosClose(_hFile);
  553.           Result := 1;
  554.           Exit;
  555.         end;
  556.  
  557.         /* Read palette data
  558.         */
  559.         if (DosRead (_hFile, pbBuffer^,
  560.             _pwinData^.ulnumColor * SizeOf(RGB),
  561.             ulNumBytes) <> 0) then
  562.         begin
  563.           DosFreeMem(pImgHdr);
  564.           DosFreeMem(pbBuffer);
  565.           DosFreeMem(pPalette[iFile]);
  566.           DosClose(_hFile);
  567.           Result := 1;
  568.           Exit;
  569.         end;
  570.  
  571.         /* Make each color from 3 bytes to 4 bytes.
  572.         */
  573.         pbTmpDst := pPalette[iFile];
  574.         for i := 0 to _pwinData^.ulnumColor - 1 do
  575.         begin
  576.           pbTmpDst^ := pbBuffer^;
  577.           Inc(pbTmpDst);
  578.           Inc(pbBuffer);
  579.  
  580.           pbTmpDst^ := pbBuffer^;
  581.           Inc(pbTmpDst);
  582.           Inc(pbBuffer);
  583.  
  584.           pbTmpDst^ := pbBuffer^;
  585.           Inc(pbTmpDst);
  586.           Inc(pbBuffer);
  587.  
  588.           Inc(pbTmpDst);
  589.           Inc(pbBuffer);
  590.         end;                            /* endfor */
  591.  
  592.         DosFreeMem(pbBuffer);
  593.       end;
  594.  
  595.       16:
  596.       begin
  597.         _pwinData^.fccColorFormat := FOURCC_R565;
  598.       end;
  599.  
  600.       24:
  601.       begin
  602.         _pwinData^.fccColorFormat := FOURCC_BGR3;
  603.       end;
  604.  
  605.     else
  606.       DosFreeMem(pImgHdr);
  607.       DosClose(_hFile);
  608.       Result := 1;
  609.       Exit;
  610.     end;                        /* endswitch */
  611.   end;
  612.  
  613.   /* Allocate a buffer for image data
  614.   */
  615.  
  616.   if (DiveAllocImageBuffer(_pwinData^._hDive,
  617.       @ulImage[iFile],
  618.       _pwinData^.fccColorFormat,
  619.       _pwinData^.ulWidth,
  620.       _pwinData^.ulHeight,
  621.       0, nil) <> 0) then
  622.   begin
  623.     if (_pwinData^.fccColorFormat = FOURCC_LUT8) then
  624.       DosFreeMem(pPalette[iFile]);
  625.     DosClose(_hFile);
  626.     Result := 1;
  627.     Exit;
  628.   end;
  629.  
  630.   if (DiveBeginImageBufferAccess(_pwinData^._hDive,
  631.       ulImage[iFile],
  632.       pbBuffer,
  633.       @ulScanLineBytes,
  634.       @ulScanLines) <> 0) then
  635.   begin
  636.     DiveFreeImageBuffer(_pwinData^._hDive, ulImage[iFile]);
  637.     if (_pwinData^.fccColorFormat = FOURCC_LUT8) then
  638.       DosFreeMem(pPalette[iFile]);
  639.     DosClose(_hFile);
  640.     Result := 1;
  641.     Exit;
  642.   end;
  643.  
  644.   /* Read image data
  645.   */
  646.   if (DosRead(_hFile, pbBuffer^,
  647.       _pwinData^.ulSrcLineSizeBytes * _pwinData^.ulHeight,
  648.       ulNumBytes) <> 0) then
  649.   begin
  650.     DiveEndImageBufferAccess(_pwinData^._hDive, ulImage[iFile]);
  651.     DiveFreeImageBuffer(_pwinData^._hDive, ulImage[iFile]);
  652.     if (_pwinData^.fccColorFormat = FOURCC_LUT8) then
  653.       DosFreeMem(pPalette[iFile]);
  654.     DosClose(_hFile);
  655.     Result := 1;
  656.     Exit;
  657.   end;
  658.  
  659.   /* Close the file and release the access to the image buffer
  660.   */
  661.   DosFreeMem(pImgHdr);
  662.   DosClose(_hFile);
  663.  
  664.   DiveEndImageBufferAccess (_pwinData^._hDive, ulImage[iFile]);
  665.  
  666.   Result := 0;
  667. end;
  668.  
  669. /****************************************************************************
  670.  *
  671.  * Name          : MyWindowProc
  672.  *
  673.  * Description   : It is the window procedure of this program.
  674.  *
  675.  * Concepts      :
  676.  *
  677.  * Parameters    : Message parameter 1
  678.  *                 Message parameter 2
  679.  *
  680.  * Return        : calling WinDefWindowProc
  681.  *
  682.  ****************************************************************************/
  683.  
  684. // MRESULT EXPENTRY MyWindowProc (HWND _hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
  685.  
  686. function MyWindowProc (_hwnd: HWND; msg: ULONG; mp1, mp2: MPARAM): MRESULT; CDECL;
  687. var
  688.   _pointl: POINTL;                    /* Point to offset from Desktop    */
  689.   _swp: SWP;                          /* Window position                 */
  690.   _hrgn: HRGN;                        /* Region handle                   */
  691.   _hps: HPS;                          /* Presentation Space handle       */
  692.   rcls: array[0..49] of RECTL;        /* Rectangle coordinates           */
  693.   rgnCtl: RGNRECT;                    /* Processing control structure    */
  694.   _pwinData: PWINDATA;                /* Pointer to window data          */
  695.   SetupBlitter: SETUP_BLITTER;        /* structure for DiveSetupBlitter  */
  696.   pPal: PLONG;
  697.   hwndDialog: HWND;
  698. begin
  699.   // Get the pointer to window data
  700.   //
  701.   _pwinData := PWINDATA(WinQueryWindowULong (_hwnd, 0));
  702.   if(_pwinData <> nil) then
  703.   begin
  704.     case Msg of
  705.       WM_COMMAND:
  706.       begin
  707.         case SHORT1FROMMP(mp1) of
  708.           ID_SNAP:
  709.           begin
  710.             /* Use the initial width and height of the window such that
  711.             ** the actual video area equals the source width and height.
  712.             */
  713.  
  714.             /* Set the new size of the window, but don't move it.
  715.             */
  716.             WinSetWindowPos (_pwinData^.hwndFrame, HWND_TOP,
  717.                     100, 100,
  718.                     _pwinData^.cxWidthWindow,
  719.                     _pwinData^.cyHeightWindow,
  720.                     SWP_SIZE | SWP_ACTIVATE | SWP_SHOW);
  721.           end;
  722.  
  723.           ID_QUERY:
  724.           begin
  725.             // Get the screen capabilities
  726.             // to display in the dialog box.
  727.  
  728.             DiveCaps.pFormatData := @fccFormats;
  729.             DiveCaps.ulFormatLength := 120;
  730.             DiveCaps.ulStructLen := SizeOf(DIVE_CAPS);
  731.  
  732.             if (DiveQueryCaps (@DiveCaps, DIVE_BUFFER_SCREEN) <> 0) then
  733.             begin
  734.               WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  735.                       'usage: DIVEDEMO failed to get screen capabilities.',
  736.                       'Error!', 0, MB_OK | MB_MOVEABLE);
  737.             end
  738.             else
  739.             begin
  740.               WinDlgBox (HWND_DESKTOP, _pwinData^.hwndClient,
  741.                          @MyDlgProc, 0,
  742.                          ID_DIALOG, _pwinData);
  743.             end;
  744.           end;
  745.  
  746.           ID_FULLSCR:            // GameSrvr
  747.           begin
  748.             WinSendMsg(_pwinData^.hwndFrame, WM_SetVideoMode, MPARAM(WS_FullScreenDive), 0); // GameSrvr
  749.           end;
  750.  
  751.           ID_EXIT:               // Post to quit the dispatch message loop.
  752.           begin
  753.             WinSendMsg(_pwinData^.hwndFrame, WM_SetVideoMode, MPARAM(WS_DesktopDive), 0); // GameSrvr
  754.             WinPostMsg (_hwnd, WM_QUIT, 0, 0);
  755.           end;
  756.  
  757.           ID_NEWTEXT:
  758.           begin
  759.             /* Write new text string to the title bar
  760.             */
  761.             WinSetWindowText (_pwinData^.hwndFrame, PCHAR(mp2)^);
  762.           end;
  763.  
  764.         else
  765.           Result := WinDefWindowProc (_hwnd, msg, mp1, mp2);
  766.         end; (* case *)
  767.       end; (* begin *)
  768.  
  769.       WM_VRNDISABLED:
  770.       begin
  771.         DiveSetupBlitter (_pwinData^._hDive, nil);
  772.       end;
  773.  
  774.       WM_VRNENABLED:
  775.       begin
  776.         _hps := WinGetPS (_hwnd);
  777.  
  778.         if (_hps <> 0) then
  779.         begin
  780.           _hrgn := GpiCreateRegion (_hps, 0, nil);
  781.  
  782.           if (_hrgn <> 0) then
  783.           begin
  784.             //      NOTE: If mp1 is zero, then this was just a move message.
  785.             //      Illustrate the visible region on a WM_VRNENABLE.
  786.  
  787.             WinQueryVisibleRegion (_hwnd, _hrgn);
  788.             rgnCtl.ircStart     := 0;
  789.             rgnCtl.crc          := 50;
  790.             rgnCtl.ulDirection  := 1;
  791.  
  792.             // Get the all ORed rectangles
  793.  
  794.             if (GpiQueryRegionRects (_hps, _hrgn, nil, rgnCtl, rcls[0])) then
  795.             begin
  796.               // Now find the window position and size, relative to parent.
  797.  
  798.               WinQueryWindowPos (_pwinData^.hwndClient, _swp);
  799.  
  800.               // Convert the point to offset from desktop lower left.
  801.  
  802.               _pointl.x := _swp.x;
  803.               _pointl.y := _swp.y;
  804.  
  805.               WinMapWindowPoints (_pwinData^.hwndFrame,
  806.                       HWND_DESKTOP, _pointl, 1);
  807.  
  808.               // Tell DIVE about the new settings.
  809.  
  810.               SetupBlitter.ulStructLen       := SizeOf(SETUP_BLITTER);
  811.               SetupBlitter.fccSrcColorFormat := _pwinData^.fccColorFormat;
  812.               SetupBlitter.ulSrcWidth        := _pwinData^.ulWidth;
  813.               SetupBlitter.ulSrcHeight       := _pwinData^.ulHeight;
  814.               SetupBlitter.ulSrcPosX         := 0;
  815.               SetupBlitter.ulSrcPosY         := 0;
  816.               SetupBlitter.fInvert           := ULONG(TRUE);  // ???
  817.               SetupBlitter.ulDitherType      := 1;
  818.  
  819.               SetupBlitter.fccDstColorFormat := FOURCC_SCRN;
  820.               SetupBlitter.ulDstWidth        := _swp.cx;
  821.               SetupBlitter.ulDstHeight       := _swp.cy;
  822.               SetupBlitter.lDstPosX          := 0;
  823.               SetupBlitter.lDstPosY          := 0;
  824.               SetupBlitter.lScreenPosX       := _pointl.x;
  825.               SetupBlitter.lScreenPosY       := _pointl.y;
  826.               SetupBlitter.ulNumDstRects     := rgnCtl.crcReturned;
  827.               SetupBlitter.pVisDstRects      := @rcls;
  828.  
  829.               DiveSetupBlitter (_pwinData^._hDive, @SetupBlitter);
  830.  
  831.               ulFramesToTime := 4;
  832.               ulNumFrames    := 1;
  833.             end
  834.  
  835.             else
  836.  
  837.             begin
  838.               DiveSetupBlitter (_pwinData^._hDive, nil);
  839.             end;
  840.  
  841.             GpiDestroyRegion(_hps, _hrgn);
  842.           end;
  843.  
  844.           WinReleasePS(_hps);
  845.         end;
  846.       end;
  847.  
  848.       WM_REALIZEPALETTE:
  849.       begin
  850.         /* This tells DIVE that the physical palette may have changed.
  851.         */
  852.         DiveSetDestinationPalette (_pwinData^._hDive, 0, 0, nil);
  853.       end;
  854.  
  855.       WM_CLOSE:
  856.       begin
  857.          // Post to quit the dispatch message loop.
  858.  
  859.         WinPostMsg (_hwnd, WM_QUIT, 0, 0);
  860.       end;
  861.  
  862.     else
  863.       // Let PM handle this message.
  864.  
  865.       Result := WinDefWindowProc(_hwnd, msg, mp1, mp2);
  866.       Exit;
  867.     end; (* case *)
  868.   end (* begin *)
  869.  
  870.   else
  871.  
  872.   begin
  873.     // Let PM handle this message.
  874.  
  875.     Result := WinDefWindowProc (_hwnd, msg, mp1, mp2);
  876.     Exit;
  877.   end;
  878.  
  879.   Result := MRESULT(FALSE);
  880. end;
  881.  
  882. /****************************************************************************
  883.  *
  884.  * Name          : MyDlgProc
  885.  *
  886.  * Description   : It is the dialog procedure of this program.
  887.  *
  888.  * Concepts      :
  889.  *
  890.  * Parameters    : Message parameter 1
  891.  *                 Message parameter 2
  892.  *
  893.  * Return        : calling WinDefDlgProc
  894.  *
  895.  ****************************************************************************/
  896.  
  897. // MRESULT EXPENTRY MyDlgProc (HWND hwndDlg, ULONG msg, MPARAM mp1, MPARAM mp2)
  898.  
  899. function MyDlgProc(hwndDlg: HWND; msg: ULONG; mp1, mp2: MPARAM): MRESULT; CDECL;
  900. var
  901.   s: string;
  902. begin
  903.   case msg of
  904.     WM_INITDLG:
  905.     begin
  906.       if (not DiveCaps.fScreenDirect) then
  907.         WinSetDlgItemText(hwndDlg, ID_EF_11, 'NO')
  908.       else
  909.         WinSetDlgItemText(hwndDlg, ID_EF_11, 'YES');
  910.  
  911.       if (not DiveCaps.fBankSwitched) then
  912.         WinSetDlgItemText(hwndDlg, ID_EF_12, 'NO')
  913.       else
  914.         WinSetDlgItemText(hwndDlg, ID_EF_12, 'YES');
  915.  
  916.       s := IntToStr(DiveCaps.ulDepth);
  917.       WinSetDlgItemText(hwndDlg, ID_EF_13, s);
  918.  
  919.       s := IntToStr(DiveCaps.ulHorizontalResolution);
  920.       WinSetDlgItemText(hwndDlg, ID_EF_14, s);
  921.  
  922.       s := IntToStr(DiveCaps.ulVerticalResolution);
  923.       WinSetDlgItemText(hwndDlg, ID_EF_15, s);
  924.  
  925.       s := IntToStr(DiveCaps.ulScanLineBytes);
  926.       WinSetDlgItemText(hwndDlg, ID_EF_16, s);
  927.  
  928.       case DiveCaps.fccColorEncoding of
  929.         FOURCC_LUT8:
  930.         begin
  931.           WinSetDlgItemText(hwndDlg, ID_EF_17, '256');
  932.         end;
  933.  
  934.         FOURCC_R565:
  935.         begin
  936.           WinSetDlgItemText(hwndDlg, ID_EF_17, '64K');
  937.         end;
  938.  
  939.         FOURCC_R555:
  940.         begin
  941.           WinSetDlgItemText(hwndDlg, ID_EF_17, '32K');
  942.         end;
  943.  
  944.         FOURCC_R664:
  945.         begin
  946.           WinSetDlgItemText(hwndDlg, ID_EF_17, '64K');
  947.         end;
  948.  
  949.         FOURCC_RGB3,
  950.         FOURCC_BGR3,
  951.         FOURCC_RGB4,
  952.         FOURCC_BGR4:
  953.         begin
  954.           WinSetDlgItemText(hwndDlg, ID_EF_17, '16M');
  955.         end;
  956.  
  957.       else
  958.         WinSetDlgItemText(hwndDlg, ID_EF_17, '???');
  959.       end;                            /* endswitch */
  960.  
  961.       s := IntToStr(DiveCaps.ulApertureSize);
  962.       WinSetDlgItemText(hwndDlg, ID_EF_18, s);
  963.  
  964.       s := IntToStr(DiveCaps.ulInputFormats);
  965.       WinSetDlgItemText(hwndDlg, ID_EF_19, s);
  966.  
  967.       s := IntToStr(DiveCaps.ulOutputFormats);
  968.       WinSetDlgItemText(hwndDlg, ID_EF_20, s);
  969.     end;
  970.  
  971.     WM_COMMAND:
  972.     begin
  973.       case SHORT1FROMMP (mp1) of
  974.         DID_OK:
  975.         begin
  976.           WinDismissDlg(hwndDlg, ULONG(TRUE));
  977.         end;
  978.       else
  979.         Result := WinDefDlgProc (hwndDlg, msg, mp1, mp2);
  980.         Exit;
  981.       end;
  982.     end
  983.   else
  984.     Result := WinDefDlgProc (hwndDlg, msg, mp1, mp2);
  985.     Exit;
  986.   end;
  987.   Result := MPARAM(FALSE);
  988. end;
  989.  
  990. /****************************************************************************
  991.  *
  992.  * Name          : Main
  993.  *
  994.  * Description   : This is main routine of this sample program.
  995.  *
  996.  * Concepts      :
  997.  *
  998.  * Parameters    : At command prompt, when the user start this EXE without
  999.  *                 any parameters, like
  1000.  *                    DIVEDEMO
  1001.  *                 it shows 16 default bitmaps which has a sequence.
  1002.  *                 When the user specifies the names of bitmap file, like
  1003.  *                    DIVEDEMO XXXXXX.BMP YYYYYY.BMP
  1004.  *                 it shows the bitmaps specified at command line in turn.
  1005.  *
  1006.  * Return        : 1 - fail
  1007.  *                 0 - suceed
  1008.  *
  1009.  ****************************************************************************/
  1010.  
  1011. var
  1012.   tidBlitThread: TID;            /* Thread ID for DirectMemMove          */
  1013.   _hmq: HMQ;                     /* Message queue handle                 */
  1014.   _qmsg: QMSG;                   /* Message from message queue           */
  1015.   flCreate: ULONG;               /* Window creation control flags        */
  1016.   i: ULONG;                      /* Index for the files to open          */
  1017.   _pwinData: PWINDATA;           /* Pointer to window data               */
  1018.   pPal: PLONG;                   /* Pointer to system physical palette   */
  1019.   cxWidthBorder: LONG;           /* Size of width of vertical border     */
  1020.   cyWidthBorder: LONG;           /* Size of width of horizontal border   */
  1021.   cyTitleBar: LONG;              /* Size of title bar                    */
  1022.   cyMenu: LONG;                  /* Size of menu                         */
  1023.   cxWindowPos: LONG;             /* X position of frame window           */
  1024.   cyWindowPos: LONG;             /* Y position of frmae window           */
  1025.  
  1026.   szErrorBuf: array[0..255] of UCHAR; // GameSrvr
  1027.   hmodGameSrvr: HMODULE;              // GameSrvr
  1028.   pfnInitGameFrameProc: PFN;          // GameSrvr
  1029.  
  1030. begin
  1031.   // Initialize global variables
  1032.  
  1033.   FillChar(DiveCaps, SizeOf(DiveCaps), 0);
  1034.   FillChar(fccFormats, SizeOf(fccFormats), 0);
  1035.  
  1036.   // Initialize the presentation manager, and create a message queue.
  1037.  
  1038.   _hab := WinInitialize (0);
  1039.   _hmq := WinCreateMsgQueue (_hab, 0);
  1040.  
  1041.   // Allocate a buffer for the window data
  1042.  
  1043.   New(_pwinData);
  1044.  
  1045.   /* Get the screen capabilities, and if the system support only 16 colors
  1046.   ** the sample should be terminated.
  1047.   */
  1048.  
  1049.   DiveCaps.pFormatData := @fccFormats;
  1050.   DiveCaps.ulFormatLength := 120;
  1051.   DiveCaps.ulStructLen := SizeOf(DIVE_CAPS);
  1052.  
  1053.   if (DiveQueryCaps (@DiveCaps, DIVE_BUFFER_SCREEN) <> 0) then
  1054.   begin
  1055.     WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  1056.             'usage: The sample program can not run on this system environment.',
  1057.             'DIVEDEMO.EXE - DIVE Sample', 0, MB_OK or MB_INFORMATION);
  1058.     Dispose(_pwinData);
  1059.     WinDestroyMsgQueue(_hmq);
  1060.     WinTerminate(_hab);
  1061.     Halt(1);
  1062.   end;
  1063.  
  1064.   if (DiveCaps.ulDepth < 8) then
  1065.   begin
  1066.     WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  1067.             'usage: The sample program can not run on this system environment.',
  1068.             'DIVEDEMO.EXE - DIVE Sample', 0, MB_OK or MB_INFORMATION);
  1069.     Dispose(_pwinData);
  1070.     WinDestroyMsgQueue(_hmq);
  1071.     WinTerminate(_hab);
  1072.     Halt(1);
  1073.   end;
  1074.  
  1075.   /* Get an instance of DIVE APIs.
  1076.   */
  1077.   if (DiveOpen(_pwinData^._hDive, FALSE, nil) <> 0) then
  1078.   begin
  1079.     WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  1080.             'usage: The sample program can not run on this system environment.',
  1081.             'DIVEDEMO.EXE - DIVE Sample', 0, MB_OK or MB_INFORMATION);
  1082.     Dispose(_pwinData);
  1083.     WinDestroyMsgQueue(_hmq);
  1084.     WinTerminate(_hab);
  1085.     Halt(1);
  1086.   end;
  1087.  
  1088.   // Read bitmap files
  1089.  
  1090.   // if (argc == 1)      // Default case
  1091.   begin
  1092.     // Read BMP file
  1093.  
  1094.     _pwinData^.ulMaxFiles := 0;
  1095.     for i := 0 to MAX_FILE - 1 do
  1096.     begin
  1097.       if (ReadFile (i, pszDefFile[i], _pwinData) <> 0) then
  1098.       begin
  1099.         WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  1100.                       'usage: DIVEDEMO failed to open bitmap file '+ pszDefFile[i],
  1101.                       'Error!', 0, MB_OK or MB_MOVEABLE);
  1102.         Halt(1);
  1103.       end
  1104.       else
  1105.       begin
  1106.         Inc(_pwinData^.ulMaxFiles);
  1107.       end;
  1108.     end;
  1109.   end;
  1110.  
  1111.   (* custom bitmaps not supported *)
  1112.   /*
  1113.   }
  1114.   else    // The case which the user specify bitmap file names
  1115.   {
  1116.       if ((argc > 1) && (argc <= MAX_FILE + 1))
  1117.       {
  1118.           for (i = 1; i < (ULONG)(argc); i++)
  1119.           {
  1120.               if (ReadFile(i-1, (unsigned char *)argv[i], _pwinData))
  1121.               {
  1122.                   WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  1123.                           (PSZ)"usage: DIVEDEMO failed to open bitmaps.",
  1124.                           (PSZ)"Error!", 0, MB_OK | MB_MOVEABLE);
  1125.                   free (_pwinData);
  1126.                   WinDestroyMsgQueue(_hmq);
  1127.                   WinTerminate(_hab);
  1128.                   return(1);
  1129.               }
  1130.           }
  1131.           _pwinData^.ulMaxFiles = argc-1;
  1132.       }
  1133.       else
  1134.       {
  1135.           WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  1136.                   (PSZ)"usage: DIVEDEMO failed to open bitmaps.",
  1137.                   (PSZ)"Error!", 0, MB_OK | MB_MOVEABLE);
  1138.           free(_pwinData);
  1139.           WinDestroyMsgQueue(_hmq);
  1140.           WinTerminate(_hab);
  1141.           return(1);
  1142.       }
  1143.   }
  1144.   */
  1145.  
  1146.   // Register a window class, and create a standard window.
  1147.  
  1148.   WinRegisterClass(_hab, pszMyWindow, @MyWindowProc, 0, SizeOf(ULONG));
  1149.  
  1150.   flCreate := FCF_TASKLIST | FCF_SYSMENU  | FCF_TITLEBAR | FCF_ICON |
  1151.   FCF_SIZEBORDER | FCF_MINMAX | FCF_MENU | FCF_SHELLPOSITION;
  1152.  
  1153.   _pwinData^.hwndFrame := WinCreateStdWindow(HWND_DESKTOP,
  1154.           WS_VISIBLE,
  1155.           flCreate,
  1156.           pszMyWindow,
  1157.           pszTitleText,
  1158.           WS_SYNCPAINT | WS_VISIBLE,
  1159.           0, ID_MAINWND,
  1160.           _pwinData^.hwndClient);
  1161.  
  1162.   WinSetWindowULong(_pwinData^.hwndClient, 0, ULONG(_pwinData));
  1163.  
  1164.   /*
  1165.  
  1166.   // GameSrvr ----------------------------------------------------begin---
  1167.  
  1168.       if (0 == DosLoadModule(szErrorBuf, 256, "GAMESRVR", &hmodGameSrvr))
  1169.       {
  1170.           if (0 == DosQueryProcAddr(hmodGameSrvr, 1, 0, &pfnInitGameFrameProc))
  1171.           {
  1172.               (pfnInitGameFrameProc)(_pwinData^.hwndFrame, 0);
  1173.           }
  1174.           {
  1175.               ULONG pvmi;
  1176.               ULONG ul;
  1177.  
  1178.               WinSendMsg(_pwinData^.hwndFrame, WM_GetVideoModeTable, (MPARAM)&pvmi, (MPARAM)&ul);
  1179.           }
  1180.       }
  1181.       else
  1182.       {
  1183.           WinMessageBox(HWND_DESKTOP, HWND_DESKTOP,
  1184.                   (PSZ)"usage: DIVEDEMO failed to load GAMESRVR.DLL.",
  1185.                   (PSZ)"Error!", 0, MB_OK | MB_MOVEABLE);
  1186.       }
  1187.  
  1188.   // GameSrvr ----------------------------------------------------end-----
  1189.  
  1190.   */
  1191.  
  1192.   cxWidthBorder := WinQuerySysValue(HWND_DESKTOP, SV_CXSIZEBORDER);
  1193.   cyWidthBorder := WinQuerySysValue(HWND_DESKTOP, SV_CYSIZEBORDER);
  1194.   cyTitleBar    := WinQuerySysValue(HWND_DESKTOP, SV_CYTITLEBAR);
  1195.   cyMenu        := WinQuerySysValue(HWND_DESKTOP, SV_CYMENU);
  1196.  
  1197.   _pwinData^.cxWidthWindow  := _pwinData^.ulWidth + cxWidthBorder * 2;
  1198.   _pwinData^.cyHeightWindow := _pwinData^.ulHeight + (cyWidthBorder * 2 +
  1199.           cyTitleBar + cyMenu);
  1200.  
  1201.   cxWindowPos   := (WinQuerySysValue(HWND_DESKTOP, SV_CXSCREEN)
  1202.           - _pwinData^.cxWidthWindow) div 2;
  1203.   cyWindowPos   := (WinQuerySysValue(HWND_DESKTOP, SV_CYSCREEN)
  1204.           - _pwinData^.cyHeightWindow) div 2;
  1205.  
  1206.   /* Set the window position and size.
  1207.   */
  1208.   WinSetWindowPos (_pwinData^.hwndFrame,
  1209.           HWND_TOP,
  1210.           cxWindowPos, cyWindowPos,
  1211.           _pwinData^.cxWidthWindow, _pwinData^.cyHeightWindow,
  1212.           SWP_SIZE | SWP_MOVE | SWP_SHOW | SWP_ACTIVATE);
  1213.  
  1214.   /* Turn on visible region notification.
  1215.   */
  1216.  
  1217.   WinSetVisibleRegionNotify(_pwinData^.hwndClient, TRUE);
  1218.  
  1219.   /* set the flag for the first time simulation of palette of bitmap data
  1220.   */
  1221.   _pwinData^.fChgSrcPalette := FALSE;
  1222.  
  1223.   /* Send an invlaidation message to the client.
  1224.   */
  1225.   WinPostMsg(_pwinData^.hwndFrame, WM_VRNENABLED, 0, 0);
  1226.  
  1227.   /* Start up the blitting thread.
  1228.   */
  1229.   if (DosCreateThread(_pwinData^.tidBlitThread,
  1230.        @DirectMoveMem,
  1231.        _pwinData, 0, 8192) <> 0) then
  1232.   begin
  1233.     WinSetVisibleRegionNotify(_pwinData^.hwndClient, FALSE);
  1234.  
  1235.     for i := 0 to _pwinData^.ulMaxFiles - 1 do
  1236.     begin
  1237.       DiveFreeImageBuffer(_pwinData^._hDive, ulImage[i]);
  1238.     end;
  1239.  
  1240.     DiveClose(_pwinData^._hDive);
  1241.     WinDestroyWindow(_pwinData^.hwndFrame);
  1242.     Dispose(_pwinData);
  1243.     WinDestroyMsgQueue(_hmq);
  1244.     WinTerminate(_hab);
  1245.     Halt(1);
  1246.   end;
  1247.  
  1248.   // Set the proiroty of the blitting thread
  1249.  
  1250.   DosSetPriority(PRTYS_THREAD, PRTYC_IDLETIME,
  1251.           0, _pwinData^.tidBlitThread);
  1252.  
  1253.   // While there are still messages, dispatch them.
  1254.  
  1255.   while (WinGetMsg(_hab, _qmsg, 0, 0, 0)) do
  1256.   begin
  1257.     WinDispatchMsg(_hab, _qmsg);
  1258.   end;
  1259.  
  1260.   // Set the variable to end the running thread, and wait for it to end.
  1261.  
  1262.   ulToEnd := 1;
  1263.   DosWaitThread(_pwinData^.tidBlitThread, DCWW_WAIT);
  1264.  
  1265.   // Turn off visible region notificationm tidy up, and terminate.
  1266.  
  1267.   WinSetVisibleRegionNotify(_pwinData^.hwndClient, FALSE);
  1268.  
  1269.   // Free the buffers allocated by DIVE and close DIVE
  1270.  
  1271.   for i := 0 to _pwinData^.ulMaxFiles - 1 do
  1272.   begin
  1273.     DiveFreeImageBuffer(_pwinData^._hDive, ulImage[i]);
  1274.   end;
  1275.   DiveClose(_pwinData^._hDive);
  1276.  
  1277.   if (_pwinData^.fccColorFormat = FOURCC_LUT8) then
  1278.   begin
  1279.     for i := 0 to _pwinData^.ulMaxFiles - 1 do
  1280.     begin
  1281.       DosFreeMem(pPalette[i]);
  1282.     end;
  1283.   end;
  1284.  
  1285.   // Process termination
  1286.  
  1287.   WinDestroyWindow(_pwinData^.hwndFrame);
  1288.   Dispose(_pwinData);
  1289.   WinDestroyMsgQueue(_hmq);
  1290.   WinTerminate(_hab);
  1291. end.
  1292.