Drawing without flickering
Asked Answered
I

4

8

I have a win32 application which was developed in c++. The application draws some stuff on the window using basic shapes (rectangles). The windows is repainted every 20ms (50hz) using InvalidateRect. All works well but the drawing is flickering. How can i prevent the flickering? In c# i normally use a double buffered component (such as pictureBox), how could i get rid of this in c++ using win32?

Inimical answered 21/9, 2011 at 15:17 Comment(0)
E
5

You can easily implement double buffering in Win32 as well. Assuming you are doing your painting directly on the Window using its device context, do this instead:

Create a "memory" device context and do all your drawing on that device context, then copy the invalidated portions of the window to the actual device context when appropriate, using the BitBlt() function

There's a pretty good (albeit high level) overview here.

Enclave answered 21/9, 2011 at 15:21 Comment(1)
choose this answer as it is the only one with an exampleInimical
F
7

You can create an in-memory device context, draw those shapes to it (just like you would to the window's device context) and then blit from it to window's device context when the window is invalidated.

You also need to disable background clearing (handle WM_ERASEBKGND window message appropriately) before the draw happens.

Edit: I stumbled upon a pretty exhaustive tutorial on flicker-free drawing in GDI, which explains all aspects of drawing in Windows and comes with examples.

Finale answered 21/9, 2011 at 15:22 Comment(2)
+1 The WM_ERASEBKGND tip is important. I forgot about that when I wrong my answer.Aright
working tutorial url: catch22.net/tuts/win32/flicker-free-drawingMethodology
E
5

You can easily implement double buffering in Win32 as well. Assuming you are doing your painting directly on the Window using its device context, do this instead:

Create a "memory" device context and do all your drawing on that device context, then copy the invalidated portions of the window to the actual device context when appropriate, using the BitBlt() function

There's a pretty good (albeit high level) overview here.

Enclave answered 21/9, 2011 at 15:21 Comment(1)
choose this answer as it is the only one with an exampleInimical
A
3

You can double buffer in C++, too.

When you get the DC to paint to, you create an offscreen bitmap (CreateCompatibleBitmap) and a memory DC (CreateCompatibleDC). Do all your painting to that DC. At the end, do a BitBlt from the memory DC to the actual DC.

For performance, you might want to cache the offscreen bitmap and DC, but remember to recreate them when the window size changes.

Aright answered 21/9, 2011 at 15:23 Comment(0)
V
2

Here's the greatest tutorial i've found yet:

https://msdn.microsoft.com/en-us/library/ms969905.aspx

In short - yes, you have to implement the double-buffering. It's done through creating the in-memory DC and then drawing everything you want to an in-memory bitmap using that DC, only afterwards commiting this bitmap to an actual DC.

Verdaverdant answered 9/5, 2018 at 5:18 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.