MFC1) создаём в своём оконном классе пустой обработчик сообщения WM_ERASEBKGND: | Код | BOOL CViewListing::OnEraseBkgnd(CDC* pDC) { return FALSE; }
|
2) в начало и конец функции обработки рисования (OnDraw или OnPaint) добавляем макросы PREPARE_BLIT_DC и DRAW_BLIT_DC: | Код | CMyView::OnDraw(CDC *pDC) { PREPARE_BLIT_DC(pDC);
// ... обычные функции рисования, например pDC->TextOut(...)
DRAW_BLIT_DC(pDC); }
|
Тексты макросов: | Код | // создаем контекст, совместимый с данным, очищаем его и подменяем указатель на контекст #define PREPARE_BLIT_DC(pDCDest) CDC dcMem;\ dcMem.CreateCompatibleDC(pDCDest);\ CBitmap *pPrevBmpMem=dcMem.GetCurrentBitmap();\ CRect rCl; GetClientRect(rCl); CBitmap BmpNewMem;\ BmpNewMem.CreateCompatibleBitmap(pDCDest, rCl.Width(), rCl.Height());\ dcMem.SelectObject(&BmpNewMem);\ dcMem.FillSolidRect(rCl, RGB(255,255,255)); \ CDC *pDCTemp=pDCDest; pDCDest=&dcMem;
// обратная подмена, переносим изображение на исходный контекст #define DRAW_BLIT_DC(pDCDest) pDCDest=pDCTemp;\ pDCDest->BitBlt(rCl.left, rCl.top, rCl.Width(), rCl.Height(), &dcMem,\ rCl.left, rCl.top, SRCCOPY);\ dcMem.SelectObject(pPrevBmpMem);
|
----- WinAPI Те-же действия, с одним отличием: в первый макрос передаётся не один а три аргумента: HWND окна (чтобы можно было определить рабочий прямоугольник), цвет для заливки бэкграунда (обычно - белый), и HDC (вместо CDC как в варианте для MFC). Текст макросов: | Код |
#define PREPARE_BLIT_DC_WIN32API(hDC, colorFill, hWnd) \ RECT rectClient; \ ::GetClientRect(hWnd, &rectClient); \ HDC hdcMem = ::CreateCompatibleDC(hDC); \ HBITMAP hPrevBmpMem = (HBITMAP)::GetCurrentObject(hdcMem, OBJ_BITMAP); \ HBITMAP hNewBmpMem = ::CreateCompatibleBitmap(hDC, rectClient.right-rectClient.left+1, rectClient.bottom-rectClient.top+1); \ ::SelectObject(hdcMem, hNewBmpMem); \ { \ HBRUSH hBrFill = ::CreateSolidBrush(colorFill); \ ::FillRect(hdcMem, &rectClient, hBrFill); \ ::DeleteObject(hBrFill); \ } \ HDC hdcTemp = hDC; hDC = hdcMem;
#define DRAW_BLIT_DC_WIN32API(hDC) \ hDC = hdcTemp; \ { \ int W = rectClient.right-rectClient.left+1; \ int H = rectClient.bottom-rectClient.top+1; \ ::BitBlt(hDC, rectClient.left, rectClient.top, W, H, hdcMem, 0, 0, SRCCOPY); \ } \ ::SelectObject(hdcMem, hPrevBmpMem); \ ::DeleteDC(hdcMem); \ ::DeleteObject(hNewBmpMem); \
|
Пример использования: | Код | void SomeDrawingFunction() { HDC hDC = // ... HWND hWnd = // ...
PREPARE_BLIT_DC_WIN32API(hDC, RGB(255,255,255), hWnd)
// // ... здесь мы рисуем на контексте "hDC"... //
DRAW_BLIT_DC_WIN32API(hDC) }
|
--------------------
| Цитата(Jimi Hendrix) | Well, I stand up next to a mountain And I chop it down with the edge of my hand |
|