Added support for an update OperationQueue to Viewer and CompositeViewer to allow asyncrnous adding of operations to be added

to the view to be done during syncronous updateTraversal().

This feature can be used for doing things like merging subgraphs that have been loaded
in a background thread.
This commit is contained in:
Robert Osfield
2007-08-11 10:28:14 +00:00
parent 0e475106dc
commit e5a365afee
9 changed files with 348 additions and 3 deletions

View File

@@ -181,6 +181,40 @@ void OperationQueue::removeAllOperations()
}
}
void OperationQueue::runOperations(Object* callingObject)
{
OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_operationsMutex);
// reset current operation iterator to begining if at end.
if (_currentOperationIterator==_operations.end()) _currentOperationIterator = _operations.begin();
for(;
_currentOperationIterator != _operations.end();
)
{
ref_ptr<Operation> operation = *_currentOperationIterator;
if (!operation->getKeep())
{
_currentOperationIterator = _operations.erase(_currentOperationIterator);
}
else
{
++_currentOperationIterator;
}
// osg::notify(osg::INFO)<<"Doing op "<<_currentOperation->getName()<<" "<<this<<std::endl;
// call the graphics operation.
(*operation)(callingObject);
}
if (_operations.empty())
{
_operationsBlock->set(false);
}
}
void OperationQueue::releaseOperationsBlock()
{
_operationsBlock->release();

View File

@@ -27,6 +27,12 @@ CompositeViewer::CompositeViewer()
constructorInit();
}
CompositeViewer::CompositeViewer(const CompositeViewer& cv,const osg::CopyOp& copyop):
osg::Object(cv,copyop)
{
constructorInit();
}
CompositeViewer::CompositeViewer(osg::ArgumentParser& arguments)
{
constructorInit();
@@ -978,6 +984,26 @@ void CompositeViewer::eventTraversal()
}
}
void CompositeViewer::addUpdateOperation(osg::Operation* operation)
{
if (!operation) return;
if (!_updateOperations) _updateOperations = new osg::OperationQueue;
_updateOperations->add(operation);
}
void CompositeViewer::removeUpdateOperation(osg::Operation* operation)
{
if (!operation) return;
if (_updateOperations.valid())
{
_updateOperations->remove(operation);
}
}
void CompositeViewer::updateTraversal()
{
if (_done) return;
@@ -1001,7 +1027,12 @@ void CompositeViewer::updateTraversal()
}
}
if (_updateOperations.valid())
{
_updateOperations->runOperations(this);
}
for(Views::iterator vitr = _views.begin();
vitr != _views.end();
++vitr)

View File

@@ -1326,6 +1326,25 @@ void Viewer::eventTraversal()
}
void Viewer::addUpdateOperation(osg::Operation* operation)
{
if (!operation) return;
if (!_updateOperations) _updateOperations = new osg::OperationQueue;
_updateOperations->add(operation);
}
void Viewer::removeUpdateOperation(osg::Operation* operation)
{
if (!operation) return;
if (_updateOperations.valid())
{
_updateOperations->remove(operation);
}
}
void Viewer::updateTraversal()
{
if (_done) return;
@@ -1343,6 +1362,11 @@ void Viewer::updateTraversal()
_scene->getDatabasePager()->updateSceneGraph(_frameStamp->getReferenceTime());
}
if (_updateOperations.valid())
{
_updateOperations->runOperations(this);
}
{
// call any camera update callbacks, but only traverse that callback, don't traverse its subgraph
// leave that to the scene update traversal.

View File

@@ -99,6 +99,11 @@ BEGIN_OBJECT_REFLECTOR(osg::OperationQueue)
__void__removeAllOperations,
"Remove all operations from OperationQueue. ",
"");
I_MethodWithDefaults1(void, runOperations, IN, osg::Object *, callingObject, 0,
Properties::NON_VIRTUAL,
__void__runOperations__Object_P1,
"Run the operations. ",
"");
I_Method0(void, releaseAllOperations,
Properties::NON_VIRTUAL,
__void__releaseAllOperations,

View File

@@ -12,10 +12,14 @@
#include <osg/ArgumentParser>
#include <osg/Camera>
#include <osg/CopyOp>
#include <osg/FrameStamp>
#include <osg/Object>
#include <osg/OperationThread>
#include <osg/Timer>
#include <osgGA/EventQueue>
#include <osgGA/EventVisitor>
#include <osgUtil/UpdateVisitor>
#include <osgViewer/CompositeViewer>
#include <osgViewer/View>
@@ -48,15 +52,44 @@ END_REFLECTOR
BEGIN_OBJECT_REFLECTOR(osgViewer::CompositeViewer)
I_DeclaringFile("osgViewer/CompositeViewer");
I_BaseType(osg::Referenced);
I_BaseType(osg::Object);
I_Constructor0(____CompositeViewer,
"",
"");
I_ConstructorWithDefaults2(IN, const osgViewer::CompositeViewer &, x, , IN, const osg::CopyOp &, copyop, osg::CopyOp::SHALLOW_COPY,
____CompositeViewer__C5_CompositeViewer_R1__C5_osg_CopyOp_R1,
"",
"");
I_Constructor1(IN, osg::ArgumentParser &, arguments,
Properties::NON_EXPLICIT,
____CompositeViewer__osg_ArgumentParser_R1,
"",
"");
I_Method0(osg::Object *, cloneType,
Properties::VIRTUAL,
__osg_Object_P1__cloneType,
"Clone the type of an object, with Object* return type. ",
"Must be defined by derived classes. ");
I_Method1(osg::Object *, clone, IN, const osg::CopyOp &, copyop,
Properties::VIRTUAL,
__osg_Object_P1__clone__C5_osg_CopyOp_R1,
"Clone an object, with Object* return type. ",
"Must be defined by derived classes. ");
I_Method1(bool, isSameKindAs, IN, const osg::Object *, obj,
Properties::VIRTUAL,
__bool__isSameKindAs__C5_osg_Object_P1,
"",
"");
I_Method0(const char *, libraryName,
Properties::VIRTUAL,
__C5_char_P1__libraryName,
"return the name of the object's library. ",
"Must be defined by derived classes. The OpenSceneGraph convention is that the namespace of a library is the same as the library name. ");
I_Method0(const char *, className,
Properties::VIRTUAL,
__C5_char_P1__className,
"return the name of the object's class type. ",
"Must be defined by derived classes. ");
I_Method1(void, addView, IN, osgViewer::View *, view,
Properties::NON_VIRTUAL,
__void__addView__osgViewer_View_P1,
@@ -147,6 +180,21 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::CompositeViewer)
__BarrierPosition__getEndBarrierPosition,
"Get the end barrier position. ",
"");
I_Method1(void, setEventVisitor, IN, osgGA::EventVisitor *, eventVisitor,
Properties::NON_VIRTUAL,
__void__setEventVisitor__osgGA_EventVisitor_P1,
"Set the EventVisitor. ",
"");
I_Method0(osgGA::EventVisitor *, getEventVisitor,
Properties::NON_VIRTUAL,
__osgGA_EventVisitor_P1__getEventVisitor,
"Get the EventVisitor. ",
"");
I_Method0(const osgGA::EventVisitor *, getEventVisitor,
Properties::NON_VIRTUAL,
__C5_osgGA_EventVisitor_P1__getEventVisitor,
"Get the const EventVisitor. ",
"");
I_Method1(void, setEventQueue, IN, osgGA::EventQueue *, eventQueue,
Properties::NON_VIRTUAL,
__void__setEventQueue__osgGA_EventQueue_P1,
@@ -182,6 +230,46 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::CompositeViewer)
__bool__getQuitEventSetsDone,
"",
"true if the viewer respond to the QUIT_APPLICATION-event ");
I_Method1(void, setUpdateVisitor, IN, osgUtil::UpdateVisitor *, updateVisitor,
Properties::NON_VIRTUAL,
__void__setUpdateVisitor__osgUtil_UpdateVisitor_P1,
"Set the UpdateVisitor. ",
"");
I_Method0(osgUtil::UpdateVisitor *, getUpdateVisitor,
Properties::NON_VIRTUAL,
__osgUtil_UpdateVisitor_P1__getUpdateVisitor,
"Get the UpdateVisitor. ",
"");
I_Method0(const osgUtil::UpdateVisitor *, getUpdateVisitor,
Properties::NON_VIRTUAL,
__C5_osgUtil_UpdateVisitor_P1__getUpdateVisitor,
"Get the const UpdateVisitor. ",
"");
I_Method1(void, setUpdateOperations, IN, osg::OperationQueue *, operations,
Properties::NON_VIRTUAL,
__void__setUpdateOperations__osg_OperationQueue_P1,
"Set the Update OperationQueue. ",
"");
I_Method0(osg::OperationQueue *, getUpdateOperations,
Properties::NON_VIRTUAL,
__osg_OperationQueue_P1__getUpdateOperations,
"Get the Update OperationQueue. ",
"");
I_Method0(const osg::OperationQueue *, getUpdateOperations,
Properties::NON_VIRTUAL,
__C5_osg_OperationQueue_P1__getUpdateOperations,
"Get the const Update OperationQueue. ",
"");
I_Method1(void, addUpdateOperation, IN, osg::Operation *, operation,
Properties::NON_VIRTUAL,
__void__addUpdateOperation__osg_Operation_P1,
"Add an update operation. ",
"");
I_Method1(void, removeUpdateOperation, IN, osg::Operation *, operation,
Properties::NON_VIRTUAL,
__void__removeUpdateOperation__osg_Operation_P1,
"Remove an update operation. ",
"");
I_Method0(int, run,
Properties::VIRTUAL,
__int__run,
@@ -313,6 +401,9 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::CompositeViewer)
I_SimpleProperty(osgGA::EventQueue *, EventQueue,
__osgGA_EventQueue_P1__getEventQueue,
__void__setEventQueue__osgGA_EventQueue_P1);
I_SimpleProperty(osgGA::EventVisitor *, EventVisitor,
__osgGA_EventVisitor_P1__getEventVisitor,
__void__setEventVisitor__osgGA_EventVisitor_P1);
I_SimpleProperty(osg::FrameStamp *, FrameStamp,
__osg_FrameStamp_P1__getFrameStamp,
0);
@@ -334,6 +425,12 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::CompositeViewer)
I_SimpleProperty(osgViewer::CompositeViewer::ThreadingModel, ThreadingModel,
__ThreadingModel__getThreadingModel,
__void__setThreadingModel__ThreadingModel);
I_SimpleProperty(osg::OperationQueue *, UpdateOperations,
__osg_OperationQueue_P1__getUpdateOperations,
__void__setUpdateOperations__osg_OperationQueue_P1);
I_SimpleProperty(osgUtil::UpdateVisitor *, UpdateVisitor,
__osgUtil_UpdateVisitor_P1__getUpdateVisitor,
__void__setUpdateVisitor__osgUtil_UpdateVisitor_P1);
I_ArrayProperty(osgViewer::View *, View,
__osgViewer_View_P1__getView__unsigned,
0,

View File

@@ -16,6 +16,8 @@
#include <osg/Node>
#include <osg/OperationThread>
#include <osg/Timer>
#include <osgGA/EventVisitor>
#include <osgUtil/UpdateVisitor>
#include <osgViewer/GraphicsWindow>
#include <osgViewer/Viewer>
@@ -138,6 +140,21 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::Viewer)
__BarrierPosition__getEndBarrierPosition,
"Get the end barrier position. ",
"");
I_Method1(void, setEventVisitor, IN, osgGA::EventVisitor *, eventVisitor,
Properties::NON_VIRTUAL,
__void__setEventVisitor__osgGA_EventVisitor_P1,
"Set the EventVisitor. ",
"");
I_Method0(osgGA::EventVisitor *, getEventVisitor,
Properties::NON_VIRTUAL,
__osgGA_EventVisitor_P1__getEventVisitor,
"Get the EventVisitor. ",
"");
I_Method0(const osgGA::EventVisitor *, getEventVisitor,
Properties::NON_VIRTUAL,
__C5_osgGA_EventVisitor_P1__getEventVisitor,
"Get the const EventVisitor. ",
"");
I_Method1(void, setKeyEventSetsDone, IN, int, key,
Properties::NON_VIRTUAL,
__void__setKeyEventSetsDone__int,
@@ -158,6 +175,46 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::Viewer)
__bool__getQuitEventSetsDone,
"",
"true if the viewer respond to the QUIT_APPLICATION-event ");
I_Method1(void, setUpdateVisitor, IN, osgUtil::UpdateVisitor *, updateVisitor,
Properties::NON_VIRTUAL,
__void__setUpdateVisitor__osgUtil_UpdateVisitor_P1,
"Set the UpdateVisitor. ",
"");
I_Method0(osgUtil::UpdateVisitor *, getUpdateVisitor,
Properties::NON_VIRTUAL,
__osgUtil_UpdateVisitor_P1__getUpdateVisitor,
"Get the UpdateVisitor. ",
"");
I_Method0(const osgUtil::UpdateVisitor *, getUpdateVisitor,
Properties::NON_VIRTUAL,
__C5_osgUtil_UpdateVisitor_P1__getUpdateVisitor,
"Get the const UpdateVisitor. ",
"");
I_Method1(void, setUpdateOperations, IN, osg::OperationQueue *, operations,
Properties::NON_VIRTUAL,
__void__setUpdateOperations__osg_OperationQueue_P1,
"Set the Update OperationQueue. ",
"");
I_Method0(osg::OperationQueue *, getUpdateOperations,
Properties::NON_VIRTUAL,
__osg_OperationQueue_P1__getUpdateOperations,
"Get the Update OperationQueue. ",
"");
I_Method0(const osg::OperationQueue *, getUpdateOperations,
Properties::NON_VIRTUAL,
__C5_osg_OperationQueue_P1__getUpdateOperations,
"Get the const Update OperationQueue. ",
"");
I_Method1(void, addUpdateOperation, IN, osg::Operation *, operation,
Properties::NON_VIRTUAL,
__void__addUpdateOperation__osg_Operation_P1,
"Add an update operation. ",
"");
I_Method1(void, removeUpdateOperation, IN, osg::Operation *, operation,
Properties::NON_VIRTUAL,
__void__removeUpdateOperation__osg_Operation_P1,
"Remove an update operation. ",
"");
I_Method0(int, run,
Properties::VIRTUAL,
__int__run,
@@ -296,6 +353,9 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::Viewer)
I_SimpleProperty(osgViewer::Viewer::BarrierPosition, EndBarrierPosition,
__BarrierPosition__getEndBarrierPosition,
__void__setEndBarrierPosition__BarrierPosition);
I_SimpleProperty(osgGA::EventVisitor *, EventVisitor,
__osgGA_EventVisitor_P1__getEventVisitor,
__void__setEventVisitor__osgGA_EventVisitor_P1);
I_SimpleProperty(int, KeyEventSetsDone,
__int__getKeyEventSetsDone,
__void__setKeyEventSetsDone__int);
@@ -317,6 +377,12 @@ BEGIN_OBJECT_REFLECTOR(osgViewer::Viewer)
I_SimpleProperty(osgViewer::Viewer::ThreadingModel, ThreadingModel,
__ThreadingModel__getThreadingModel,
__void__setThreadingModel__ThreadingModel);
I_SimpleProperty(osg::OperationQueue *, UpdateOperations,
__osg_OperationQueue_P1__getUpdateOperations,
__void__setUpdateOperations__osg_OperationQueue_P1);
I_SimpleProperty(osgUtil::UpdateVisitor *, UpdateVisitor,
__osgUtil_UpdateVisitor_P1__getUpdateVisitor,
__void__setUpdateVisitor__osgUtil_UpdateVisitor_P1);
I_SimpleProperty(bool, UseMainThreadForRenderingTraversals,
__bool__getUseMainThreadForRenderingTraversals,
__void__setUseMainThreadForRenderingTraversals__bool);