Good stuff.Limit frame rate (ie, frame rate capping) is good. But how about Fixed frame rate though? Where the OSG renders at a specified frame rate no matter what.


Robert Osfield wrote:
Hi All,

When following up on a bug report about the pager not handling on
demand/lazy frame rendering I resolved the the problems wasn't down to
the pager, just the way the end user viewer code was set up to the the
on demand frame rendering.  Rather than leave this type of viewer
usage open to end users come up with lots of different schemes to
attempt to the same thing, and with it the potential fall out in terms
of support of trying to help debug them I've coded up a solution for
osgViewer that can either be used directly or as a template for others
to learn from.

What I have done is to refactor osgViewer::ViewerBase::run() so that
it's frame loop now has two new capabilities:

   1) On demand (lazy) frame rendering  vs Continuous frame rendering
(the original functionality, and still the default.)
   2) Optional frame rate capping to a specified maximum frame rate
(defaults to off.)

Now item 2 isn't a required for on demand frame rendering, but it more
for coping with end user system not having vsync enabled by default.
Since I was working on this piece of code I thought I'd tackle this
item as well.  The actual ViewerBase::run() method (use by both Viewer
and CompositeViewer) now looks like:

int ViewerBase::run()
    if (!isRealized())

    const char* str = getenv("OSG_RUN_FRAME_COUNT");
    int runTillFrameNumber = str==0 ? -1 : atoi(str);

    while(!done() || (runTillFrameNumber>=0 &&
        double minFrameTime = _runMaxFrameRate>0.0 ? 1.0/_runMaxFrameRate : 0.0;
        osg::Timer_t startFrameTick = osg::Timer::instance()->tick();
        if (_runFrameScheme==ON_DEMAND)
            if (checkNeedToDoFrame()) frame();

        // work out if we need to force a sleep to hold back the frame rate
        osg::Timer_t endFrameTick = osg::Timer::instance()->tick();
        double frameTime =
osg::Timer::instance()->delta_s(startFrameTick, endFrameTick);
        if (frameTime < minFrameTime)

    return 0;

The code isn't final yet, but is certainly good enough for us to start
testing.  You can test it by setting the env vars:


            or go back to default




            or switch off and the default


You can also use the following command line options:

  osgviewer cow.osg --run-on-demand

  osgviewer cow.osg --run-continuous

  osgviewer cow.osg --run-continuous  --run-max-frame-rate 30.0

The on demand frame rendering does already support paged databases,
and I've updated various event handles to manually do a
requestRedraw() which prompts the viewer::run() to rendering a new
frame.   What I have got working yet is handling of the update visitor
doing updates. so on demand rendering just freezes things like
particle systems and animations till you move the eye point, trigger
an event.  I'll have a look at support event callbacks next.

Please note this support only affect viewer::run() it doesn't effect
apps that roll their own frame loop.

osg-users mailing list

osg-users mailing list

Reply via email to