思想:
之所以閃屏,是因爲鼠標在移動過程中,一直都在執行修補語句
pDC->BitBlt(rect.left,rect.top ,rect.Width(),rect.Height(),&DownmemDc,rect.left,rect.top,SRCCOPY);
(從在鼠標Down下去的時候保存的屏幕DC設備中截取相應大小的位圖去填補在鼠標UP之前的鼠標移動過所產生的線段的痕跡,從而達到畫橡皮線的效果)
雙緩存是創建了兩個內存設備,把貼圖修補的工作留在了另一個內存設備中進行。修補完以後,才把圖貼到屏幕上,從而解決閃屏的問題。
步驟1. 在頭文件中創建 內存設備,起始點,終點
CDC DownmemDc;
CPoint m_PtDown;
CPoint m_PtEnd;
步驟2. 在BUTTONdown事件中添加代碼:
m_PtDown = point;
m_PtEnd = point;
if ( DownmemDc) // 如果Up事件不在客戶區發生,將導致程序崩潰,所以每次Down事件開始要做判斷。
DownmemDc.DeleteDC();
CDC *pDc = GetDC();
CRect rect;
GetClientRect(&rect);
CBitmap bitmap;
bitmap.CreateCompatibleBitmap(pDc,rect.Width(),rect.Height());
DownmemDc.CreateCompatibleDC(pDc); // 內存設備1
DownmemDc.SelectObject(&bitmap);
DownmemDc.BitBlt(0,0,rect.Width(),rect.Height(),pDc,0,0,SRCCOPY);
ReleaseDC(pDc); // 釋放DC設備
步驟3 . 在MOUSEMove事件 中添加代碼:
CDC *pDc = GetDC();
if(nFlags & MK_LBUTTON)
{
CBrush brush; // 創建畫刷
brush.CreateStockObject(NULL_BRUSH);
CRect rectScreen; // 創建與當前設備大小的相同的矩形
GetClientRect( &rectScreen);
CBitmap bitmap; // 創建與當前設備兼容的BITMAP位圖
bitmap.CreateCompatibleBitmap(pDc,rectScreen.Width(),rectScreen.Height());
DownmemDc2.CreateCompatibleDC(pDc); // 創建與當前設備兼容的內存設備2
DownmemDc2.SelectObject( &bitmap);
// 修補位圖
CRect rect(m_PtDown,m_PtEnd);
rect.NormalizeRect();
rect.InflateRect(3,3);
// 從第一個內存設備中截取相應大小的位圖填補鼠標劃過生成的線段,( 這個過程在另一個內存設備中進行)
DownmemDc2.BitBlt(0,0 ,rectScreen.Width(),rectScreen.Height(),&DownmemDc,0,0,SRCCOPY);
m_PtEnd = point;
CRect NewRect(m_PtDown,point);
// 在內存上畫線 (雙緩存畫線)
DownmemDc2.SelectObject(&brush);
DownmemDc2.MoveTo(m_PtDown);
DownmemDc2.LineTo(point);
//////////////////////////////////////////////////////////////
/////////// 把從內存設備中修補好的圖貼到屏幕設備上
pDc->BitBlt(0,0,rectScreen.Width(),rectScreen.Height(),&DownmemDc2,0,0,SRCCOPY);
DownmemDc2.DeleteDC(); // 刪除內存設備
bitmap.DeleteObject(); // 刪除bitmap變量
ReleaseDC(pDc); // 釋放pDc
如有錯誤,還請批評指正,共同學習!