home *** CD-ROM | disk | FTP | other *** search
/ BUG 4 / BUGCD1997_05.BIN / aplic / clip4win / clip4win.exe / C4W30E.HUF / SOURCE / DRAW.PRG < prev    next >
Text File  |  1993-10-14  |  4KB  |  148 lines

  1. ////////////////////////////
  2. //
  3. //    draw.prg
  4. //
  5. //    Copyright (C) 1993 Skelton Software, Kendal Cottage, Hillam, Leeds, UK.
  6. //    All Rights Reserved.
  7. //
  8. //    Drawing program, using a window procedure.
  9. //
  10. //    Instructions:
  11. //        press left mouse button somewhere in the client area
  12. //        move around
  13. //        release button
  14. //
  15. //        (use system box or Alt-F4 to make program exit)
  16. //
  17. ////////////////////////////
  18.  
  19. #define    WIN_WANT_ALL
  20. #include "windows.ch"
  21. #include "msg.ch"
  22. #include "paint.ch"
  23.  
  24.  
  25. #define    MAXPOINTS    2000
  26. #define    MOUSE_LBUTTON    MK_LBUTTON    // from windows.ch
  27.  
  28.  
  29. static    aX[MAXPOINTS]
  30. static    aY[MAXPOINTS]
  31.  
  32.  
  33. function main()
  34. local    hWnd
  35. local    aMsg[MSG_LENGTH]
  36. local    cAppName := "Draw"
  37.  
  38. if _GetPrevInstance() == 0
  39.     if !RegisterClass(CS_HREDRAW + CS_VREDRAW,    ; // class style
  40.               _GetInstance(),        ; // app instance
  41.               LoadIcon(0, IDI_APPLICATION),    ; // icon
  42.               LoadCursor(0, IDC_CROSS),    ; // cursor
  43.               GetStockObject(WHITE_BRUSH),    ; // background brush
  44.               cAppName,            ; // app name
  45.               {|hWnd, nMsg, nwParam, nlParam| ;
  46.                WndProc(hWnd, nMsg, nwParam, nlParam)}, ; // window proc
  47.               {WM_DESTROY,            ;
  48.                WM_LBUTTONDOWN, WM_LBUTTONUP,;
  49.                WM_MOUSEMOVE,        ;
  50.                WM_PAINT},            ;
  51.              )    // defaults for the rest
  52.                 // (an important default is RCF_WINDOW,
  53.                 // so unwanted msgs go to the default handler)
  54.  
  55.         return -1
  56.     endif
  57. endif
  58.  
  59. hWnd = CreateWindow(cAppName,        ;    // window class
  60.             "Join the dots",    ;    // caption for title bar
  61.             WS_OVERLAPPEDWINDOW,;    // window style
  62.             CW_USEDEFAULT,    ;    // x co-ordinate
  63.             CW_USEDEFAULT,    ;    // y co-ordinate
  64.             0,            ;    // width
  65.             0,            ;    // height
  66.             0,            ;    // hWnd of parent (none)
  67.             0,            ;    // hMenu of menu (none yet)
  68.             _GetInstance())        // our own app instance
  69.  
  70. if hWnd == 0
  71.     MessageBox(, "Window Creation Failed!", "Error", MB_ICONEXCLAMATION + MB_OK)
  72.     return -1
  73. endif
  74.  
  75. // make sure it's displayed ...
  76. ShowWindow(hWnd, _GetnCmdShow())
  77.  
  78. // ... and up to date
  79. UpdateWindow(hWnd)            // WndProc() can get called from here
  80.  
  81.  
  82. do while GetMessage(aMsg, 0, 0, 0)
  83.     TranslateMessage(aMsg)
  84.     DispatchMessage(aMsg)        // WndProc() often gets called from here
  85. enddo
  86.  
  87. UnregisterClass(cAppName, _GetInstance())
  88.  
  89. return aMsg[MSG_wParam]
  90.  
  91.  
  92.  
  93. function WndProc(hWnd, nMsg, nwParam, nlParam)
  94. static    nCount := 0
  95. local    aPaint[PS_LENGTH], hDC, i, j
  96.  
  97. do case
  98.     case nMsg == WM_LBUTTONDOWN
  99.         // this is logically the 1st event we want to handle...
  100.         nCount = 0
  101.         InvalidateRect(hWnd)
  102.         return 0    // 0 means we processed the msg
  103.     case nMsg == WM_MOUSEMOVE
  104.         // ... but it would be faster to put this first
  105.         //     (only matters on a _slow_ cpu) ...
  106.         if C4W_And(nwParam, MOUSE_LBUTTON) != 0 .and. nCount < MAXPOINTS
  107.             nCount++
  108.             aX[nCount] = c4w_LoWord(nlParam)
  109.             aY[nCount] = c4w_HiWord(nlParam)
  110.  
  111.             // leave a trail of black dots
  112.             hDC = GetDC(hWnd)
  113.             SetPixel(hDC, aX[nCount], aY[nCount], RGB(0,0,0))
  114.             ReleaseDC(hWnd, hDC)
  115.         endif
  116.         return 0    // 0 means we processed the msg
  117.     case nMsg == WM_LBUTTONUP
  118.         // ... then this is the last of the sequence, before...
  119.         InvalidateRect(hWnd)
  120.         return 0    // 0 means we processed the msg
  121.     case nMsg == WM_PAINT
  122.         // ... now we join the dots in many ways!
  123.         hDC = BeginPaint(hWnd, aPaint)
  124.  
  125.         for i = 1 to nCount - 1
  126.             for j = 1 to nCount
  127.                 MoveTo(hDC, aX[i], aY[i])
  128.                 LineTo(hDC, aX[j], aY[j])
  129.             next j
  130.         next i
  131.  
  132.         EndPaint(hWnd, aPaint)
  133.         return 0    // 0 means we processed the msg
  134.  
  135.     case nMsg == WM_DESTROY
  136.         // leave out this, and you can't exit!!
  137.         PostQuitMessage(0)
  138.         return 0    // 0 means we processed the msg
  139. endcase
  140.  
  141. // This could _only_ get used with WM_USER and above msgs -- because of
  142. // the array of msgs we specified with RegisterClass() -- and we're
  143. // not using WM_USER etc.  However, it's always a good idea to allow
  144. // for the unexpected.
  145.  
  146. return DefWindowProc(hWnd, nMsg, nwParam, nlParam)
  147.  
  148.