Example #1
0
bool
TileSource::hasData(const osgEarth::TileKey& key) const
{
    //sematics: might have data.

    //If no data extents are provided, just return true
    if (_dataExtents.size() == 0) 
        return true;

    const osgEarth::GeoExtent& keyExtent = key.getExtent();
    bool intersectsData = false;

    for (DataExtentList::const_iterator itr = _dataExtents.begin(); itr != _dataExtents.end(); ++itr)
    {
        if ((keyExtent.intersects( *itr )) && 
            (!itr->minLevel().isSet() || itr->minLevel() <= key.getLOD()) &&
            (!itr->maxLevel().isSet() || itr->maxLevel() >= key.getLOD()))
        {
            intersectsData = true;
            break;
        }
    }

    return intersectsData;
}
void 
PolyhedralLineOfSightNode::terrainChanged(const osgEarth::TileKey& tileKey,
                                          osg::Node*               patch)
{
    if ( tileKey.getExtent().intersects(_extent) )
    {
        updateSamples();
    }
}
bool
TileSource::hasData(const osgEarth::TileKey& key) const
{
    //sematics: "might have data"

    if ( !key.valid() )
        return false;

    // If no data extents are provided, and there's no data level override,
    // return true because there might be data but there's no way to tell.
    if (_dataExtents.size() == 0 && !_options.maxDataLevel().isSet())
    {
        return true;
    }

    unsigned int lod = key.getLevelOfDetail();

    // Remap the lod to an appropriate lod if it's not in the same SRS        
    if (!key.getProfile()->isHorizEquivalentTo( getProfile() ) )
    {        
        lod = getProfile()->getEquivalentLOD( key.getProfile(), key.getLevelOfDetail() );        
    }

    // If there's an explicit LOD override and we've exceeded it, no data.
    if (_options.maxDataLevel().isSet() && lod > _options.maxDataLevel().value())
    {
        return false;
    }

    // If there are no extents to check, there might be data.
    if (_dataExtents.size() == 0)
    {
        return true;
    }

    bool intersectsData = false;
    const osgEarth::GeoExtent& keyExtent = key.getExtent();
    
    for (DataExtentList::const_iterator itr = _dataExtents.begin(); itr != _dataExtents.end(); ++itr)
    {
        if ((keyExtent.intersects( *itr )) && 
            (!itr->minLevel().isSet() || itr->minLevel() <= lod ) &&
            (!itr->maxLevel().isSet() || itr->maxLevel() >= lod ))
        {
            intersectsData = true;
            break;
        }
    }

    return intersectsData;
}
Example #4
0
void TerrainProfileCalculator::onTileAdded(const osgEarth::TileKey& tileKey, osg::Node* graph, TerrainCallbackContext&)
{
    if (_start.isValid() && _end.isValid())
    {
        GeoExtent extent( _start.getSRS());
        extent.expandToInclude(_start.x(), _start.y());
        extent.expandToInclude(_end.x(), _end.y());

        if (tileKey.getExtent().intersects( extent ))
        {
            recompute();
        }
    }
}
Example #5
0
    virtual void onTileAdded(const osgEarth::TileKey& tileKey, osg::Node* terrain, TerrainCallbackContext&)
    {           
        if ((int)tileKey.getLevelOfDetail() > _minLevel && _maxLevel < (int)tileKey.getLevelOfDetail())
        {
            osg::Vec3d position = _locator->getLocator()->getPosition();

            if (tileKey.getExtent().contains(position.x(), position.y()))
            {
                //Compute our location in geocentric
                const osg::EllipsoidModel* ellipsoid = tileKey.getProfile()->getSRS()->getEllipsoid();
                double x, y, z;            
                ellipsoid->convertLatLongHeightToXYZ(
                    osg::DegreesToRadians(position.y()), osg::DegreesToRadians(position.x()), 0,
                    x, y, z);
                //Compute the up vector
                osg::Vec3d up = ellipsoid->computeLocalUpVector(x, y, z );
                up.normalize();
                osg::Vec3d world(x, y, z);

                double segOffset = 50000;

                osg::Vec3d start = world + (up * segOffset);
                osg::Vec3d end = world - (up * segOffset);

                osgUtil::LineSegmentIntersector* i = new osgUtil::LineSegmentIntersector( start, end );

                osgUtil::IntersectionVisitor iv;            
                iv.setIntersector( i );
                terrain->accept( iv );

                osgUtil::LineSegmentIntersector::Intersections& results = i->getIntersections();
                if ( !results.empty() )
                {
                    const osgUtil::LineSegmentIntersector::Intersection& result = *results.begin();
                    osg::Vec3d hit = result.getWorldIntersectPoint();
                    double lat, lon, height;
                    ellipsoid->convertXYZToLatLongHeight(hit.x(), hit.y(), hit.z(), 
                        lat, lon, height);                
                    position.z() = height;
                    //OE_NOTICE << "Got hit, setting new height to " << height << std::endl;
                    _maxLevel = tileKey.getLevelOfDetail();
                    _locator->getLocator()->setPosition( position );
                }            
            }            
        }            

    }
Example #6
0
bool
TileSource::hasData(const osgEarth::TileKey& key) const
{
    //If no data extents are provided, just return true
    if (_dataExtents.size() == 0) return true;

    const osgEarth::GeoExtent& keyExtent = key.getExtent();
    bool intersectsData = false;

    for (DataExtentList::const_iterator itr = _dataExtents.begin(); itr != _dataExtents.end(); ++itr)
    {
        if (keyExtent.intersects( *itr ) && key.getLevelOfDetail() >= itr->getMinLevel() && key.getLevelOfDetail() <= itr->getMaxLevel())
        {
            intersectsData = true;
            break;
        }
    }

    return intersectsData;
}
bool
TileSource::getBestAvailableTileKey(const osgEarth::TileKey& key,
                                    osgEarth::TileKey&       output) const
{
    // trivial reject
    if ( !key.valid() )
        return false;

    // trivial accept: no data extents = not enough info.
    if (_dataExtents.size() == 0)
    {
        output = key;
        return true;
    }

    // trivial reject: key doesn't intersect the union of data extents at all.
    if ( !getDataExtentsUnion().intersects(key.getExtent()) )
    {
        return false;
    }

    bool     intersects = false;
    unsigned highestLOD = 0;

    // We must use the equivalent lod b/c the key can be in any profile.
    int layerLOD = getProfile()->getEquivalentLOD( key.getProfile(), key.getLOD() );
    
    for (DataExtentList::const_iterator itr = _dataExtents.begin(); itr != _dataExtents.end(); ++itr)
    {
        // check for 2D intersection:
        if (key.getExtent().intersects( *itr ))
        {
            // check that the extent isn't higher-resolution than our key:
            if ( !itr->minLevel().isSet() || layerLOD >= itr->minLevel().get() )
            {
                // Got an intersetion; now test the LODs:
                intersects = true;
                
                // Is the high-LOD set? If not, there's not enough information
                // so just assume our key might be good.
                if ( itr->maxLevel().isSet() == false )
                {
                    output = key;
                    return true;
                }

                // Is our key at a lower or equal LOD than the max key in this extent?
                // If so, our key is good.
                else if ( layerLOD <= itr->maxLevel().get() )
                {
                    output = key;
                    return true;
                }

                // otherwise, record the highest encountered LOD that
                // intersects our key.
                else if ( itr->maxLevel().get() > highestLOD )
                {
                    highestLOD = itr->maxLevel().get();
                }
            }
        }
    }

    if ( intersects )
    {
        output = key.createAncestorKey( highestLOD );
        return true;
    }
    else
    {
        return false;
    }
}