[SDL] sluggish SDL_Flip
Paulo V W Radtke
pvwr at sympatico.ca
Wed Oct 16 18:15:01 PDT 2002
>In my test program, I obtain the following results:
>1)in software mode, it's very fast
>2)both in hardware and opengl mode, without double buffer, it goes warp
>speeds - I can barely see it (however, it flickers)
On these two tests your program is not waiting for the vertical
retrace, so it will be like that. You have to use a delay on it. But being
that fast is not good, because you're actually loosing visual information.
>3)both in hardware and opengl mode, with double buffer, it's *incredibly*
>slow (about 10ms each frame! There's no difference if
>SDL_Delay(10) is commented out or not!)
Because you're waiting for the vertical retrace. Actually your
program is just as fast as ins hardware in single buffer, but as it has to
wait the vertical retrace, it WILL spend some time waiting for it so it
won't have tearing. If your video card is set to, let's say, 75Hz, it won't
update the screen more than 75 times per second, no matter if it takes 1ms
to draw the whole scene or less, but there's no point in updating it more
than that as you can't show two or more different in just one.
>If I comment out SDL_Flip, I can't see anything: that means that I'm using
>a real double buffer surface and SDL_Flip doesn't just do an
>SDL_UpdateRect on the whole screen. Also, this way the program terminates
>real fast, that means that SDL_Flip is the actual bottleneck in the whole
>stuff.
Not exactly a bottleneck, it's just doing it the way it should be
done. You can't sync your animation based on how many times you can update
the screen, as it depends on vertical retrace of the display adapter (which
the user can change), but on time itself. Start experiencing with
SDL_GetTicks, determine how much time your animation should take and sync
it according to how much time has passed since the animation started (the
first tick you got) and the current ticks count (instead of the number of
frames you could update, this is completely wrong).
Just a small example, suppose you want to move an object 200
points on the x axis in 3 seconds, from 0 to 200, you'll have to do
something like that:
Uint32 start, now;
// We'll use double, but you can use int anyway
double x;
start = SDL_GetTicks();
while( (now=SDL_GetTicks()) - start < 3000)
{
x = 200.0 * (double)now / (double)start;
// Draw your object and update the display
...
}
Of course, this code can be improved, as there's no way to stop
the animation (as in a game, if the user want to skip it, etc), but it can
give you a rough idea on how things. Of course, this won't help you to stop
the wasting on processor power (after all, it will be still drawing more
frames than it should), but use SDL_Delay for it (there's absolutly no
point in updating the screen more than it needs).
Paulo
More information about the SDL
mailing list