home *** CD-ROM | disk | FTP | other *** search
/ Power-Programmierung / CD1.mdf / magazine / pcmagazi / 1992 / 17 / bugs / bugsmsc.c < prev    next >
C/C++ Source or Header  |  1992-09-24  |  24KB  |  765 lines

  1. //========================================================================
  2. //       Bugs.c - A screen saver 
  3. //  
  4. //        Douglas Boling
  5. //
  6. //        Copyright (c) 1992 Doulgas Boling
  7. //========================================================================
  8.  
  9. #include <windows.h>
  10. #include <mmsystem.h>
  11.  
  12. //------------------------------------------------------------------------
  13. //Includes specific to Bugs
  14. //------------------------------------------------------------------------
  15. #include "Bugsmsc.h"
  16. #include <stdlib.h>
  17. #include <string.h>
  18.  
  19. //------------------------------------------------------------------------
  20. //Function prototypes used by all screen savers
  21. //------------------------------------------------------------------------
  22. BOOL    RegisterDialogClasses (HANDLE hInst);
  23. LONG FAR PASCAL ScreenSaverProc(HWND, unsigned, WORD, LONG);
  24. extern BOOL FAR PASCAL ScreenSaverConfigureDialog(HWND hDlg, WORD msg, 
  25.                                                   WORD wParam, LONG lParam);
  26.  
  27. void GetStrings(void);
  28.  
  29. //------------------------------------------------------------------------
  30. //Function prototypes used by Bugs
  31. //------------------------------------------------------------------------
  32. BOOL FAR PASCAL AboutDlgProc(HWND, WORD, WORD, LONG);
  33. void BugSmarts (HWND);
  34. void GetProfile (void);
  35. void SetText (HWND, int, int, char*);
  36. int BugCmp (BUGSTRUCT *, BUGSTRUCT *);
  37.  
  38. //------------------------------------------------------------------------
  39. //Global Data required for SCRNSAVE.LIB
  40. //------------------------------------------------------------------------
  41. HANDLE    hMainInstance;
  42. HWND        hMainWindow;
  43. char        szNAME[TITLEBARNAMELEN];
  44. char        szIsPassword[22];
  45. char        szIniFile[MAXFILELEN];
  46. char        szScreenSaver[22];
  47. char        szPassword[16];
  48. char        szDifferentPW[BUFFLEN];
  49. char        szChangePW[30];
  50. char        szBadOldPW[BUFFLEN];
  51. char        szHelpFile[MAXFILELEN];
  52. char        szNoHelpMemory[BUFFLEN];
  53. WORD        MyHelpMessage;
  54. FARPROC    fpMessageFilter;
  55.  
  56. //------------------------------------------------------------------------
  57. //Global Data for Bugs
  58. //------------------------------------------------------------------------
  59. char        szAppName[40];
  60. char        szIniName[] = "CONTROL.INI";
  61.  
  62. BUGSTRUCT bsBugArray [MAXBUGS+1];
  63.  
  64. WORD    wRNutrition = 1;
  65. WORD    wGNutrition = 1;
  66. WORD    wBNutrition = 1;
  67. int    sStartBugs = 10;
  68. int    sScoutLimit = 10;
  69. int    sBabyLevel;
  70. int    sSustenance;
  71. int    sBugLimit;
  72. BOOL    bBColorFlag;
  73. BOOL    bDColorFlag;
  74. BOOL    bPWEnabled;
  75. int    sNumBugs = 1;
  76.  
  77. //========================================================================
  78. //RegisterDialogClasses - Called by the screen saver applet during
  79. //                        initialzation.
  80. //========================================================================
  81. BOOL    RegisterDialogClasses (HANDLE hInst) {
  82.  
  83.     return TRUE;
  84. }
  85.  
  86. //========================================================================
  87. //ScreenSaverProc - The Window procedure
  88. //========================================================================
  89. LONG FAR PASCAL ScreenSaverProc(HWND hwnd, WORD msg, WORD wParam, 
  90.                                 LONG lParam) {
  91.     static    HWND    hwndDesktop;
  92.     static    int    sScreenCx, sScreenCy;
  93.     static    WORD    wTimer;
  94.     static    WORD    wTimer1;
  95.  
  96.     HDC        hdc;
  97.     int        i, j;
  98.  
  99.     switch(msg) {
  100.         case WM_CREATE:
  101.             hwndDesktop = GetDesktopWindow();
  102.  
  103.             GetStrings();
  104.             GetProfile();
  105.   
  106.             hdc = GetDC (hwndDesktop);
  107.             sScreenCx = GetDeviceCaps (hdc, HORZRES);
  108.             sScreenCy = GetDeviceCaps (hdc, VERTRES);
  109.             ReleaseDC (hwndDesktop, hdc);
  110.  
  111.             srand (LOWORD (GetCurrentTime()));
  112.             sScoutLimit = sBugLimit / 10;
  113.             if (sSustenance > 100)
  114.                 sSustenance += sSustenance/100;
  115.             else
  116.                 sSustenance++;
  117.  
  118.             PostMessage (hwnd, WM_USER, 0, 0);
  119.  
  120.             //----------------------------------------------------------
  121.             //Use timer 1 if BugSmarts routine is called from WM_TIMER
  122.             //instead of from the message loop.
  123.             //----------------------------------------------------------
  124.             wTimer = SetTimer (hwnd, 1, 100, NULL);
  125.             //
  126.             //Timer 2 used for population ctl
  127.             //
  128.             wTimer1 = SetTimer (hwnd, 2, 15000, NULL);
  129.             break;
  130.  
  131.  
  132.         case WM_USER:
  133.             //
  134.             // WM_USER message used to reseed bug population
  135.             //
  136.             hdc = GetDC (hwnd);
  137.             for (i = 0; i < 6; i++)
  138.                 for (j = 0; j < 6; j++)
  139.                     SetPixel (hdc, i, j, 0x000000);
  140.             
  141.             if (sSustenance > 100)
  142.                 sSustenance -= (sSustenance/100);
  143.             else 
  144.                 if (sSustenance > 0) sSustenance--;
  145.                 
  146.             sNumBugs = 1;
  147.             //
  148.             //10 trys to find a non black pixel
  149.             //
  150.             for (i = 0; i < 10; i++) {
  151.                 bsBugArray[0].PosX = (sScreenCx / 100) * (rand() % 100)+50;
  152.                 bsBugArray[0].PosY = (sScreenCy / 100) * (rand() % 100)+50;
  153.                 if (GetPixel (hdc, bsBugArray[0].PosX, bsBugArray[0].PosY)) 
  154.                     break;
  155.             }
  156.             bsBugArray[0].wXVec = rand() % 3;
  157.             bsBugArray[0].wYVec = rand() % 3;
  158.             bsBugArray[0].lFood = sSustenance * 20;
  159.             bsBugArray[0].dwColor = 0x00000000;
  160.  
  161.             ReleaseDC (hwnd, hdc);
  162.             break;
  163.  
  164.         case WM_TIMER:
  165.             //----------------------------------------------------------
  166.             //Use two timers if BugSmarts called from timer routine
  167.             //----------------------------------------------------------
  168.             if (wParam == 1) {
  169.                 BugSmarts(hwnd);
  170.             } else {
  171.                 if (sNumBugs > (sBugLimit/5) * 4) { 
  172.                     qsort (bsBugArray, sNumBugs, sizeof(BUGSTRUCT), BugCmp);
  173.                     sNumBugs -= (sNumBugs / 5);
  174.                 }
  175.             }
  176.             break;
  177.  
  178.         case WM_ERASEBKGND:
  179.             //
  180.             // We don't want the background erased
  181.             //
  182.             return 0;
  183.  
  184.         case WM_DESTROY:
  185.  
  186.             //----------------------------------------------------------
  187.             //Use timer 1 if BugSmarts routine is called from WM_TIMER
  188.             //instead of from the message loop.
  189.             //----------------------------------------------------------
  190.             if (wTimer) KillTimer(hwnd, 1);
  191.             if (wTimer1) KillTimer(hwnd, 2);
  192.             break;
  193.     }
  194.     return DefScreenSaverProc(hwnd, msg, wParam, lParam);
  195. }
  196.  
  197. //========================================================================
  198. //ScreenSaverConfigureDialog - Dialog procedure for configure dialog box
  199. //========================================================================
  200. BOOL FAR PASCAL ScreenSaverConfigureDialog(HWND hDlg, WORD msg, WORD wParam, 
  201.                                            LONG lParam) {
  202.     int    i, j;
  203.     char    szTemp[10];
  204.  
  205.     switch (msg) {
  206.         case WM_INITDIALOG:
  207.  
  208.  
  209.             GetStrings();
  210.  
  211.             GetProfile();
  212.             SetText (hDlg, IDD_REDTEXT, wRNutrition, "Red: ");
  213.             SetText (hDlg, IDD_GREENTEXT, wGNutrition, "Green: ");
  214.             SetText (hDlg, IDD_BLUETEXT, wBNutrition, "Blue: ");
  215.             SetText (hDlg, IDD_MAXBTEXT, sBugLimit, "Max Number of Bugs: ");
  216.             SetText (hDlg, IDD_BIRTHTEXT, sBabyLevel, "Reproduction Level: ");
  217.             SetText (hDlg, IDD_SUSTEXT, sSustenance, "Sustenance Level: ");
  218.  
  219.             SetScrollRange (GetDlgItem (hDlg, IDD_REDLEVEL), 
  220.                             SB_CTL, 0, 10, FALSE);
  221.             SetScrollPos (GetDlgItem (hDlg, IDD_REDLEVEL), 
  222.                           SB_CTL, wRNutrition, TRUE);
  223.  
  224.             SetScrollRange (GetDlgItem (hDlg, IDD_GREENLEVEL), 
  225.                             SB_CTL, 0, 10, FALSE);
  226.             SetScrollPos (GetDlgItem (hDlg, IDD_GREENLEVEL), 
  227.                           SB_CTL, wGNutrition, TRUE);
  228.  
  229.             SetScrollRange (GetDlgItem (hDlg, IDD_BLUELEVEL), 
  230.                             SB_CTL, 0, 10, FALSE);
  231.             SetScrollPos (GetDlgItem (hDlg, IDD_BLUELEVEL), 
  232.                           SB_CTL, wBNutrition, TRUE);
  233.  
  234.             if (sBugLimit > 100)
  235.                 i = ((sBugLimit - 100) / 10) + 100;
  236.             else
  237.                 i = sBugLimit;
  238.             SetScrollRange (GetDlgItem (hDlg, IDD_MAXBLEVEL), 
  239.                             SB_CTL, 0, (MAXBUGS-100)/10+100, FALSE);
  240.             SetScrollPos (GetDlgItem (hDlg, IDD_MAXBLEVEL), 
  241.                           SB_CTL, i, TRUE);
  242.  
  243.             if (sBabyLevel > 100)
  244.                 i = ((sBabyLevel - 100) / 10) + 100;
  245.             else
  246.                 i = sBabyLevel;
  247.             SetScrollRange (GetDlgItem (hDlg, IDD_BIRTHLEVEL), 
  248.                             SB_CTL, 0, 500, FALSE);
  249.             SetScrollPos (GetDlgItem (hDlg, IDD_BIRTHLEVEL), 
  250.                           SB_CTL, i, TRUE);
  251.  
  252.             if (sSustenance > 100)
  253.                 i = ((sSustenance - 100) / 10) + 100;
  254.             else
  255.                 i = sSustenance;
  256.             SetScrollRange (GetDlgItem (hDlg, IDD_SUSLEVEL), 
  257.                             SB_CTL, 0, 500, FALSE);
  258.             SetScrollPos (GetDlgItem (hDlg, IDD_SUSLEVEL), 
  259.                           SB_CTL, i, TRUE);
  260.  
  261.             SendDlgItemMessage (hDlg, IDD_BIRTHCOLOR, BM_SETCHECK, 
  262.                                 bBColorFlag, 0);
  263.             SendDlgItemMessage (hDlg, IDD_DEATHCOLOR, BM_SETCHECK, 
  264.                                 bDColorFlag, 0);
  265.             SendDlgItemMessage (hDlg, IDD_PWENABLE, BM_SETCHECK, 
  266.                                 bPWEnabled, 0);
  267.             return TRUE;
  268.  
  269.         case WM_COMMAND:
  270.             switch (wParam) {
  271.  
  272.                 case IDD_BIRTHCOLOR:
  273.                     if (HIWORD (lParam) == BN_CLICKED) {
  274.                         if (SendDlgItemMessage (hDlg, IDD_BIRTHCOLOR, 
  275.                                                 BM_GETCHECK, 0, 0) == 0)
  276.                             SendDlgItemMessage (hDlg, IDD_BIRTHCOLOR, BM_SETCHECK,
  277.                                             1, 0);
  278.                         else
  279.                             SendDlgItemMessage (hDlg, IDD_BIRTHCOLOR, BM_SETCHECK,
  280.                                             0, 0);
  281.                     }
  282.                     break;
  283.  
  284.                 case IDD_DEATHCOLOR:
  285.                     if (HIWORD (lParam) == BN_CLICKED) {
  286.                         if (SendDlgItemMessage (hDlg, IDD_DEATHCOLOR, 
  287.                                                 BM_GETCHECK, 0, 0) == 0)
  288.                             SendDlgItemMessage (hDlg, IDD_DEATHCOLOR, BM_SETCHECK,
  289.                                                 1, 0);
  290.                         else
  291.                             SendDlgItemMessage (hDlg, IDD_DEATHCOLOR, BM_SETCHECK,
  292.                                                 0, 0);
  293.                     }
  294.                     break;
  295.  
  296.                 case IDD_PWENABLE:
  297.                     if (HIWORD (lParam) == BN_CLICKED) {
  298.                         if (SendDlgItemMessage (hDlg, IDD_PWENABLE, 
  299.                                                 BM_GETCHECK, 0, 0) == 0)
  300.                             SendDlgItemMessage (hDlg, IDD_PWENABLE, BM_SETCHECK,
  301.                                                 1, 0);
  302.                         else
  303.                             SendDlgItemMessage (hDlg, IDD_PWENABLE, BM_SETCHECK,
  304.                                                 0, 0);
  305.                     }
  306.                     break;
  307.  
  308.                 case IDD_PWSET: {
  309.                         FARPROC    lpfnPWDlgProc;
  310.                         lpfnPWDlgProc = MakeProcInstance (DlgChangePassword, 
  311.                                                              hMainInstance);
  312.                         DialogBox (hMainInstance, 
  313.                                    MAKEINTRESOURCE (DLG_CHANGEPASSWORD),
  314.                                    hDlg, lpfnPWDlgProc);
  315.                         FreeProcInstance (lpfnPWDlgProc);
  316.                     }
  317.                     break;
  318.  
  319.                 case IDD_HELP: {
  320.                         FARPROC    lpfnAboutDlgProc;
  321.                         lpfnAboutDlgProc = MakeProcInstance (AboutDlgProc, 
  322.                                                              hMainInstance);
  323.                         DialogBox (hMainInstance, "About", hDlg, lpfnAboutDlgProc);
  324.                         FreeProcInstance (lpfnAboutDlgProc);
  325.                     }
  326.                     break;
  327.  
  328.                 case IDOK:
  329.                     i = GetScrollPos (GetDlgItem (hDlg, IDD_REDLEVEL), SB_CTL);
  330.                     itoa (i, szTemp, 10);
  331.                     WritePrivateProfileString (szAppName, "Red", szTemp,
  332.                                                szIniName);
  333.  
  334.                     i = GetScrollPos (GetDlgItem (hDlg, IDD_GREENLEVEL), SB_CTL);
  335.                     itoa (i, szTemp, 10);
  336.                     WritePrivateProfileString (szAppName, "Green", szTemp,
  337.                                                szIniName);
  338.  
  339.                     i = GetScrollPos (GetDlgItem (hDlg, IDD_BLUELEVEL), SB_CTL);
  340.                     itoa (i, szTemp, 10);
  341.                     WritePrivateProfileString (szAppName, "Blue", szTemp,
  342.                                                szIniName);
  343.  
  344.                     i = GetScrollPos (GetDlgItem (hDlg, IDD_MAXBLEVEL), SB_CTL);
  345.                     if (i > 100) i = 100 + ((i - 100) * 10);
  346.                     itoa (i, szTemp, 10);
  347.                     WritePrivateProfileString (szAppName, "MaxBugs", szTemp,
  348.                                                szIniName);
  349.  
  350.                     i = GetScrollPos (GetDlgItem (hDlg, IDD_BIRTHLEVEL), SB_CTL);
  351.                     if (i > 100) i = 100 + ((i - 100) * 10);
  352.                     itoa (i, szTemp, 10);
  353.                     WritePrivateProfileString (szAppName, "BabyLevel", szTemp,
  354.                                                szIniName);
  355.  
  356.                     i = GetScrollPos (GetDlgItem (hDlg, IDD_SUSLEVEL), SB_CTL);
  357.                     if (i > 100) i = 100 + ((i - 100) * 10);
  358.                     itoa (i, szTemp, 10);
  359.                     WritePrivateProfileString (szAppName, "Sustenance", szTemp,
  360.                                                szIniName);
  361.  
  362.                     i = (int) SendDlgItemMessage (hDlg, IDD_BIRTHCOLOR, 
  363.                                                   BM_GETCHECK, 0, 0);
  364.                     itoa (i, szTemp, 10);
  365.                     WritePrivateProfileString (szAppName, "BirthColor", szTemp,
  366.                                                szIniName);
  367.                     i = (int) SendDlgItemMessage (hDlg, IDD_DEATHCOLOR, 
  368.                                                   BM_GETCHECK, 0, 0);
  369.                     itoa (i, szTemp, 10);
  370.                     WritePrivateProfileString (szAppName, "DeathColor", szTemp,
  371.                                                szIniName);
  372.                     i = (int) SendDlgItemMessage (hDlg, IDD_PWENABLE, 
  373.                                                   BM_GETCHECK, 0, 0);
  374.                     itoa (i, szTemp, 10);
  375.                     WritePrivateProfileString (szAppName, szIsPassword, szTemp,
  376.                                                szIniName);
  377.                     EndDialog (hDlg, TRUE);
  378.                     return TRUE;
  379.                 case IDCANCEL:
  380.                     EndDialog (hDlg, FALSE);
  381.                     return TRUE;
  382.             }
  383.             break;
  384.  
  385.  
  386.         case WM_HSCROLL:
  387.  
  388.             i = GetScrollPos (HIWORD (lParam), SB_CTL);    // Get Scroll bar Pos
  389.             j = GetDlgCtrlID (HIWORD (lParam));            // Get Scroll bar ID
  390.  
  391.             switch (wParam) {
  392.                 case SB_LINEUP:
  393.                     i--;
  394.                     break;
  395.  
  396.                 case SB_LINEDOWN:
  397.                     i++;
  398.                     break;
  399.  
  400.                 case SB_PAGEUP:
  401.                     if (j == IDD_REDLEVEL || 
  402.                         j == IDD_GREENLEVEL || 
  403.                         j == IDD_BLUELEVEL)
  404.                         i -=2;
  405.                     else
  406.                         i -= 10;
  407.                     break;
  408.  
  409.                 case SB_PAGEDOWN:
  410.                     if (j == IDD_REDLEVEL || 
  411.                         j == IDD_GREENLEVEL || 
  412.                          j == IDD_BLUELEVEL)
  413.                         i += 2;
  414.                     else
  415.                         i += 10;
  416.                     break;
  417.  
  418.                 case SB_THUMBTRACK:
  419.                 case SB_THUMBPOSITION:
  420.                     i = LOWORD (lParam);
  421.                     break;
  422.             }
  423.             SetScrollPos (HIWORD (lParam), SB_CTL, i, TRUE);
  424.  
  425.             switch (j) {
  426.                 case IDD_REDLEVEL:
  427.                     SetText (hDlg, IDD_REDTEXT, i, "Red: ");
  428.                     break;
  429.  
  430.                 case IDD_GREENLEVEL:
  431.                     SetText (hDlg, IDD_GREENTEXT, i, "Green: ");
  432.                     break;
  433.  
  434.                 case IDD_BLUELEVEL:
  435.                     SetText (hDlg, IDD_BLUETEXT, i, "Blue: ");
  436.                     break;
  437.  
  438.                 case IDD_MAXBLEVEL:
  439.                     if (i > 100) i = 100 + ((i - 100) * 10);
  440.                     SetText (hDlg, IDD_MAXBTEXT, i, "Max Number of Bugs: ");
  441.                     break;
  442.  
  443.                 case IDD_SUSLEVEL:
  444.                     if (i > 100) i = 100 + ((i - 100) * 10);
  445.                     SetText (hDlg, IDD_SUSTEXT, i, "Sustenance Level: ");
  446.                     break;
  447.  
  448.                 case IDD_BIRTHLEVEL:
  449.                     if (i > 100) i = 100 + ((i - 100) * 10);
  450.                     SetText (hDlg, IDD_BIRTHTEXT, i, "Reproduction Level: ");
  451.                     break;
  452.             }
  453.             break;
  454.     }
  455.     return FALSE;
  456. }    
  457. //========================================================================
  458. //About Dlg Proc - Processes messages for the About box.
  459. //========================================================================
  460. BOOL FAR PASCAL AboutDlgProc(HWND hDlg, WORD msg, WORD wParam, LONG lParam) {
  461.  
  462.     switch (msg) {
  463.  
  464.         case WM_INITDIALOG:
  465.             return TRUE;
  466.  
  467.         case WM_COMMAND:
  468.             switch (wParam) {
  469.  
  470.                 case IDOK:
  471.                 case IDCANCEL:
  472.                     EndDialog (hDlg, TRUE);
  473.                     return TRUE;
  474.             }
  475.             break;
  476.     }
  477.     return FALSE;
  478. }    
  479.  
  480. //------------------------------------------------------------------------
  481. //Process dead bugs using C code.
  482. //------------------------------------------------------------------------
  483. void DeadBugsC (HDC hdc, int sNumBugs, int sDeadBugs, BUGSTRUCT *bsBugArray) {
  484.  
  485.     BUGSTRUCT    * bspCurrBug;
  486.     BUGSTRUCT    * bspNextBug;
  487.     int            i, j;
  488.  
  489.     if (sDeadBugs) {
  490.         i = 0;
  491.         j = 1;
  492.         while (i < sNumBugs && j < sNumBugs) {
  493.  
  494.             bspCurrBug = &bsBugArray[i];
  495.             bspNextBug = &bsBugArray[j];
  496.  
  497.             if (bspCurrBug->lFood <= 0) {
  498.                 if (bDColorFlag)
  499.                     SetPixel (hdc, bspCurrBug->PosX, bspCurrBug->PosY, 0x000040);
  500.                 bspCurrBug->PosX = bspNextBug->PosX;
  501.                 bspCurrBug->PosY = bspNextBug->PosY;
  502.                 bspCurrBug->wXVec = bspNextBug->wXVec;
  503.                 bspCurrBug->wYVec = bspNextBug->wYVec;
  504.                 bspCurrBug->lFood = bspNextBug->lFood;
  505.                 bspCurrBug->dwColor = bspNextBug->dwColor;
  506.                 j++;
  507.             } else {
  508.                 i++;
  509.                 if (i <= j) j = i + 1;
  510.             }
  511.         }
  512.     }
  513. }
  514. //------------------------------------------------------------------------
  515. //Process dead bugs using assembler code
  516. //------------------------------------------------------------------------
  517. void DeadBugs (HDC hdc, int sNumBugs, int sDeadBugs, BUGSTRUCT *bsBugArray) {
  518.  
  519.     int    sBugSize ;
  520.  
  521.     if (sDeadBugs) {
  522.         sBugSize = sizeof (BUGSTRUCT);
  523.         _asm {
  524.             push    di                                                ;MSC requires SI,DI saved
  525.             push    si
  526.             push    es
  527.             pushf
  528.             cld
  529.             mov    di,ds                                            ;ES = DS
  530.             mov    es,di
  531.             mov    si,bsBugArray                                ;SI = bpNextBug
  532.             mov    di,si                                            ;DI = bpCurrBug
  533.             mov    ax,sNumBugs                                    ;Compute offset of end
  534.             mul    sBugSize                                        ;  of the array.
  535.             add    ax,di
  536. deadbugs_1:
  537.                 cmp    si,ax                                         ;while (bsNextBug >= 
  538.                 jae    deadbugs_4                                ;  bsBugArray + sNumBugs){
  539.                 xor    dx,dx                                        ;DX = 0
  540.                 cmp    word ptr [di.lFood+2],dx            ;bsNextBug->lFood <= 0
  541.                 jl     deadbugs_2
  542.                 ja     deadbugs_3
  543.                 cmp    word ptr [di.lFood],dx
  544.                 jne    deadbugs_3
  545. deadbugs_2:
  546.                 cmp    bDColorFlag,dx                            ;if (bColorFlag) {
  547.                 je        deadbugs_21
  548.  
  549.                 push    ax
  550.                 push    es
  551.                 push    hdc                                        ;SetPixel(hdc, bspCurr
  552.                 push    [di.PosX]                                ;         bspCurrBug.PosX,
  553.                 push    [di.PosY]                                ;         bspCurrBug.PosY,
  554.                 push    dx                                            ;         0x000080);
  555.                 mov    dl,80h
  556.                 push    dx
  557.                 call    SetPixel                                    ;Win trashes all regs but
  558.                 pop    es                                            ;  DS, BP, SI, and DI.
  559.                 pop    ax
  560.                 cld                                                ;}
  561. deadbugs_21:
  562.                 push    di                                            ;for (i=0;
  563.                 mov    cx,sBugSize                                ;     i<sizeof(BUGSTRUCT);
  564.                 rep    movsb                                        ;     i++;) {
  565.                 pop    di                                            ;  *bsCurrBug=*bsNextBug
  566.                 jmp    short deadbugs_1
  567. deadbugs_3:
  568.                 add    di,sBugSize                               ;bspCurrBug++
  569.                 cmp    si,di                                        ;if (bspCurrBug>bspNextBug)
  570.                 ja        deadbugs_1                                ;  bspNextBug=bspCurrBug+1
  571.                 mov    si,di
  572.                 add    si,sBugSize
  573.                 jmp    short deadbugs_1                        ;}
  574. deadbugs_4:
  575.             popf
  576.             pop    es
  577.             pop    si
  578.             pop    di
  579.         }
  580.     }
  581. }
  582.  
  583. //-----------------------------------------------------------------------
  584. //BugSmarts - Routine that computes the next move for each of the bugs
  585. //-----------------------------------------------------------------------
  586. void BugSmarts (HWND hwnd) {
  587.  
  588.     HDC            hdc;
  589.     int            i, sNewBugs, sDeadBugs, sRandom;
  590.     DWORD            dwOldPel;
  591.     long            lPelFood;
  592.  
  593.     BUGSTRUCT    * bspCurrBug;
  594.     BUGSTRUCT    * bspNextBug;    
  595.  
  596.     hdc = GetDC (hwnd);
  597.     sNewBugs = 0;
  598.     sDeadBugs = 0;
  599.  
  600.     for (i = 0; i < sNumBugs; i++) {
  601.  
  602.         bspCurrBug = &bsBugArray[i];
  603.         sRandom = rand();
  604.         //
  605.         //Compute next move
  606.         //
  607.         if (i < sScoutLimit) {
  608.             bspCurrBug->PosX += bspCurrBug->wXVec + (sRandom % 3) - 2;
  609.             bspCurrBug->PosY += bspCurrBug->wYVec + ((sRandom >> 2) % 3) - 2;
  610.         } else {
  611.             bspCurrBug->PosX += (sRandom % 3) - 1;
  612.             bspCurrBug->PosY += ((sRandom >> 2) % 3) - 1;
  613.         }
  614.         //
  615.         //Get pixel
  616.         //
  617.         dwOldPel = GetPixel (hdc, bspCurrBug->PosX, bspCurrBug->PosY);
  618.         //
  619.         //Determine the nutritional value of Pel by its color
  620.         //
  621.         if (dwOldPel == -1) {
  622.             bspCurrBug->lFood = 0;
  623.         } else {
  624.             lPelFood = (BYTE)dwOldPel * wRNutrition +
  625.                         ((WORD)dwOldPel >> 8) * wGNutrition +
  626.                         (dwOldPel >> 16) * wBNutrition;
  627.             bspCurrBug->lFood += lPelFood;
  628.             bspCurrBug->lFood -= sSustenance;
  629.         }
  630.         //
  631.         //Check for dead bugs
  632.         //
  633.         if (bspCurrBug->lFood <= 0) 
  634.             sDeadBugs++;
  635.         else {
  636.             //
  637.             //If not getting enough food, try a new direction
  638.             //
  639.             if (lPelFood <= sSustenance) {
  640.                 bspCurrBug->wXVec = (sRandom >> 4) % 3;
  641.                 bspCurrBug->wYVec = (sRandom >> 6) % 3;
  642.             }
  643.             if (dwOldPel != 0)
  644.                 SetPixel (hdc, bspCurrBug->PosX, bspCurrBug->PosY, 
  645.                           bspCurrBug->dwColor);
  646.         }
  647.         //
  648.         //See if bug can reproduce
  649.         //
  650.         if (sNumBugs + sNewBugs < sBugLimit) 
  651.             if (bspCurrBug->lFood > sBabyLevel) {
  652.  
  653.                 bspNextBug = &bsBugArray[sNumBugs + sNewBugs];
  654.  
  655.                 bspNextBug->wXVec = (sRandom % 3) - 1;
  656.                 bspNextBug->wYVec = ((sRandom >> 2) % 3) - 1;
  657.  
  658.                 bspNextBug->PosX = bspCurrBug->PosX + 
  659.                                      bspCurrBug->wXVec +
  660.                                      bspNextBug->wXVec;
  661.                 bspNextBug->PosY = bspCurrBug->PosY + 
  662.                                      bspCurrBug->wYVec +
  663.                                      bspNextBug->wYVec;
  664.  
  665.                 bspNextBug->lFood = sSustenance * 2;
  666.                 bspNextBug->dwColor = 0x000000;
  667.                 if (bBColorFlag)
  668.                     SetPixel (hdc, bspCurrBug->PosX, bspCurrBug->PosY, 0x008000);
  669.  
  670.                 bspCurrBug->lFood -= sBabyLevel/2;
  671.                 sNewBugs++;
  672.             }
  673.     }
  674.     sNumBugs += sNewBugs;
  675.     //
  676.     //If any dead bugs, compress data in array
  677.     //
  678.     DeadBugs (hdc, sNumBugs, sDeadBugs, bsBugArray);
  679.     
  680.     if (sDeadBugs) {
  681.         sNumBugs -= sDeadBugs;
  682.     }
  683.     if (sNumBugs >= sBugLimit) {
  684.         SetPixel (hdc, 0, 0, 0x0000ff);
  685.         SetPixel (hdc, 0, 1, 0x0000ff);
  686.         SetPixel (hdc, 1, 0, 0x0000ff);
  687.         SetPixel (hdc, 1, 1, 0x0000ff);
  688.     } else {
  689.         SetPixel (hdc, 0, 0, 0x00ff00);
  690.         SetPixel (hdc, 0, 1, 0x00ff00);
  691.         SetPixel (hdc, 1, 0, 0x00ff00);
  692.         SetPixel (hdc, 1, 1, 0x00ff00);
  693.     }     
  694.     ReleaseDC (hwnd, hdc);
  695.     if (sNumBugs == 0) 
  696.         PostMessage (hwnd, WM_USER, 0, 0);
  697.  
  698.     return;
  699. }
  700.  
  701. //------------------------------------------------------------------------
  702. //Compare function used for sorting Bug array
  703. //------------------------------------------------------------------------
  704. int BugCmp (BUGSTRUCT * Bug1, BUGSTRUCT * Bug2) {
  705.     
  706.     if (Bug1->lFood > Bug2->lFood)
  707.         return -1;
  708.     else
  709.         return 1;
  710. }
  711. //------------------------------------------------------------------------
  712. //Get Profile - Reads the profile info from CONTROL.INI.
  713. //------------------------------------------------------------------------
  714. void GetProfile (void) {
  715.     wRNutrition = GetPrivateProfileInt (szAppName, "Red", 1,
  716.                                         szIniName);
  717.     wGNutrition = GetPrivateProfileInt (szAppName, "Green", 1,
  718.                                         szIniName);         
  719.     wBNutrition = GetPrivateProfileInt (szAppName, "Blue", 1,
  720.                                         szIniName);         
  721.     sBugLimit = GetPrivateProfileInt (szAppName, "MaxBugs", 512,
  722.                                         szIniName);
  723.     sSustenance = GetPrivateProfileInt (szAppName, "Sustenance", 512,
  724.                                         szIniName);
  725.     sBabyLevel = GetPrivateProfileInt (szAppName, "BabyLevel", 128,
  726.                                        szIniName);
  727.     bBColorFlag = GetPrivateProfileInt (szAppName, "BirthColor", TRUE,
  728.                                        szIniName);
  729.     bDColorFlag = GetPrivateProfileInt (szAppName, "DeathColor", TRUE,
  730.                                        szIniName);
  731.     bPWEnabled = GetPrivateProfileInt (szAppName, szIsPassword, FALSE,
  732.                                        szIniName);
  733.     return;
  734. }
  735. //------------------------------------------------------------------------
  736. //Set Text - Sets the text for a dialog box control
  737. //------------------------------------------------------------------------
  738. void SetText (HWND hwnd, int sCtlID, int sVal, char* szText) {
  739.  
  740.     char    szTemp[80], szTemp1[10];
  741.  
  742.     strcpy (szTemp, szText);
  743.     itoa (sVal, szTemp1, 10);
  744.     strcat (szTemp, szTemp1);
  745.     SetDlgItemText (hwnd, sCtlID, szTemp);
  746.     return;
  747.  
  748. //------------------------------------------------------------------------
  749. //GetStrings - Loads the screen saver vars from the RC file
  750. //------------------------------------------------------------------------
  751. void GetStrings(void)
  752. {
  753.     LoadString(hMainInstance, idsAppName, szAppName, sizeof (szAppName));
  754.     LoadString(hMainInstance, idsIsPassword, szIsPassword, 22);
  755.     LoadString(hMainInstance, idsIniFile, szIniFile, MAXFILELEN);
  756.     LoadString(hMainInstance, idsScreenSaver, szScreenSaver, 22);
  757.     LoadString(hMainInstance, idsPassword, szPassword, 16);
  758.     LoadString(hMainInstance, idsDifferentPW, szDifferentPW, BUFFLEN);
  759.     LoadString(hMainInstance, idsChangePW, szChangePW, 30);
  760.     LoadString(hMainInstance, idsBadOldPW, szBadOldPW, 255);
  761.     LoadString(hMainInstance, idsHelpFile, szHelpFile, MAXFILELEN);
  762.     LoadString(hMainInstance, idsNoHelpMemory, szNoHelpMemory, BUFFLEN);
  763. }
  764.