这里直接贴上MFC window程序设计的代码,然后加上编程需要注意的地方
CMainWindow::CMainWindow ()
{
m_bTracking = FALSE;
m_bCaptureEnabled = TRUE;
//
// Register a WNDCLASS.
//
CString strWndClass = AfxRegisterWndClass (
0,
AfxGetApp ()->LoadStandardCursor (IDC_CROSS), //加载window的十字光标
(HBRUSH) (COLOR_WINDOW + 1),
AfxGetApp ()->LoadStandardIcon (IDI_WINLOGO)
);
//
// Create a window.
//
Create (strWndClass, _T ("Mouse Capture Demo (Capture Enabled)"));
}
void CMainWindow::OnLButtonDown (UINT nFlags, CPoint point)
{
//
// Record the anchor point and set the tracking flag.
//
m_ptFrom = point;
m_ptTo = point;
m_bTracking = TRUE;
//
// If capture is enabled, capture the mouse.
//
if (m_bCaptureEnabled)
SetCapture (); //这里“捕获”鼠标,意思是即使鼠标不在客户区,也发送鼠标消息到窗口
}
void CMainWindow::OnMouseMove (UINT nFlags, CPoint point)
{
//
// If the mouse is moved while we're "tracking" (that is, while a
// line is being rubber-banded), erase the old rubber-band line and
// draw a new one.
//
if (m_bTracking) {
CClientDC dc (this);
InvertLine (&dc, m_ptFrom, m_ptTo);
InvertLine (&dc, m_ptFrom, point);
m_ptTo = point;
}
}
void CMainWindow::OnLButtonUp (UINT nFlags, CPoint point)
{
//
// If the left mouse button is released while we're tracking, release
// the mouse if it's currently captured, erase the last rubber-band
// line, and draw a thick red line in its place.
// //假如没有捕获鼠标,鼠标在非客户区抬起时,不会发送消息到窗口
if (m_bTracking) {
m_bTracking = FALSE;
if (GetCapture () == this)
::ReleaseCapture (); //假如有捕获鼠标,在这一定要释放掉
CClientDC dc (this);
InvertLine (&dc, m_ptFrom, m_ptTo);
CPen pen (PS_SOLID, 16, RGB (255, 0, 0));
dc.SelectObject (&pen);
dc.MoveTo (m_ptFrom);
dc.LineTo (point);
}
}
void CMainWindow::OnNcLButtonDown (UINT nHitTest, CPoint point)
{
//
// When the window's title bar is clicked with the left mouse button,
// toggle the capture flag on or off and update the window title.
//
//非客户区鼠标左键点击会发送此消息
if (nHitTest == HTCAPTION) {
m_bCaptureEnabled = m_bCaptureEnabled ? FALSE : TRUE;
SetWindowText (m_bCaptureEnabled ?
_T ("Mouse Capture Demo (Capture Enabled)") :
_T ("Mouse Capture Demo (Capture Disabled)"));
}
CFrameWnd::OnNcLButtonDown (nHitTest, point); //这里要把消息发给子类,让window去处理,否则鼠标的其他操作会失效
}
void CMainWindow::InvertLine (CDC* pDC, CPoint ptFrom, CPoint ptTo)
{
//
// Invert a line of pixels by drawing a line in the R2_NOT drawing mode.
//
int nOldMode = pDC->SetROP2 (R2_NOT); //这是设置前背景渲染模式,R2_NOT是取反
pDC->MoveTo (ptFrom);
pDC->LineTo (ptTo);
pDC->SetROP2 (nOldMode);
}