flickering on mac

BlitzMax Forums/BlitzMax Beginners Area/flickering on mac

Warner(Posted 2009) [#1]
My current application uses minib3d+max2d. I developed the program on a PC, where it works fine. However, on several Macs I tested it on, the screen flickers. Strangely enough, it doesn't happen all the time.

I'm using max2d to draw the GUI elements. They are only updated when needed. (mouse enter/leave/click etc) I call Flip once pro loop.

The main loop looks basically like this:
cls
repeat
    button$ = drawgui() 'may or may not draw gui elements
    flip
forever


Could the problem be this: On Mac, backbuffer and frontbuffer are swapped when Flip is called, where on PC, backbuffer is copied onto frontbuffer when Flip is called?


slenkar(Posted 2009) [#2]
have you tried redrawing the gui every frame?


_Skully(Posted 2009) [#3]
I know the Mac is bad for tearing which is what you might be perceiving as flickering. Are you using Flip false?


Warner(Posted 2009) [#4]
Well, maybe flickering doesn't describe exactly enough what it does. It is more like a strobelight effect. When I have the chance, I'll try redrawing the GUI.


xlsior(Posted 2009) [#5]
Are you redrawing the entire screen each frame, or are you counting on the existing contents to survive after a flip?

If so, that may very well be the problem. Some video adapters will remember the old contents, others will clear it, and others may cycle through multiple backbuffers causing the background to continuously rewind one, two, three or even four frames, causing all kinds of very nasty flickering.

the only way to ensure that everything works consistently on ALL computers is to redraw the entire screen each and every frame.


Warner(Posted 2009) [#6]
Are you redrawing the entire screen each frame, or are you counting on the existing contents to survive after a flip?
Yes, exactly.
If so, that may very well be the problem. Some video adapters will remember the old contents, others will clear it, and others may cycle through multiple backbuffers causing the background to continuously rewind one, two, three or even four frames, causing all kinds of very nasty flickering.
Ah, that explains.
the only way to ensure that everything works consistently on ALL computers is to redraw the entire screen each and every frame.
I will do that, thanks!


ImaginaryHuman(Posted 2009) [#7]
Flip defaults to -1, which means do not sync to the vertical blank, which means it will tear.

Always use Flip 1.


Warner(Posted 2009) [#8]
Okay, today, I tried out redrawing the GUI each frame. That does indeed solve the strobe-like flickering problem. Indeed, I was relying on the backbuffer data to exist after Flip.

Is there a way to avoid drawing the GUI each frame? This way, the GUI takes to much time away from the other components of the program.
I tried storing the GUI elements in an image, and redrawing those images each frame, but still, it is too heavy.

So what I would like to find is a fast way to restore the backbuffer after calling Flip. Any ideas?


ImaginaryHuman(Posted 2009) [#9]
On some drivers the backbuffer content is retained, but it's totally unreliable. On my iMac it doesn't retain it, or it retains parts and trashes some with other data. So you either have to draw your gui elements to a texture, or draw it to the backbuffer once then grab it into a texture, so that you can then just redraw 1 texture. But you've still got to redraw it each frame somehow.


Warner(Posted 2009) [#10]
I see .. then is there a way to draw/copyrect images (or pixmaps) onto a portion of a Pixmap/Image? Or alternatively, to draw directly onto the frontbuffer? I've been looking through the docs, but didn't find too much that could be helpful.


Warner(Posted 2009) [#11]
Ah, wait .. here it is:

http://www.blitzmax.com/Community/posts.php?topic=55281
Thanks, ImaginaryHuman!


xlsior(Posted 2009) [#12]
I see .. then is there a way to draw/copyrect images (or pixmaps) onto a portion of a Pixmap/Image? Or alternatively, to draw directly onto the frontbuffer? I've been looking through the docs, but didn't find too much that could be helpful.


Not natively.

What you're looking for is 'render to texture', which is not part of the current command set. There are, however, some code snippets floating around on the forums that can add this functionality, by directly manipulating OpenGL / DirectX.

IIRC Indiepath had a render to texture module, but I'm not sure if it still works in the current version of blitzmax.


Warner(Posted 2009) [#13]
There seems to be a Render2Texture function in minib3d. But I'm afraid I don't understand what to do with it, since: the GUI I wrote uses images, not textures? I suspect there is a link between the two, but I fail to see it.

I was looking into a method where I try only to 'Flip' the part of the backbuffer that has been drawn to. I tried setting up glCopyPixels, but it has no result on my PC. So, instead, I'm now using GrabImage and DrawImage:

Is there a way to further optimize this 'FlipRect' routine?
<edit>hmm .. I tried implementing this, but somehow my computer locked up completely and I had to reboot.


Warner(Posted 2009) [#14]
Topic continued in the OpenGL section
here


ImaginaryHuman(Posted 2009) [#15]
I found some problems in changing the read and write buffers, whereby different platforms and graphics drivers seem to handle it differently. My old iBook in particular did some very unpredictable things after trying to set the front buffer.

Copypixels might copy from/to the same buffer, not between front and back?

Even if you could just copy backbuffer to front buffer without flipping, you will end up with tearing because there is no vertical blank sync.


Warner(Posted 2009) [#16]
I see, well the sync isn't my biggest concern, since it is just an editor I'm writing. But I'm somewhat worried about the unpredictable buffers. I'll test it on several machines when I have the chance. Thanks for explaining this!