Force repaint

Hi All,

We have a couple of customers complaining about missing viewport refresh even if the invalidates the window. We are working on Windows and with OpenGL software implementation in this specific case.

At the same time we noticed that many OpenGL based application have a setting called “force repaint”/“force redraw”?

What are we missing?

Thanks,

Alberto

Invalidate window actually post WM_ERASEBKGRND and WM_PAINT in app message queue. App should respond on those messages. In case of WM_ERASEBKGRND it should skip clearing to avoid flickering and in WM_PAINT make current context, redraw OpenGL and swap buffers.

So… make sure your app properly respond on those messages and also check WM_SIZE message to update viewport size.

Can you tell us which OpenGL applications have settings force repaint/force redraw.

Yooyo,

We already catch properly the messages you mentioned, a proof of that is that our app works properly in the 90% of machines.

But now we face the problem with these customers that use the following graphics hardwares:

Intel® 82865G Graphics
Intel® 82845G/GL/GE/PE/GV
Intel® 965 Express

Considering that these are embedded GPUs we disabled hardware acceleration but this issue still remains.

Is there any windows style that could help in this case?

Rhino3D for example has this setting.

Thanks,

Alberto

Have you tried intercepting WM_SIZE messages and adding a repaint there?

It does not happen during a resize operation but simply changing view and calling the window.Invalidate() func. In many machines this is enough but not on the hardwares I’ve listed.

Thanks,

Alberto

So what happens is you call Invalidate() but the WM_PAINT message never arrives?

Off the top of my head, some things you might wish to try:

  1. make sure the window has the WS_OWNDC style but not the WS_EX_TRANSPARENT style.
  2. Make sure you return 0 when you handle WM_PAINT.
  3. Make sure you invalidate the correct window (the message could be sent to the wrong window - mistakes happen).
  4. Log all WM_* messages and compare the logs of the machines that work against the ones that don’t. Maybe you will find some clues there.

Why do you call invalidate from WM_SIZE? It should be called anyway by system.

difficult to get. does some glFlush help?

This sound interesting, we are doing:

// From http://www.opengl.org/wiki/index.php/Common_Mistakes#Unsupported_formats_.231
// 
// Use glFlush if you are rendering directly to your window. It is better to
// have a double buffered window but if you have a case where you want to render
// to the window directly, then go ahead.
//
// There is a lot of tutorial website that show this 
// 
// glFlush();
// SwapBuffers();
//
// Never call glFlush before calling SwapBuffers. The SwapBuffer command takes care of flushing and command processing.
// gl.Flush();

if (swapBuffer)

   renderingContext.SwapBuffers();

else
   // see above
    gl.Flush();

Do you see somthing strange?

Alberto

Yes.
glFlush will not present your rendered image in double buffering mode. It just flush gl commands queue.

So… the question is do you use single or double buffering?
If you use single buffering, just call glFlush. If you use doublebuffering just call SwapBuffers.

And… why do you force software implementaation on Intel cards. I know their drivers sucks a lot, but it should work properly if you use plain OpenGL 1.1. Can you check which feature doesnt work properly and try to make workaround. Any hw acceleration is better than no-acceleration.

just our of interest, does the Rhino3D help says what “force repaint” actually does and when its important to switch on?

If you see some viewports not updating correctly…

We always work in double buffered mode (I guess that also OpenGL software implementation supports it) and use glFlush only for offscreen rendering with glReadPixel().

Shall we always use glFlush() with not hardware accelerated pixel formats?

Thanks,

Alberto

i guess, not hardware accelerated pixel format is converted, thus is slow, thus stalls the pipe, thus needs to be flushed? glFlush returns immediately which which isn’t bad at all but any SwapBuffers does a flush automatically otherwise your backbuffer picture won’t be complete. check Mesa3D software rendering see if its any different.

If I remember correctly, you should call glFinish() not glFlush() before you call glReadPixels() on your offscreen buffer. The former forces rendering to complete; the latter only flushes the command buffer.

I could imagine some drivers giving you an incomplete rendering if you use glFlush() instead of glFinish().

This is interesting not for this issue because it happens with standard rendering and therefore with SwapBuffer, by the way does anybody else agree with the glFinish() theory?

Thanks,

Alberto

OK… things getting complicated. Now you have rendering to offscreen buffer, glReadPixels, glFlush, SwapBuffers and double buffered context…

Can you explain to us what are you trying to do? Im really confused.

Yooyo,

Yes, lets go back to the main problem. The app works fine in the 90% of computers but doesn’t refresh some times on the intel hardwares I listed above…

Thanks,

Alberto

Fine. This is really great.
Now lets get back to the main problem. You give us very little informations about your problem. Unless you provide more details nobody can help you. Problem that you have can be Intel driver bug or your software bug. We (community) cant help you if you are not willing to expose your problem and make it intresting for people here.

So its up to you.

Just a wild guess… turn off shadows under menus.

Can we somehow reproduce it? How do you enforce the use of software rasterization, are you really sure Intel’s drivers are left untouched? I’ve seen way more horrible+random stuff on GMA3100 with both GL and DX, and that 965 chipset afaik is GMA3000 (differs from 3100 just by its clock).

Do you validate the region before or after issuing the GL commands and SwapBuffers ?

Does your “window.Invalidate()” invalidate the whole region, i.e to what InvalidateRect params does it map?

“Force repaint” should be something like using a 5Hz WM_TIMER to redraw the whole UI.

A LockWindowUpdate might be a hackish way to cause or cure the thing (wild speculation).