I am creating a simple pong clone using assembly (masm) and utilizing the native windows GDI to do it (should be plenty fast).. however I am running into a problem.. The window gets created properly and everything works pretty good, except the backbuffer gets drawn in the top left corner of the screen :(.. I know why this happens. it is because I create a DC from an empty HWND.. and a HWND = NULL is the desktop, or screen...

How do I initialize an empty HWND for use as a backbuffer?
Posted on 2006-06-28 17:30:43 by talmir
Get the DC of your window and use CreateCompatibleDC to create the backbuffer DC based on it.
Posted on 2006-06-28 17:34:48 by Eóin
Whoah! That was fast.. Thanks a million man :) You really helped me.
Posted on 2006-06-28 17:36:15 by talmir
Exactly the same sort of thing I'm doing with my program, actually (another Pong clone :P). Except that I'm not using hWnd = NULL, I'm making a popup window that's the full screen size.
Posted on 2006-06-28 18:24:44 by Bobbias
Erm... Now everything gets black :(


This is my code:

  invoke GetDC,hwnd
  mov hdc, eax
  invoke BeginPaint, hwnd, ADDR ps
  invoke CreateCompatibleDC, ps.hdc
  mov buffer, eax
  invoke GetClientRect, hwnd, ADDR rect 
  invoke DrawSquare, 5, 5, 5, 5, 000000255, buffer ;function call, draws a *gosh* square :)
  invoke BitBlt, ps.hdc, 0, 0, 100, 100, buffer, 0, 0, SRCCOPY
  invoke EndPaint, hwnd, addr ps
  invoke DeleteDC, buffer
  invoke DeleteDC, hdc
Posted on 2006-06-28 19:17:27 by talmir
I attach a quick hacked project which creates a BackBuffer and a Bitmap. Then it paints the bitmap onto the backbuffer. The Bitmap will follow your mouse. ;) But watch it - I didn't add any bounds checking.

I hope this will help both of you somewhat. (Why don't you guys get together?)
Posted on 2006-06-28 20:34:27 by JimmyClif
if nothing else, we should compare code and see what eachother is doing. This could turn out to be a learning process for the both of us.
Posted on 2006-06-28 21:29:58 by Bobbias
BeginPaint/EndPaint/InvalidateRect for a game is not as good as GetDC/ReleaseDC/ValidateRect.

ValidateRect: the only call when handling WM_PAINT

every frame (of 30fps, for instance):

DrawGame proc
  ; draw game onto backbuff (the backDC)
  ...
 
  ; finally, update screen
  GetDC of window
  BitBlt back to front
  ReleaseDC  of window
  ret
DrawGame endp

btw, Macromedia Flash uses this approach, too - it's just the best for animation.
Posted on 2006-06-30 07:50:49 by Ultrano
Interesting.

...and you skip the whole WM_PAINT handler? I'll try it next time.

Thanks.
Posted on 2006-06-30 08:33:08 by JimmyClif
Simply skipping it is bad - you have to tell Windows that your window is "clean". Otherwise, the OS will frantically try to redraw your window, causing 100% cpu usage. The way out is:


.elseif uMsg==WM_PAINT
  invoke ValidateRect,hWnd,0
  xor eax,eax
  ret
.elseif ...


Posted on 2006-06-30 17:25:40 by Ultrano
Hmm, that's actually a good suggestion about bypassing the WM_PAINT handler.. I'll try that once i begin working on my pong again. (yook a smal break to learn a bit more asm,a nd to stop thinking of pong 24/7)
Posted on 2006-06-30 17:48:16 by Bobbias
Thank you. Good to know. I tried it and it works fine. I'm glad to know that there is a better way out there.
Posted on 2006-07-02 02:44:51 by JimmyClif