Example #1
0
void
MapNode::traverse( osg::NodeVisitor& nv )
{
    if ( nv.getVisitorType() == osg::NodeVisitor::EVENT_VISITOR )
    {
        unsigned int numBlacklist = Registry::instance()->getNumBlacklistedFilenames();
        if (numBlacklist != _lastNumBlacklistedFilenames)
        {
            //Only remove the blacklisted filenames if new filenames have been added since last time.
            _lastNumBlacklistedFilenames = numBlacklist;
            RemoveBlacklistedFilenamesVisitor v;
            //accept( v );
            _terrainEngine->accept( v );
        }
    }

    osg::Group::traverse( nv );
}
Example #2
0
void
LODScaleGroup::traverse(osg::NodeVisitor& nv)
{
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        osg::CullStack* cs = dynamic_cast<osg::CullStack*>( &nv );
        if ( cs )
        {
            float lodscale = cs->getLODScale();
            cs->setLODScale( lodscale * _scaleFactor );
            std::for_each( _children.begin(), _children.end(), osg::NodeAcceptOp(nv));
            cs->setLODScale( lodscale );
            return;
        }
    }

    osg::Group::traverse( nv );
}
Example #3
0
void
OSGTerrainEngineNode::traverse( osg::NodeVisitor& nv )
{
    if ( _cull_mapf ) // ensures initialize() has been called
    {
        if ( nv.getVisitorType() == osg::NodeVisitor::CULL_VISITOR )
        {
            // update the cull-thread map frame if necessary. (We don't need to sync the
            // update_mapf becuase that happens in response to a map callback.)

            // TODO: address the fact that this can happen from multiple threads.
            // Really we need a _cull_mapf PER view. -gw
            _cull_mapf->sync();
        }
    }

    TerrainEngineNode::traverse( nv );
}
Example #4
0
void
HorizonNode::traverse(osg::NodeVisitor& nv)
{
    bool isStealth = (VisitorData::isSet(nv, "osgEarth.Stealth"));

    if (nv.getVisitorType() == nv.CULL_VISITOR)
    {
        if (!isStealth)
        {
            //Horizon* h = Horizon::get(nv);
            osg::ref_ptr<Horizon> h = new Horizon();

            osgUtil::CullVisitor* cv = dynamic_cast<osgUtil::CullVisitor*>(&nv);

            osg::Vec3d eye = osg::Vec3d(0,0,0) * cv->getCurrentCamera()->getInverseViewMatrix();
            h->setEye(eye);

            osg::Plane plane;
            if (h->getPlane(plane))
            {
                osg::Quat q;
                q.makeRotate(osg::Plane::Vec3_type(0,0,1), plane.getNormal());

                double dist = plane.distance(osg::Vec3d(0,0,0));

                osg::Matrix m;
                m.preMultRotate(q);
                m.preMultTranslate(osg::Vec3d(0, 0, -dist));
                m.preMultScale(osg::Vec3d(15e6, 15e6, 15e6));

                setMatrix(m);
            }
        }
        else
        {
            osg::MatrixTransform::traverse(nv);
        }
    }
       
    else
    {
        osg::MatrixTransform::traverse(nv);
    }
}
void ossimPlanetPointModel::traverse(osg::NodeVisitor& nv)
{
   if(!enableFlag()||!theNode.valid())
   {
      ossimPlanetAnnotationLayerNode::traverse(nv);
      return;
   }
   switch(nv.getVisitorType())
   {
      case osg::NodeVisitor::UPDATE_VISITOR:
      {
         setRedrawFlag(false); // let's reset the redraw notification
         if(!theLsrSpaceTransform->model()&&layer()) theLsrSpaceTransform->setModel(layer()->model());
         
 //        if(checkPointers())
         {
            OpenThreads::ScopedLock<OpenThreads::Mutex> lock(thePointModelPropertyMutex);
            if(theNodeChangedFlag)
            {
               if(theLsrSpaceTransform->getNumChildren() > 0)
               {
                  theLsrSpaceTransform->removeChildren(0, theLsrSpaceTransform->getNumChildren());
               }
               theLsrSpaceTransform->addChild(theNode.get());
               theNodeChangedFlag = false;
           }
         }
         break;
      }
      case osg::NodeVisitor::CULL_VISITOR:
      {
         break;
      }
      default:
      {
         break;
      }
   }
   
   theLsrSpaceTransform->accept(nv);
   ossimPlanetAnnotationLayerNode::traverse(nv);
}
Example #6
0
void
FadeLOD::traverse( osg::NodeVisitor& nv )
{
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        osgUtil::CullVisitor* cv = Culling::asCullVisitor(nv);
        PerViewData& data = _perViewData.get(cv);
        if ( !data._opacity.valid() )
        {
            data._opacity = new osg::Uniform(osg::Uniform::FLOAT, "oe_FadeLOD_opacity");
            data._stateSet = new osg::StateSet();
            data._stateSet->addUniform( data._opacity.get() );
        }
        
        float p = cv->clampedPixelSize(getBound()) / cv->getLODScale();
        
        float opacity;

        if ( p < _minPixelExtent )
            opacity = 0.0f;
        else if ( p < _minPixelExtent + _minFadeExtent )
            opacity = (p - _minPixelExtent) / _minFadeExtent;
        else if ( p < _maxPixelExtent - _maxFadeExtent )
            opacity = 1.0f;
        else if ( p < _maxPixelExtent )
            opacity = (_maxPixelExtent - p) / _maxFadeExtent;
        else
            opacity = 0.0f;

        data._opacity->set( opacity );

        //OE_INFO << LC << "r = " << getBound().radius() << ", p = " << p << ", o = " << opacity << std::endl;

        cv->pushStateSet( data._stateSet.get() );
        osg::Group::traverse( nv );
        cv->popStateSet();
    }
    else
    {
        osg::Group::traverse( nv );
    }
}
void
MPTerrainEngineNode::traverse(osg::NodeVisitor& nv)
{
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        // since the root tiles are manually added, the pager never has a chance to 
        // register the PagedLODs in their children. So we have to do it manually here.
        if ( !_rootTilesRegistered )
        {
            Threading::ScopedMutexLock lock(_rootTilesRegisteredMutex);

            if ( !_rootTilesRegistered )
            {
                osgDB::DatabasePager* pager = dynamic_cast<osgDB::DatabasePager*>(nv.getDatabaseRequestHandler());
                if ( pager )
                {
                    //OE_WARN << "Registering plods." << std::endl;
                    pager->registerPagedLODs( _terrain );
                    _rootTilesRegistered = true;
                }
            }
        }

        // Inform the registry of the current frame so that Tiles have access
        // to the information.
        if ( _liveTiles.valid() && nv.getFrameStamp() )
        {
            _liveTiles->setTraversalFrame( nv.getFrameStamp()->getFrameNumber() );
        }
    }

#if 0
    static int c = 0;
    if ( ++c % 60 == 0 )
    {
        OE_NOTICE << LC << "Live = " << _liveTiles->size() << ", Dead = " << _deadTiles->size() << std::endl;
        _liveTiles->run( CheckForOrphans() );
    }
#endif

    TerrainEngineNode::traverse( nv );
}
Example #8
0
File: Dragger.cpp Project: 4ker/osg
void Dragger::traverse(osg::NodeVisitor& nv)
{
    if (_handleEvents && nv.getVisitorType()==osg::NodeVisitor::EVENT_VISITOR)
    {
        osgGA::EventVisitor* ev = dynamic_cast<osgGA::EventVisitor*>(&nv);
        if (ev)
        {
            for(osgGA::EventQueue::Events::iterator itr = ev->getEvents().begin();
                itr != ev->getEvents().end();
                ++itr)
            {
                osgGA::GUIEventAdapter* ea = (*itr)->asGUIEventAdapter();
                if (ea && handle(*ea, *(ev->getActionAdapter()))) ea->setHandled(true);
            }
        }
        return;
    }

    MatrixTransform::traverse(nv);
}
Example #9
0
void DOFTransform::traverse(osg::NodeVisitor& nv)
{
    if (nv.getVisitorType()==osg::NodeVisitor::UPDATE_VISITOR)
    {
        // ensure that we do not operate on this node more than
        // once during this traversal.  This is an issue since node
        // can be shared between multiple parents.
        if ((nv.getTraversalNumber()!=_previousTraversalNumber) && nv.getFrameStamp())
        {
            double newTime = nv.getFrameStamp()->getSimulationTime();

            animate((float)(newTime-_previousTime));

            _previousTraversalNumber = nv.getTraversalNumber();
            _previousTime = newTime;
        }
    }

    Transform::traverse(nv);
}
Example #10
0
void
TileNode::traverse(osg::NodeVisitor& nv)
{
    // Cull only:
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        if (_empty == false)
        {
            TerrainCuller* culler = dynamic_cast<TerrainCuller*>(&nv);
        
            if (VisitorData::isSet(culler->getParent(), "osgEarth.Stealth"))
            {
                accept_cull_stealth( culler );
            }
            else
            {
                accept_cull( culler );
            }
        }
    }

    // Everything else: update, GL compile, intersection, compute bound, etc.
    else
    {
        // If there are child nodes, traverse them:
        int numChildren = getNumChildren();
        if ( numChildren > 0 )
        {
            for(int i=0; i<numChildren; ++i)
            {
                _children[i]->accept( nv );
            }
        }

        // Otherwise traverse the surface.
        else if (_surface.valid())
        {
            _surface->accept( nv );
        }
    }
}
Example #11
0
void VolumeTile::traverse(osg::NodeVisitor& nv)
{
    if (!_hasBeenTraversal)
    {
        if (!_volume)
        {
            osg::NodePath& nodePath = nv.getNodePath();
            if (!nodePath.empty())
            {
                for(osg::NodePath::reverse_iterator itr = nodePath.rbegin();
                    itr != nodePath.rend() && !_volume;
                    ++itr)
                {
                    osgVolume::Volume* volume = dynamic_cast<Volume*>(*itr);
                    if (volume)
                    {
                        OSG_INFO<<"Assigning volume system "<<volume<<std::endl;
                        setVolume(volume);
                    }
                }
            }
        }

        _hasBeenTraversal = true;
    }

    if (nv.getVisitorType()==osg::NodeVisitor::UPDATE_VISITOR &&
        _layer->requiresUpdateTraversal())
    {
        _layer->update(nv);
    }

    if (_volumeTechnique.valid())
    {
        _volumeTechnique->traverse(nv);
    }
    else
    {
        osg::Group::traverse(nv);
    }
}
Example #12
0
void
TileNode::traverse( osg::NodeVisitor& nv )
{
    if ( _model.valid() && nv.getVisitorType() == nv.CULL_VISITOR )
    {
        osg::ClusterCullingCallback* ccc = dynamic_cast<osg::ClusterCullingCallback*>(getCullCallback());
        if (ccc)
        {
            if (ccc->cull(&nv,0,static_cast<osg::State *>(0))) return;
        }

        // if this tile is marked dirty, bump the marker so the engine knows it
        // needs replacing.
        if ( _dirty || _model->_revision != _maprevision )
        {
            _outOfDate = true;
        }
    }

    osg::MatrixTransform::traverse( nv );
}
Example #13
0
    void traverse( osg::NodeVisitor& nv )
    {
        if ( _dragger.valid() )
        {
            if ( _active && nv.getVisitorType()==osg::NodeVisitor::CULL_VISITOR )
            {
                osgUtil::CullVisitor* cv = static_cast<osgUtil::CullVisitor*>(&nv);

                float pixelSize = cv->pixelSize(_dragger->getBound().center(), 0.48f);
                if ( pixelSize!=_draggerSize )
                {
                    float pixelScale = pixelSize>0.0f ? _draggerSize/pixelSize : 1.0f;
                    osg::Vec3d scaleFactor(pixelScale, pixelScale, pixelScale);

                    osg::Vec3 trans = _dragger->getMatrix().getTrans();
                    _dragger->setMatrix( osg::Matrix::scale(scaleFactor) * osg::Matrix::translate(trans) );
                }
            }
        }
        osg::Group::traverse(nv);
    }
Example #14
0
void
SilverLiningNode::traverse(osg::NodeVisitor& nv)
{
	if ( nv.getVisitorType() == nv.CULL_VISITOR )
	{
		osgUtil::CullVisitor* cv = Culling::asCullVisitor(nv);
		osg::Camera* camera  = cv->getCurrentCamera();
		if ( camera )
		{
			if(_cameraNodeMap.find(camera) == _cameraNodeMap.end())
			{ 
				SilverLiningContextNode *slContextNode = new SilverLiningContextNode(this, camera, _light, _map, _options);
				_cameraNodeMap[camera] = slContextNode;
//Use camera cull mask that will remove the need for context check 
//in SilverLiningContextNode, SilverLiningSkyDrawable and SilverLiningCloudsDrawable
#ifdef SL_USE_CULL_MASK 
				static int nodeMask = 0x1;
				slContextNode->getSLGeode()->setNodeMask(nodeMask);
				slContextNode->setNodeMask(nodeMask);

				int inheritanceMask = 
					(osg::CullSettings::VariablesMask::ALL_VARIABLES &
					~osg::CullSettings::VariablesMask::CULL_MASK);

				camera->setInheritanceMask(inheritanceMask);
				camera->setCullMask(nodeMask);
				nodeMask = nodeMask << 1;
#endif
				addChild(slContextNode);
			}
		}
	}

    osgEarth::Util::SkyNode::traverse( nv );

    if ( _lightSource.valid() )
    {
        _lightSource->accept(nv);
    }
}
Example #15
0
void
TileNode::traverse(osg::NodeVisitor& nv)
{
    // Cull only:
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        osgUtil::CullVisitor* cv = dynamic_cast<osgUtil::CullVisitor*>(&nv);

        if (VisitorData::isSet(nv, "osgEarth.Stealth"))
        {
            accept_cull_stealth( cv );
        }
        else
        {
            accept_cull( cv );
        }
    }

    // Everything else: update, GL compile, intersection, compute bound, etc.
    else
    {
        // If there are child nodes, traverse them:
        int numChildren = getNumChildren();
        if ( numChildren > 0 )
        {
            for(int i=0; i<numChildren; ++i)
            {
                _children[i]->accept( nv );
            }
        }

        // Otherwise traverse the surface.
        // TODO: in what situations should we traverse the landcover as well? GL compile?
        else 
        {
            _surface->accept( nv );
        }
    }
}
Example #16
0
void
TileGroup::traverse(osg::NodeVisitor& nv)
{
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        // only check for update if an update isn't already in progress:
        if ( !_updateAgent.valid() )
        {
            bool updateRequired = false;
            for( unsigned q=0; q<4; ++q)
            {
                if ( getTileNode(q)->isOutOfDate() )
                {
                    updateRequired = true;
                    break;
                }
            }

            if ( updateRequired )
            {
                // lock keeps multiple traversals from doing the same thing
                Threading::ScopedMutexLock exclusive( _updateMutex );

                // double check to prevent a race condition:
                if ( !_updateAgent.valid() )
                {
                    _updateAgent = new UpdateAgent(this);
                }
            }
        }

        if ( _updateAgent.valid() )
        {
            _updateAgent->accept( nv );
        }
    }

    osg::Group::traverse( nv );
}
void Terrain::traverse(osg::NodeVisitor& nv)
{
    if (nv.getVisitorType()==osg::NodeVisitor::UPDATE_VISITOR)
    {
        // need to check if any TerrainTechniques need to have their update called on them.
        osgUtil::UpdateVisitor* uv = dynamic_cast<osgUtil::UpdateVisitor*>(&nv);
        if (uv)
        {
            OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_mutex);
            for(TerrainTileSet::iterator itr = _updateTerrainTileSet.begin();
                itr != _updateTerrainTileSet.end();
                ++itr)
            {
                TerrainTile* tile = *itr;
                tile->traverse(nv);
            }
            _updateTerrainTileSet.clear();
        }
    }

    Group::traverse(nv);
}
Example #18
0
void
TileNode::traverse( osg::NodeVisitor& nv )
{
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        osg::ClusterCullingCallback* ccc = dynamic_cast<osg::ClusterCullingCallback*>(getCullCallback());
        if (ccc)
        {
            if (ccc->cull(&nv,0,static_cast<osg::State *>(0))) return;
        }

        // if this tile is marked dirty, bump the marker so the engine knows it
        // needs replacing.
        if ( _dirty || _model->_revision != _maprevision )
        {
            _outOfDate = true;
        }

        // reset the "birth" time if necessary - this is the time at which the 
        // node passes cull (not multi-view compatible)
        const osg::FrameStamp* fs = nv.getFrameStamp();
        if ( fs )
        {
            unsigned frame = fs->getFrameNumber();

            if ( (frame - _lastTraversalFrame > 1) || (_bornTime == 0.0) )
            {
                _bornTime = fs->getReferenceTime();
                _bornUniform->set( (float)_bornTime );
            }

            _lastTraversalFrame = frame;
        }
    }

    osg::MatrixTransform::traverse( nv );
}
Example #19
0
	void Bar::traverse(osg::NodeVisitor& nv) {
		if (nv.getVisitorType() == osg::NodeVisitor::CULL_VISITOR) {
			float time = nv.getFrameStamp()->getReferenceTime();
			float dt = time-_time;
			_time = time;
			
			if (_valueptr)
				setValue(*_valueptr);
			if (_markptr)
				setMark(*_markptr);
			
			if (_drawmark) {
				// Make mark follow bar
				if (_markmode != STATIC && _mark < _value) {
					_mark = _value;
					_marktime = _time;
				}
				// Make mark fall after delay has run out
				if (_time - _marktime > _markdelay) {
					if (_markmode == FALL) {
						if (_mark > _value)
							_mark -= _markrate*dt;
						update();
					}
				}
			}
			if (_time - _bartime > _bardelay) {
				if (_barmode == FALL) {
					if (_value > 0)
						_value -= _barrate*dt;
					if (_value < 0)
						_value = 0;
					update();
				}
			}
		}
	}
        void traverse(osg::NodeVisitor& nv)
        {
            if (nv.getVisitorType() == nv.UPDATE_VISITOR)
            {
                if ( (nv.getFrameStamp()->getFrameNumber() % 2) == 0 )
                {
                    _toggle = !_toggle;

                    VirtualProgram* vp = VirtualProgram::getOrCreate(this->getOrCreateStateSet());
                    if ( _toggle )
                    {
                        vp->setFunction(
                            "make_it_red", fragShader,
                            osgEarth::ShaderComp::LOCATION_FRAGMENT_COLORING,
                            new Acceptor() );
                    }
                    else
                    {
                        vp->removeShader("make_it_red");
                    }
                }
            }
            osg::Group::traverse(nv);
        }
Example #21
0
void
GeometryPool::traverse(osg::NodeVisitor& nv)
{
    if (nv.getVisitorType() == nv.UPDATE_VISITOR && _releaser.valid() && _enabled)
    {
        // look for usused pool objects and push them to the resource releaser.
        ResourceReleaser::ObjectList objects;
        {
            Threading::ScopedMutexLock exclusive( _geometryMapMutex );

            std::vector<GeometryKey> keys;

            for (GeometryMap::iterator i = _geometryMap.begin(); i != _geometryMap.end(); ++i)
            {
                if (i->second.get()->referenceCount() == 1)
                {
                    keys.push_back(i->first);
                    objects.push_back(i->second.get());
                    
                    //OE_INFO << "Releasing: " << i->second.get() << std::endl;
                }
            }
            for (std::vector<GeometryKey>::iterator key = keys.begin(); key != keys.end(); ++key)
            {
                _geometryMap.erase(*key);
            }
        }

        if (!objects.empty())
        {
            _releaser->push(objects);
        }
    }

    osg::Group::traverse(nv);
}
Example #22
0
void Page::traverse(osg::NodeVisitor& nv)
{
    // if app traversal update the frame count.
    if (nv.getVisitorType()==osg::NodeVisitor::UPDATE_VISITOR)
    {
        const osg::FrameStamp* framestamp = nv.getFrameStamp();
        if (framestamp)
        {
            double t = framestamp->getSimulationTime();
            
            if (_rotation!=_targetRotation)
            {
                if (t>=_targetTime) _rotation = _targetRotation;
                else _rotation += (_targetRotation-_rotation)*(t-_lastTimeTraverse)/(_targetTime-_lastTimeTraverse);
                
                dirtyBound();
            }
            
            _lastTimeTraverse = t;

        }
    }
    Transform::traverse(nv);
}
Example #23
0
void
OverlayDecorator::traverse( osg::NodeVisitor& nv )
{
    if ( true ) //if (_totalOverlayChildren > 0 )
    {
        // in the CULL traversal, find the per-view data associated with the 
        // cull visitor's current camera view and work with that:
        if ( nv.getVisitorType() == nv.CULL_VISITOR )
        {
            osgUtil::CullVisitor* cv = static_cast<osgUtil::CullVisitor*>( &nv );
            osg::Camera* camera = cv->getCurrentCamera();

            if ( camera != 0L && (_rttTraversalMask & nv.getTraversalMask()) != 0 )
            {
                PerViewData& pvd = getPerViewData( camera );

                //TODO:
                // check whether we need to recalculate the RTT camera params.
                // don't do it if the main camera hasn't moved;
                // also, tell the ClampingTech not to re-snap the depth texture
                // unless something has changed (e.g. camera params, terrain bounds..?
                // what about paging..?)

                // technique-specific setup prior to traversing:
                for(unsigned i=0; i<_techniques.size(); ++i)
                {
                    _techniques[i]->preCullTerrain( pvd._techParams[i], cv );
                }

                // shared terrain culling pass:
                cullTerrainAndCalculateRTTParams( cv, pvd );

                // prep and traverse the RTT camera(s):
                for(unsigned i=0; i<_techniques.size(); ++i)
                {
                    TechRTTParams& params = pvd._techParams[i];
                    _techniques[i]->cullOverlayGroup( params, cv );
                }
            }
            else
            {
                osg::Group::traverse(nv);
            }
        }

        else
        {
            // Some other type of visitor (like update or intersection). Skip the technique
            // and traverse the geometry directly.
            for(unsigned i=0; i<_overlayGroups.size(); ++i)
            {
                _overlayGroups[i]->accept( nv );
            }

            osg::Group::traverse( nv );
        }
    }
    else
    {
        osg::Group::traverse( nv );
    }
}
Example #24
0
void
OverlayNode::traverse( osg::NodeVisitor& nv )
{
    if ( !_overlayProxyContainer.valid() )
    {
        osg::Group::traverse( nv );
    }
    else
    {
        if ( nv.getVisitorType() == osg::NodeVisitor::CULL_VISITOR )
        {
            if ( _active )
            {
                // do nothing -- culling will happen via the OverlayProxy instead.
            }
            else
            {
                // for a non-active node, just traverse children as usual.
                osg::Group::traverse( nv );
            }
        }

        else if ( nv.getVisitorType() == osg::NodeVisitor::UPDATE_VISITOR )
        {
            if ( _dirty )
            {
                applyChanges();
                _dirty = false;
                ADJUST_UPDATE_TRAV_COUNT( this, -1 );
            }
            
            // traverse children directly, regardles of active status
            osg::Group::traverse( nv );
        }

        else if (dynamic_cast<osgUtil::IntersectionVisitor*>(&nv))
        {
            /*
               In order to properly intersect with overlay geometries, attempt to find the point on the terrain where the pick occurred
               cast a second intersector vertically at that point.

               Currently this is only imlpemented for our custom PrimitiveIntersector.
            */
            osgUtil::IntersectionVisitor* iv = dynamic_cast<osgUtil::IntersectionVisitor*>(&nv);
            osgEarth::PrimitiveIntersector* pi = dynamic_cast<osgEarth::PrimitiveIntersector *>(iv->getIntersector());

            osg::ref_ptr<MapNode> mapNode;
            if (pi && !pi->getOverlayIgnore() && _mapNode.lock(mapNode))
            { 
                osg::NodePath path = iv->getNodePath();
                osg::NodePath prunedNodePath( path.begin(), path.end()-1 );
                osg::Matrix modelToWorld = osg::computeLocalToWorld(prunedNodePath);
                osg::Vec3d worldStart = pi->getStart() * modelToWorld;
                osg::Vec3d worldEnd = pi->getEnd() * modelToWorld;

                osg::ref_ptr<DPLineSegmentIntersector> lsi = new DPLineSegmentIntersector(worldStart, worldEnd);
                osgUtil::IntersectionVisitor ivTerrain(lsi.get());
                mapNode->getTerrainEngine()->accept(ivTerrain);

                if (lsi->containsIntersections())
                {
                  osg::Vec3d worldIntersect = lsi->getFirstIntersection().getWorldIntersectPoint();
                  
                  GeoPoint mapIntersect;
                  mapIntersect.fromWorld(mapNode->getMapSRS(), worldIntersect);

                  osg::Vec3d newMapStart(mapIntersect.x(), mapIntersect.y(), 25000.0);
                  osg::Vec3d newMapEnd(mapIntersect.x(), mapIntersect.y(), -25000.0);

                  osg::Vec3d newWorldStart;
                  mapNode->getMapSRS()->transformToWorld(newMapStart, newWorldStart);

                  osg::Vec3d newWorldEnd;
                  mapNode->getMapSRS()->transformToWorld(newMapEnd, newWorldEnd);

                  osg::Matrix worldToModel;
                  worldToModel.invert(modelToWorld);

                  osg::Vec3d newModelStart = newWorldStart * worldToModel;
                  osg::Vec3d newModelEnd = newWorldEnd * worldToModel;

                  osg::ref_ptr<osgEarth::PrimitiveIntersector> pi2 = new osgEarth::PrimitiveIntersector(osgUtil::Intersector::MODEL, newModelStart, newModelEnd, pi->getThickness(), true);
                  osgUtil::IntersectionVisitor iv2(pi2);
                  iv2.setTraversalMask(iv->getTraversalMask());
                  path[0]->accept(iv2);

                  if (pi2->containsIntersections())
                  {
                    // Insert newlly found intersections into the original intersector.
                    for (PrimitiveIntersector::Intersections::iterator it = pi2->getIntersections().begin(); it != pi2->getIntersections().end(); ++it)
                    {
                      PrimitiveIntersector::Intersection intersection(*it);
                      intersection.ratio = 1.0;
                      pi->insertIntersection(intersection);
                    }
                  }
                }
                else
                {
                  //OE_WARN << LC << "No hits on terrain!" << std::endl;
                }
            }
            else
            {
              osg::Group::traverse( nv );
            }
        }

        // handle other visitor types (like intersections, etc) by simply
        // traversing the child graph.
        else // if ( nv.getNodeVisitor() == osg::NodeVisitor::NODE_VISITOR )
        {
            osg::Group::traverse( nv );
        }
    }
}
Example #25
0
void SoundNode::traverse(osg::NodeVisitor &nv)
{
    // continue only if the visitor actually is a cull visitor
    if (nv.getVisitorType() == osg::NodeVisitor::CULL_VISITOR)
    {
        // Make sure we only execute this once during this frame.
        // There could be two or more culls for stereo/multipipe...
        if (!m_sound_state.valid()) {
            // call the inherited method
            osg::notify(osg::DEBUG_INFO) << "SoundNode::traverse() No soundstate attached to soundnode" << std::endl;
            Node::traverse(nv);
            return;
        }
        if ( m_sound_state.valid() && nv.getTraversalNumber() != m_last_traversal_number && nv.getFrameStamp())
        {

            m_last_traversal_number = nv.getTraversalNumber();

            // retrieve the current time
            double t = nv.getFrameStamp()->getReferenceTime();
            double time = t - m_last_time;

            if(time >= m_sound_manager->getUpdateFrequency()) {

                osg::Matrix m;
                m = osg::computeLocalToWorld(nv.getNodePath());

                osg::Vec3 pos = m.getTrans();

                m_sound_state->setPosition(pos);

                //Calculate velocity
                osg::Vec3 velocity(0,0,0);

                if (m_first_run) {
                    m_first_run = false;
                    m_last_time = t;
                    m_last_pos = pos;
                }
                else {
                    velocity = pos - m_last_pos;
                    m_last_pos = pos;
                    m_last_time = t;
                    velocity /= time;
                }

                if(m_sound_manager->getClampVelocity()) {
                    float max_vel = m_sound_manager->getMaxVelocity();
                    float len = velocity.length();
                    if ( len > max_vel) {
                        velocity.normalize();
                        velocity *= max_vel;
                    }
                }

                m_sound_state->setVelocity(velocity);

                //Get new direction
                osg::Vec3 dir(0,1,0);

                dir = dir * m;
                dir.normalize();
                m_sound_state->setDirection(dir);      

                // Only do occlusion calculations if the sound is playing
                if (m_sound_state->getPlay() && m_occlude_callback.valid())
                    m_occlude_callback->apply(m_sound_manager->getListenerMatrix(), pos, m_sound_state.get());
            } // if
        }
    } // if cullvisitor

    // call the inherited method
    Node::traverse(nv);
}
Example #26
0
void
DrapingCullSet::accept(osg::NodeVisitor& nv)
{
    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        osgUtil::CullVisitor* cv = static_cast<osgUtil::CullVisitor*>( &nv );

        // We will use the visitor's path to prevent doubely-applying the statesets
        // of common ancestors
        const osg::NodePath& nvPath = nv.getNodePath();

        int frame = nv.getFrameStamp() ? nv.getFrameStamp()->getFrameNumber() : 0u;

        for( std::vector<Entry>::iterator entry = _entries.begin(); entry != _entries.end(); ++entry )
        {
            if ( frame - entry->_frame > 1 )
                continue;

            // If there's an active (non-identity matrix), apply it
            if ( entry->_matrix.valid() )
            {
                entry->_matrix->postMult( *cv->getModelViewMatrix() );
                cv->pushModelViewMatrix( entry->_matrix.get(), osg::Transform::RELATIVE_RF );
            }

            // After pushing the matrix, we can perform the culling bounds test.
            if ( !cv->isCulled( entry->_node->getBound() ) )
            {
                // Apply the statesets in the entry's node path, but skip over the ones that are
                // shared with the current visitor's path since they are already in effect.
                // Count them so we can pop them later.
                int numStateSets = 0;
                osg::RefNodePath nodePath;
                if ( entry->_path.getRefNodePath(nodePath) )
                {
                    for(unsigned i=0; i<nodePath.size(); ++i)
                    {
                        if (nodePath[i].valid())
                        {
                            if (i >= nvPath.size() || nvPath[i] != nodePath[i].get())
                            {
                                osg::StateSet* stateSet = nodePath[i]->getStateSet();
                                if ( stateSet )
                                {
                                    cv->pushStateSet( stateSet );
                                    ++numStateSets;
                                }
                            }
                        }
                    }
                }

                // Cull the DrapeableNode's children (but not the DrapeableNode itself!)
                // TODO: make sure we aren't skipping any cull callbacks, etc. by calling traverse 
                // instead of accept. (Cannot call accept b/c that calls traverse)
                for(unsigned i=0; i<entry->_node->getNumChildren(); ++i)
                {
                    entry->_node->getChild(i)->accept( nv );
                }
            
                // pop the same number we pushed
                for(int i=0; i<numStateSets; ++i)
                {
                    cv->popStateSet();
                }
            }

            // pop the model view:
            if ( entry->_matrix.valid() )
            {
                cv->popModelViewMatrix();
            }
        }

        // mark this set so it will reset for the next frame
        _frameCulled = true;
    }

    else
    {
        for( std::vector<Entry>::iterator entry = _entries.begin(); entry != _entries.end(); ++entry )
        {
            
        }
    }
}
Example #27
0
void
RexTerrainEngineNode::traverse(osg::NodeVisitor& nv)
{
    if ( nv.getVisitorType() == nv.UPDATE_VISITOR && _quickReleaseInstalled == false )
    {
        osg::Camera* cam = findFirstParentOfType<osg::Camera>( this );
        if ( cam )
        {
            // get the installed PDC so we can nest them:
            osg::Camera::DrawCallback* cbToNest = cam->getPostDrawCallback();

            // if it's another QR callback, we'll just replace it.
            QuickReleaseGLObjects* previousQR = dynamic_cast<QuickReleaseGLObjects*>(cbToNest);
            if ( previousQR )
                cbToNest = previousQR->_next.get();

            cam->setPostDrawCallback( new QuickReleaseGLObjects(_deadTiles.get(), cbToNest) );

            _quickReleaseInstalled = true;
            OE_INFO << LC << "Quick release enabled" << std::endl;

            // knock down the trav count set in the constructor.
            ADJUST_UPDATE_TRAV_COUNT( this, -1 );
        }
    }

    if ( nv.getVisitorType() == nv.CULL_VISITOR )
    {
        // Inform the registry of the current frame so that Tiles have access
        // to the information.
        if ( _liveTiles.valid() && nv.getFrameStamp() )
        {
            _liveTiles->setTraversalFrame( nv.getFrameStamp()->getFrameNumber() );
        }
    }

#if 0
    static int c = 0;
    if ( ++c % 60 == 0 )
    {
        OE_NOTICE << LC << "Live = " << _liveTiles->size() << ", Dead = " << _deadTiles->size() << std::endl;
        _liveTiles->run( CheckForOrphans() );
    }
#endif
    
    if ( _loader.valid() ) // ensures that postInitialize has run
    {
        TraversalData* tdata = TraversalData::get(nv);
        if ( tdata )
        {
            RefUID& uid = tdata->getOrCreate<RefUID>("landcover.zone");
            getEngineContext()->_landCoverData->_currentZoneIndex = uid;
        }

        // Pass the tile creation context to the traversal.
        osg::ref_ptr<osg::Referenced> data = nv.getUserData();
        nv.setUserData( this->getEngineContext() );

        osgUtil::CullVisitor* cv = static_cast<osgUtil::CullVisitor*>(&nv);

        this->getEngineContext()->startCull( cv );
        TerrainEngineNode::traverse( nv );
        this->getEngineContext()->endCull( cv );

        if ( data.valid() )
            nv.setUserData( data.get() );
    }

    else
    {
        TerrainEngineNode::traverse( nv );
    }
}
Example #28
0
void
ShadowCaster::traverse(osg::NodeVisitor& nv)
{
    if (_supported                             && 
        nv.getVisitorType() == nv.CULL_VISITOR && 
        _castingGroup->getNumChildren() > 0    && 
        _shadowmap.valid() )
    {
        osgUtil::CullVisitor* cv = Culling::asCullVisitor(nv);
        osg::Camera* camera = cv->getCurrentCamera();
        if ( camera )
        {
            osg::Matrix MV = *cv->getModelViewMatrix();
            osg::Matrix inverseMV;
            inverseMV.invert(MV);

            osg::Vec3d camEye, camTo, camUp;
            MV.getLookAt( camEye, camTo, camUp, 1.0 );

            // position the light. We only really care about the directional vector.
            osg::Vec4d lp4 = _light->getPosition();
            osg::Vec3d lightVectorWorld( -lp4.x(), -lp4.y(), -lp4.z() );
            lightVectorWorld.normalize();
            osg::Vec3d lightPosWorld = osg::Vec3d(0,0,0) * inverseMV;
            //osg::Vec3d lightPosWorld( lp4.x(), lp4.y(), lp4.z() ); // jitter..

            // construct the view matrix for the light. The up vector doesn't really
            // matter so we'll just use the camera's.
            osg::Matrix lightViewMat;
            osg::Vec3d lightUp(0,0,1);
            osg::Vec3d side = lightVectorWorld ^ lightUp;
            lightUp = side ^ lightVectorWorld;
            lightUp.normalize();
            lightViewMat.makeLookAt(lightPosWorld, lightPosWorld+lightVectorWorld, lightUp);
            
            //int i = nv.getFrameStamp()->getFrameNumber() % (_ranges.size()-1);
            int i;
            for(i=0; i < (int) _ranges.size()-1; ++i)
            {
                double n = _ranges[i];
                double f = _ranges[i+1];

                // take the camera's projection matrix and clamp it's near and far planes
                // to our shadow map slice range.
                osg::Matrix proj = _prevProjMatrix;
                //cv->clampProjectionMatrix(proj, n, f);
                double fovy,ar,zn,zf;
                proj.getPerspective(fovy,ar,zn,zf);
                proj.makePerspective(fovy,ar,std::max(n,zn),std::min(f,zf));
                
                // extract the corner points of the camera frustum in world space.
                osg::Matrix MVP = MV * proj;
                osg::Matrix inverseMVP;
                inverseMVP.invert(MVP);
                osgShadow::ConvexPolyhedron frustumPH;
                frustumPH.setToUnitFrustum(true, true);
                frustumPH.transform( inverseMVP, MVP );
                std::vector<osg::Vec3d> verts;
                frustumPH.getPoints( verts );

                // project those on to the plane of the light camera and fit them
                // to a bounding box. That box will form the extent of our orthographic camera.
                osg::BoundingBoxd bbox;
                for( std::vector<osg::Vec3d>::iterator v = verts.begin(); v != verts.end(); ++v )
                    bbox.expandBy( (*v) * lightViewMat );

                osg::Matrix lightProjMat;
                n = -std::max(bbox.zMin(), bbox.zMax());
                f = -std::min(bbox.zMin(), bbox.zMax());
                lightProjMat.makeOrtho(bbox.xMin(), bbox.xMax(), bbox.yMin(), bbox.yMax(), n, f);

                // configure the RTT camera for this slice:
                _rttCameras[i]->setViewMatrix( lightViewMat );
                _rttCameras[i]->setProjectionMatrix( lightProjMat );

                // this xforms from clip [-1..1] to texture [0..1] space
                static osg::Matrix s_scaleBiasMat = 
                    osg::Matrix::translate(1.0,1.0,1.0) * 
                    osg::Matrix::scale(0.5,0.5,0.5);
                
                // set the texture coordinate generation matrix that the shadow
                // receiver will use to sample the shadow map. Doing this on the CPU
                // prevents nasty precision issues!
                osg::Matrix VPS = lightViewMat * lightProjMat * s_scaleBiasMat;
                _shadowMapTexGenUniform->setElement(i, inverseMV * VPS);
            }

            // install the shadow-casting traversal mask:
            unsigned saveMask = cv->getTraversalMask();
            cv->setTraversalMask( _traversalMask & saveMask );

            // render the shadow maps.
            cv->pushStateSet( _rttStateSet.get() );
            for(i=0; i < (int) _rttCameras.size(); ++i)
            {
                _rttCameras[i]->accept( nv );
            }
            cv->popStateSet();

            // restore the previous mask
            cv->setTraversalMask( saveMask );
            
            // render the shadowed subgraph.
            cv->pushStateSet( _renderStateSet.get() );
            osg::Group::traverse( nv );
            cv->popStateSet();

            // save the projection matrix for the next frame.
            _prevProjMatrix = *cv->getProjectionMatrix();

            return;
        }
    }

    osg::Group::traverse(nv);
}
Example #29
0
void Compositor::traverse( osg::NodeVisitor& nv )
{
    if ( nv.getVisitorType()==osg::NodeVisitor::CULL_VISITOR )
    {
        osgUtil::CullVisitor* cv = static_cast<osgUtil::CullVisitor*>( &nv );
        osg::RefMatrix* projectionMatrix = cv->getProjectionMatrix();
        if ( _inbuiltUniforms.size()>0 )
        {
            double fovy = 0.0, aspectRatio = 0.0, zNear = 0.0, zFar = 0.0;
            if ( projectionMatrix ) projectionMatrix->getPerspective( fovy, aspectRatio, zNear, zFar );
            if ( _preservedZNear!=FLT_MAX ) zNear = _preservedZNear;
            if ( _preservedZFar!=-FLT_MAX ) zFar = _preservedZFar;
            
            for ( InbuiltUniformList::const_iterator itr=_inbuiltUniforms.begin();
                  itr!=_inbuiltUniforms.end(); ++itr )
            {
                if ( !itr->second ) continue;
                switch ( itr->first )
                {
                case EYE_POSITION:
                    itr->second->set( cv->getEyeLocal() );
                    break;
                case VIEW_POINT:
                    itr->second->set( cv->getViewPointLocal() );
                    break;
                case LOOK_VECTOR:
                    itr->second->set( cv->getLookVectorLocal() );
                    break;
                case UP_VECTOR:
                    itr->second->set( cv->getUpLocal() );
                    break;
                case LEFT_VECTOR:
                    itr->second->set( cv->getLookVectorLocal() ^ cv->getUpLocal() );
                    break;
                case VIEWPORT_X:
                    if ( cv->getViewport() ) itr->second->set( (float)cv->getViewport()->x() );
                    break;
                case VIEWPORT_Y:
                    if ( cv->getViewport() ) itr->second->set( (float)cv->getViewport()->y() );
                    break;
                case VIEWPORT_WIDTH:
                    if ( cv->getViewport() ) itr->second->set( (float)cv->getViewport()->width() );
                    break;
                case VIEWPORT_HEIGHT:
                    if ( cv->getViewport() ) itr->second->set( (float)cv->getViewport()->height() );
                    break;
                case WINDOW_MATRIX:
                    itr->second->set( osg::Matrixf(cv->getWindowMatrix()) );
                    break;
                case INV_WINDOW_MATRIX:
                    itr->second->set( osg::Matrixf::inverse(cv->getWindowMatrix()) );
                    break;
                case FRUSTUM_NEAR_PLANE:
                    itr->second->set( (float)zNear );
                    break;
                case FRUSTUM_FAR_PLANE:
                    itr->second->set( (float)zFar );
                    break;
                case SCENE_FOV_IN_RADIANS:
                    itr->second->set( (float)osg::DegreesToRadians(fovy) );
                    break;
                case SCENE_ASPECT_RATIO:
                    itr->second->set( (float)aspectRatio );
                    break;
                case SCENE_MODELVIEW_MATRIX:
                    if ( cv->getModelViewMatrix() ) itr->second->set( osg::Matrixf(*cv->getModelViewMatrix()) );
                    break;
                case SCENE_INV_MODELVIEW_MATRIX:
                    if ( cv->getModelViewMatrix() ) itr->second->set( osg::Matrixf::inverse(*cv->getModelViewMatrix()) );
                    break;
                case SCENE_PROJECTION_MATRIX:
                    if ( projectionMatrix ) itr->second->set( osg::Matrixf(*projectionMatrix) );
                    break;
                case SCENE_INV_PROJECTION_MATRIX:
                    if ( projectionMatrix ) itr->second->set( osg::Matrixf::inverse(*projectionMatrix) );
                    break;
                default: break;
                }
            }
        }
        traverseAllPasses( nv );
        return;  // don't traverse as usual
    }
    
    if ( nv.getVisitorType()==osg::NodeVisitor::UPDATE_VISITOR ||
         nv.getVisitorType()==osg::NodeVisitor::EVENT_VISITOR )
    {
        traverseAllPasses( nv );  // just handle uniform callbacks
    }
    osg::Group::traverse( nv );
}
Example #30
0
void
PagerLoader::traverse(osg::NodeVisitor& nv)
{
    // only called when _mergesPerFrame > 0
    if ( nv.getVisitorType() == nv.UPDATE_VISITOR )
    {
        if ( nv.getFrameStamp() )
        {
            setFrameStamp(nv.getFrameStamp());
        }

        int count;
        for(count=0; count < _mergesPerFrame && !_mergeQueue.empty(); ++count)
        {
            Request* req = _mergeQueue.begin()->get();
            if ( req && req->_lastTick >= _checkpoint )
            {
                OE_START_TIMER(req_apply);
                req->apply( getFrameStamp() );
                double s = OE_STOP_TIMER(req_apply);

                req->setState(Request::FINISHED);
            }

            _mergeQueue.erase( _mergeQueue.begin() );
        }

        // cull finished requests.
        {
            Threading::ScopedMutexLock lock( _requestsMutex );

            unsigned fn = 0;
            if ( nv.getFrameStamp() )
                fn = nv.getFrameStamp()->getFrameNumber();

            // Purge expired requests.
            for(Requests::iterator i = _requests.begin(); i != _requests.end(); )
            {
                Request* req = i->second.get();

                if ( req->isFinished() )
                {
                    //OE_INFO << LC << req->getName() << "(" << i->second->getUID() << ") finished." << std::endl; 
                    req->setState( Request::IDLE );
                    if ( REPORT_ACTIVITY )
                        Registry::instance()->endActivity( req->getName() );
                    _requests.erase( i++ );
                }

                else if ( !req->isMerging() && (fn - req->getLastFrameSubmitted() > 2) )
                {
                    //OE_INFO << LC << req->getName() << "(" << i->second->getUID() << ") died waiting after " << fn-req->getLastFrameSubmitted() << " frames" << std::endl; 
                    req->setState( Request::IDLE );
                    if ( REPORT_ACTIVITY )
                        Registry::instance()->endActivity( req->getName() );
                    _requests.erase( i++ );
                }

                else // still valid.
                {
                    ++i;
                }
            }

            //OE_NOTICE << LC << "PagerLoader: requests=" << _requests.size() << "; mergeQueue=" << _mergeQueue.size() << std::endl;
        }
    }

    LoaderGroup::traverse( nv );
}