ÀÌ ¼½¼ÇÀÇ ¿¹¿¡¼´Â ¸¶¿ì½º Ä¿¼¸¦ ÃßÀû ÇÏ´Â ¹æ¹ýÀ» º¸¿© ÁÝ´Ï´Ù. ±×°ÍÀº »ç¿ëÀÚ°¡ ¸¶¿ì½º¸¦ µå·¡±× ÇÏ ¿© ¼±À» âÀÇ Å¬¶óÀÌ¾ðÆ® ¿µ¿ª¿¡ ±×¸± ¼ö ÀÖµµ·Ï Çϴ â ÇÁ·Î½ÃÀúÀÇ ºÎºÐÀ» Æ÷ÇÔ.
â ÇÁ·Î½ÃÀú WM_LBUTTONDOWN ¸Þ½ÃÁö¸¦ ¼ö½Å ÇÏ´Â °æ¿ì ¸¶¿ì½º¸¦ ĸóÇϰí Ä¿¼¸¦ ÁÙÀÇ ½ÃÀÛ ÁöÁ¡À¸·Î ÇØ´ç ÁÂÇ¥¸¦ »ç¿ë ÇÏ ¿© ÁÂÇ¥¸¦ ÀúÀå ÇÕ´Ï´Ù. ±×°ÍÀº ¶ÇÇÑ ClipCursor ÇÔ¼ö¸¦ »ç¿ë ÇÏ ¿© ¼± ±×¸®±â ÀÛ¾÷ ÇÏ´Â µ¿¾È Ŭ¶óÀÌ¾ðÆ® ¿µ¿ª¿¡ Ä¿¼¸¦ Á¦ÇÑ.
ù ¹øÂ° WM_MOUSEMOVE ¸Þ½ÃÁö¸¦ ÇÏ´Â µ¿¾È â ÇÁ·Î½ÃÀú¸¦ ¼±À» ±×¸³´Ï´Ù ½ÃÀÛ ÁöÁ¡¿¡¼ Ä¿¼ÀÇ ÇöÀç À§Ä¡¸¦. ÈÄ¼Ó WM_MOUSEMOVE ¸Þ½ÃÁö µ¿¾È â ÇÁ·Î½ÃÀú°¡ Áö¿ó´Ï´Ù ÀÌÀü ÁÙÀ» µå·ÎÀ׿¡ ÀÇÇØ ±×°ÍÀ» ÅëÇØ °Å²Ù·Î Ææ »öÀ¸·Î. ´ÙÀ½ ±×°ÍÀº »õ·Î¿î ¼±À» ±×¸³´Ï´Ù ½ÃÀÛ ÁöÁ¡¿¡¼ Ä¿¼ÀÇ »õ À§Ä¡.
WM_LBUTTONUP ¸Þ½ÃÁö´Â ±×¸®±â ÀÛ¾÷ÀÇ ³¡À» ¾Ë¸³´Ï´Ù. â ÇÁ·Î½ÃÀú ¸¶¿ì½º ĸó¸¦ ÇØÁ¦ ÇÏ °í Ŭ¶óÀÌ¾ðÆ® ¿µ¿ª¿¡¼ ¸¶¿ì½º¸¦ ÇØÁ¦.
LRESULT APIENTRY MainWndProc(HWND hwndMain, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
HDC hdc; // handle of device context
RECT rcClient; // client area rectangle
POINT ptClientUL; // client upper left corner
POINT ptClientLR; // client lower right corner
static POINTS ptsBegin; // beginning point
static POINTS ptsEnd; // new endpoint
static POINTS ptsPrevEnd; // previous endpoint
static BOOL fPrevLine = FALSE; // previous line flag
switch (uMsg)
{
case WM_LBUTTONDOWN:
// Capture mouse input.
SetCapture(hwndMain);
// Retrieve the screen coordinates of the client area,
// and convert them into client coordinates.
GetClientRect(hwndMain, &rcClient);
ptClientUL.x = rcClient.left;
ptClientUL.y = rcClient.top;
// Add one to the right and bottom sides, because the
// coordinates retrieved by GetClientRect do not
// include the far left and lowermost pixels.
ptClientLR.x = rcClient.right + 1;
ptClientLR.y = rcClient.bottom + 1;
ClientToScreen(hwndMain, &ptClientUL);
ClientToScreen(hwndMain, &ptClientLR);
// Copy the client coordinates of the client area
// to the rcClient structure. Confine the mouse cursor
// to the client area by passing the rcClient structure
// to the ClipCursor function.
SetRect(&rcClient, ptClientUL.x, ptClientUL.y,
ptClientLR.x, ptClientLR.y);
ClipCursor(&rcClient);
// Convert the cursor coordinates into a POINTS
// structure, which defines the beginning point of the
// line drawn during a WM_MOUSEMOVE message.
ptsBegin = MAKEPOINTS(lParam);
return 0;
case WM_MOUSEMOVE:
// When moving the mouse, the user must hold down
// the left mouse button to draw lines.
if (wParam & MK_LBUTTON)
{
// Retrieve a device context (DC) for the client area.
hdc = GetDC(hwndMain);
// The following function ensures that pixels of
// the previously drawn line are set to white and
// those of the new line are set to black.
SetROP2(hdc, R2_NOTXORPEN);
// If a line was drawn during an earlier WM_MOUSEMOVE
// message, draw over it. This erases the line by
// setting the color of its pixels to white.
if (fPrevLine)
{
MoveToEx(hdc, ptsBegin.x, ptsBegin.y,
(LPPOINT) NULL);
LineTo(hdc, ptsPrevEnd.x, ptsPrevEnd.y);
}
// Convert the current cursor coordinates to a
// POINTS structure, and then draw a new line.
ptsEnd = MAKEPOINTS(lParam);
MoveToEx(hdc, ptsBegin.x, ptsBegin.y, (LPPOINT) NULL);
LineTo(hdc, ptsEnd.x, ptsEnd.y);
// Set the previous line flag, save the ending
// point of the new line, and then release the DC.
fPrevLine = TRUE;
ptsPrevEnd = ptsEnd;
ReleaseDC(hwndMain, hdc);
}
break;
case WM_LBUTTONUP:
// The user has finished drawing the line. Reset the
// previous line flag, release the mouse cursor, and
// release the mouse capture.
fPrevLine = FALSE;
ClipCursor(NULL);
ReleaseCapture();
return 0;
case WM_DESTROY:
PostQuitMessage(0);
break;
// Process other messages.