WorldWind源码剖析系列:WorldWind瓦片调度策略说明

1 基于源码的分析

首先我们来看WorldWind中摄像头变化相关的几个方法的内部逻辑。

1.1 NltTerrainAccessor. GetElevationAt

方法声明:public override float GetElevationAt(double latitude, double longitude, double targetSamplesPerDegree)。

当摄像头高度低于30万米时,才开始显示地面海拔高度值。根据摄像头的经纬度和视野范围(100/视野范围作为计算级别的标准,即每度坐标代表的高程数据跨度)计算取哪个级别、哪个瓦片的地形数据。进而得到该块的cache存放目录,读取cache文件得到高程矩阵。如果cache中没有该瓦片则从服务下载瓦片到cache中。最后计算当前经纬度的海拔高度值。

1.2 CameraBase. Update

方法声明:public virtual void Update(Device device)。

摄像头的视野范围算法,其中弧度计算公式为abs(sin(摄像头的高度/球的半径))*2;度计算公式为abs(sin(摄像头的高度/球的半径))*2*180/3.14。

1.3 QuadTileSet. Update

方法声明:public override void Update(DrawArgs drawArgs)。

如果摄像头的视野范围大于2* TileDrawDistance *LevelZeroTileSizeDegrees,则不显示任何瓦片,同时清空下载请求列表。遥感影像的LevelZeroTileSizeDegrees设置为2.25,地形为18,国界线为36,单位均为度。TileDrawDistance的值系统默认为3.5,即当视野的范围大于7个0级瓦片时,不进行加载显示。因为摄像头的前俯视角度默认为45度,所以图像的0级显示高度为2.25*7*111.13*0.5=875.149km(估算)。

2 调度策略

WorldWind按如下策略调度瓦片:

1) 启动新线程对球体进行遍历更新,根据摄像头的视野范围判断是否需要加载瓦片。如果需要,清空瓦片调度表里面不在当前显示区域范围内的瓦片,并进行瓦片调度

2) 瓦片更新跨度为4,即每次更新的瓦片队列为一个0级的6*6的瓦片矩阵,如下图所示。第一轮,更新加载摄像头经纬度所在瓦片,即下图中0所示瓦片;第二轮、三轮、四轮依次更新数字为1、2、3的瓦片。每轮的策略均为从左到右,从下到上。

 

图1瓦片更新轮次图

3) 更新单个瓦片的调度流程如下图所示。

 

图2单瓦片调度流程图

对于上图,在此做以下说明:

a) 初始时,在earth中有Images和Boundaries两种子集。系统对这两个子集遍历调度;

b) 调度表为系统要渲染的瓦片集合;

c) 下载最优算法:在屏幕中占有面积最大的瓦片优先调度下载;

d) 条件a:镜头的视野范围小于2*3.5*块大小并且镜头到块的中心点的距离要小于2.9*块大小*1.25并且块在显示区域范围内;

e) 条件b:镜头的视野范围小于3.5*块大小并且镜头到块的中心点的距离小于2.9*块大小并且块在显示区域范围内。该条件的业务含义是镜头视野范围每缩小一倍,显示级别增加一级,离镜头距离大于2.9个块大小的块,显示级别要低一级。

————————————————

版权声明:本文为CSDN博主「李明子」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。

原文链接:https://blog.csdn.net/free1985/article/details/77440207

猜你喜欢

转载自www.cnblogs.com/rainbow70626/p/12099832.html