Refactor of DatabasePage/IncrementalCompileOperation to use the IncrementalCompileOperator for compiling objects
This commit is contained in:
parent
c040b25699
commit
017a03ffe5
@ -110,8 +110,6 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
void setActive(bool active) { _active = active; }
|
||||
bool getActive() const { return _active; }
|
||||
|
||||
double getTimeSinceStartOfIteration() const;
|
||||
|
||||
virtual int cancel();
|
||||
|
||||
virtual void run();
|
||||
@ -120,12 +118,11 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
|
||||
virtual ~DatabaseThread();
|
||||
|
||||
bool _done;
|
||||
bool _active;
|
||||
volatile bool _done;
|
||||
volatile bool _active;
|
||||
DatabasePager* _pager;
|
||||
Mode _mode;
|
||||
std::string _name;
|
||||
osg::Timer_t _tickSinceStartOfIteration;
|
||||
|
||||
};
|
||||
|
||||
@ -188,42 +185,6 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
bool getDoPreCompile() const { return _doPreCompile; }
|
||||
|
||||
|
||||
/** Set the target frame rate that the DatabasePager should assume.
|
||||
* Typically one would set this to the value refresh rate of your display system i.e. 60Hz.
|
||||
* Default value is 100.
|
||||
* Usage notes. The TargetFrameRate and the MinimumTimeAvailableForGLCompileAndDeletePerFrame
|
||||
* parameters are not directly used by DatabasePager, but are should be used as a guide for how
|
||||
* long to set aside per frame for compiling and deleting OpenGL objects - ie. the value to use
|
||||
* when calling DatabasePager::compileGLObjectgs(state,availableTime,). The longer amount of
|
||||
* time to set aside cthe faster databases will be paged in but with increased chance of frame drops,
|
||||
* the lower the amount of time the set aside the slower databases will paged it but with better
|
||||
* chance of avoid any frame drops. The default values are chosen to achieve the later when running
|
||||
* on a modern mid to high end PC.
|
||||
* The way to compute the amount of available time use a scheme such as :
|
||||
* availableTime = maximum(1.0/targetFrameRate - timeTakenDuringUpdateCullAndDraw, minimumTimeAvailableForGLCompileAndDeletePerFrame).
|
||||
*/
|
||||
void setTargetFrameRate(double tfr) { _targetFrameRate = tfr; }
|
||||
|
||||
/** Get the target frame rate that the DatabasePager should assume.*/
|
||||
double getTargetFrameRate() const { return _targetFrameRate; }
|
||||
|
||||
/** Set the minimum amount of time (in seconds) that should be made available for compiling and delete OpenGL objects per frame.
|
||||
* Default value is 0.001 (1 millisecond).
|
||||
* For usage see notes in setTargetFrameRate.*/
|
||||
void setMinimumTimeAvailableForGLCompileAndDeletePerFrame(double ta) { _minimumTimeAvailableForGLCompileAndDeletePerFrame = ta; }
|
||||
|
||||
/** Get the minimum amount of time that should be made available for compiling and delete OpenGL objects per frame.
|
||||
* For usage see notes in setTargetFrameRate.*/
|
||||
double getMinimumTimeAvailableForGLCompileAndDeletePerFrame() const { return _minimumTimeAvailableForGLCompileAndDeletePerFrame; }
|
||||
|
||||
/** Set the maximum number of OpenGL objects that the page should attempt to compile per frame.
|
||||
* Note, Lower values reduces chances of a frame drop but lower the rate that database will be paged in at.
|
||||
* Default value is 8. */
|
||||
void setMaximumNumOfObjectsToCompilePerFrame(unsigned int num) { _maximumNumOfObjectsToCompilePerFrame = num; }
|
||||
|
||||
/** Get the maximum number of OpenGL objects that the page should attempt to compile per frame.*/
|
||||
unsigned int getMaximumNumOfObjectsToCompilePerFrame() const { return _maximumNumOfObjectsToCompilePerFrame; }
|
||||
|
||||
|
||||
/** Set the target maximum number of PagedLOD to maintain in memory.
|
||||
* Note, if more than the target number are required for rendering of a frame then these active PagedLOD are excempt from being expiried.
|
||||
@ -276,29 +237,6 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
* Note, must only be called from single thread update phase. */
|
||||
virtual void updateSceneGraph(const osg::FrameStamp& frameStamp);
|
||||
|
||||
/** Turn the compilation of rendering objects for specified graphics context on (true) or off(false). */
|
||||
void setCompileGLObjectsForContextID(unsigned int contextID, bool on);
|
||||
|
||||
/** Get whether the compilation of rendering objects for specified graphics context on (true) or off(false). */
|
||||
bool getCompileGLObjectsForContextID(unsigned int contextID);
|
||||
|
||||
/** Return true if an external draw thread should call compileGLObjects(..) or not.*/
|
||||
bool requiresExternalCompileGLObjects(unsigned int contextID) const;
|
||||
|
||||
/** Return true if there are pending compile operations that are required.
|
||||
* If requiresCompileGLObjects() return true the application should call compileGLObjects() .*/
|
||||
bool requiresCompileGLObjects() const;
|
||||
|
||||
/** Compile the rendering objects (display lists,texture objects, VBO's) on loaded subgraph.
|
||||
* note, should only be called from the draw thread.
|
||||
* Note, must only be called from a valid graphics context. */
|
||||
virtual void compileGLObjects(osg::State& state,double& availableTime, bool doFlush = false);
|
||||
|
||||
/** Compile the rendering objects (display lists,texture objects, VBO's) on loaded subgraph.
|
||||
* note, should only be called from the draw thread.
|
||||
* Note, must only be called from a valid graphics context. */
|
||||
virtual void compileAllGLObjects(osg::State& state, bool doFlush = false);
|
||||
|
||||
/** Report how many items are in the _fileRequestList queue */
|
||||
unsigned int getFileRequestListSize() const { return _fileRequestQueue->size() + _httpRequestQueue->size(); }
|
||||
|
||||
@ -325,10 +263,6 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
|
||||
typedef std::set< osg::ref_ptr<osg::StateSet> > StateSetList;
|
||||
typedef std::vector< osg::ref_ptr<osg::Drawable> > DrawableList;
|
||||
typedef osgUtil::CompileData DataToCompile;
|
||||
typedef std::map< unsigned int, DataToCompile > DataToCompileMap;
|
||||
typedef std::set<unsigned int> ActiveGraphicsContexts;
|
||||
typedef std::vector< osg::observer_ptr<osg::GraphicsContext> > CompileGraphicsContexts;
|
||||
|
||||
class CountPagedLODsVisitor;
|
||||
|
||||
@ -386,10 +320,11 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
osg::ObserverNodePath _observerNodePath;
|
||||
osg::Group* _groupForAddingLoadedSubgraph;
|
||||
osg::ref_ptr<osg::Node> _loadedModel;
|
||||
DataToCompileMap _dataToCompileMap;
|
||||
osg::ref_ptr<Options> _loadOptions;
|
||||
RequestQueue* _requestQueue;
|
||||
|
||||
osg::observer_ptr<osgUtil::IncrementalCompileOperation::CompileSet> _compileSet;
|
||||
|
||||
bool isRequestCurrent (int frameNumber) const
|
||||
{
|
||||
return _valid && (frameNumber - _frameNumberLastRequest <= 1);
|
||||
@ -404,6 +339,8 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
RequestQueue(DatabasePager* pager);
|
||||
|
||||
void add(DatabaseRequest* databaseRequest);
|
||||
void remove(DatabaseRequest* databaseRequest);
|
||||
|
||||
void addNoLock(DatabaseRequest* databaseRequest);
|
||||
|
||||
void takeFirst(osg::ref_ptr<DatabaseRequest>& databaseRequest);
|
||||
@ -413,6 +350,8 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
|
||||
virtual void updateBlock() {}
|
||||
|
||||
void invalidate(DatabaseRequest* dr);
|
||||
|
||||
bool empty() const { return size()==0; }
|
||||
|
||||
unsigned int size() const { return _size; }
|
||||
@ -424,7 +363,7 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
void swap(RequestList& requestList);
|
||||
|
||||
DatabasePager* _pager;
|
||||
unsigned int _size;
|
||||
volatile unsigned int _size;
|
||||
RequestList _requestList;
|
||||
OpenThreads::Mutex _requestMutex;
|
||||
int _frameNumberLastPruned;
|
||||
@ -473,93 +412,6 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
OpenThreads::Mutex _run_mutex;
|
||||
bool _startThreadCalled;
|
||||
|
||||
// Helper functions for determining if objects need to be
|
||||
// compiled.
|
||||
inline static bool isCompiled(const osg::Texture* texture,
|
||||
unsigned int contextID)
|
||||
{
|
||||
return( texture->getTextureObject(contextID) != NULL );
|
||||
}
|
||||
// Is texture compiled for all active contexts?
|
||||
inline bool isCompiled(osg::Texture* texture) const
|
||||
{
|
||||
for (ActiveGraphicsContexts::const_iterator iter=_activeGraphicsContexts.begin();
|
||||
iter!=_activeGraphicsContexts.end(); ++iter )
|
||||
{
|
||||
if ( texture->getTextureObject(*iter) == NULL ) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
inline static bool isCompiled(const osg::StateSet* stateSet,
|
||||
unsigned int contextID)
|
||||
{
|
||||
for (unsigned i = 0;
|
||||
i < stateSet->getTextureAttributeList().size();
|
||||
++i)
|
||||
{
|
||||
const osg::Texture* texture
|
||||
= dynamic_cast<const osg::Texture*>(stateSet->getTextureAttribute(i,osg::StateAttribute::TEXTURE));
|
||||
if (texture && !isCompiled(texture, contextID))
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
inline bool isCompiled(osg::StateSet* stateSet)
|
||||
{
|
||||
for (unsigned i = 0;
|
||||
i < stateSet->getTextureAttributeList().size();
|
||||
++i)
|
||||
{
|
||||
osg::Texture* texture
|
||||
= dynamic_cast<osg::Texture*>(stateSet->getTextureAttribute(i,osg::StateAttribute::TEXTURE));
|
||||
if (texture)
|
||||
{
|
||||
for (ActiveGraphicsContexts::iterator iter=_activeGraphicsContexts.begin();
|
||||
iter!=_activeGraphicsContexts.end(); ++iter )
|
||||
{
|
||||
if ( texture->getTextureObject(*iter) == NULL ) return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
inline static bool isCompiled(const osg::Drawable* drawable,
|
||||
unsigned int contextID)
|
||||
{
|
||||
if (drawable->getUseVertexBufferObjects())
|
||||
{
|
||||
// say it's not compiled leaving it up to the compileGLObjects() to handle.
|
||||
return false;
|
||||
}
|
||||
else if (drawable->getUseDisplayList())
|
||||
{
|
||||
return drawable->getDisplayList(contextID) != 0;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
inline bool isCompiled(const osg::Drawable* drawable) const
|
||||
{
|
||||
if (drawable->getUseVertexBufferObjects())
|
||||
{
|
||||
// say it's not compiled leaving it up to the compileGLObjects() to handle.
|
||||
return false;
|
||||
}
|
||||
if (drawable->getUseDisplayList())
|
||||
{
|
||||
for (ActiveGraphicsContexts::const_iterator iter=_activeGraphicsContexts.begin();
|
||||
iter!=_activeGraphicsContexts.end(); ++iter )
|
||||
{
|
||||
if ( drawable->getDisplayList(*iter) == 0 ) return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void compileCompleted(DatabaseRequest* databaseRequest);
|
||||
|
||||
/** Iterate through the active PagedLOD nodes children removing
|
||||
@ -583,9 +435,8 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
|
||||
osg::ref_ptr<ReadQueue> _fileRequestQueue;
|
||||
osg::ref_ptr<ReadQueue> _httpRequestQueue;
|
||||
|
||||
|
||||
osg::ref_ptr<RequestQueue> _dataToCompileList;
|
||||
osg::ref_ptr<RequestQueue> _dataToMergeList;
|
||||
|
||||
DrawablePolicy _drawablePolicy;
|
||||
|
||||
@ -596,36 +447,20 @@ class OSGDB_EXPORT DatabasePager : public osg::NodeVisitor::DatabaseRequestHandl
|
||||
|
||||
bool _deleteRemovedSubgraphsInDatabaseThread;
|
||||
|
||||
osg::ref_ptr<RequestQueue> _dataToMergeList;
|
||||
|
||||
osg::ref_ptr<PagedLODList> _activePagedLODList;
|
||||
osg::ref_ptr<PagedLODList> _inactivePagedLODList;
|
||||
|
||||
unsigned int _targetMaximumNumberOfPageLOD;
|
||||
|
||||
ActiveGraphicsContexts _activeGraphicsContexts;
|
||||
// CompileGraphicsContexts _compileGraphicsContexts;
|
||||
|
||||
bool _doPreCompile;
|
||||
osg::ref_ptr<osgUtil::IncrementalCompileOperation> _incrementalCompileOperation;
|
||||
|
||||
double _targetFrameRate;
|
||||
double _minimumTimeAvailableForGLCompileAndDeletePerFrame;
|
||||
unsigned int _maximumNumOfObjectsToCompilePerFrame;
|
||||
|
||||
double _minimumTimeToMergeTile;
|
||||
double _maximumTimeToMergeTile;
|
||||
double _totalTimeToMergeTiles;
|
||||
unsigned int _numTilesMerges;
|
||||
|
||||
struct CompileOperation : public osg::GraphicsOperation
|
||||
{
|
||||
CompileOperation(DatabasePager* databasePager);
|
||||
|
||||
virtual void operator () (osg::GraphicsContext* context);
|
||||
|
||||
osg::observer_ptr<DatabasePager> _databasePager;
|
||||
};
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -25,8 +25,8 @@
|
||||
#include <osgDB/Options>
|
||||
#include <osgDB/DotOsgWrapper>
|
||||
#include <osgDB/ObjectWrapper>
|
||||
#include <osgDB/DatabasePager>
|
||||
#include <osgDB/FileCache>
|
||||
#include <osgDB/SharedStateManager>
|
||||
|
||||
#include <vector>
|
||||
#include <map>
|
||||
@ -308,10 +308,10 @@ class OSGDB_EXPORT Registry : public osg::Referenced
|
||||
}
|
||||
}
|
||||
|
||||
/** Set the callback to use inform the DatabasePager whether a file is located on local or remote file system.*/
|
||||
/** Set the callback to use inform to the DatabasePager whether a file is located on local or remote file system.*/
|
||||
void setFileLocationCallback( FileLocationCallback* cb) { _fileLocationCallback = cb; }
|
||||
|
||||
/** Get the callback to use inform the DatabasePager whether a file is located on local or remote file system.*/
|
||||
/** Get the callback to use inform to the DatabasePager whether a file is located on local or remote file system.*/
|
||||
FileLocationCallback* getFileLocationCallback() const { return _fileLocationCallback.get(); }
|
||||
|
||||
|
||||
|
@ -266,7 +266,7 @@ class OSGUTIL_EXPORT IncrementalCompileOperation : public osg::GraphicsOperation
|
||||
return true;
|
||||
}
|
||||
|
||||
osg::ref_ptr<osg::Group> _attachmentPoint;
|
||||
osg::observer_ptr<osg::Group> _attachmentPoint;
|
||||
osg::ref_ptr<osg::Node> _subgraphToCompile;
|
||||
osg::ref_ptr<CompileCompletedCallback> _compileCompletedCallback;
|
||||
CompileMap _compileMap;
|
||||
@ -287,9 +287,12 @@ class OSGUTIL_EXPORT IncrementalCompileOperation : public osg::GraphicsOperation
|
||||
/** Add a CompileSet to be compiled.*/
|
||||
void add(CompileSet* compileSet, bool callBuildCompileMap=true);
|
||||
|
||||
/** Remove CompileSet from list.*/
|
||||
void remove(CompileSet* compileSet);
|
||||
|
||||
|
||||
OpenThreads::Mutex* getToCompiledMutex() { return &_toCompileMutex; }
|
||||
CompileSets& getToCompile() { return _compiled; }
|
||||
CompileSets& getToCompile() { return _toCompile; }
|
||||
|
||||
OpenThreads::Mutex* getCompiledMutex() { return &_compiledMutex; }
|
||||
CompileSets& getCompiled() { return _compiled; }
|
||||
|
@ -480,6 +480,10 @@ class OSGUTIL_EXPORT SceneView : public osg::Object, public osg::CullSettings
|
||||
/** Extract stats for current draw list. */
|
||||
bool getStats(Statistics& primStats);
|
||||
|
||||
/** Set whether the SceneView should automatically call flishDeletedObjects() on each new frame.*/
|
||||
void setAutomaticFlush(bool automaticFlush) { _automaticFlush = automaticFlush; }
|
||||
bool getAutomaticFlush() const { return _automaticFlush; }
|
||||
|
||||
protected:
|
||||
|
||||
virtual ~SceneView();
|
||||
@ -536,6 +540,7 @@ class OSGUTIL_EXPORT SceneView : public osg::Object, public osg::CullSettings
|
||||
|
||||
bool _prioritizeTextures;
|
||||
|
||||
bool _automaticFlush;
|
||||
bool _requiresFlush;
|
||||
|
||||
int _activeUniforms;
|
||||
|
@ -68,50 +68,6 @@ class OSGVIEWER_EXPORT Renderer : public osg::GraphicsOperation
|
||||
|
||||
virtual void release();
|
||||
|
||||
|
||||
/** Set the target frame rate that the DatabasePager should assume.
|
||||
* Typically one would set this to the value refresh rate of your display system i.e. 60Hz.
|
||||
* Default value is 100.
|
||||
* Usage notes. The TargetFrameRate and the MinimumTimeAvailableForGLCompileAndDeletePerFrame
|
||||
* parameters are not directly used by DatabasePager, but are should be used as a guide for how
|
||||
* long to set aside per frame for compiling and deleting OpenGL objects - ie. the value to use
|
||||
* when calling DatabasePager::compileGLObjectgs(state,availableTime,). The longer amount of
|
||||
* time to set aside cthe faster databases will be paged in but with increased chance of frame drops,
|
||||
* the lower the amount of time the set aside the slower databases will paged it but with better
|
||||
* chance of avoid any frame drops. The default values are chosen to achieve the later when running
|
||||
* on a modern mid to high end PC.
|
||||
* The way to compute the amount of available time use a scheme such as :
|
||||
* availableTime = maximum(1.0/targetFrameRate - timeTakenDuringUpdateCullAndDraw, minimumTimeAvailableForGLCompileAndDeletePerFrame).
|
||||
*
|
||||
* Note, the actual TargetFrameRate used is the minimum of this value and that set in the DatabasePager. */
|
||||
void setTargetFrameRate(double tfr) { _targetFrameRate = tfr; }
|
||||
|
||||
/** Get the target frame rate that the DatabasePager should assume.*/
|
||||
double getTargetFrameRate() const { return _targetFrameRate; }
|
||||
|
||||
/** Set the minimum amount of time (in seconds) that should be made available for compiling and delete OpenGL objects per frame.
|
||||
* Default value is 0.001 (1 millisecond).
|
||||
* For usage see notes in setTargetFrameRate.
|
||||
*
|
||||
* Note, the actual TargetFrameRate used is the minimum of this value and that set in the DatabasePager. */
|
||||
void setMinimumTimeAvailableForGLCompileAndDeletePerFrame(double ta) { _minimumTimeAvailableForGLCompileAndDeletePerFrame = ta; }
|
||||
|
||||
/** Get the minimum amount of time that should be made available for compiling and delete OpenGL objects per frame.
|
||||
* For usage see notes in setTargetFrameRate.*/
|
||||
double getMinimumTimeAvailableForGLCompileAndDeletePerFrame() const { return _minimumTimeAvailableForGLCompileAndDeletePerFrame; }
|
||||
|
||||
/** FlushTimeRatio governs how much of the spare time in each frame is used for flushing deleted OpenGL objects.
|
||||
* Default value is 0.5, valid range is 0.1 to 0.9.*/
|
||||
void setFlushTimeRatio(double ratio) { _flushTimeRatio = ratio; }
|
||||
double getFlushTimeRatio() const { return _flushTimeRatio; }
|
||||
|
||||
/** ConservativeTimeRatio governs how much of the measured spare time in each frame is used for flushing deleted and compile new OpenGL objects.
|
||||
* Default value is 0.5, valid range is 0.1 to 1.0.
|
||||
* A ratio near 1.0 will lead to paged databases being compiled and merged quicker but increase the chances of frame drop.
|
||||
* A ratio near 0.1 will lead to paged databases being compiled and merged closer but reduse the chances of frame drop.*/
|
||||
void setConservativeTimeRatio(double ratio) { _conservativeTimeRatio = ratio; }
|
||||
double getConservativeTimeRatio() const { return _conservativeTimeRatio; }
|
||||
|
||||
/** Force update of state associated with cameras. */
|
||||
void setCameraRequiresSetUp(bool flag);
|
||||
bool getCameraRequiresSetUp() const;
|
||||
@ -121,12 +77,6 @@ class OSGVIEWER_EXPORT Renderer : public osg::GraphicsOperation
|
||||
virtual ~Renderer();
|
||||
|
||||
virtual void updateSceneView(osgUtil::SceneView* sceneView);
|
||||
virtual void flushAndCompile(double currentElapsedFrameTime, osgUtil::SceneView* sceneView, osgDB::DatabasePager* databasePager, osg::GraphicsThread* compileThread);
|
||||
|
||||
double _targetFrameRate;
|
||||
double _minimumTimeAvailableForGLCompileAndDeletePerFrame;
|
||||
double _flushTimeRatio;
|
||||
double _conservativeTimeRatio;
|
||||
|
||||
osg::observer_ptr<osg::Camera> _camera;
|
||||
|
||||
@ -136,9 +86,6 @@ class OSGVIEWER_EXPORT Renderer : public osg::GraphicsOperation
|
||||
|
||||
osg::ref_ptr<osgUtil::SceneView> _sceneView[2];
|
||||
|
||||
osg::ref_ptr<osg::FlushDeletedGLObjectsOperation> _flushOperation;
|
||||
|
||||
|
||||
struct OSGVIEWER_EXPORT ThreadSafeQueue
|
||||
{
|
||||
OpenThreads::Mutex _mutex;
|
||||
|
@ -44,8 +44,6 @@ using namespace osgDB;
|
||||
using namespace OpenThreads;
|
||||
|
||||
static osg::ApplicationUsageProxy DatabasePager_e0(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_DO_PRE_COMPILE <ON/OFF>","Switch on or off the pre compile of OpenGL object database pager.");
|
||||
static osg::ApplicationUsageProxy DatabasePager_e1(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_MINIMUM_COMPILE_TIME_PER_FRAME <float>","minimum compile time alloted to compiling OpenGL objects per frame in database pager.");
|
||||
static osg::ApplicationUsageProxy DatabasePager_e2(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_MAXIMUM_OBJECTS_TO_COMPILE_PER_FRAME <int>","maximum number of OpenGL objects to compile per frame in database pager.");
|
||||
static osg::ApplicationUsageProxy DatabasePager_e3(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_DATABASE_PAGER_DRAWABLE <mode>","Set the drawable policy for setting of loaded drawable to specified type. mode can be one of DoNotModify, DisplayList, VBO or VertexArrays>.");
|
||||
static osg::ApplicationUsageProxy DatabasePager_e4(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_DATABASE_PAGER_PRIORITY <mode>", "Set the thread priority to DEFAULT, MIN, LOW, NOMINAL, HIGH or MAX.");
|
||||
static osg::ApplicationUsageProxy DatabasePager_e7(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_EXPIRY_DELAY <float> ","Set the length of time a PagedLOD child is kept in memory, without being used, before its tagged as expired, and ear marked to deletion.");
|
||||
@ -127,6 +125,13 @@ struct DatabasePager::DatabasePagerCompileCompletedCallback : public osgUtil::In
|
||||
};
|
||||
|
||||
|
||||
void DatabasePager::compileCompleted(DatabaseRequest* databaseRequest)
|
||||
{
|
||||
//OSG_NOTICE<<"DatabasePager::compileCompleted("<<databaseRequest<<")"<<std::endl;
|
||||
_dataToCompileList->remove(databaseRequest);
|
||||
_dataToMergeList->add(databaseRequest);
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// CountPagedLODList
|
||||
@ -335,13 +340,11 @@ public:
|
||||
class DatabasePager::FindCompileableGLObjectsVisitor : public osg::NodeVisitor
|
||||
{
|
||||
public:
|
||||
FindCompileableGLObjectsVisitor(DatabasePager::DataToCompile* dataToCompile,
|
||||
bool changeAutoUnRef, bool valueAutoUnRef,
|
||||
FindCompileableGLObjectsVisitor(bool changeAutoUnRef, bool valueAutoUnRef,
|
||||
bool changeAnisotropy, float valueAnisotropy,
|
||||
DatabasePager::DrawablePolicy drawablePolicy,
|
||||
const DatabasePager* pager):
|
||||
osg::NodeVisitor(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN),
|
||||
_dataToCompile(dataToCompile),
|
||||
_changeAutoUnRef(changeAutoUnRef), _valueAutoUnRef(valueAutoUnRef),
|
||||
_changeAnisotropy(changeAnisotropy), _valueAnisotropy(valueAnisotropy),
|
||||
_drawablePolicy(drawablePolicy), _pager(pager)
|
||||
@ -355,6 +358,8 @@ public:
|
||||
|
||||
META_NodeVisitor("osgDB","FindCompileableGLObjectsVisitor")
|
||||
|
||||
bool requiresCompilation() const { return true; }
|
||||
|
||||
virtual void apply(osg::Node& node)
|
||||
{
|
||||
apply(node.getStateSet());
|
||||
@ -402,20 +407,6 @@ public:
|
||||
if (_changeAnisotropy)
|
||||
texture->setMaxAnisotropy(_valueAnisotropy);
|
||||
}
|
||||
|
||||
if (!_pager->isCompiled(texture))
|
||||
{
|
||||
_dataToCompile->_textures.insert(texture);
|
||||
|
||||
if (osg::getNotifyLevel() >= osg::DEBUG_INFO)
|
||||
{
|
||||
OSG_INFO <<"Found compilable texture " << texture << " ";
|
||||
osg::Image* image = texture->getImage(0);
|
||||
if (image) OSG_INFO << image->getFileName();
|
||||
OSG_INFO << std:: endl;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -452,18 +443,8 @@ public:
|
||||
// OSG_NOTICE<<"USE_VERTEX_ARRAYS"<<std::endl;
|
||||
break;
|
||||
}
|
||||
// Don't compile if already compiled. This can happen if the
|
||||
// subgraph is shared with already-loaded nodes.
|
||||
//
|
||||
// XXX This "compiles" VBOs too, but compilation doesn't do
|
||||
// anything for VBOs, does it?
|
||||
if (_dataToCompile && (drawable->getUseVertexBufferObjects() || drawable->getUseDisplayList()) && !_pager->isCompiled(drawable))
|
||||
{
|
||||
_dataToCompile->_drawables.insert(drawable);
|
||||
}
|
||||
}
|
||||
|
||||
DatabasePager::DataToCompile* _dataToCompile;
|
||||
bool _changeAutoUnRef;
|
||||
bool _valueAutoUnRef;
|
||||
bool _changeAnisotropy;
|
||||
@ -506,8 +487,8 @@ void DatabasePager::DatabaseRequest::invalidate()
|
||||
_valid = false;
|
||||
_groupForAddingLoadedSubgraph = 0;
|
||||
_loadedModel = 0;
|
||||
_dataToCompileMap.clear();
|
||||
_requestQueue = 0;
|
||||
_compileSet = 0;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
@ -528,10 +509,25 @@ DatabasePager::RequestQueue::~RequestQueue()
|
||||
itr != _requestList.end();
|
||||
++itr)
|
||||
{
|
||||
(*itr)->invalidate();
|
||||
invalidate(itr->get());
|
||||
}
|
||||
}
|
||||
|
||||
void DatabasePager::RequestQueue::invalidate(DatabaseRequest* dr)
|
||||
{
|
||||
// OSG_NOTICE<<"DatabasePager::RequestQueue::invalidate(DatabaseRequest* dr) dr->_compileSet="<<dr->_compileSet.get()<<std::endl;
|
||||
|
||||
osg::ref_ptr<osgUtil::IncrementalCompileOperation::CompileSet> compileSet;
|
||||
if (dr->_compileSet.lock(compileSet) && _pager->getIncrementalCompileOperation())
|
||||
{
|
||||
_pager->getIncrementalCompileOperation()->remove(compileSet.get());
|
||||
}
|
||||
|
||||
|
||||
dr->invalidate();
|
||||
}
|
||||
|
||||
|
||||
bool DatabasePager::RequestQueue::pruneOldRequestsAndCheckIfEmpty()
|
||||
{
|
||||
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_requestMutex);
|
||||
@ -548,7 +544,7 @@ bool DatabasePager::RequestQueue::pruneOldRequestsAndCheckIfEmpty()
|
||||
}
|
||||
else
|
||||
{
|
||||
(*citr)->invalidate();
|
||||
invalidate(citr->get());
|
||||
|
||||
OSG_INFO<<"DatabasePager::RequestQueue::pruneOldRequestsAndCheckIfEmpty(): Pruning "<<(*citr)<<std::endl;
|
||||
citr = _requestList.erase(citr);
|
||||
@ -578,7 +574,7 @@ void DatabasePager::RequestQueue::clear()
|
||||
citr != _requestList.end();
|
||||
++citr)
|
||||
{
|
||||
(*citr)->invalidate();
|
||||
invalidate(citr->get());
|
||||
}
|
||||
|
||||
_requestList.clear();
|
||||
@ -603,6 +599,25 @@ void DatabasePager::RequestQueue::add(DatabasePager::DatabaseRequest* databaseRe
|
||||
addNoLock(databaseRequest);
|
||||
}
|
||||
|
||||
void DatabasePager::RequestQueue::remove(DatabasePager::DatabaseRequest* databaseRequest)
|
||||
{
|
||||
// OSG_NOTICE<<"DatabasePager::RequestQueue::remove(DatabaseRequest* databaseRequest)"<<std::endl;
|
||||
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_requestMutex);
|
||||
for(RequestList::iterator citr = _requestList.begin();
|
||||
citr != _requestList.end();
|
||||
++citr)
|
||||
{
|
||||
if (citr->get()==databaseRequest)
|
||||
{
|
||||
// OSG_NOTICE<<" done remove(DatabaseRequest* databaseRequest)"<<std::endl;
|
||||
_requestList.erase(citr);
|
||||
--_size;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void DatabasePager::RequestQueue::addNoLock(DatabasePager::DatabaseRequest* databaseRequest)
|
||||
{
|
||||
_requestList.push_back(databaseRequest);
|
||||
@ -649,7 +664,7 @@ void DatabasePager::RequestQueue::takeFirst(osg::ref_ptr<DatabaseRequest>& datab
|
||||
}
|
||||
else
|
||||
{
|
||||
(*citr)->invalidate();
|
||||
invalidate(citr->get());
|
||||
|
||||
OSG_INFO<<"DatabasePager::RequestQueue::takeFirst(): Pruning "<<(*citr)<<std::endl;
|
||||
citr = _requestList.erase(citr);
|
||||
@ -708,8 +723,7 @@ DatabasePager::DatabaseThread::DatabaseThread(DatabasePager* pager, Mode mode, c
|
||||
_active(false),
|
||||
_pager(pager),
|
||||
_mode(mode),
|
||||
_name(name),
|
||||
_tickSinceStartOfIteration(0)
|
||||
_name(name)
|
||||
{
|
||||
}
|
||||
|
||||
@ -718,8 +732,7 @@ DatabasePager::DatabaseThread::DatabaseThread(const DatabaseThread& dt, Database
|
||||
_active(false),
|
||||
_pager(pager),
|
||||
_mode(dt._mode),
|
||||
_name(dt._name),
|
||||
_tickSinceStartOfIteration(0)
|
||||
_name(dt._name)
|
||||
{
|
||||
}
|
||||
|
||||
@ -750,30 +763,22 @@ int DatabasePager::DatabaseThread::cancel()
|
||||
break;
|
||||
}
|
||||
|
||||
// release the frameBlock and _databasePagerThreadBlock in case its holding up thread cancellation.
|
||||
// _databasePagerThreadBlock->release();
|
||||
|
||||
// then wait for the the thread to stop running.
|
||||
while(isRunning())
|
||||
{
|
||||
// commenting out debug info as it was cashing crash on exit, presumable
|
||||
// due to OSG_NOTICE or std::cout destructing earlier than this destructor.
|
||||
// OSG_INFO<<"Waiting for DatabasePager to cancel"<<std::endl;
|
||||
// OSG_INFO<<"Waiting for DatabasePager::DatabaseThread to cancel"<<std::endl;
|
||||
OpenThreads::Thread::YieldCurrentThread();
|
||||
}
|
||||
|
||||
// _startThreadCalled = false;
|
||||
}
|
||||
//std::cout<<"DatabasePager::~DatabasePager() stopped running"<<std::endl;
|
||||
//OSG_NOTICE<<"DatabasePager::DatabaseThread stopped running"<<std::endl;
|
||||
return result;
|
||||
|
||||
}
|
||||
|
||||
double DatabasePager::DatabaseThread::getTimeSinceStartOfIteration() const
|
||||
{
|
||||
return osg::Timer::instance()->delta_s(_tickSinceStartOfIteration, osg::Timer::instance()->tick());
|
||||
}
|
||||
|
||||
void DatabasePager::DatabaseThread::run()
|
||||
{
|
||||
OSG_INFO<<_name<<": DatabasePager::DatabaseThread::run"<<std::endl;
|
||||
@ -803,11 +808,12 @@ void DatabasePager::DatabaseThread::run()
|
||||
{
|
||||
_active = false;
|
||||
|
||||
_tickSinceStartOfIteration = osg::Timer::instance()->tick();
|
||||
|
||||
read_queue->block();
|
||||
|
||||
_tickSinceStartOfIteration = osg::Timer::instance()->tick();
|
||||
if (_done)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
_active = true;
|
||||
|
||||
@ -960,53 +966,32 @@ void DatabasePager::DatabaseThread::run()
|
||||
|
||||
//OSG_NOTICE<<" node read in "<<osg::Timer::instance()->delta_m(before,osg::Timer::instance()->tick())<<" ms"<<std::endl;
|
||||
|
||||
bool loadedObjectsNeedToBeCompiled = false;
|
||||
|
||||
if (databaseRequest->_loadedModel.valid())
|
||||
{
|
||||
databaseRequest->_loadedModel->getBound();
|
||||
|
||||
osg::NodePath nodePath;
|
||||
|
||||
for(osg::RefNodePath::iterator rnp_itr = refNodePath.begin();
|
||||
rnp_itr != refNodePath.end();
|
||||
++rnp_itr)
|
||||
{
|
||||
nodePath.push_back(rnp_itr->get());
|
||||
}
|
||||
|
||||
// force a compute of the loaded model's bounding volume, so that when the subgraph
|
||||
// merged with the main scene graph and large computeBound() isn't incurred.
|
||||
ActiveGraphicsContexts::iterator itr = _pager->_activeGraphicsContexts.begin();
|
||||
|
||||
DataToCompile* dtc = 0;
|
||||
if (itr != _pager->_activeGraphicsContexts.end())
|
||||
{
|
||||
dtc = &(databaseRequest->_dataToCompileMap[*itr]);
|
||||
++itr;
|
||||
}
|
||||
|
||||
// find all the compileable rendering objects
|
||||
DatabasePager::FindCompileableGLObjectsVisitor frov(dtc,
|
||||
_pager->_changeAutoUnRef, _pager->_valueAutoUnRef,
|
||||
DatabasePager::FindCompileableGLObjectsVisitor frov(_pager->_changeAutoUnRef, _pager->_valueAutoUnRef,
|
||||
_pager->_changeAnisotropy, _pager->_valueAnisotropy,
|
||||
_pager->_drawablePolicy,
|
||||
_pager);
|
||||
|
||||
// push the soon to be parent on the nodepath of the NodeVisitor so that
|
||||
// during traversal one can test for where it'll be in the overall scene graph
|
||||
for(osg::NodePath::iterator nitr = nodePath.begin();
|
||||
nitr != nodePath.end();
|
||||
++nitr)
|
||||
for(osg::RefNodePath::iterator rnp_itr = refNodePath.begin();
|
||||
rnp_itr != refNodePath.end();
|
||||
++rnp_itr)
|
||||
{
|
||||
frov.pushOntoNodePath(*nitr);
|
||||
frov.pushOntoNodePath(rnp_itr->get());
|
||||
}
|
||||
|
||||
databaseRequest->_loadedModel->accept(frov);
|
||||
|
||||
if (_pager->_doPreCompile && !dtc->empty())
|
||||
{
|
||||
if (_pager->_incrementalCompileOperation.valid())
|
||||
bool loadedObjectsNeedToBeCompiled = (_pager->_doPreCompile && frov.requiresCompilation() && _pager->_incrementalCompileOperation.valid());
|
||||
|
||||
// move the databaseRequest from the front of the fileRequest to the end of
|
||||
// dataToCompile or dataToMerge lists.
|
||||
if (loadedObjectsNeedToBeCompiled)
|
||||
{
|
||||
// OSG_NOTICE<<"Using IncrementalCompileOperation"<<std::endl;
|
||||
|
||||
@ -1015,70 +1000,17 @@ void DatabasePager::DatabaseThread::run()
|
||||
|
||||
_pager->_incrementalCompileOperation->add(compileSet);
|
||||
|
||||
loadedObjectsNeedToBeCompiled = true;
|
||||
}
|
||||
else if (!_pager->_activeGraphicsContexts.empty())
|
||||
{
|
||||
// copy the objects from the compile list to the other graphics context list.
|
||||
for(;
|
||||
itr != _pager->_activeGraphicsContexts.end();
|
||||
++itr)
|
||||
{
|
||||
databaseRequest->_dataToCompileMap[*itr] = *dtc;
|
||||
}
|
||||
}
|
||||
}
|
||||
databaseRequest->_compileSet = compileSet;
|
||||
|
||||
// move the databaseRequest from the front of the fileRequest to the end of
|
||||
// dataToCompile or dataToMerge lists.
|
||||
if (loadedObjectsNeedToBeCompiled)
|
||||
{
|
||||
if (!_pager->_incrementalCompileOperation)
|
||||
{
|
||||
_pager->_dataToCompileList->add(databaseRequest.get());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
_pager->_dataToMergeList->add(databaseRequest.get());
|
||||
}
|
||||
}
|
||||
|
||||
// Prepare and prune the to-be-compiled list here in
|
||||
// the pager thread rather than in the draw or
|
||||
// graphics context thread(s).
|
||||
if (loadedObjectsNeedToBeCompiled)
|
||||
{
|
||||
loadedObjectsNeedToBeCompiled = ! _pager->_dataToCompileList->pruneOldRequestsAndCheckIfEmpty();
|
||||
}
|
||||
|
||||
if (loadedObjectsNeedToBeCompiled && !_pager->_activeGraphicsContexts.empty())
|
||||
{
|
||||
for(ActiveGraphicsContexts::iterator itr = _pager->_activeGraphicsContexts.begin();
|
||||
itr != _pager->_activeGraphicsContexts.end();
|
||||
++itr)
|
||||
{
|
||||
osg::GraphicsContext* gc = osg::GraphicsContext::getCompileContext(*itr);
|
||||
if (gc)
|
||||
{
|
||||
osg::GraphicsThread* gt = gc->getGraphicsThread();
|
||||
if (gt)
|
||||
{
|
||||
gt->add(new DatabasePager::CompileOperation(_pager));
|
||||
}
|
||||
else
|
||||
{
|
||||
gc->makeCurrent();
|
||||
|
||||
_pager->compileAllGLObjects(*(gc->getState()));
|
||||
|
||||
gc->releaseContext();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// OSG_NOTICE<<"Done compiling in paging thread"<<std::endl;
|
||||
}
|
||||
// _pager->_dataToCompileList->pruneOldRequestsAndCheckIfEmpty();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1175,19 +1107,6 @@ DatabasePager::DatabasePager()
|
||||
strcmp(ptr,"on")==0 || strcmp(ptr,"ON")==0;
|
||||
}
|
||||
|
||||
_targetFrameRate = 100.0;
|
||||
_minimumTimeAvailableForGLCompileAndDeletePerFrame = 0.001; // 1ms.
|
||||
_maximumNumOfObjectsToCompilePerFrame = 4;
|
||||
if( (ptr = getenv("OSG_MINIMUM_COMPILE_TIME_PER_FRAME")) != 0)
|
||||
{
|
||||
_minimumTimeAvailableForGLCompileAndDeletePerFrame = osg::asciiToDouble(ptr);
|
||||
}
|
||||
|
||||
if( (ptr = getenv("OSG_MAXIMUM_OBJECTS_TO_COMPILE_PER_FRAME")) != 0)
|
||||
{
|
||||
_maximumNumOfObjectsToCompilePerFrame = atoi(ptr);
|
||||
}
|
||||
|
||||
// initialize the stats variables
|
||||
resetStats();
|
||||
|
||||
@ -1260,16 +1179,11 @@ DatabasePager::DatabasePager(const DatabasePager& rhs)
|
||||
_changeAnisotropy = rhs._changeAnisotropy;
|
||||
_valueAnisotropy = rhs._valueAnisotropy;
|
||||
|
||||
|
||||
_deleteRemovedSubgraphsInDatabaseThread = rhs._deleteRemovedSubgraphsInDatabaseThread;
|
||||
|
||||
|
||||
_targetMaximumNumberOfPageLOD = rhs._targetMaximumNumberOfPageLOD;
|
||||
|
||||
_doPreCompile = rhs._doPreCompile;
|
||||
_targetFrameRate = rhs._targetFrameRate;
|
||||
_minimumTimeAvailableForGLCompileAndDeletePerFrame = rhs._minimumTimeAvailableForGLCompileAndDeletePerFrame;
|
||||
_maximumNumOfObjectsToCompilePerFrame = rhs._maximumNumOfObjectsToCompilePerFrame;
|
||||
|
||||
_fileRequestQueue = new ReadQueue(this,"fileRequestQueue");
|
||||
_httpRequestQueue = new ReadQueue(this,"httpRequestQueue");
|
||||
@ -1313,7 +1227,23 @@ void DatabasePager::setIncrementalCompileOperation(osgUtil::IncrementalCompileOp
|
||||
|
||||
DatabasePager::~DatabasePager()
|
||||
{
|
||||
// cancel the threads
|
||||
cancel();
|
||||
|
||||
// destruct all the threads
|
||||
_databaseThreads.clear();
|
||||
|
||||
// destruct all the queues
|
||||
_fileRequestQueue = 0;
|
||||
_httpRequestQueue = 0;
|
||||
_dataToCompileList = 0;
|
||||
_dataToMergeList = 0;
|
||||
|
||||
// remove reference to the ICO
|
||||
_incrementalCompileOperation = 0;
|
||||
|
||||
//_activePagedLODList;
|
||||
//_inactivePagedLODList;
|
||||
}
|
||||
|
||||
osg::ref_ptr<DatabasePager>& DatabasePager::prototype()
|
||||
@ -1411,7 +1341,7 @@ int DatabasePager::cancel()
|
||||
(*dt_itr)->setDone(true);
|
||||
}
|
||||
|
||||
// release the frameBlock and _databasePagerThreadBlock in case its holding up thread cancellation.
|
||||
// release the queue blocks in case they are holding up thread cancellation.
|
||||
_fileRequestQueue->release();
|
||||
_httpRequestQueue->release();
|
||||
|
||||
@ -1425,7 +1355,6 @@ int DatabasePager::cancel()
|
||||
_done = true;
|
||||
_startThreadCalled = false;
|
||||
|
||||
//std::cout<<"DatabasePager::~DatabasePager() stopped running"<<std::endl;
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -1637,8 +1566,16 @@ void DatabasePager::requestNodeFile(const std::string& fileName,osg::Group* grou
|
||||
|
||||
void DatabasePager::signalBeginFrame(const osg::FrameStamp* framestamp)
|
||||
{
|
||||
#if 0
|
||||
OSG_NOTICE<<"DatabasePager : _fileRequestQueue->size()="<<_fileRequestQueue->size()
|
||||
<<", _httpRequestQueue->size()= "<<_httpRequestQueue->size()
|
||||
<<", _dataToCompileList->size()= "<<_dataToCompileList->size()
|
||||
<<", _dataToMergeList->size()= "<<_dataToMergeList->size()<<std::endl;
|
||||
#endif
|
||||
if (framestamp)
|
||||
{
|
||||
_dataToCompileList->pruneOldRequestsAndCheckIfEmpty();
|
||||
|
||||
//OSG_INFO << "signalBeginFrame "<<framestamp->getFrameNumber()<<">>>>>>>>>>>>>>>>"<<std::endl;
|
||||
_frameNumber = framestamp->getFrameNumber();
|
||||
|
||||
@ -1713,7 +1650,7 @@ void DatabasePager::addLoadedDataToSceneGraph(const osg::FrameStamp &frameStamp)
|
||||
|
||||
RequestQueue::RequestList localFileLoadedList;
|
||||
|
||||
// get the data for the _dataToCompileList, leaving it empty via a std::vector<>.swap.
|
||||
// get the data from the _dataToMergeList, leaving it empty via a std::vector<>.swap.
|
||||
_dataToMergeList->swap(localFileLoadedList);
|
||||
|
||||
mid = osg::Timer::instance()->tick();
|
||||
@ -1945,235 +1882,3 @@ void DatabasePager::registerPagedLODs(osg::Node* subgraph, int frameNumber)
|
||||
FindPagedLODsVisitor fplv(*_activePagedLODList, frameNumber);
|
||||
subgraph->accept(fplv);
|
||||
}
|
||||
|
||||
bool DatabasePager::requiresCompileGLObjects() const
|
||||
{
|
||||
return !_dataToCompileList->empty();
|
||||
}
|
||||
|
||||
void DatabasePager::setCompileGLObjectsForContextID(unsigned int contextID, bool on)
|
||||
{
|
||||
if (on)
|
||||
{
|
||||
_activeGraphicsContexts.insert(contextID);
|
||||
}
|
||||
else
|
||||
{
|
||||
_activeGraphicsContexts.erase(contextID);
|
||||
}
|
||||
}
|
||||
|
||||
bool DatabasePager::getCompileGLObjectsForContextID(unsigned int contextID)
|
||||
{
|
||||
return _activeGraphicsContexts.count(contextID)!=0;
|
||||
}
|
||||
|
||||
|
||||
DatabasePager::CompileOperation::CompileOperation(osgDB::DatabasePager* databasePager):
|
||||
osg::GraphicsOperation("DatabasePager::CompileOperation",false),
|
||||
_databasePager(databasePager)
|
||||
{
|
||||
}
|
||||
|
||||
void DatabasePager::CompileOperation::operator () (osg::GraphicsContext* context)
|
||||
{
|
||||
// OSG_NOTICE<<"Background thread compiling"<<std::endl;
|
||||
|
||||
if (_databasePager.valid()) _databasePager->compileAllGLObjects(*(context->getState()), true);
|
||||
|
||||
}
|
||||
|
||||
bool DatabasePager::requiresExternalCompileGLObjects(unsigned int contextID) const
|
||||
{
|
||||
if (_activeGraphicsContexts.count(contextID)==0) return false;
|
||||
|
||||
return osg::GraphicsContext::getCompileContext(contextID)==0;
|
||||
}
|
||||
|
||||
void DatabasePager::compileCompleted(DatabaseRequest* databaseRequest)
|
||||
{
|
||||
//OSG_NOTICE<<"DatabasePager::compileCompleted("<<databaseRequest<<")"<<std::endl;
|
||||
_dataToMergeList->add(databaseRequest);
|
||||
}
|
||||
|
||||
void DatabasePager::compileAllGLObjects(osg::State& state, bool doFlush)
|
||||
{
|
||||
double availableTime = DBL_MAX;
|
||||
compileGLObjects(state, availableTime, doFlush);
|
||||
}
|
||||
|
||||
void DatabasePager::compileGLObjects(osg::State& state, double& availableTime, bool doFlush)
|
||||
{
|
||||
// OSG_NOTICE<<"DatabasePager::compileGLObjects "<<_frameNumber<<std::endl;
|
||||
|
||||
bool compileAll = (availableTime==DBL_MAX);
|
||||
|
||||
SharedStateManager *sharedManager
|
||||
= Registry::instance()->getSharedStateManager();
|
||||
osg::RenderInfo renderInfo;
|
||||
renderInfo.setState(&state);
|
||||
|
||||
if (availableTime>0.0)
|
||||
{
|
||||
|
||||
const osg::Timer& timer = *osg::Timer::instance();
|
||||
osg::Timer_t start_tick = timer.tick();
|
||||
double elapsedTime = 0.0;
|
||||
double estimatedTextureDuration = 0.0001;
|
||||
double estimatedDrawableDuration = 0.0001;
|
||||
|
||||
osg::ref_ptr<DatabaseRequest> databaseRequest;
|
||||
_dataToCompileList->takeFirst(databaseRequest);
|
||||
|
||||
unsigned int numObjectsCompiled = 0;
|
||||
|
||||
// while there are valid databaseRequest's in the to compile list and there is
|
||||
// sufficient time left compile each databaseRequest's stateset and drawables.
|
||||
while (databaseRequest.valid() && databaseRequest->valid() && (compileAll || (elapsedTime<availableTime && numObjectsCompiled<_maximumNumOfObjectsToCompilePerFrame)) )
|
||||
{
|
||||
DataToCompileMap& dcm = databaseRequest->_dataToCompileMap;
|
||||
DataToCompile& dtc = dcm[state.getContextID()];
|
||||
if (!dtc._textures.empty() && (elapsedTime+estimatedTextureDuration)<availableTime && numObjectsCompiled<_maximumNumOfObjectsToCompilePerFrame)
|
||||
{
|
||||
|
||||
#if !defined(OSG_GLES1_AVAILABLE) && !defined(OSG_GLES2_AVAILABLE) && !defined(OSG_GL3_AVAILABLE)
|
||||
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_PRIORITY, 1.0);
|
||||
#endif
|
||||
|
||||
//OSG_INFO<<"Compiling textures"<<std::endl;
|
||||
|
||||
// we have Textures to compile
|
||||
typedef osgUtil::CompileData::Textures Textures;
|
||||
Textures& textures = dtc._textures;
|
||||
Textures::iterator itr=textures.begin();
|
||||
unsigned int objTemp = numObjectsCompiled;
|
||||
for(;
|
||||
itr!=textures.end() && (compileAll || ((elapsedTime+estimatedTextureDuration)<availableTime && numObjectsCompiled<_maximumNumOfObjectsToCompilePerFrame));
|
||||
++itr)
|
||||
{
|
||||
OSG_INFO<<" Compiling texture "<<(*itr).get()<<std::endl;
|
||||
if (isCompiled(itr->get(), state.getContextID())
|
||||
|| (sharedManager && sharedManager->isShared(itr->get())))
|
||||
{
|
||||
elapsedTime = timer.delta_s(start_tick,timer.tick());
|
||||
continue;
|
||||
}
|
||||
double startCompileTime = timer.delta_s(start_tick,timer.tick());
|
||||
|
||||
(*itr)->apply(state);
|
||||
|
||||
#if !defined(OSG_GLES1_AVAILABLE) && !defined(OSG_GLES2_AVAILABLE) && !defined(OSG_GL3_AVAILABLE)
|
||||
GLint p;
|
||||
glGetTexParameteriv(GL_TEXTURE_2D, GL_TEXTURE_RESIDENT, &p);
|
||||
#endif
|
||||
|
||||
elapsedTime = timer.delta_s(start_tick,timer.tick());
|
||||
|
||||
// estimate the duration of the compile based on current compile duration.
|
||||
estimatedTextureDuration = (elapsedTime-startCompileTime);
|
||||
|
||||
++numObjectsCompiled;
|
||||
}
|
||||
if (osg::getNotifyLevel() >= osg::DEBUG_INFO
|
||||
&& numObjectsCompiled > objTemp)
|
||||
OSG_NOTICE<< _frameNumber << " compiled "
|
||||
<< numObjectsCompiled - objTemp
|
||||
<< " StateSets" << std::endl;
|
||||
// remove the compiled statesets from the list.
|
||||
textures.erase(textures.begin(),itr);
|
||||
}
|
||||
|
||||
if (!dtc._drawables.empty() && (compileAll || ((elapsedTime+estimatedDrawableDuration)<availableTime && numObjectsCompiled<_maximumNumOfObjectsToCompilePerFrame)))
|
||||
{
|
||||
// we have Drawable's to compile
|
||||
//OSG_INFO<<"Compiling drawables"<<std::endl;
|
||||
typedef osgUtil::CompileData::Drawables Drawables;
|
||||
Drawables& dwlist = dtc._drawables;
|
||||
Drawables::iterator itr = dwlist.begin();
|
||||
unsigned int objTemp = numObjectsCompiled;
|
||||
for(;
|
||||
itr!=dwlist.end() && (compileAll || ((elapsedTime+estimatedDrawableDuration)<availableTime && numObjectsCompiled<_maximumNumOfObjectsToCompilePerFrame));
|
||||
++itr)
|
||||
{
|
||||
//OSG_INFO<<" Compiling drawable "<<(*itr).get()<<std::endl;
|
||||
if (isCompiled(itr->get(), state.getContextID()))
|
||||
{
|
||||
elapsedTime = timer.delta_s(start_tick,timer.tick());
|
||||
continue;
|
||||
}
|
||||
double startCompileTime = timer.delta_s(start_tick,timer.tick());
|
||||
(*itr)->compileGLObjects(renderInfo);
|
||||
elapsedTime = timer.delta_s(start_tick,timer.tick());
|
||||
|
||||
// estimate the duration of the compile based on current compile duration.
|
||||
estimatedDrawableDuration = (elapsedTime-startCompileTime);
|
||||
|
||||
++numObjectsCompiled;
|
||||
|
||||
}
|
||||
if (osg::getNotifyLevel() >= osg::DEBUG_INFO
|
||||
&& numObjectsCompiled > objTemp)
|
||||
{
|
||||
OSG_INFO<< _frameNumber << " compiled "
|
||||
<< numObjectsCompiled - objTemp
|
||||
<< " Drawables" << std::endl;
|
||||
}
|
||||
// remove the compiled drawables from the list.
|
||||
dwlist.erase(dwlist.begin(),itr);
|
||||
}
|
||||
|
||||
//OSG_INFO<<"Checking if compiled"<<std::endl;
|
||||
|
||||
// now check the to compile entries for all active graphics contexts
|
||||
// to make sure that all have been compiled. They won't be
|
||||
// if we ran out of time or if another thread is still
|
||||
// compiling for its graphics context.
|
||||
bool allCompiled = true;
|
||||
for(DataToCompileMap::iterator itr=dcm.begin();
|
||||
itr!=dcm.end() && allCompiled;
|
||||
++itr)
|
||||
{
|
||||
if (!(itr->second.empty())) allCompiled=false;
|
||||
}
|
||||
|
||||
if (numObjectsCompiled > 0)
|
||||
OSG_NOTICE<< "Framenumber "<<_frameNumber << ": compiled " << numObjectsCompiled << " objects" << std::endl;
|
||||
|
||||
if (allCompiled)
|
||||
{
|
||||
if (doFlush)
|
||||
{
|
||||
glFlush();
|
||||
}
|
||||
|
||||
// we've compiled all of the current databaseRequest so we can now pop it off the
|
||||
// to compile list and place it on the merge list.
|
||||
OSG_INFO<<"All compiled"<<std::endl;
|
||||
|
||||
_dataToMergeList->add(databaseRequest.get());
|
||||
|
||||
databaseRequest = 0;
|
||||
_dataToCompileList->takeFirst(databaseRequest);
|
||||
}
|
||||
else
|
||||
{
|
||||
OSG_INFO<<"Not all compiled"<<std::endl;
|
||||
_dataToCompileList->add(databaseRequest.get());
|
||||
databaseRequest = 0;
|
||||
}
|
||||
|
||||
elapsedTime = timer.delta_s(start_tick,timer.tick());
|
||||
}
|
||||
|
||||
availableTime -= elapsedTime;
|
||||
|
||||
//OSG_NOTICE<<"elapsedTime="<<elapsedTime<<"\ttime remaining ="<<availableTime<<"\tnumObjectsCompiled = "<<numObjectsCompiled<<std::endl;
|
||||
//OSG_NOTICE<<"estimatedTextureDuration="<<estimatedTextureDuration;
|
||||
//OSG_NOTICE<<"\testimatedDrawableDuration="<<estimatedDrawableDuration<<std::endl;
|
||||
}
|
||||
else
|
||||
{
|
||||
availableTime = 0.0f;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -18,6 +18,7 @@
|
||||
#include <osg/GLObjects>
|
||||
#include <osg/Depth>
|
||||
#include <osg/ColorMask>
|
||||
#include <osg/ApplicationUsage>
|
||||
|
||||
#include <OpenThreads/ScopedLock>
|
||||
|
||||
@ -29,6 +30,23 @@ namespace osgUtil
|
||||
{
|
||||
|
||||
|
||||
// TODO
|
||||
// priority of CompileSets
|
||||
// isCompiled
|
||||
// time estimation
|
||||
// early completion
|
||||
// needs compile given time slot
|
||||
// custom CompileData elements
|
||||
// pruneOldRequestsAndCheckIfEmpty()
|
||||
// Use? :
|
||||
// #if !defined(OSG_GLES1_AVAILABLE) && !defined(OSG_GLES2_AVAILABLE) && !defined(OSG_GL3_AVAILABLE)
|
||||
// GLint p;
|
||||
// glGetTexParameteriv(GL_TEXTURE_2D, GL_TEXTURE_RESIDENT, &p);
|
||||
// #endif
|
||||
|
||||
static osg::ApplicationUsageProxy ICO_e1(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_MINIMUM_COMPILE_TIME_PER_FRAME <float>","minimum compile time alloted to compiling OpenGL objects per frame in database pager.");
|
||||
static osg::ApplicationUsageProxy UCO_e2(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_MAXIMUM_OBJECTS_TO_COMPILE_PER_FRAME <int>","maximum number of OpenGL objects to compile per frame in database pager.");
|
||||
|
||||
/////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// CompileStats
|
||||
@ -248,6 +266,11 @@ void CompileOperator::runTimingTests(osg::RenderInfo& renderInfo)
|
||||
|
||||
bool CompileOperator::compile(osg::RenderInfo& renderInfo, CompileData& cd, unsigned int& maxNumObjectsToCompile, double& compileTime)
|
||||
{
|
||||
osg::NotifySeverity level = osg::INFO;
|
||||
//osg::NotifySeverity level = osg::NOTICE;
|
||||
|
||||
OSG_NOTIFY(level)<<"compile(..,maxNumObjectsToCompile="<<maxNumObjectsToCompile<<", compileTime="<<compileTime<<")"<<std::endl;
|
||||
|
||||
osg::Timer_t startTick = osg::Timer::instance()->tick();
|
||||
|
||||
if (!_timingTestsCompleted)
|
||||
@ -255,7 +278,6 @@ bool CompileOperator::compile(osg::RenderInfo& renderInfo, CompileData& cd, unsi
|
||||
runTimingTests(renderInfo);
|
||||
}
|
||||
|
||||
osg::NotifySeverity level = osg::INFO;
|
||||
|
||||
unsigned int totalDataSizeCompiled = 0;
|
||||
unsigned int drawablesCompiled = 0;
|
||||
@ -436,7 +458,7 @@ bool CompileOperator::compile(osg::RenderInfo& renderInfo, CompileData& cd, unsi
|
||||
|
||||
double timeUsed = osg::Timer::instance()->delta_s(startTick, osg::Timer::instance()->tick());
|
||||
|
||||
OSG_NOTIFY(level)<<"compile time, texturesCompiled="<<texturesCompiled<<", drawablesCompiled="<<drawablesCompiled<<", programsCompiled="<<programsCompiled<<", timeUsed="<<timeUsed*1000.0<<" totalDataSizeCompiled="<<totalDataSizeCompiled<<" bytes, download rate="<<double(totalDataSizeCompiled)/(1024.0*1024*timeUsed)<<"Mb/sec"<<std::endl;
|
||||
OSG_NOTIFY(level)<<" texturesCompiled="<<texturesCompiled<<", drawablesCompiled="<<drawablesCompiled<<", programsCompiled="<<programsCompiled<<", timeUsed="<<timeUsed*1000.0<<" totalDataSizeCompiled="<<totalDataSizeCompiled<<" bytes, download rate="<<double(totalDataSizeCompiled)/(1024.0*1024*timeUsed)<<"Mb/sec"<<std::endl;
|
||||
|
||||
compileTime -= timeUsed;
|
||||
|
||||
@ -467,6 +489,8 @@ IncrementalCompileOperation::IncrementalCompileOperation():
|
||||
}
|
||||
|
||||
_compileOperator = new CompileOperator;
|
||||
|
||||
// assignForceTextureDownloadGeometry();
|
||||
}
|
||||
|
||||
IncrementalCompileOperation::~IncrementalCompileOperation()
|
||||
@ -551,6 +575,44 @@ void IncrementalCompileOperation::add(CompileSet* compileSet, bool callBuildComp
|
||||
_toCompile.push_back(compileSet);
|
||||
}
|
||||
|
||||
void IncrementalCompileOperation::remove(CompileSet* compileSet)
|
||||
{
|
||||
// OSG_NOTICE<<"IncrementalCompileOperation::remove(CompileSet* compileSet)"<<std::endl;
|
||||
|
||||
if (!compileSet) return;
|
||||
|
||||
// remove CompileSet from _toCompile list if it's present.
|
||||
{
|
||||
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_toCompileMutex);
|
||||
for(CompileSets::iterator itr = _toCompile.begin();
|
||||
itr != _toCompile.end();
|
||||
++itr)
|
||||
{
|
||||
if (*itr == compileSet)
|
||||
{
|
||||
_toCompile.erase(itr);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// remove CompileSet from _compiled list if it's present.
|
||||
{
|
||||
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_compiledMutex);
|
||||
for(CompileSets::iterator itr = _compiled.begin();
|
||||
itr != _compiled.end();
|
||||
++itr)
|
||||
{
|
||||
if (*itr == compileSet)
|
||||
{
|
||||
_toCompile.erase(itr);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void IncrementalCompileOperation::mergeCompiledSubgraphs()
|
||||
{
|
||||
// OSG_INFO<<"IncrementalCompileOperation::mergeCompiledSubgraphs()"<<std::endl;
|
||||
@ -562,9 +624,10 @@ void IncrementalCompileOperation::mergeCompiledSubgraphs()
|
||||
++itr)
|
||||
{
|
||||
CompileSet* cs = itr->get();
|
||||
if (cs->_attachmentPoint.valid())
|
||||
osg::ref_ptr<osg::Group> group;
|
||||
if (cs->_attachmentPoint.lock(group))
|
||||
{
|
||||
cs->_attachmentPoint->addChild(cs->_subgraphToCompile.get());
|
||||
group->addChild(cs->_subgraphToCompile.get());
|
||||
}
|
||||
}
|
||||
|
||||
@ -756,6 +819,8 @@ void IncrementalCompileOperation::operator () (osg::GraphicsContext* context)
|
||||
#endif
|
||||
|
||||
|
||||
//level = osg::NOTICE;
|
||||
|
||||
osg::RenderInfo renderInfo;
|
||||
renderInfo.setState(context->getState());
|
||||
|
||||
@ -766,7 +831,7 @@ void IncrementalCompileOperation::operator () (osg::GraphicsContext* context)
|
||||
}
|
||||
|
||||
for(CompileSets::iterator itr = toCompileCopy.begin();
|
||||
itr != toCompileCopy.end() && compileTime>0.0;
|
||||
itr != toCompileCopy.end() && compileTime>0.0 && maxNumOfObjectsToCompilePerFrame>0;
|
||||
++itr)
|
||||
{
|
||||
CompileSet* cs = itr->get();
|
||||
@ -810,6 +875,8 @@ void IncrementalCompileOperation::operator () (osg::GraphicsContext* context)
|
||||
}
|
||||
}
|
||||
}
|
||||
//glFush();
|
||||
//glFinish();
|
||||
}
|
||||
|
||||
} // end of namespace osgUtil
|
||||
|
@ -148,7 +148,8 @@ SceneView::SceneView(DisplaySettings* ds)
|
||||
|
||||
_camera->setDrawBuffer(GL_BACK);
|
||||
|
||||
_requiresFlush = true;
|
||||
_automaticFlush = true;
|
||||
_requiresFlush = false;
|
||||
|
||||
_activeUniforms = DEFAULT_UNIFORMS;
|
||||
|
||||
@ -180,7 +181,8 @@ SceneView::SceneView(const SceneView& rhs, const osg::CopyOp& copyop):
|
||||
|
||||
_initCalled = false;
|
||||
|
||||
_requiresFlush = rhs._requiresFlush;
|
||||
_automaticFlush = rhs._automaticFlush;
|
||||
_requiresFlush = false;
|
||||
|
||||
_activeUniforms = rhs._activeUniforms;
|
||||
|
||||
@ -1025,6 +1027,8 @@ void SceneView::flushAllDeletedGLObjects()
|
||||
|
||||
void SceneView::flushDeletedGLObjects(double& availableTime)
|
||||
{
|
||||
// OSG_NOTICE<<"SceneView::flushDeletedGLObjects(availableTime="<<availableTime<<")"<<std::endl;
|
||||
|
||||
osg::State* state = _renderInfo.getState();
|
||||
|
||||
_requiresFlush = false;
|
||||
@ -1061,7 +1065,7 @@ void SceneView::draw()
|
||||
}
|
||||
|
||||
// assume the the draw which is about to happen could generate GL objects that need flushing in the next frame.
|
||||
_requiresFlush = true;
|
||||
_requiresFlush = _automaticFlush;
|
||||
|
||||
RenderLeaf* previous = NULL;
|
||||
if (_displaySettings.valid() && _displaySettings->getStereo())
|
||||
|
@ -327,10 +327,6 @@ static OpenThreads::Mutex s_drawSerializerMutex;
|
||||
// Renderer
|
||||
Renderer::Renderer(osg::Camera* camera):
|
||||
osg::GraphicsOperation("Renderer",true),
|
||||
_targetFrameRate(100.0),
|
||||
_minimumTimeAvailableForGLCompileAndDeletePerFrame(0.001),
|
||||
_flushTimeRatio(0.5),
|
||||
_conservativeTimeRatio(0.5),
|
||||
_camera(camera),
|
||||
_done(false),
|
||||
_graphicsThreadDoesCull(true),
|
||||
@ -359,6 +355,9 @@ Renderer::Renderer(osg::Camera* camera):
|
||||
}
|
||||
|
||||
osgViewer::View* view = dynamic_cast<osgViewer::View*>(_camera->getView());
|
||||
osgViewer::ViewerBase* viewer = view ? view->getViewerBase() : 0;
|
||||
osgUtil::IncrementalCompileOperation* ico = viewer ? viewer->getIncrementalCompileOperation() : 0;
|
||||
bool automaticFlush = (ico==NULL);
|
||||
|
||||
osg::DisplaySettings* ds = _camera->getDisplaySettings() ? _camera->getDisplaySettings() :
|
||||
((view && view->getDisplaySettings()) ? view->getDisplaySettings() : osg::DisplaySettings::instance().get());
|
||||
@ -374,9 +373,11 @@ Renderer::Renderer(osg::Camera* camera):
|
||||
}
|
||||
}
|
||||
|
||||
_sceneView[0]->setAutomaticFlush(automaticFlush);
|
||||
_sceneView[0]->setGlobalStateSet(global_stateset);
|
||||
_sceneView[0]->setSecondaryStateSet(secondary_stateset);
|
||||
|
||||
_sceneView[1]->setAutomaticFlush(automaticFlush);
|
||||
_sceneView[1]->setGlobalStateSet(global_stateset);
|
||||
_sceneView[1]->setSecondaryStateSet(secondary_stateset);
|
||||
|
||||
@ -395,8 +396,6 @@ Renderer::Renderer(osg::Camera* camera):
|
||||
_availableQueue.add(_sceneView[1].get());
|
||||
|
||||
DEBUG_MESSAGE<<"_availableQueue.size()="<<_availableQueue._queue.size()<<std::endl;
|
||||
|
||||
_flushOperation = new osg::FlushDeletedGLObjectsOperation(0.1);
|
||||
}
|
||||
|
||||
Renderer::~Renderer()
|
||||
@ -460,6 +459,11 @@ void Renderer::updateSceneView(osgUtil::SceneView* sceneView)
|
||||
}
|
||||
|
||||
osgViewer::View* view = dynamic_cast<osgViewer::View*>(_camera->getView());
|
||||
osgViewer::ViewerBase* viewer = view ? view->getViewerBase() : 0;
|
||||
osgUtil::IncrementalCompileOperation* ico = viewer ? viewer->getIncrementalCompileOperation() : 0;
|
||||
bool automaticFlush = (ico==NULL);
|
||||
|
||||
sceneView->setAutomaticFlush(automaticFlush);
|
||||
|
||||
osgDB::DatabasePager* databasePager = view ? view->getDatabasePager() : 0;
|
||||
sceneView->getCullVisitor()->setDatabaseRequestHandler(databasePager);
|
||||
@ -469,8 +473,6 @@ void Renderer::updateSceneView(osgUtil::SceneView* sceneView)
|
||||
|
||||
sceneView->setFrameStamp(view ? view->getFrameStamp() : state->getFrameStamp());
|
||||
|
||||
if (databasePager) databasePager->setCompileGLObjectsForContextID(state->getContextID(), true);
|
||||
|
||||
osg::DisplaySettings* ds = _camera->getDisplaySettings() ? _camera->getDisplaySettings() :
|
||||
((view &&view->getDisplaySettings()) ? view->getDisplaySettings() : osg::DisplaySettings::instance().get());
|
||||
|
||||
@ -611,9 +613,6 @@ void Renderer::draw()
|
||||
|
||||
DEBUG_MESSAGE<<"draw() got SceneView "<<sceneView<<std::endl;
|
||||
|
||||
osg::GraphicsContext* compileContext = sceneView ? osg::GraphicsContext::getCompileContext(sceneView->getState()->getContextID()) : 0;
|
||||
osg::GraphicsThread* compileThread = compileContext ? compileContext->getGraphicsThread() : 0;
|
||||
|
||||
if (sceneView && !_done)
|
||||
{
|
||||
// since we are running the draw thread in parallel with the main thread it's possible to unreference Camera's
|
||||
@ -626,9 +625,6 @@ void Renderer::draw()
|
||||
compile();
|
||||
}
|
||||
|
||||
osgViewer::View* view = dynamic_cast<osgViewer::View*>(_camera->getView());
|
||||
osgDB::DatabasePager* databasePager = view ? view->getDatabasePager() : 0;
|
||||
|
||||
// OSG_NOTICE<<"Drawing buffer "<<_currentDraw<<std::endl;
|
||||
|
||||
if (_done)
|
||||
@ -695,13 +691,6 @@ void Renderer::draw()
|
||||
|
||||
_availableQueue.add(sceneView);
|
||||
|
||||
osg::Timer_t afterDispatchTick = osg::Timer::instance()->tick();
|
||||
|
||||
double dispatchTime = osg::Timer::instance()->delta_s(beforeDrawTick, afterDispatchTick);
|
||||
|
||||
// now flush delete OpenGL objects and compile any objects as required by the DatabasePager
|
||||
flushAndCompile(dispatchTime, sceneView, databasePager, compileThread);
|
||||
|
||||
if (acquireGPUStats)
|
||||
{
|
||||
_querySupport->endQuery(state);
|
||||
@ -749,11 +738,6 @@ void Renderer::cull_draw()
|
||||
}
|
||||
|
||||
osgViewer::View* view = dynamic_cast<osgViewer::View*>(_camera->getView());
|
||||
osgDB::DatabasePager* databasePager = view ? view->getDatabasePager() : 0;
|
||||
|
||||
osg::GraphicsContext* compileContext = osg::GraphicsContext::getCompileContext(sceneView->getState()->getContextID());
|
||||
osg::GraphicsThread* compileThread = compileContext ? compileContext->getGraphicsThread() : 0;
|
||||
|
||||
|
||||
// OSG_NOTICE<<"RenderingOperation"<<std::endl;
|
||||
|
||||
@ -832,13 +816,6 @@ void Renderer::cull_draw()
|
||||
sceneView->draw();
|
||||
}
|
||||
|
||||
osg::Timer_t afterDispatchTick = osg::Timer::instance()->tick();
|
||||
double cullAndDispatchTime = osg::Timer::instance()->delta_s(beforeCullTick, afterDispatchTick);
|
||||
|
||||
// now flush delete OpenGL objects and compile any objects as required by the DatabasePager
|
||||
flushAndCompile(cullAndDispatchTime, sceneView, databasePager, compileThread);
|
||||
|
||||
|
||||
if (acquireGPUStats)
|
||||
{
|
||||
_querySupport->endQuery(state);
|
||||
@ -864,54 +841,6 @@ void Renderer::cull_draw()
|
||||
|
||||
}
|
||||
|
||||
void Renderer::flushAndCompile(double currentElapsedFrameTime, osgUtil::SceneView* sceneView, osgDB::DatabasePager* databasePager, osg::GraphicsThread* compileThread)
|
||||
{
|
||||
|
||||
double targetFrameRate = _targetFrameRate;
|
||||
double minimumTimeAvailableForGLCompileAndDeletePerFrame = _minimumTimeAvailableForGLCompileAndDeletePerFrame;
|
||||
|
||||
if (databasePager)
|
||||
{
|
||||
targetFrameRate = std::min(targetFrameRate, databasePager->getTargetFrameRate());
|
||||
minimumTimeAvailableForGLCompileAndDeletePerFrame = std::min(minimumTimeAvailableForGLCompileAndDeletePerFrame, databasePager->getMinimumTimeAvailableForGLCompileAndDeletePerFrame());
|
||||
}
|
||||
|
||||
double targetFrameTime = 1.0/targetFrameRate;
|
||||
|
||||
double availableTime = std::max((targetFrameTime - currentElapsedFrameTime)*_conservativeTimeRatio,
|
||||
minimumTimeAvailableForGLCompileAndDeletePerFrame);
|
||||
|
||||
double flushTime = availableTime * _flushTimeRatio;
|
||||
double compileTime = availableTime - flushTime;
|
||||
|
||||
#if 0
|
||||
OSG_NOTICE<<"total availableTime = "<<availableTime*1000.0<<std::endl;
|
||||
OSG_NOTICE<<" flushTime = "<<flushTime*1000.0<<std::endl;
|
||||
OSG_NOTICE<<" compileTime = "<<compileTime*1000.0<<std::endl;
|
||||
#endif
|
||||
|
||||
if (compileThread)
|
||||
{
|
||||
compileThread->add(_flushOperation.get());
|
||||
}
|
||||
else
|
||||
{
|
||||
sceneView->flushDeletedGLObjects(flushTime);
|
||||
}
|
||||
|
||||
// if any time left over from flush add this to compile time.
|
||||
if (flushTime>0.0) compileTime += flushTime;
|
||||
|
||||
#if 0
|
||||
OSG_NOTICE<<" revised compileTime = "<<compileTime*1000.0<<std::endl;
|
||||
#endif
|
||||
|
||||
if (databasePager && databasePager->requiresExternalCompileGLObjects(sceneView->getState()->getContextID()))
|
||||
{
|
||||
databasePager->compileGLObjects(*(sceneView->getState()), compileTime);
|
||||
}
|
||||
}
|
||||
|
||||
void Renderer::operator () (osg::Object* object)
|
||||
{
|
||||
osg::GraphicsContext* context = dynamic_cast<osg::GraphicsContext*>(object);
|
||||
|
Loading…
Reference in New Issue
Block a user