Click here to Skip to main content
15,884,815 members
Home / Discussions / C / C++ / MFC
   

C / C++ / MFC

 
QuestionRe: [win32]Draw on a background bitmap Pin
Mark Salsbery26-May-11 10:57
Mark Salsbery26-May-11 10:57 
AnswerRe: [win32]Draw on a background bitmap Pin
Member 296547126-May-11 11:45
Member 296547126-May-11 11:45 
GeneralRe: [win32]Draw on a background bitmap Pin
Mark Salsbery26-May-11 11:45
Mark Salsbery26-May-11 11:45 
GeneralRe: [win32]Draw on a background bitmap Pin
Member 296547126-May-11 11:47
Member 296547126-May-11 11:47 
GeneralRe: [win32]Draw on a background bitmap Pin
Mark Salsbery26-May-11 11:54
Mark Salsbery26-May-11 11:54 
GeneralRe: [win32]Draw on a background bitmap Pin
Member 296547126-May-11 12:07
Member 296547126-May-11 12:07 
GeneralRe: [win32]Draw on a background bitmap Pin
Mark Salsbery26-May-11 12:11
Mark Salsbery26-May-11 12:11 
AnswerRe: [win32]Draw on a background bitmap [modified] Pin
Mark Salsbery26-May-11 13:57
Mark Salsbery26-May-11 13:57 
Since this is fun and I haven't touched C++ in years, here's a double-buffered version...

Note I moved stuff out of the WM_PAINT handler that didn't need to be done every paint. For example, the offscreen buffer is only (re)created when the window size changes, the client rect is only updated when the window size changes, and the bitmap and its associated memoryDC are only loaded/created once (in WM_CREATE handler in the sample code).

Flicker free! Smile | :)

C++
POINT pt;
BITMAP Bitmap;
HANDLE hBitmap = 0;
HDC hBitmapMemoryDC = 0;
RECT ClientRect;
HBITMAP hOffScreenBitmap = 0;
HDC hOffScreenMemoryDC = 0;


LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
    PAINTSTRUCT ps;
    HDC hdc;

    switch (message)
    {
    case WM_CREATE:
        hBitmap = ::LoadImage(hInst, MAKEINTRESOURCE(IDB_BITMAP1), IMAGE_BITMAP, 0, 0, LR_CREATEDIBSECTION);
        ::GetObject(hBitmap, sizeof(Bitmap), &Bitmap);
        hBitmapMemoryDC = ::CreateCompatibleDC(0);
        ::SelectObject(hBitmapMemoryDC, hBitmap);
        break;
    case WM_PAINT:
        hdc = BeginPaint(hWnd, &ps);
        // blt the bitmap to the offscreen buffer
        ::StretchBlt(hOffScreenMemoryDC, 0, 0, ClientRect.right, ClientRect.bottom, hBitmapMemoryDC, 0, 0, Bitmap.bmWidth, Bitmap.bmHeight, SRCCOPY);
        // draw crosshairs on the offscreen buffer
        ::MoveToEx(hOffScreenMemoryDC, pt.x , 0 , NULL); 
        ::LineTo(hOffScreenMemoryDC, pt.x, ClientRect.bottom); 
        ::MoveToEx(hOffScreenMemoryDC, 0, pt.y, NULL); 
        ::LineTo(hOffScreenMemoryDC, ClientRect.right, pt.y); 
        // blt the offscreen buffer to the screen
        ::BitBlt(hdc, 0, 0, ClientRect.right, ClientRect.bottom, hOffScreenMemoryDC, 0, 0, SRCCOPY);
        EndPaint(hWnd, &ps);
        break;
    case WM_MOUSEMOVE:
        pt.x = LOWORD(lParam);
        pt.y = HIWORD(lParam);
        ::InvalidateRect(hWnd,NULL,FALSE); // changed to FALSE since we draw the entire client area
        ::UpdateWindow(hWnd);
        break;	
    case WM_ERASEBKGND:
        // We draw the background in WM_PAINT - don't do it here!
        return 1;
    case WM_SIZE:
        ClientRect.left = 0;
        ClientRect.top = 0;
        ClientRect.right = LOWORD(lParam);
        ClientRect.bottom = HIWORD(lParam);
        // (Re)Create the offscreen buffer
        if (hOffScreenBitmap != 0)
            ::DeleteObject(hOffScreenBitmap);
        if (hOffScreenMemoryDC != 0)
            ::DeleteDC(hOffScreenMemoryDC);
        hdc = ::GetDC(hWnd);
        hOffScreenMemoryDC = ::CreateCompatibleDC(hdc);
        hOffScreenBitmap = ::CreateCompatibleBitmap(hdc, ClientRect.right, ClientRect.bottom);
        ::SelectObject(hOffScreenMemoryDC, hOffScreenBitmap);
        ::ReleaseDC(hWnd, hdc);
        break;
    case WM_DESTROY:
        if (hBitmap != 0)
            ::DeleteObject(hBitmap);
        if (hBitmapMemoryDC != 0)
            ::DeleteDC(hBitmapMemoryDC);
        if (hOffScreenBitmap != 0)
            ::DeleteObject(hOffScreenBitmap);
        if (hOffScreenMemoryDC != 0)
            ::DeleteDC(hOffScreenMemoryDC);
         PostQuitMessage(0);
        break;
    default:
        return DefWindowProc(hWnd, message, wParam, lParam);
    }
    return 0;
}

Mark Salsbery
Microsoft MVP - Visual C++

Java | [Coffee]
modified on Thursday, May 26, 2011 8:30 PM

AnswerRe: [win32]Draw on a background bitmap Pin
bob1697228-May-11 18:59
bob1697228-May-11 18:59 
QuestionUsing streams Pin
Berlus26-May-11 2:40
Berlus26-May-11 2:40 
QuestionRe: Using streams Pin
David Crow26-May-11 2:49
David Crow26-May-11 2:49 
AnswerRe: Using streams [modified] Pin
Stefan_Lang26-May-11 3:01
Stefan_Lang26-May-11 3:01 
GeneralRe: Using streams Pin
Berlus26-May-11 10:05
Berlus26-May-11 10:05 
GeneralRe: Using streams Pin
Stefan_Lang26-May-11 21:14
Stefan_Lang26-May-11 21:14 
QuestionProblem opening URL Pin
pix_programmer26-May-11 1:44
pix_programmer26-May-11 1:44 
AnswerRe: Problem opening URL Pin
Richard MacCutchan26-May-11 1:53
mveRichard MacCutchan26-May-11 1:53 
GeneralRe: Problem opening URL Pin
pix_programmer26-May-11 1:58
pix_programmer26-May-11 1:58 
GeneralRe: Problem opening URL Pin
Richard MacCutchan26-May-11 2:59
mveRichard MacCutchan26-May-11 2:59 
GeneralRe: Problem opening URL [modified] Pin
pix_programmer26-May-11 3:20
pix_programmer26-May-11 3:20 
GeneralRe: Problem opening URL Pin
Richard MacCutchan26-May-11 3:32
mveRichard MacCutchan26-May-11 3:32 
AnswerRe: Problem opening URL Pin
Niklas L26-May-11 4:49
Niklas L26-May-11 4:49 
GeneralRe: Problem opening URL Pin
pix_programmer26-May-11 20:32
pix_programmer26-May-11 20:32 
GeneralRe: Problem opening URL Pin
Niklas L26-May-11 21:40
Niklas L26-May-11 21:40 
GeneralRe: Problem opening URL Pin
pix_programmer26-May-11 22:15
pix_programmer26-May-11 22:15 
QuestionRe: Problem opening URL Pin
Niklas L27-May-11 1:09
Niklas L27-May-11 1:09 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.