Memory DC's

Started by
19 comments, last by shalom 22 years, 8 months ago
Hi: I''m writing a game in Visual Basic. VB isn''t very good with graphics, so everyone bypasses the VB graphics and uses the GDI. For some reason, though, no-one makes their own device contexts. Everyone uses invisible PictureBox controls (a simple VB control that displays pictures) because they have a DC property. For example, if someone wanted to blit a transparent picture on to the window, they would have three PictureBox controls, let''s say Pic1, Pic2, and Pic3. They would load the picture they want to blit onto in Pic1, the picture they want to blit in Pic2, and a mask in Pic3. They would import the GDI BitBlt function and use the following VB code: BitBlt Pic1.hDC, 0, 0, 100, 100, Pic3.hDC, 0, 0, SRCAND BitBlt Pic1.hDC, 0, 0, 100, 100, Pic2.hDC, 0, 0, SRCPAINT BitBlt Me.hDC, 0, 0, 100, 100, Pic1.hDC, 0, 0, SRCCOPY. This is all fine if your doing a little animation or something, but if I want to make a full game, perhaps using independant classes that may not have access to windows and their PictureBoxes, how do I use the GDI to make memory DC''s? I can''t find it anywhere. How do C programmers, who don''t have access to PictureBox controls, make memory DCs that can be used to temporarily Blt on to and off again? Thanx in advance, Shalom
In my thunking device, what happens to the inherited pointer to the original base class when I override the function & how do I access it in my inline assembly code, assuming that we are referencing the higher byte of the 16-bit variable?
Advertisement
You''ll have much better luck with this post in the general programming forum, so I''am moving it.
" The fastest code is the code you don't call "
Windows apps have one or more windows. For any windows you can gets its DC by calling GetDC(hwnd) where hwnd is the handle of the window. This is usually done in response to a paint message (WM_PAINT) but can be done any time. This is what I do...

void Paint (HWND hwnd)
{
HDC dc = GetDC(hwnd);
int savedc = SaveDC(dc);

// there are many DC related draw functions:
// SelectObject(), MoveTo(), LineTo(), SetPixel(),
// BitBlt(), TextOut(), Rectangle(), Ellipse(),
// SetTextColor(), SetTextAlign(), on and on

RestoreDC(dc, savedc);
ReleaseDC(hwnd, dc);
}

DC''s have a ton of state information that you have to make sure is restored before you release them, or you get GDI leaks, so I always save/restore the whole thing.
Hi, I can access the window''s DC, but how do I make a temporary DC? For example, let''s take a simple case - double buffering. How would I make a little animation in an imaginary DC and then BitBlt from that imaginary DC to the window''s DC? How do I make a sort of "buffer" DC?

Thanks,
Shalom
In my thunking device, what happens to the inherited pointer to the original base class when I override the function & how do I access it in my inline assembly code, assuming that we are referencing the higher byte of the 16-bit variable?
hi shalom,

Device Contexts are just some sort of a "reference" to the device and they don''t anything on their own (they don''t hold the picture, they just point to the device that displays it...), and for that reason the term "temporary dc" doesn''t really mean anything cause it''s just a refernce to the device and you have to handle some sort of buffer yourself(by maybe having something hidden you draw into and then copying for the hidden object to the display object).

this is just a thought, havn''t been using VB for grahpics or the such
Isn''t there a way of making a device in memory, without having a physical object?
In my thunking device, what happens to the inherited pointer to the original base class when I override the function & how do I access it in my inline assembly code, assuming that we are referencing the higher byte of the 16-bit variable?
In other words, how do I make a buffer that I can point a device context to, with out having access to a window with my invisible objects and whatever?
In my thunking device, what happens to the inherited pointer to the original base class when I override the function & how do I access it in my inline assembly code, assuming that we are referencing the higher byte of the 16-bit variable?
I''m just writing this off the top of my head and its been a while since I''ve used DCs, but I think this will work:

  HDC buffer;HDC window;HBITMAP temp;window = GetDC( window_hWnd );buffer = CreateCompatibleDC( window );temp = CreateCompatibleBitmap( buffer, width_of_image, height_of_image );SelectObject( buffer, temp );DeleteObject( temp );ReleaseDC( window_hWnd, window );  


That will create an offscreen DC you can use to draw to. You must create a bitmap object and select it into the DC or you won''t be able to use the DC. I''m sure that I messed up some of the parameters (I don''t remember them all), but you should be able to look up the API functions and see what the parameters should be.

I don''t really remember VB that well, but I''d guess that the VB code would be something like:

  DIM buffer as LongDIM window as LongDIM temp as LongSet window = GetDC( Form1.hWnd )Set buffer = CreateCompatibleDC( window );Set temp = CreateCompatibleBitmap( buffer, width, height )Call SelectObject( buffer, temp )Call DeleteObject( temp );Call ReleaseDC( Form1.hWnd, window );  


Im assuming that since you use BitBlt you know how to declare APIs for use in VB.

If you want direct access to the bits being displayed, I recomend that you create the bitmap object that you are going to select into the buffer DC with CreateDIBSection. That way you will have a pointer to the actual bits which will allow you to do things like alpha blending (I realize that alpha blending can be done with GetPixel/SetPixel, but that is to slow).

Feel free to email me any questions you might have
Mike010@netZero.net
Thank you so much, Mike. It seems silly to get stuck on such a simple point. I have my entire game planned out and most of it programmed, and I don''t know how to use the GDI! Well, I''ll try it out.
In my thunking device, what happens to the inherited pointer to the original base class when I override the function & how do I access it in my inline assembly code, assuming that we are referencing the higher byte of the 16-bit variable?
Oh no! I used the following code exactly, and it makes a square the right size in the top left corner of the window, but its all black! What did I do wrong?
  Option ExplicitPrivate Sub Form_Load()Dim buffer As LongDim window As LongDim temp As Longwindow = GetDC(Form1.hwnd)buffer = CreateCompatibleDC(window)temp = CreateCompatibleBitmap(buffer, Picture1.ScaleWidth, Picture1.ScaleHeight)SelectObject buffer, tempDeleteObject tempReleaseDC Form1.hwnd, windowBitBlt buffer, 0, 0, Picture1.ScaleWidth, Picture1.ScaleHeight, Picture1.hdc, 0, 0, SRCCOPYBitBlt Me.hdc, 0, 0, Picture1.ScaleWidth, Picture1.ScaleHeight, buffer, 0, 0, SRCCOPYForm1.RefreshDeleteDC bufferEnd Sub  


Sigh... I''m causing so much trouble with such a simple problem. Oh well.
In my thunking device, what happens to the inherited pointer to the original base class when I override the function & how do I access it in my inline assembly code, assuming that we are referencing the higher byte of the 16-bit variable?

This topic is closed to new replies.

Advertisement