From Michael Gronager, osgSim::VisibilityGroup
This commit is contained in:
@@ -232,6 +232,14 @@ SOURCE=..\..\..\src\osgPlugins\osgSim\IO_MultiSwitch.cpp
|
||||
|
||||
# End Source File
|
||||
|
||||
# Begin Source File
|
||||
|
||||
|
||||
|
||||
SOURCE=..\..\..\src\osgPlugins\osgSim\IO_VisibilityGroup.cpp
|
||||
|
||||
# End Source File
|
||||
|
||||
# End Group
|
||||
|
||||
# Begin Group "Header Files"
|
||||
|
||||
@@ -139,6 +139,10 @@ SOURCE=..\..\src\osgSim\MultiSwitch.cpp
|
||||
|
||||
SOURCE=..\..\src\osgSim\Version.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\..\src\osgSim\VisibilityGroup.cpp
|
||||
# End Source File
|
||||
# End Group
|
||||
# Begin Group "Header Files"
|
||||
|
||||
@@ -195,6 +199,10 @@ SOURCE=..\..\include\osgSim\Export
|
||||
|
||||
SOURCE=..\..\include\osgSim\Version
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\..\include\osgSim\VisibilityGroup
|
||||
# End Source File
|
||||
# End Group
|
||||
# Begin Group "Resource Files"
|
||||
|
||||
|
||||
58
include/osgSim/VisibilityGroup
Normal file
58
include/osgSim/VisibilityGroup
Normal file
@@ -0,0 +1,58 @@
|
||||
/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2003 Robert Osfield
|
||||
*
|
||||
* This library is open source and may be redistributed and/or modified under
|
||||
* the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or
|
||||
* (at your option) any later version. The full license is in LICENSE file
|
||||
* included with this distribution, and on the openscenegraph.org website.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* OpenSceneGraph Public License for more details.
|
||||
*/
|
||||
|
||||
#ifndef OSGSIM_VISIBILITYGROUP
|
||||
#define OSGSIM_VISIBILITYGROUP 1
|
||||
|
||||
#include <osg/Node>
|
||||
#include <osg/Group>
|
||||
#include <osg/NodeVisitor>
|
||||
|
||||
#include <osgSim/Export>
|
||||
|
||||
namespace osgSim {
|
||||
|
||||
class OSGSIM_EXPORT VisibilityGroup : public osg::Group
|
||||
{
|
||||
public :
|
||||
|
||||
VisibilityGroup();
|
||||
|
||||
/** Copy constructor using CopyOp to manage deep vs shallow copy.*/
|
||||
VisibilityGroup(const VisibilityGroup&,const osg::CopyOp& copyop=osg::CopyOp::SHALLOW_COPY);
|
||||
|
||||
META_Node(osgSim, VisibilityGroup)
|
||||
|
||||
virtual void traverse(osg::NodeVisitor& nv);
|
||||
|
||||
void setVisibilityVolume(osg::Node* node) { _visibilityVolume = node; }
|
||||
osg::Node* getVisibilityVolume() { return _visibilityVolume.get(); }
|
||||
const osg::Node* getVisibilityVolume() const { return _visibilityVolume.get(); }
|
||||
|
||||
void setVolumeIntersectionMask(osg::Node::NodeMask mask) { _volumeIntersectionMask = mask; }
|
||||
osg::Node::NodeMask getVolumeIntersectionMask() const { return _volumeIntersectionMask; }
|
||||
|
||||
void setSegmentLength(float length) { _segmentLength = length; }
|
||||
float getSegmentLength() const { return _segmentLength; }
|
||||
|
||||
protected :
|
||||
|
||||
virtual ~VisibilityGroup() {}
|
||||
|
||||
osg::ref_ptr<osg::Node> _visibilityVolume;
|
||||
osg::Node::NodeMask _volumeIntersectionMask;
|
||||
float _segmentLength;
|
||||
};
|
||||
|
||||
}
|
||||
#endif
|
||||
@@ -7,7 +7,9 @@ CXXFILES =\
|
||||
IO_LightPoint.cpp\
|
||||
IO_BlinkSequence.cpp\
|
||||
IO_MultiSwitch.cpp\
|
||||
IO_Sector.cpp
|
||||
IO_Sector.cpp\
|
||||
IO_VisibilityGroup.cpp\
|
||||
|
||||
|
||||
LIBS += -losgSim -losgText $(OSG_LIBS) $(OTHER_LIBS)
|
||||
|
||||
|
||||
79
src/osgPlugins/osgSim/IO_VisibilityGroup.cpp
Normal file
79
src/osgPlugins/osgSim/IO_VisibilityGroup.cpp
Normal file
@@ -0,0 +1,79 @@
|
||||
#include "osgSim/VisibilityGroup"
|
||||
|
||||
#include "osgDB/Registry"
|
||||
#include "osgDB/Input"
|
||||
#include "osgDB/Output"
|
||||
|
||||
using namespace osg;
|
||||
using namespace osgSim;
|
||||
using namespace osgDB;
|
||||
|
||||
// forward declare functions to use later.
|
||||
bool VisibilityGroup_readLocalData(Object& obj, Input& fr);
|
||||
bool VisibilityGroup_writeLocalData(const Object& obj, Output& fw);
|
||||
|
||||
// register the read and write functions with the osgDB::Registry.
|
||||
RegisterDotOsgWrapperProxy g_VisibilityGroupProxy
|
||||
(
|
||||
new VisibilityGroup,
|
||||
"VisibilityGroup",
|
||||
"Object Node VisibilityGroup Group",
|
||||
&VisibilityGroup_readLocalData,
|
||||
&VisibilityGroup_writeLocalData
|
||||
);
|
||||
|
||||
bool VisibilityGroup_readLocalData(Object& obj, Input& fr)
|
||||
{
|
||||
bool iteratorAdvanced = false;
|
||||
|
||||
VisibilityGroup& vg = static_cast<VisibilityGroup&>(obj);
|
||||
|
||||
unsigned int mask = vg.getVolumeIntersectionMask();
|
||||
if (fr[0].matchWord("volumeIntersectionMask") && fr[1].getUInt(mask))
|
||||
{
|
||||
vg.setNodeMask(mask);
|
||||
fr+=2;
|
||||
iteratorAdvanced = true;
|
||||
}
|
||||
|
||||
if (fr[0].matchWord("segmentLength"))
|
||||
{
|
||||
if (fr[1].isFloat())
|
||||
{
|
||||
float value;
|
||||
fr[1].getFloat(value);
|
||||
vg.setSegmentLength(value);
|
||||
iteratorAdvanced = true;
|
||||
fr += 2;
|
||||
}
|
||||
}
|
||||
|
||||
if (fr.matchSequence("visibilityVolume"))
|
||||
{
|
||||
// int entry = fr[0].getNoNestedBrackets();
|
||||
++fr;
|
||||
Node* node = NULL;
|
||||
if((node=fr.readNode())!=NULL)
|
||||
{
|
||||
vg.setVisibilityVolume(node);
|
||||
iteratorAdvanced = true;
|
||||
}
|
||||
}
|
||||
|
||||
return iteratorAdvanced;
|
||||
}
|
||||
|
||||
|
||||
bool VisibilityGroup_writeLocalData(const Object& obj, Output& fw)
|
||||
{
|
||||
const VisibilityGroup& vg = static_cast<const VisibilityGroup&>(obj);
|
||||
|
||||
fw.indent()<<"volumeIntersectionMask 0x"<<std::hex<<vg.getVolumeIntersectionMask()<<std::dec<<std::endl;
|
||||
fw.indent()<<"segmentLength "<<vg.getSegmentLength()<<std::endl;
|
||||
fw.indent()<<"visibilityVolume" <<std::endl;
|
||||
fw.moveIn();
|
||||
fw.writeObject(*vg.getVisibilityVolume());
|
||||
fw.moveOut();
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -15,6 +15,8 @@ CXXFILES = \
|
||||
SphereSegment.cpp\
|
||||
MultiSwitch.cpp\
|
||||
Version.cpp\
|
||||
VisibilityGroup.cpp\
|
||||
|
||||
|
||||
DEF += -DOSGSIM_LIBRARY
|
||||
|
||||
|
||||
84
src/osgSim/VisibilityGroup.cpp
Normal file
84
src/osgSim/VisibilityGroup.cpp
Normal file
@@ -0,0 +1,84 @@
|
||||
/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2003 Robert Osfield
|
||||
*
|
||||
* This library is open source and may be redistributed and/or modified under
|
||||
* the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or
|
||||
* (at your option) any later version. The full license is in LICENSE file
|
||||
* included with this distribution, and on the openscenegraph.org website.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* OpenSceneGraph Public License for more details.
|
||||
*/
|
||||
|
||||
#include <osgSim/VisibilityGroup>
|
||||
|
||||
#include <osgUtil/CullVisitor>
|
||||
#include <osgUtil/IntersectVisitor>
|
||||
|
||||
using namespace osgSim;
|
||||
|
||||
VisibilityGroup::VisibilityGroup():
|
||||
_volumeIntersectionMask(0xFFFFFFFF),
|
||||
_segmentLength(0.f)
|
||||
{
|
||||
}
|
||||
|
||||
VisibilityGroup::VisibilityGroup(const VisibilityGroup& sw,const osg::CopyOp& copyop):
|
||||
osg::Group(sw,copyop),
|
||||
_volumeIntersectionMask(0xFFFFFFFF),
|
||||
_segmentLength(0.f)
|
||||
{
|
||||
}
|
||||
|
||||
void VisibilityGroup::traverse(osg::NodeVisitor& nv)
|
||||
{
|
||||
if (nv.getTraversalMode()==osg::NodeVisitor::TRAVERSE_ACTIVE_CHILDREN && nv.getVisitorType() == osg::NodeVisitor::CULL_VISITOR)
|
||||
{
|
||||
// cast to cullvisitor
|
||||
osgUtil::CullVisitor& cv = (osgUtil::CullVisitor&) nv;
|
||||
|
||||
// here we test if we are inside the visibilityvolume
|
||||
|
||||
// first get the eyepoint and in local coordinates
|
||||
osg::Vec3 eye = cv.getEyeLocal();
|
||||
osg::Vec3 look = cv.getLookVectorLocal();
|
||||
|
||||
// now scale the segment to the segment length - if 0 use the group bounding sphere radius
|
||||
float length = _segmentLength;
|
||||
if(length == 0.f)
|
||||
length = getBound().radius();
|
||||
look *= length;
|
||||
osg::Vec3 center = eye + look;
|
||||
|
||||
osg::Vec3 seg = center - eye;
|
||||
|
||||
// perform the intersection using the given mask
|
||||
osgUtil::IntersectVisitor iv;
|
||||
osg::ref_ptr<osg::LineSegment> lineseg = new osg::LineSegment;
|
||||
lineseg->set(eye, center);
|
||||
iv.addLineSegment(lineseg.get());
|
||||
iv.setTraversalMask(_volumeIntersectionMask);
|
||||
|
||||
if(_visibilityVolume.valid())
|
||||
_visibilityVolume->accept(iv);
|
||||
|
||||
// now examine the hit record
|
||||
if(iv.hits())
|
||||
{
|
||||
osgUtil::IntersectVisitor::HitList& hitList = iv.getHitList(lineseg.get());
|
||||
if(!hitList.empty()) // we actually hit something
|
||||
{
|
||||
// notify(INFO) << "Hit obstruction"<< std::endl;
|
||||
osg::Vec3 normal = hitList.front().getLocalIntersectNormal();
|
||||
if((normal*seg) > 0.f ) // we are inside
|
||||
Group::traverse(nv);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Group::traverse(nv);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user