Changeset 10098

Show
Ignore:
Timestamp:
04/24/09 18:20:50 (6 years ago)
Author:
robert
Message:

Introduce new run frame rate management support to allow control of maximum frame rate and to support on demand rendering of frames

Location:
OpenSceneGraph/trunk
Files:
10 modified

Legend:

Unmodified
Added
Removed
  • OpenSceneGraph/trunk/include/osgViewer/CompositeViewer

    r9554 r10098  
    7474 
    7575        virtual double elapsedTime(); 
    76          
     76 
    7777        virtual osg::FrameStamp* getViewerFrameStamp() { return getFrameStamp(); } 
    78          
     78 
    7979 
    8080        /** Execute a main frame loop. 
     
    8585        virtual int run(); 
    8686 
     87        /** check to see if the new frame is required, called by run(..) when FrameScheme is set to ON_DEMAND.*/ 
     88        virtual bool checkNeedToDoFrame(); 
     89 
    8790        virtual void advance(double simulationTime=USE_REFERENCE_TIME); 
    8891 
     
    9093 
    9194        virtual void updateTraversal(); 
    92          
    93          
     95 
     96 
    9497        void setCameraWithFocus(osg::Camera* camera); 
    9598        osg::Camera* getCameraWithFocus() { return _cameraWithFocus.get(); } 
    9699        const osg::Camera* getCameraWithFocus() const { return _cameraWithFocus.get(); } 
    97          
     100 
    98101        osgViewer::View* getViewWithFocus() { return _viewWithFocus.get(); } 
    99102        const osgViewer::View* getViewWithFocus() const { return _viewWithFocus.get(); } 
  • OpenSceneGraph/trunk/include/osgViewer/View

    r9909 r10098  
    234234        osgUtil::SceneView::FusionDistanceMode  _fusionDistanceMode; 
    235235        float                                   _fusionDistanceValue; 
     236 
    236237}; 
    237238 
  • OpenSceneGraph/trunk/include/osgViewer/Viewer

    r9554 r10098  
    3636 
    3737        virtual ~Viewer(); 
    38          
     38 
    3939        META_Object(osgViewer,Viewer); 
    4040 
     
    7575 
    7676        virtual double elapsedTime(); 
    77          
     77 
    7878        virtual osg::FrameStamp* getViewerFrameStamp() { return getFrameStamp(); } 
    79  
    8079 
    8180        /** Execute a main frame loop. 
     
    8685        virtual int run(); 
    8786 
     87        /** check to see if the new frame is required, called by run(..) when FrameScheme is set to ON_DEMAND.*/ 
     88        virtual bool checkNeedToDoFrame(); 
     89 
    8890        virtual void advance(double simulationTime=USE_REFERENCE_TIME); 
    8991 
     
    9193 
    9294        virtual void updateTraversal(); 
    93          
     95 
    9496        void setCameraWithFocus(osg::Camera* camera) { _cameraWithFocus = camera; } 
    9597        osg::Camera* getCameraWithFocus() { return _cameraWithFocus.get(); } 
    9698        const osg::Camera* getCameraWithFocus() const { return _cameraWithFocus.get(); } 
    97          
     99 
    98100        virtual void getCameras(Cameras& cameras, bool onlyActive=true); 
    99          
     101 
    100102        virtual void getContexts(Contexts& contexts, bool onlyValid=true); 
    101103 
  • OpenSceneGraph/trunk/include/osgViewer/ViewerBase

    r9917 r10098  
    200200        void checkWindowStatus(); 
    201201 
    202  
     202        enum FrameScheme 
     203        { 
     204            ON_DEMAND, 
     205            CONTINUOUS 
     206        }; 
     207 
     208        void setRunFrameScheme(FrameScheme fs) { _runFrameScheme = fs; } 
     209        FrameScheme getRunFrameScheme() const { return _runFrameScheme; } 
     210 
     211        void setRunMaxFrameRate(double frameRate) { _runMaxFrameRate = frameRate; } 
     212        double getRunMaxFrameRate() const { return _runMaxFrameRate; } 
    203213 
    204214        /** Execute a main frame loop. 
     
    207217          * and installs trackball manipulator if one is not already assigned. 
    208218          */ 
    209         virtual int run() = 0; 
     219        virtual int run(); 
     220 
     221        /** check to see if the new frame is required, called by run(..) when FrameScheme is set to ON_DEMAND.*/ 
     222        virtual bool checkNeedToDoFrame() = 0; 
    210223 
    211224        /** Render a complete new frame. 
     
    250263         
    251264    protected: 
    252      
     265 
     266        void viewerBaseInit(); 
     267 
     268        friend class osgViewer::View; 
     269 
    253270        inline void makeCurrent(osg::GraphicsContext* gc) 
    254271        { 
    255272            if (_currentContext==gc) return; 
    256              
     273 
    257274            releaseContext(); 
    258              
     275 
    259276            if (gc && gc->valid() && gc->makeCurrent()) _currentContext = gc; 
    260277        } 
    261          
     278 
    262279        inline void releaseContext() 
    263280        { 
     
    276293        bool                                                _quitEventSetsDone; 
    277294        bool                                                _releaseContextAtEndOfFrameHint; 
    278          
     295 
    279296        ThreadingModel                                      _threadingModel; 
    280297        bool                                                _threadsRunning; 
     298 
     299        bool                                                _requestRedraw; 
     300        bool                                                _requestContinousUpdate; 
     301 
     302        FrameScheme                                         _runFrameScheme; 
     303        double                                              _runMaxFrameRate; 
     304 
    281305 
    282306        BarrierPosition                                     _endBarrierPosition; 
     
    285309        osg::ref_ptr<osg::BarrierOperation>                 _endRenderingDispatchBarrier; 
    286310        osg::ref_ptr<osg::EndOfDynamicDrawBlock>            _endDynamicDrawBlock; 
    287          
     311 
    288312        osg::ref_ptr<osgGA::EventVisitor>                   _eventVisitor; 
    289          
     313 
    290314        osg::ref_ptr<osg::OperationQueue>                   _updateOperations; 
    291315        osg::ref_ptr<osgUtil::UpdateVisitor>                _updateVisitor; 
    292          
     316 
    293317        osg::ref_ptr<osg::Operation>                        _realizeOperation; 
    294318        osg::ref_ptr<osgUtil::IncrementalCompileOperation>  _incrementalCompileOperation; 
  • OpenSceneGraph/trunk/src/osgViewer/CompositeViewer.cpp

    r9997 r10098  
    3838{ 
    3939    constructorInit(); 
    40      
     40 
     41    arguments.getApplicationUsage()->addCommandLineOption("--SingleThreaded","Select SingleThreaded threading model for viewer."); 
     42    arguments.getApplicationUsage()->addCommandLineOption("--CullDrawThreadPerContext","Select CullDrawThreadPerContext threading model for viewer."); 
     43    arguments.getApplicationUsage()->addCommandLineOption("--DrawThreadPerContext","Select DrawThreadPerContext threading model for viewer."); 
     44    arguments.getApplicationUsage()->addCommandLineOption("--CullThreadPerCameraDrawThreadPerContext","Select CullThreadPerCameraDrawThreadPerContext threading model for viewer."); 
     45 
     46    arguments.getApplicationUsage()->addCommandLineOption("--run-on-demand","Set the run methods frame rate management to only rendering frames when required."); 
     47    arguments.getApplicationUsage()->addCommandLineOption("--run-continuous","Set the run methods frame rate management to rendering frames continuously."); 
     48    arguments.getApplicationUsage()->addCommandLineOption("--run-max-frame-rate","Set the run methods maximum permissable frame rate, 0.0 is default and switching off frame rate capping."); 
     49 
     50 
    4151    std::string filename; 
    4252    bool readConfig = false; 
     
    5161    while (arguments.read("--CullThreadPerCameraDrawThreadPerContext")) setThreadingModel(CullThreadPerCameraDrawThreadPerContext); 
    5262 
     63 
     64    while(arguments.read("--run-on-demand")) { setRunFrameScheme(ON_DEMAND); } 
     65    while(arguments.read("--run-continuous")) { setRunFrameScheme(CONTINUOUS); } 
     66 
     67    double runMaxFrameRate; 
     68    while(arguments.read("--run-max-frame-rate", runMaxFrameRate)) { setRunMaxFrameRate(runMaxFrameRate); } 
     69 
     70 
    5371    osg::DisplaySettings::instance()->readCommandLine(arguments); 
    5472    osgDB::readCommandLine(arguments); 
     
    221239     
    222240    return numRealizedWindows > 0; 
     241} 
     242 
     243bool CompositeViewer::checkNeedToDoFrame() 
     244{ 
     245    if (_requestRedraw) return true; 
     246    if (_requestContinousUpdate) return true; 
     247 
     248    for(RefViews::iterator itr = _views.begin(); 
     249        itr != _views.end(); 
     250        ++itr) 
     251    { 
     252        osgViewer::View* view = itr->get(); 
     253        if (view) 
     254        { 
     255            // If the database pager is going to update the scene the render flag is 
     256            // set so that the updates show up 
     257            if (view->getDatabasePager()->requiresUpdateSceneGraph() || 
     258                view->getDatabasePager()->getRequestsInProgress()) return true; 
     259        } 
     260    } 
     261 
     262    // now do a eventTraversal to see if any events might require a new frame. 
     263    eventTraversal(); 
     264 
     265    if (_requestRedraw) return true; 
     266    if (_requestContinousUpdate) return true; 
     267 
     268    return false; 
    223269} 
    224270 
  • OpenSceneGraph/trunk/src/osgViewer/StatsHandler.cpp

    r9624 r10098  
    184184                    } 
    185185 
    186  
     186                    aa.requestRedraw(); 
    187187                } 
    188188                return true; 
  • OpenSceneGraph/trunk/src/osgViewer/View.cpp

    r9909 r10098  
    16971697void View::requestRedraw() 
    16981698{ 
    1699 } 
    1700  
    1701 void View::requestContinuousUpdate(bool) 
    1702 { 
     1699    getViewerBase()->_requestRedraw = true; 
     1700} 
     1701 
     1702void View::requestContinuousUpdate(bool flag) 
     1703{ 
     1704    getViewerBase()->_requestContinousUpdate = flag; 
    17031705} 
    17041706 
  • OpenSceneGraph/trunk/src/osgViewer/Viewer.cpp

    r9868 r10098  
    5454    arguments.getApplicationUsage()->addCommandLineOption("--screen <num>","Set the screen to use when multiple screens are present."); 
    5555    arguments.getApplicationUsage()->addCommandLineOption("--window <x y w h>","Set the position (x,y) and size (w,h) of the viewer window."); 
     56 
     57    arguments.getApplicationUsage()->addCommandLineOption("--run-on-demand","Set the run methods frame rate management to only rendering frames when required."); 
     58    arguments.getApplicationUsage()->addCommandLineOption("--run-continuous","Set the run methods frame rate management to rendering frames continuously."); 
     59    arguments.getApplicationUsage()->addCommandLineOption("--run-max-frame-rate","Set the run methods maximum permissable frame rate, 0.0 is default and switching off frame rate capping."); 
     60 
    5661    // FIXME: Uncomment these lines when the options have been documented properly 
    5762    //arguments.getApplicationUsage()->addCommandLineOption("--3d-sd",""); 
     
    8590        else osg::notify(osg::WARN)<<"Invalid clear color \""<<colorStr<<"\""<<std::endl; 
    8691    } 
    87      
     92 
     93 
     94    while(arguments.read("--run-on-demand")) { setRunFrameScheme(ON_DEMAND); } 
     95    while(arguments.read("--run-continuous")) { setRunFrameScheme(CONTINUOUS); } 
     96 
     97    double runMaxFrameRate; 
     98    while(arguments.read("--run-max-frame-rate", runMaxFrameRate)) { setRunMaxFrameRate(runMaxFrameRate); } 
     99 
     100 
    88101    int screenNum = -1; 
    89102    while (arguments.read("--screen",screenNum)) {} 
    90      
     103 
    91104    int x = -1, y = -1, width = -1, height = -1; 
    92105    while (arguments.read("--window",x,y,width,height)) {} 
    93      
     106 
    94107    bool ss3d = false; 
    95108    bool wowvx20 = false; 
     
    310323} 
    311324 
     325bool Viewer::checkNeedToDoFrame() 
     326{ 
     327    if (_requestRedraw) return true; 
     328    if (_requestContinousUpdate) return true; 
     329 
     330    // If the database pager is going to update the scene the render flag is 
     331    // set so that the updates show up 
     332    if(getDatabasePager()->requiresUpdateSceneGraph() || getDatabasePager()->getRequestsInProgress()) return true; 
     333 
     334    // now do a eventTraversal to see if any events might require a new frame. 
     335    eventTraversal(); 
     336 
     337    if (_requestRedraw) return true; 
     338    if (_requestContinousUpdate) return true; 
     339 
     340    return false; 
     341} 
     342 
    312343int Viewer::run() 
    313344{ 
     
    316347        setCameraManipulator(new osgGA::TrackballManipulator()); 
    317348    } 
    318      
     349 
    319350    setReleaseContextAtEndOfFrameHint(false); 
    320              
     351 
    321352    return ViewerBase::run(); 
    322353} 
     
    325356{ 
    326357    View::setStartTick(tick); 
    327      
     358 
    328359    Contexts contexts; 
    329360    getContexts(contexts,false); 
  • OpenSceneGraph/trunk/src/osgViewer/ViewerBase.cpp

    r9886 r10098  
    3434static osg::ApplicationUsageProxy ViewerBase_e2(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_SCREEN <value>","Set the default screen that windows should open up on."); 
    3535static osg::ApplicationUsageProxy ViewerBase_e3(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_WINDOW x y width height","Set the default window dimensions that windows should open up on."); 
    36  
     36static osg::ApplicationUsageProxy ViewerBase_e4(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_RUN_FRAME_SCHEME","Frame rate manage scheme that viewer run should use,  ON_DEMAND or CONTINUOUS (default)."); 
     37static osg::ApplicationUsageProxy ViewerBase_e5(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_RUN_MAX_FRAME_RATE","Set the maximum number of frame as second that viewer run. 0.0 is default and disables an frame rate capping."); 
    3738 
    3839using namespace osgViewer; 
     
    4041ViewerBase::ViewerBase(): 
    4142    osg::Object(true) 
     43{ 
     44    viewerBaseInit(); 
     45} 
     46 
     47ViewerBase::ViewerBase(const ViewerBase& base): 
     48    osg::Object(true) 
     49{ 
     50    viewerBaseInit(); 
     51} 
     52 
     53void ViewerBase::viewerBaseInit() 
    4254{ 
    4355    _firstFrame = true; 
     
    4961    _threadsRunning = false; 
    5062    _endBarrierPosition = AfterSwapBuffers; 
    51 } 
    52  
    53 ViewerBase::ViewerBase(const ViewerBase& base): 
    54     osg::Object(true) 
    55 { 
    56     _firstFrame = true; 
    57     _done = false; 
    58     _keyEventSetsDone = osgGA::GUIEventAdapter::KEY_Escape; 
    59     _quitEventSetsDone = true; 
    60     _releaseContextAtEndOfFrameHint = true; 
    61     _threadingModel = AutomaticSelection; 
    62     _threadsRunning = false; 
    63     _endBarrierPosition = AfterSwapBuffers; 
     63    _requestRedraw = true; 
     64    _requestContinousUpdate = false; 
     65 
     66    _runFrameScheme = CONTINUOUS; 
     67    _runMaxFrameRate = 0.0f; 
     68 
     69    const char* str = getenv("OSG_RUN_FRAME_SCHEME"); 
     70    if (str) 
     71    { 
     72        if      (strcmp(str, "ON_DEMAND")==0) _runFrameScheme = ON_DEMAND; 
     73        else if (strcmp(str, "CONTINUOUS")==0) _runFrameScheme = CONTINUOUS; 
     74    } 
     75 
     76    str = getenv("OSG_RUN_MAX_FRAME_RATE"); 
     77    if (str) 
     78    { 
     79        _runMaxFrameRate = atof(str); 
     80    } 
    6481} 
    6582 
     
    574591    } 
    575592 
    576 #if 0 
    577     while (!done()) 
    578     { 
    579         frame(); 
    580     } 
    581 #else 
    582  
    583593    const char* str = getenv("OSG_RUN_FRAME_COUNT"); 
    584     if (str) 
    585     { 
    586         int runTillFrameNumber = atoi(str); 
    587         while (!done() && getViewerFrameStamp()->getFrameNumber()<runTillFrameNumber) 
     594    int runTillFrameNumber = str==0 ? -1 : atoi(str); 
     595 
     596    while(!done() || (runTillFrameNumber>=0 && getViewerFrameStamp()->getFrameNumber()>runTillFrameNumber)) 
     597    { 
     598        double minFrameTime = _runMaxFrameRate>0.0 ? 1.0/_runMaxFrameRate : 0.0; 
     599        osg::Timer_t startFrameTick = osg::Timer::instance()->tick(); 
     600        if (_runFrameScheme==ON_DEMAND) 
     601        { 
     602            if (checkNeedToDoFrame()) frame(); 
     603        } 
     604        else 
    588605        { 
    589606            frame(); 
    590607        } 
    591     } 
    592     else 
    593     { 
    594         while (!done()) 
    595         { 
    596             frame(); 
    597         } 
    598     } 
    599 #endif     
     608 
     609        // work out if we need to force a sleep to hold back the frame rate 
     610        osg::Timer_t endFrameTick = osg::Timer::instance()->tick(); 
     611        double frameTime = osg::Timer::instance()->delta_s(startFrameTick, endFrameTick); 
     612        if (frameTime < minFrameTime) OpenThreads::Thread::microSleep(1000000.0*(minFrameTime-frameTime)); 
     613    } 
     614 
    600615    return 0; 
    601616} 
     
    843858        getViewerStats()->setAttribute(frameStamp->getFrameNumber(), "Rendering traversals time taken", endRenderingTraversals-beginRenderingTraversals); 
    844859    } 
    845 } 
    846  
     860 
     861    _requestRedraw = false; 
     862} 
     863 
  • OpenSceneGraph/trunk/src/osgViewer/ViewerEventHandlers.cpp

    r9340 r10098  
    101101                    toggleFullscreen(*itr); 
    102102                } 
     103 
     104                aa.requestRedraw(); 
    103105                return true; 
    104106            } 
     
    115117                    changeWindowedResolution(*itr, true); 
    116118                } 
     119 
     120                aa.requestRedraw(); 
    117121                return true; 
    118122            } 
     
    129133                    changeWindowedResolution(*itr, false); 
    130134                } 
     135 
     136                aa.requestRedraw(); 
    131137                return true; 
    132138            } 
     
    318324            if (_changeThreadingModel == true && ea.getKey() == _keyEventChangeThreadingModel && delta > 1.0) 
    319325            { 
     326 
    320327                _tickOrLastKeyPress = osg::Timer::instance()->tick(); 
    321328 
     
    349356                    break; 
    350357                } 
     358 
     359                aa.requestRedraw(); 
    351360                return true; 
    352361            } 
     
    364373                    break; 
    365374                } 
     375 
     376                aa.requestRedraw(); 
    366377                return true; 
    367378            } 
     
    576587                camera->setLODScale(camera->getLODScale()*1.1); 
    577588                osg::notify(osg::NOTICE)<<"LODScale = "<<camera->getLODScale()<<std::endl; 
     589 
     590                aa.requestRedraw(); 
    578591                return true; 
    579592            } 
     
    583596                camera->setLODScale(camera->getLODScale()/1.1); 
    584597                osg::notify(osg::NOTICE)<<"LODScale = "<<camera->getLODScale()<<std::endl; 
    585                 return true; 
    586             }         
     598 
     599                aa.requestRedraw(); 
     600                return true; 
     601            } 
    587602 
    588603            break;