diff --git a/include/osg/AnimationPath b/include/osg/AnimationPath index ff996c1be..f9b5127e4 100644 --- a/include/osg/AnimationPath +++ b/include/osg/AnimationPath @@ -7,6 +7,7 @@ #include #include +#include #include @@ -131,6 +132,61 @@ class SG_EXPORT AnimationPath : public virtual osg::Object }; + +class SG_EXPORT AnimationPathCallback : public NodeCallback, public NodeVisitor +{ + public: + + AnimationPathCallback(): + _timeOffset(0.0), + _timeMultiplier(1.0), + _firstTime(0.0), + _animationTime(0.0) {} + + + AnimationPathCallback(const AnimationPathCallback& apc,const CopyOp& copyop): + NodeCallback(apc,copyop), + _animationPath(apc._animationPath), + _timeOffset(apc._timeOffset), + _timeMultiplier(apc._timeMultiplier), + _firstTime(apc._firstTime), + _animationTime(apc._animationTime) {} + + + META_Object(osg,AnimationPathCallback) + + AnimationPathCallback(AnimationPath* ap,double timeOffset=0.0f,double timeMultiplier=1.0f): + _animationPath(ap), + _timeOffset(timeOffset), + _timeMultiplier(timeMultiplier), + _firstTime(0.0), + _animationTime(0.0) {} + + + + void setAnimationPath(AnimationPath* path) { _animationPath = path; } + + AnimationPath* getAnimationPath() { return _animationPath.get(); } + + const AnimationPath* getAnimationPath() const { return _animationPath.get(); } + + + /** implements the callback*/ + virtual void operator()(Node* node, NodeVisitor* nv); + + virtual void apply(MatrixTransform& mt); + + virtual void apply(PositionAttitudeTransform& pat); + + public: + + ref_ptr _animationPath; + double _timeOffset; + double _timeMultiplier; + double _firstTime; + mutable double _animationTime; +}; + } #endif diff --git a/include/osg/MatrixTransform b/include/osg/MatrixTransform index 4797aba3d..417bd47e1 100644 --- a/include/osg/MatrixTransform +++ b/include/osg/MatrixTransform @@ -28,8 +28,6 @@ class SG_EXPORT MatrixTransform : public Transform META_Node(osg, MatrixTransform); - virtual void traverse(NodeVisitor& nv); - /** Set the transform's matrix.*/ void setMatrix(const Matrix& mat) { (*_matrix) = mat; _inverseDirty=true; dirtyBound(); } @@ -53,68 +51,10 @@ class SG_EXPORT MatrixTransform : public Transform return *_inverse; } - virtual bool computeLocalToWorldMatrix(Matrix& matrix,NodeVisitor*) const - { - if (_referenceFrame==RELATIVE_TO_PARENTS) - { - matrix.preMult(*_matrix); - } - else // absolute - { - matrix = *_matrix; - } - return true; - } + virtual bool computeLocalToWorldMatrix(Matrix& matrix,NodeVisitor*) const; - virtual bool computeWorldToLocalMatrix(Matrix& matrix,NodeVisitor*) const - { - const Matrix& inverse = getInverseMatrix(); + virtual bool computeWorldToLocalMatrix(Matrix& matrix,NodeVisitor*) const; - if (_referenceFrame==RELATIVE_TO_PARENTS) - { - matrix.postMult(inverse); - } - else // absolute - { - matrix = inverse; - } - return true; - } - - - - /** Set an optional animation path. */ - void setAnimationPath(AnimationPath* ap) { _animationPath = ap; } - - /** Get a read only version of the AnimationPath object*/ - AnimationPath* getAnimationPath() { return _animationPath.get(); } - - /** Get a read only version of the AnimationPath object*/ - const AnimationPath* getAnimationPath() const { return _animationPath.get(); } - - - - /** Callback which can be attached to a MatrixTransform as an app - * callback to allow it to follow the path defined by a AnimationPath. - * note, now deprecated by attaching an AnimationPath directly to MatrixTransform.*/ - class SG_EXPORT AnimationPathCallback : public NodeCallback - { - public: - - AnimationPathCallback(AnimationPath* ap,double timeOffset=0.0f,double timeMultiplier=1.0f): - _animationPath(ap), - _timeOffset(timeOffset), - _timeMultiplier(timeMultiplier), - _firstTime(0.0) {} - - /** implements the callback*/ - virtual void operator()(Node* node, NodeVisitor* nv); - - ref_ptr _animationPath; - double _timeOffset; - double _timeMultiplier; - double _firstTime; - }; protected : @@ -123,8 +63,6 @@ class SG_EXPORT MatrixTransform : public Transform ref_ptr _matrix; mutable ref_ptr _inverse; mutable bool _inverseDirty; - - osg::ref_ptr _animationPath; }; diff --git a/include/osg/NodeCallback b/include/osg/NodeCallback index e278ec507..4f33ef82b 100644 --- a/include/osg/NodeCallback +++ b/include/osg/NodeCallback @@ -5,7 +5,7 @@ #ifndef OSG_NODECALLBACK #define OSG_NODECALLBACK 1 -#include +#include #include namespace osg { @@ -13,13 +13,18 @@ namespace osg { class Node; class NodeVisitor; -class SG_EXPORT NodeCallback : public virtual Referenced { +class SG_EXPORT NodeCallback : public virtual Object { public : NodeCallback(){} - virtual ~NodeCallback() {} + + NodeCallback(const NodeCallback&,const CopyOp&): + _nestedCallback(_nestedCallback) {} + + + META_Object(osg,NodeCallback) /** Callback method call by the NodeVisitor when visiting a node.*/ @@ -71,6 +76,10 @@ class SG_EXPORT NodeCallback : public virtual Referenced { public: ref_ptr _nestedCallback; + + protected: + + virtual ~NodeCallback() {} }; } // namespace diff --git a/include/osg/NodeVisitor b/include/osg/NodeVisitor index 17bf16b78..981452b3a 100644 --- a/include/osg/NodeVisitor +++ b/include/osg/NodeVisitor @@ -42,7 +42,7 @@ class Sequence; myVisitor.apply(*root). The later method will bypass the double dispatch and the appropriate NodeVisitor::apply(..) method will not be called. */ -class SG_EXPORT NodeVisitor : public Referenced +class SG_EXPORT NodeVisitor : public virtual Referenced { public: @@ -51,8 +51,7 @@ class SG_EXPORT NodeVisitor : public Referenced TRAVERSE_NONE, TRAVERSE_PARENTS, TRAVERSE_ALL_CHILDREN, - TRAVERSE_ACTIVE_CHILDREN, - TRAVERSE_VISITOR + TRAVERSE_ACTIVE_CHILDREN }; enum VisitorType @@ -137,26 +136,18 @@ class SG_EXPORT NodeVisitor : public Referenced NodeVisitor has been attached via setTraverseVisitor() and the new mode is not TRAVERSE_VISITOR then the attached visitor is detached. Default mode is TRAVERSE_NONE.*/ - void setTraversalMode(TraversalMode mode); + inline void setTraversalMode(TraversalMode mode) { _traversalMode = mode; } /** Get the traversal mode.*/ inline TraversalMode getTraversalMode() const { return _traversalMode; } - /** Set a visitor to handle traversal. - Overrides the traverse mode setting it to TRAVERSAL_VISITOR.*/ - void setTraversalVisitor(NodeVisitor* nv); - - /** Get the traversal visitor, returns NULL if none is attached.*/ - inline NodeVisitor* getTraversalVisitor() { return _traversalVisitor.get(); } - /** Method for handling traversal of a nodes. If you intend to use the visitor for actively traversing the scene graph then make sure the accept() methods call this method unless they handle traversal directly.*/ inline void traverse(Node& node) { - if (_traversalVisitor.valid()) node.accept(*_traversalVisitor); - else if (_traversalMode==TRAVERSE_PARENTS) node.ascend(*this); + if (_traversalMode==TRAVERSE_PARENTS) node.ascend(*this); else if (_traversalMode!=TRAVERSE_NONE) node.traverse(*this); } @@ -234,8 +225,6 @@ class SG_EXPORT NodeVisitor : public Referenced int _traversalNumber; ref_ptr _frameStamp; - - ref_ptr _traversalVisitor; TraversalMode _traversalMode; Node::NodeMask _traversalMask; diff --git a/include/osg/PositionAttitudeTransform b/include/osg/PositionAttitudeTransform index 59a6c7572..a20fbcba2 100644 --- a/include/osg/PositionAttitudeTransform +++ b/include/osg/PositionAttitudeTransform @@ -30,19 +30,19 @@ class SG_EXPORT PositionAttitudeTransform : public Transform META_Node(osg, PositionAttitudeTransform); - void setPosition(const Vec3& pos) { _position = pos; dirtyBound(); } + inline void setPosition(const Vec3& pos) { _position = pos; dirtyBound(); } - const Vec3& getPosition() const { return _position; } + inline const Vec3& getPosition() const { return _position; } - void setAttitude(const Quat& quat) { _attitude = quat; dirtyBound(); } + inline void setAttitude(const Quat& quat) { _attitude = quat; dirtyBound(); } - const Quat& getAttitude() const { return _attitude; } + inline const Quat& getAttitude() const { return _attitude; } - void setPivotPoint(const Vec3& pivot) { _pivotPoint = pivot; dirtyBound(); } + inline void setPivotPoint(const Vec3& pivot) { _pivotPoint = pivot; dirtyBound(); } - const Vec3& getPivotPoint() const { return _pivotPoint; } + inline const Vec3& getPivotPoint() const { return _pivotPoint; } virtual bool computeLocalToWorldMatrix(Matrix& matrix,NodeVisitor* nv) const; @@ -50,28 +50,6 @@ class SG_EXPORT PositionAttitudeTransform : public Transform virtual bool computeWorldToLocalMatrix(Matrix& matrix,NodeVisitor* nv) const; - /** Callback which can be attached to a PositionAttitudeTransform - * as an app callback to allow it to follow the path defined by a - * AnimationPath.*/ - class SG_EXPORT AnimationPathCallback : public virtual NodeCallback - { - public: - - AnimationPathCallback(AnimationPath* ap,double timeOffset=0.0f,double timeMultiplier=1.0f): - _animationPath(ap), - _timeOffset(timeOffset), - _timeMultiplier(timeMultiplier), - _firstTime(0.0) {} - - /** implements the callback*/ - virtual void operator()(Node* node, NodeVisitor* nv); - - ref_ptr _animationPath; - double _timeOffset; - double _timeMultiplier; - double _firstTime; - }; - protected : diff --git a/src/Demos/osganimate/osganimate.cpp b/src/Demos/osganimate/osganimate.cpp index 684765228..55e1f25d1 100644 --- a/src/Demos/osganimate/osganimate.cpp +++ b/src/Demos/osganimate/osganimate.cpp @@ -143,7 +143,7 @@ osg::Node* createMovingModel(const osg::Vec3& center, float radius) positioned->addChild(glider); osg::PositionAttitudeTransform* xform = new osg::PositionAttitudeTransform; - xform->setUpdateCallback(new osg::PositionAttitudeTransform::AnimationPathCallback(animationPath,0.0,1.0)); + xform->setUpdateCallback(new osg::AnimationPathCallback(animationPath,0.0,1.0)); xform->addChild(positioned); model->addChild(xform); @@ -164,7 +164,7 @@ osg::Node* createMovingModel(const osg::Vec3& center, float radius) positioned->addChild(cessna); osg::MatrixTransform* xform = new osg::MatrixTransform; - xform->setUpdateCallback(new osg::MatrixTransform::AnimationPathCallback(animationPath,0.0f,2.0)); + xform->setUpdateCallback(new osg::AnimationPathCallback(animationPath,0.0f,2.0)); xform->addChild(positioned); model->addChild(xform); diff --git a/src/Demos/osglight/osglight.cpp b/src/Demos/osglight/osglight.cpp index 0f1aa8921..f95f55ee1 100644 --- a/src/Demos/osglight/osglight.cpp +++ b/src/Demos/osglight/osglight.cpp @@ -124,7 +124,7 @@ osg::Node* createLights(osg::BoundingBox& bb,osg::StateSet* rootStateSet) animationPath->insert(8.0,osg::AnimationPath::ControlPoint(bb.corner(0))); animationPath->setLoopMode(osg::AnimationPath::SWING); - mt->setUpdateCallback(new osg::MatrixTransform::AnimationPathCallback(animationPath)); + mt->setUpdateCallback(new osg::AnimationPathCallback(animationPath)); } // create marker for point light. diff --git a/src/Demos/osgpbuffer/osgpbuffer.cpp b/src/Demos/osgpbuffer/osgpbuffer.cpp index b96b13159..1dd7dec8a 100644 --- a/src/Demos/osgpbuffer/osgpbuffer.cpp +++ b/src/Demos/osgpbuffer/osgpbuffer.cpp @@ -248,7 +248,7 @@ class MyGeometryCallback : osg::Vec3* end = begin+count; for (osg::Vec3* itr=begin;itraddChild(cessna); osg::MatrixTransform* xform = new osg::MatrixTransform; - xform->setUpdateCallback(new osg::MatrixTransform::AnimationPathCallback(animationPath,0.0f,2.0)); + xform->setUpdateCallback(new osg::AnimationPathCallback(animationPath,0.0f,2.0)); xform->addChild(positioned); model->addChild(xform); diff --git a/src/osg/AnimationPath.cpp b/src/osg/AnimationPath.cpp index 6b8210ede..e7e559484 100644 --- a/src/osg/AnimationPath.cpp +++ b/src/osg/AnimationPath.cpp @@ -1,5 +1,6 @@ #include -#include +#include +#include using namespace osg; @@ -67,3 +68,43 @@ bool AnimationPath::getInterpolatedControlPoint(double time,ControlPoint& contro } return true; } + + +void AnimationPathCallback::operator()(Node* node, NodeVisitor* nv) +{ + if (_animationPath.valid() && + nv->getVisitorType()==NodeVisitor::UPDATE_VISITOR && + nv->getFrameStamp()) + { + double time = nv->getFrameStamp()->getReferenceTime(); + if (_firstTime==0.0) _firstTime = time; + + _animationTime = ((time-_firstTime)-_timeOffset)*_timeMultiplier; + + node->accept(*this); + + } + + // must call any nested node callbacks and continue subgraph traversal. + NodeCallback::traverse(node,nv); +} + +void AnimationPathCallback::apply(MatrixTransform& mt) +{ + Matrix matrix; + if (_animationPath->getMatrix(_animationTime,matrix)) + { + mt.setMatrix(matrix); + } +} + + +void AnimationPathCallback::apply(PositionAttitudeTransform& pat) +{ + AnimationPath::ControlPoint cp; + if (_animationPath->getInterpolatedControlPoint(_animationTime,cp)) + { + pat.setPosition(cp._position); + pat.setAttitude(cp._rotation); + } +} diff --git a/src/osg/MatrixTransform.cpp b/src/osg/MatrixTransform.cpp index 77adc1ace..6a2e2c0a9 100644 --- a/src/osg/MatrixTransform.cpp +++ b/src/osg/MatrixTransform.cpp @@ -13,10 +13,8 @@ MatrixTransform::MatrixTransform(const MatrixTransform& transform,const CopyOp& Transform(transform,copyop), _matrix(new Matrix(*transform._matrix)), _inverse(new Matrix(*transform._inverse)), - _inverseDirty(transform._inverseDirty), - _animationPath(dynamic_cast(copyop(transform._animationPath.get()))) + _inverseDirty(transform._inverseDirty) { - if (_animationPath.valid()) setNumChildrenRequiringUpdateTraversal(getNumChildrenRequiringUpdateTraversal()+1); } MatrixTransform::MatrixTransform(const Matrix& mat ) @@ -33,38 +31,30 @@ MatrixTransform::~MatrixTransform() { } - -void MatrixTransform::traverse(NodeVisitor& nv) +bool MatrixTransform::computeLocalToWorldMatrix(Matrix& matrix,NodeVisitor*) const { - // if app traversal update the frame count. - if (_animationPath.valid() && - nv.getVisitorType()==NodeVisitor::UPDATE_VISITOR && - nv.getFrameStamp()) + if (_referenceFrame==RELATIVE_TO_PARENTS) { - double time = nv.getFrameStamp()->getReferenceTime(); - _animationPath->getMatrix(time,*_matrix); + matrix.preMult(*_matrix); } - - // must call any nested node callbacks and continue subgraph traversal. - Transform::traverse(nv); + else // absolute + { + matrix = *_matrix; + } + return true; } -void MatrixTransform::AnimationPathCallback::operator()(Node* node, NodeVisitor* nv) +bool MatrixTransform::computeWorldToLocalMatrix(Matrix& matrix,NodeVisitor*) const { - MatrixTransform* mt = dynamic_cast(node); - if (mt && - _animationPath.valid() && - nv->getVisitorType()==NodeVisitor::UPDATE_VISITOR && - nv->getFrameStamp()) + const Matrix& inverse = getInverseMatrix(); + + if (_referenceFrame==RELATIVE_TO_PARENTS) { - double time = nv->getFrameStamp()->getReferenceTime(); - if (_firstTime==0.0) _firstTime = time; - Matrix matrix; - if (_animationPath->getMatrix(((time-_firstTime)-_timeOffset)*_timeMultiplier,matrix)) - { - mt->setMatrix(matrix); - } + matrix.postMult(inverse); } - // must call any nested node callbacks and continue subgraph traversal. - traverse(node,nv); + else // absolute + { + matrix = inverse; + } + return true; } diff --git a/src/osg/NodeVisitor.cpp b/src/osg/NodeVisitor.cpp index e2ee32a26..9f0a4d3ac 100644 --- a/src/osg/NodeVisitor.cpp +++ b/src/osg/NodeVisitor.cpp @@ -9,7 +9,6 @@ NodeVisitor::NodeVisitor(TraversalMode tm) _visitorType = NODE_VISITOR; _traversalNumber = -1; - _traversalVisitor = NULL; _traversalMode = tm; _traversalMask = 0xffffffff; _nodeMaskOverride = 0x0; @@ -20,7 +19,6 @@ NodeVisitor::NodeVisitor(VisitorType type,TraversalMode tm) _visitorType = type; _traversalNumber = -1; - _traversalVisitor = NULL; _traversalMode = tm; _traversalMask = 0xffffffff; _nodeMaskOverride = 0x0; @@ -32,32 +30,6 @@ NodeVisitor::~NodeVisitor() // if (_traversalVisitor) detach from _traversalVisitor; } - -void NodeVisitor::setTraversalMode(TraversalMode mode) -{ - if (_traversalMode==mode) return; - if (mode==TRAVERSE_VISITOR) - { - if (_traversalVisitor==NULL) _traversalMode = TRAVERSE_NONE; - else _traversalMode = TRAVERSE_VISITOR; - } - else - { - if (_traversalVisitor.valid()) _traversalVisitor=NULL; - _traversalMode = mode; - } -} - - -void NodeVisitor::setTraversalVisitor(NodeVisitor* nv) -{ - if (_traversalVisitor==nv) return; - _traversalVisitor = nv; - if (_traversalVisitor.valid()) _traversalMode = TRAVERSE_VISITOR; - else _traversalMode = TRAVERSE_NONE; -} - - class TransformVisitor : public NodeVisitor { public: diff --git a/src/osg/PositionAttitudeTransform.cpp b/src/osg/PositionAttitudeTransform.cpp index 29d861a41..576d27c5e 100644 --- a/src/osg/PositionAttitudeTransform.cpp +++ b/src/osg/PositionAttitudeTransform.cpp @@ -40,24 +40,3 @@ bool PositionAttitudeTransform::computeWorldToLocalMatrix(Matrix& matrix,NodeVis } return true; } - -void PositionAttitudeTransform::AnimationPathCallback::operator()(Node* node, NodeVisitor* nv) -{ - PositionAttitudeTransform* pat = dynamic_cast(node); - if (pat && - _animationPath.valid() && - nv->getVisitorType()==NodeVisitor::UPDATE_VISITOR && - nv->getFrameStamp()) - { - double time = nv->getFrameStamp()->getReferenceTime(); - if (_firstTime==0.0) _firstTime = time; - AnimationPath::ControlPoint cp; - if (_animationPath->getInterpolatedControlPoint(((time-_firstTime)-_timeOffset)*_timeMultiplier,cp)) - { - pat->setPosition(cp._position); - pat->setAttitude(cp._rotation); - } - } - // must call any nested node callbacks and continue subgraph traversal. - traverse(node,nv); -} diff --git a/src/osgPlugins/flt/FltFile.cpp b/src/osgPlugins/flt/FltFile.cpp index 627cbb6e9..259226840 100644 --- a/src/osgPlugins/flt/FltFile.cpp +++ b/src/osgPlugins/flt/FltFile.cpp @@ -24,6 +24,8 @@ FltFile::FltFile( TexturePool* pTexturePool, MaterialPool* pMaterialPool) { + _useTextureAlphaForTransparancyBinning = true; + if (pColorPool) { // use external color palette, ignore internal @@ -91,6 +93,7 @@ osg::Node* FltFile::readNode(const std::string& fileName) osg::Group* FltFile::convert() { ConvertFromFLT visit; + visit.setUseTextureAlphaForTransparancyBinning(getUseTextureAlphaForTransparancyBinning()); return visit.convert(getHeaderRecord()); } diff --git a/src/osgPlugins/flt/FltFile.h b/src/osgPlugins/flt/FltFile.h index 29b85f021..3e0727180 100644 --- a/src/osgPlugins/flt/FltFile.h +++ b/src/osgPlugins/flt/FltFile.h @@ -44,6 +44,9 @@ class FltFile : public osg::Referenced inline const bool useInternalTexturePalette() const { return _useInternalTexturePalette; } inline const bool useInternalMaterialPalette() const { return _useInternalMaterialPalette; } + void setUseTextureAlphaForTransparancyBinning(bool flag) { _useTextureAlphaForTransparancyBinning=flag; } + bool getUseTextureAlphaForTransparancyBinning() const { return _useTextureAlphaForTransparancyBinning; } + int getFlightVersion() const; inline HeaderRecord* getHeaderRecord() { return _headerRecord.get(); } @@ -61,6 +64,7 @@ class FltFile : public osg::Referenced bool _useInternalColorPalette; bool _useInternalTexturePalette; bool _useInternalMaterialPalette; + bool _useTextureAlphaForTransparancyBinning; std::string _directory; diff --git a/src/osgPlugins/flt/ReaderWriterFLT.cpp b/src/osgPlugins/flt/ReaderWriterFLT.cpp index 56ea03c41..e0896c01a 100644 --- a/src/osgPlugins/flt/ReaderWriterFLT.cpp +++ b/src/osgPlugins/flt/ReaderWriterFLT.cpp @@ -20,14 +20,19 @@ osgDB::ReaderWriter::ReadResult ReaderWriterFLT::readObject(const std::string& f } -osgDB::ReaderWriter::ReadResult ReaderWriterFLT::readNode(const std::string& fileName, const osgDB::ReaderWriter::Options*) +osgDB::ReaderWriter::ReadResult ReaderWriterFLT::readNode(const std::string& fileName, const osgDB::ReaderWriter::Options* options) { if( !acceptsExtension(osgDB::getFileExtension(fileName) )) return ReadResult::FILE_NOT_HANDLED; osg::ref_ptr read = new FltFile; + + if (options) + { + read->setUseTextureAlphaForTransparancyBinning(options->getOptionString().find("noTextureAlphaForTransparancyBinning")!=std::string::npos); + } - osg::Node* node = read.get()->readNode(fileName); + osg::Node* node = read->readNode(fileName); if (node) return node; else return ReadResult::FILE_NOT_HANDLED; } diff --git a/src/osgPlugins/flt/flt2osg.cpp b/src/osgPlugins/flt/flt2osg.cpp index 9bc80bf48..032f0238b 100644 --- a/src/osgPlugins/flt/flt2osg.cpp +++ b/src/osgPlugins/flt/flt2osg.cpp @@ -77,6 +77,7 @@ ConvertFromFLT::ConvertFromFLT() : _wObjTransparency = 0; _nSubfaceLevel = 0; _unitScale = 1.0; + _useTextureAlphaForTranspancyBinning = true; _bHdrRgbMode = false; } @@ -1180,7 +1181,7 @@ void ConvertFromFLT::setTexture ( FaceRecord *rec, SFace *pSFace, osg::StateSet if (osgTexture) { osg::Image* osgImage = osgTexture->getImage(); - if (osgImage->isImageTranslucent()) bBlend = true; + if (getUseTextureAlphaForTransparancyBinning() && osgImage->isImageTranslucent()) bBlend = true; } diff --git a/src/osgPlugins/flt/flt2osg.h b/src/osgPlugins/flt/flt2osg.h index fd88b6333..0f9b6295b 100644 --- a/src/osgPlugins/flt/flt2osg.h +++ b/src/osgPlugins/flt/flt2osg.h @@ -153,6 +153,10 @@ class ConvertFromFLT int visitVertexList(GeoSetBuilder* pParent, VertexListRecord* rec); int visitLocalVertexPool(GeoSetBuilder* pBuilder, LocalVertexPoolRecord* rec); + + void setUseTextureAlphaForTransparancyBinning(bool flag) { _useTextureAlphaForTranspancyBinning=flag; } + bool getUseTextureAlphaForTransparancyBinning() const { return _useTextureAlphaForTranspancyBinning; } + private: int addMeshPrimitives ( osg::Group &osgParent, GeoSetBuilder *pBuilder, MeshRecord *rec ); @@ -188,6 +192,7 @@ class ConvertFromFLT double _unitScale; bool _bHdrRgbMode; osg::Vec4 _faceColor; + bool _useTextureAlphaForTranspancyBinning; osg::Group* _osgParent; }; diff --git a/src/osgPlugins/osg/AnimationPath.cpp b/src/osgPlugins/osg/AnimationPath.cpp index 699b4058d..de2544e08 100644 --- a/src/osgPlugins/osg/AnimationPath.cpp +++ b/src/osgPlugins/osg/AnimationPath.cpp @@ -61,85 +61,45 @@ bool AnimationPath_readLocalData(osg::Object &obj, osgDB::Input &fr) if (fr.matchSequence("ControlPoints {")) { - int entry = fr[1].getNoNestedBrackets(); + int entry = fr[0].getNoNestedBrackets(); fr += 2; - float fTime = -1; - - osg::AnimationPath::ControlPoint CtrlPoint; - bool bPosParsed = false; - bool bRotParsed = false; - bool bScaleParsed = false; + float time; + Vec3 position,scale; + Quat rotation; + while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) { - bool handled=false; - - if (fr[0].matchWord("Time") && - fr[1].isFloat()) + if (fr[0].getFloat(time) && + fr[1].getFloat(position[0]) && + fr[2].getFloat(position[1]) && + fr[3].getFloat(position[2]) && + fr[4].getFloat(rotation[0]) && + fr[5].getFloat(rotation[1]) && + fr[6].getFloat(rotation[2]) && + fr[7].getFloat(rotation[3]) && + fr[8].getFloat(scale[0]) && + fr[9].getFloat(scale[1]) && + fr[10].getFloat(scale[2])) { - if (bPosParsed || bRotParsed || bScaleParsed) - { - ap->insert(fTime, CtrlPoint); - - bPosParsed = false; - bRotParsed = false; - bScaleParsed = false; - } - fr[1].getFloat(fTime); - fr+=2; - handled = true; - } - Vec3 vec3; - if (fr[0].matchWord("Position") && - fr[1].getFloat(vec3[0]) && - fr[2].getFloat(vec3[1]) && - fr[3].getFloat(vec3[2])) - { - CtrlPoint._position = vec3; - fr+=4; - bPosParsed = true; - handled = true; + osg::AnimationPath::ControlPoint ctrlPoint; + ctrlPoint._position = position; + ctrlPoint._rotation = rotation; + ctrlPoint._scale = scale; + + ap->insert(time, ctrlPoint); + + fr+=11; } - - - Vec4 vec4; - if (fr[0].matchWord("Rotation") && - fr[1].getFloat(vec4[0]) && - fr[2].getFloat(vec4[1]) && - fr[3].getFloat(vec4[2]) && - fr[4].getFloat(vec4[3])) - { - CtrlPoint._rotation.makeRotate(vec4[0], vec4[1], vec4[2], vec4[3]); - fr+=5; - bRotParsed = true; - handled = true; - } - - - if (fr[0].matchWord("Scale") && - fr[1].getFloat(vec3[0]) && - fr[2].getFloat(vec3[1]) && - fr[3].getFloat(vec3[2])) - { - CtrlPoint._scale = vec3; - fr+=4; - bScaleParsed = true; - handled = true; - } - - if (!handled) fr.advanceOverCurrentFieldOrBlock(); + else fr.advanceOverCurrentFieldOrBlock(); } - // If all values have been parsed in - if (bPosParsed && bRotParsed && bScaleParsed) - { - ap->insert(fTime, CtrlPoint); - } + itAdvanced = true; } @@ -171,43 +131,11 @@ bool AnimationPath_writeLocalData(const osg::Object &obj, osgDB::Output &fw) fw.indent() << "ControlPoints {"<< std::endl; fw.moveIn(); - bool bPosSet = false; - bool bRotSet = false; - bool bScaleSet = false; - AnimationPath::TimeControlPointMap::const_iterator itr; - for (itr=tcpm.begin(); + for (AnimationPath::TimeControlPointMap::const_iterator itr=tcpm.begin(); itr!=tcpm.end(); ++itr) { - if (itr->second._position != Vec3(0,0,0)) - bPosSet = true; - if (itr->second._rotation.asVec4() != Vec4(0,0,0,1)) - bRotSet = true; - if (itr->second._scale != Vec3(1,1,1)) - bScaleSet = true; - } - - for (itr=tcpm.begin(); - itr!=tcpm.end(); - ++itr) - { - Vec4 Rot; - - fw.indent() << "Time " << itr->first; - - if (bPosSet) - fw << " Position " << itr->second._position; - - if (bRotSet) - { - itr->second._rotation.getRotate (Rot[0], Rot[1], Rot[2], Rot[3]); - fw << " Rotation " << Rot; - } - - if (bScaleSet) - fw << " Scale " << itr->second._scale; - - fw << std::endl; + fw.indent() << itr->first << " " << itr->second._position << " " << itr->second._rotation << " " << itr->second._scale << std::endl; } @@ -216,3 +144,51 @@ bool AnimationPath_writeLocalData(const osg::Object &obj, osgDB::Output &fw) return true; } + + + + +// forward declare functions to use later. +bool AnimationPathCallback_readLocalData(osg::Object &obj, osgDB::Input &fr); +bool AnimationPathCallback_writeLocalData(const osg::Object &obj, osgDB::Output &fw); + + +// register the read and write functions with the osgDB::Registry. +osgDB::RegisterDotOsgWrapperProxy AnimationPathCallback_Proxy +( + new osg::AnimationPathCallback, + "AnimationPathCallback", + "Object AnimationPathCallback", + AnimationPathCallback_readLocalData, + AnimationPathCallback_writeLocalData, + DotOsgWrapper::READ_AND_WRITE +); + +bool AnimationPathCallback_readLocalData(osg::Object &obj, osgDB::Input &fr) +{ + osg::AnimationPathCallback *apc = dynamic_cast(&obj); + if (!apc) return false; + + static osg::ref_ptr s_path = new osg::AnimationPath; + ref_ptr object = fr.readObjectOfType(*s_path); + osg::AnimationPath* animpath = dynamic_cast(object.get()); + if (animpath) apc->setAnimationPath(animpath); + + bool itrAdvanced = object.valid(); + + return itrAdvanced; +} + + +bool AnimationPathCallback_writeLocalData(const osg::Object &obj, osgDB::Output &fw) +{ + const osg::AnimationPathCallback* apc = dynamic_cast(&obj); + if (!apc) return false; + + if (apc->getAnimationPath()) + { + fw.writeObject(*(apc->getAnimationPath())); + } + + return true; +} diff --git a/src/osgPlugins/osg/MatrixTransform.cpp b/src/osgPlugins/osg/MatrixTransform.cpp index acc2a5d7e..dc134a01f 100644 --- a/src/osgPlugins/osg/MatrixTransform.cpp +++ b/src/osgPlugins/osg/MatrixTransform.cpp @@ -1,8 +1,8 @@ -#include "osg/MatrixTransform" +#include -#include "osgDB/Registry" -#include "osgDB/Input" -#include "osgDB/Output" +#include +#include +#include using namespace osg; using namespace osgDB; @@ -68,22 +68,6 @@ bool MatrixTransform_readLocalData(Object& obj, Input& fr) iteratorAdvanced = true; } - if (fr[0].matchWord("AnimationPath")) - { - static osg::ref_ptr prototype = new osg::AnimationPath; - osg::ref_ptr object = fr.readObjectOfType(*prototype); - osg::AnimationPath* path = dynamic_cast(object.get()); - if (path) - { - transform.setAnimationPath(path); - } - else - { - osg::Node* node = dynamic_cast(object.get()); - if (node) transform.addChild(node); - } - } - return iteratorAdvanced; } @@ -94,10 +78,5 @@ bool MatrixTransform_writeLocalData(const Object& obj, Output& fw) fw.writeObject(transform.getMatrix()); - if (transform.getAnimationPath()) - { - fw.writeObject(*transform.getAnimationPath()); - } - return true; } diff --git a/src/osgPlugins/osg/Node.cpp b/src/osgPlugins/osg/Node.cpp index 644092496..eec2f4db5 100644 --- a/src/osgPlugins/osg/Node.cpp +++ b/src/osgPlugins/osg/Node.cpp @@ -95,6 +95,37 @@ bool Node_readLocalData(Object& obj, Input& fr) } + static ref_ptr s_nodecallback = new osg::NodeCallback; + while (fr.matchSequence("UpdateCallback {")) + { + int entry = fr[0].getNoNestedBrackets(); + fr += 2; + + while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + NodeCallback* nodecallback = dynamic_cast(fr.readObjectOfType(*s_nodecallback)); + if (nodecallback) node.setUpdateCallback(nodecallback); + else ++fr; + } + iteratorAdvanced = true; + + } + + while (fr.matchSequence("CullCallback {")) + { + int entry = fr[0].getNoNestedBrackets(); + fr += 2; + + while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + NodeCallback* nodecallback = dynamic_cast(fr.readObjectOfType(*s_nodecallback)); + if (nodecallback) node.setUpdateCallback(nodecallback); + else ++fr; + } + iteratorAdvanced = true; + + } + return iteratorAdvanced; } @@ -147,6 +178,24 @@ bool Node_writeLocalData(const Object& obj, Output& fw) { fw.writeObject(*node.getStateSet()); } + + if (node.getUpdateCallback()) + { + fw.indent() << "UpdateCallbacks {" << std::endl; + fw.moveIn(); + fw.writeObject(*node.getUpdateCallback()); + fw.moveOut(); + fw.indent() << "}" << std::endl; + } + + if (node.getCullCallback()) + { + fw.indent() << "CullCallbacks {" << std::endl; + fw.moveIn(); + fw.writeObject(*node.getCullCallback()); + fw.moveOut(); + fw.indent() << "}" << std::endl; + } return true; }