平台的强大之处也在于其可以将时间运用到三维地球上,平台不仅仅是3D的地理空间的展示,同时也具备“时间维度”的时序的相关控制,具备空间+时间的管理,可以根据“时间”进行动画、轨迹记录、地球的光照等等所有与时间相关的可视化效果。
1、打开时间相关控件
为了更好理解Clock,我们可以在地图中打开2个Cesium内置时钟Clock相关的控件。
//合并属性参数,可覆盖config.json中的对应配置
var mapOptions = mars3d.Util.merge(options, {
control: {
animation: true, //是否创建 动画小器件,左下角仪表
timeline: true, //是否显示 时间线控件
},
})
//创建三维地球场景
let map = new mars3d.Map('mars3dContainer', mapOptions)
2、时序控制相关对象
2.1 clock时钟对象
map.clock(opens new window)时钟对象,由三维地图内部创建的Clock(opens new window)类,可以对时间维度做相关控制。
clock对象是一个同步系统时间的一个对象,想要实现时间驱动数据的动态化渲染,都需要clock对象去创建一个时间序列。一般来说电脑屏幕的刷新率都是60hz,cesium定义的是每秒刷新60次,每帧需要的时间大概是16.67mm。
Clock中默认开始时间(startTime)为当前时间,终止时间(stopTime)为24小时后,并能获取当前时间(currentTime)。
clock对象的构造器有以下几个常用属性:
- map.clock.shouldAnimate = true : 控制开始和停止
- map.clock.startTime = Cesium.JulianDate.fromIso8601(‘2017-08-25’):开始时间
- map.clock.stopTime = Cesium.JulianDate.fromIso8601(‘2017-08-26’):结束时间
- map.clock.currentTime = Cesium.JulianDate.fromIso8601(‘2017-08-25T12:18:20Z’) :当前时间
- map.clock.multiplier= 2.0:时间速率(快速播放与慢速播放),默认1.0
- map.clock.clockRange = Cesium.ClockRange.UNBOUNDED:表示时间轴达到终点之后的行为, 可选值:CLAMPED 达到终止时间后停止,LOOP_STOP 达到终止时间后重新循环,UNBOUNDED 达到终止时间后继续读秒。
2.2 JulianDate时间类
Clock内部以儒略日(JulianDate)维护时间。其起始日期为公元前4713年1月1日中午12时,这和我们常用的格林威治时间略有不同,主要是天文学家使用。
JulianDate类(opens new window)提供了非常丰富的接口,时间的对比,运算,和格林威治时间的转换等,简单易用,完全满足各类需求。同时内部还可以采用国际原子时(TAI)的方式来记录。3、时序控制的应用
3.1 动态加载时间序列瓦片
所谓时间序列瓦片是指存在多套瓦片,每套瓦片不是单独的,与时间有关。比如我们每天拍摄一遍地球影像,然后把每天的影像都做成一套瓦片,那么一年下来就会有365套瓦片,采用传统方案我们只能写365个页面每个页面加载一天的瓦片。这样非常麻烦,并且没有一个动态变化的效果也无法进行对比。
时间序列瓦片与普通瓦片的区别正在此处。其创建时需要多指定与时间有关的参数。如下: ```javascript //interval表示传入的时间区间,index表示是第几个区间,这两个参数也就分割了times中的完整时间段,所以我们可以给time赋值为任意想要设置的值。 function dataCallback(interval, index) { console.log(index); var time; if (index === 0) {
} else {time = Cesium.JulianDate.toIso8601(interval.stop);
} //返回的是key、value形式,此处Time为key,而其必须与创建图层时候的{Time}字符串一致,否则请求的时候无法替换时间信息。 return {time = Cesium.JulianDate.toIso8601(interval.start);
}; }Time: time
var times = Cesium.TimeIntervalCollection.fromIso8601({ iso8601: ‘2015-07-30/2017-06-16/P20D’, //iso8601参数为时间范围及间隔,用’/‘分割,第一个表示开始时间,第二个表示结束时间,P20D表示间隔20天,还可以是P1M、P1Y、P1Y3M5DT6H7M30S等,代表不同的时间间隔。 leadingInterval: true, trailingInterval: true, isStopIncluded: false, dataCallback: dataCallback //dataCallback表示在每个时间段内如何取值 });
var tileLayer = new mars3d.layer.WmtsLayer({ url : ‘https://gibs.earthdata.nasa.gov/wmts/epsg4326/{best}/{Layer}/{Style}/{Time}/{TileMatrixSet}/{TileMatrix}/{TileRow}/{TileCol}.png‘, //{TileMatrix}/{TileRow}/{TileCol}表示z、x、y,无需手动设置 layer : ‘AMSR2_Snow_Water_Equivalent’, style : ‘default’,//style参数会替换掉url中的{Style}字符串 tileMatrixSetID : ‘2km’, //tileMatrixSetID会替换掉{TileMatrixSet}字符串 format : ‘image/png’, dimensions: {//dimensions里面的参数只要出现在url中全部会被其value替换掉。 Layer : ‘AMSR2_Snow_Water_Equivalent’, best: ‘best’ }, clock: map.clock, //clock表示所使用的时钟,直接设置为系统时钟 times: times, //重点 maximumLevel : 5 }) map.addLayer(tileLayer)
<a name="uzUJo"></a>
#### 3.2 动画轨迹
在平台中,提供[SampledPositionProperty类(opens new window)](http://mars3d.cn/api/cesium/SampledPositionProperty.html)来实现矢量对象的时序控制,达到 模型等点状对象 沿轨迹平滑移动的目的。只需要指定每个时间对应的坐标即可,中间平台自动进行按时间平滑动画移动。
```javascript
//构造时序轨迹对象
let propertyFJ = getSampledPositionProperty([
[116.341348, 30.875522, 500],
[116.341432, 30.871815, 500],
[116.341181, 30.85326, 500],
[116.345028, 30.870436, 500],
])
//飞机模型
var graphicModel = new mars3d.graphic.ModelEntity({
position: propertyFJ,
orientation: new Cesium.VelocityOrientationProperty(propertyFJ),
style: {
url: 'http://data.mars3d.cn/gltf/mars/wrj.glb',
scale: 0.1,
minimumPixelSize: 20,
},
})
graphicLayer.addGraphic(graphicModel)
//计算演示的轨迹
function getSampledPositionProperty(points) {
let property = new Cesium.SampledPositionProperty()
let start = map.clock.currentTime
let positions = mars3d.LatLngArray.toCartesians(points)
for (let i = 0; i < positions.length; i++) {
let time = Cesium.JulianDate.addSeconds(start, i * 20, new Cesium.JulianDate())
let position = positions[i]
property.addSample(time, position) //指定每个时间对应的位置
}
return property
}