osgEarth的Rex引擎原理分析(四十二)osgEarth::SpatialReference和osgEarth::Profile的关系

本文深入探讨osgEarth中的osgEarth::SpatialReference和osgEarth::Profile的关系。内容涉及Profile的关注点如空间范围、LOD,以及SpatialReference的投影方式、椭球体信息。同时列出一系列关于osgEarth引擎内部机制的问题,包括地理信息引擎节点创建、地形变形、瓦片管理、多线程、缓存等主题。

目标:(三十六)中的问题102

osgEarth::Profile关注空间范围、初始LOD数目等信息。GeoExtent中有SpatialReference信息,因此通过Profile能获取到SpatialReference信息。每一个高程、影像层都有自己的Profile。

osgEarth/Profile
    class OSGEARTH_EXPORT Profile : public osg::Referenced
    {
        GeoExtent   _extent;
        GeoExtent   _latlong_extent;
        unsigned    _numTilesWideAtLod0;
        unsigned    _numTilesHighAtLod0;
        std::string _fullSignature;
        std::string _horizSignature;
    }

osgEarth::SpatialReference关注投影方式、椭球体等信息

osgEarth/SpatialReference
    class OSGEARTH_EXPORT SpatialReference : public osg::Referenced
    {
        bool _initialized;
        void* _handle;
        bool _owns_handle;
        bool _is_geographic;
        bool _is_mercator;
        bool _is_spherical_mercator;
        bool _is_north_polar, _is_south_polar;
        bool _is_cube;
        bool _is_contiguous;
        bool _is_user_defined;
        bool _is_ltp;
        bool _is_plate_carre;
        bool _is_ecef;
        unsigned _ellipsoidId;
        std::string _name;
        Key _key;
        std::string _wkt;
        std::string _proj4;
        std::string _init_type;
        std::string _datum;
        Units       _units;
        osg::ref_ptr<osg::EllipsoidModel> _ellipsoid;
        osg::ref_ptr<SpatialRef
<think>我们正在讨论的是osgEarth中的TMSElevationLayer,特别是setMinLevelsetMaxLevel两个方法。 根据用户的问题,需要说明这两个方法的使用方法、作用以及相关注意事项。 首先,TMSElevationLayer是用于加载TMS(Tile Map Service)格式的高程数据(地形)的图层类。它继承自ElevationLayer,而ElevationLayer又继承自TileLayer。在TileLayer中,有设置最小最大层级的函数。 作用: 1. setMinLevel(unsigned int level): 设置图层加载的最小瓦片级别(层级)。低于此级别的瓦片不会被加载。 2. setMaxLevel(unsigned int level): 设置图层加载的最大瓦片级别(层级)。高于此级别的瓦片不会被加载。 使用方法: 在代码中,可以通过创建TMSElevationLayer的实例,然后调用这两个方法来设置。 注意事项: 1. 级别(Level)从0开始,0级表示最粗粒度的瓦片(覆盖范围最大,分辨率最低),级别越高,瓦片分辨率越高。 2. 设置合理的层级范围可以避免加载不必要的数据,提高性能。 3. 如果设置的最大层级超过了数据源实际提供的最大层级,则不会加载任何数据(或者只会加载到数据源的最大层级,具体取决于驱动实现)。 4. 同样,如果设置的最小层级高于数据源的最小层级,则最低层级的瓦片将不会被加载(可能会显示空白或使用其他图层的数据)。 下面结合代码示例进行说明: 示例代码: ```cpp #include <osgEarth/TMSElevationLayer> #include <osgEarth/Map> // 创建TMS高程图层 osgEarth::TMSElevationLayer* tmsElevation = new osgEarth::TMSElevationLayer(); // 配置TMS的URL tmsElevation->setURL("http://tileserver/tms.xml"); // 假设的TMS服务地址 // 设置最小层级为3,即从第3级开始加载(0,1,2级不加载) tmsElevation->setMinLevel(3); // 设置最大层级为15,即最多加载到第15级(16级及以上不加载) tmsElevation->setMaxLevel(15); // 将图层添加到地图 osgEarth::Map* map = ...; // 获取地图指针 map->addLayer(tmsElevation); ``` 另外,也可以通过TMSOptions来设置: ```cpp #include <osgEarth/TMS> osgEarth::TMSOptions options; options.url() = "http://tileserver/tms.xml"; options.minLevel() = 3; options.maxLevel() = 15; osgEarth::TMSElevationLayer* tmsElevation = new osgEarth::TMSElevationLayer(options); map->addLayer(tmsElevation); ``` 注意事项补充: 1. 在设置层级时,需要确保数据源在指定的层级范围内有数据,否则可能导致地形显示不完整。 2. 当多个高程图层叠加时,每个图层都可以设置自己的层级范围,osgEarth会进行融合。 3. 如果同时设置了TileSource的DataExtent(数据范围,包括层级范围),那么实际加载的层级范围是两者(setMinLevel/setMaxLevelDataExtent)的交集。 引用站内资料: 在引用[2]中提到了osgEarth的缓存机制(MemCache),设置层级范围也会影响缓存的数据量[^2]。 关于性能优化: 合理设置最小最大层级是优化性能的重要手段,避免加载过细或过粗的瓦片,减少内存占用网络请求。 总结: setMinLevelsetMaxLevel用于控制TMSElevationLayer加载瓦片的层级范围,从而控制数据加载的粒度性能。 相关问题: 1. 如何根据当前视图动态调整地形瓦片的加载层级? 2. 在osgEarth中如何合并多个高程图层的显示? 3. osgEarth中地形瓦片的缓存机制是如何工作的?[^2] </think> ### OSGEarth::TMSElevationLayer 中 `setMinLevel` `setMaxLevel` 详解 #### 🎯 作用与功能 这两个方法用于控制 TMS 高程瓦片图层的加载范围: 1. **`setMinLevel(level)`** - 设置**最低加载层级**(最粗糙分辨率) - 低于此层级的瓦片不会被加载 - 例如:`setMinLevel(5)` 表示跳过 0-4 级瓦片 2. **`setMaxLevel(level)`** - 设置**最高加载层级**(最精细分辨率) - 高于此层级的瓦片不会被加载 - 例如:`setMaxLevel(18)` 表示停止加载 19 级及以上瓦片 #### 📝 使用方法 ##### 代码示例 ```cpp #include <osgEarth/TMS> #include <osgEarth/ElevationLayer> // 创建 TMS 高程图层 osgEarth::TMSElevationLayer* tmsLayer = new osgEarth::TMSElevationLayer(); // 设置服务地址(示例URL) tmsLayer->setURL("http://tileserver/{z}/{x}/{y}.terrain"); // 设置层级范围:仅加载 5-18 级瓦片 tmsLayer->setMinLevel(5); // 最低层级 tmsLayer->setMaxLevel(18); // 最高层级 // 添加到地图 osgEarth::Map* map = ...; map->addLayer(tmsLayer); ``` ##### Earth 文件配置 ```xml <elevation name="tms_terrain" driver="tms"> <url>http://tileserver/{z}/{x}/{y}.terrain</url> <min_level>5</min_level> <!-- 最低层级 --> <max_level>18</max_level> <!-- 最高层级 --> </elevation> ``` #### ⚠️ 核心注意事项 1. **层级范围有效性** - 层级值必须满足:$0 \leq \text{minLevel} \leq \text{maxLevel} \leq \text{服务最高层级}$ - 超出实际层级范围会导致空白区域(如 `maxLevel=25` 但服务只支持到 20 级) 2. **性能优化平衡** - **`minLevel` 过高** → 远距离地形粗糙 (示例:`minLevel=10` 时,远山呈块状) - **`maxLevel` 过高** → 内存/显存消耗剧增[^2] (每提升 1 级,瓦片数量增加约 4 倍) 3. **引擎层级限制** osgEarth Rex 引擎默认支持最大 21 级,如需更高层级需修改配置: ```cpp osgEarth::Registry::instance()->setMaxTextureLevel(23); ``` 4. **坐标系一致性** 确保层级定义与 TMS 服务的原始坐标系匹配(如 Web Mercator 的层级定义不同于经纬度坐标系)[^3] 5. **多图层协同** 当多个高程图层叠加时,实际显示层级范围由各图层的 `minLevel/maxLevel` 共同决定 #### 💡 应用场景示例 ```cpp // 根据视点距离动态调整层级 osgEarth::ViewPoint vp = earthManipulator->getViewpoint(); double range = vp.range()->as(osgEarth::Units::METERS); if (range > 10000) { // 远距离:加载粗糙瓦片 tmsLayer->setMinLevel(3); tmsLayer->setMaxLevel(10); } else { // 近距离:加载精细瓦片 tmsLayer->setMinLevel(10); tmsLayer->setMaxLevel(18); } ``` #### 📚 引用说明 - 层级限制影响内存缓存机制[^2] - 与视点距离 (`range`) 协同实现动态加载
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值