EDIT: I am aware this is the slowest way to draw a square, but I do need to set pixels individually for a separate purpose.
I'm pretty sure what I'm trying to do is create a Frame Buffer. I have the following code:
... /* Other Unrelated (<- I promise) Code */
switch(message)
{
/* Window is being created*/
case WM_CREATE:
return 0;
break;
/* Window is closing*/
case WM_CLOSE:
PostQuitMessage(0);
return 0;
break;
/* Window needs update*/
case WM_PAINT:
hDC = BeginPaint(hwnd,&paintStruct);
/* Draw a Red Square pixel by pixel*/
for (int x=100;x<300;x++) {
for (int y = 300;y>100;y--) {
SetPixel(hDC, x, y, 0x000000FF);
}
}
EndPaint(hwnd, &paintStruct);
return 0;
break;
default:
break;
}
... /* Other Unrelated (<- I promise) Code*/
The desired result
A red square that doesn't show each pixel being drawn, but rather, just a red square being drawn instantaneously. To break it down, I want the memory to fill up before releasing it to video memory rather than going 1 by 1 to video memory (I hope I'm using the right words here...)
The problem
The opposite of the desired result, I am getting a quick drawing of the square from left right as each pixel is being set.
What I'm looking for
A command to enable output buffering to my window or a function to store pixels then draw them all at once, or any other method that would get me the desired result.
Thank you in advance. I think it would be helpful to say that I have only been programming in the C++ language for 5 days, and that any breaking down or direct answer would be greatly appreciated.
You need to create a memory HDC, and a bitmap, select the bitmap in to memory, draw on memory, then BitBlt
the memory dc on to the final HDC
. Example:
case WM_PAINT:
{
PAINTSTRUCT ps;
HDC hdc = BeginPaint(hWnd, &ps);
HDC memdc = CreateCompatibleDC(hdc);
HBITMAP bitmap = CreateCompatibleBitmap(hdc, 300, 300);
HBITMAP oldbmp = (HBITMAP)SelectObject(memdc, bitmap);
for(int x = 100; x<300; x++)
for(int y = 300; y>100; y--)
SetPixelV(memdc, x, y, 0x000000FF);
BitBlt(hdc, 0, 0, w, h, memdc, 0, 0, SRCCOPY);
//cleanup:
SelectObject(memdc, oldbmp);
DeleteDC(memdc);
DeleteObject(bitmap);
EndPaint(hWnd, &ps);
return 0;
}
Note that you have access to all GDI functions. In this example you can use FillRect
instead:
RECT rc{ 100, 100, 300, 300 };
SetDCBrushColor(memdc, RGB(255, 0, 0));
FillRect(memdc, &rc, (HBRUSH)GetStockObject(DC_BRUSH));
Or use GetDIBits
to manipulate the bitmap.
User contributions licensed under CC BY-SA 3.0