原文链接及内容

效果如下视频所示:

示例代码如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
/**
* 此示例举例说明了 CallbackPositionProperty 的用法,这是一种通过回调函数延迟计算其值的位置属性。
* 当您的数据无法预先计算或需要在运行时从其他属性派生时,请使用 CallbackPositionProperty。
* 使用场景:动态位置计算,如路径移动。
*
* Catmull-Rom spline: Catmull-Rom样条曲线,可以参考:https://www.mvps.org/directx/articles/catmull/
*/
const viewer = new Cesium.Viewer("cesiumContainer", {
geocoder: false,
sceneModePicker: false,
homeButton: false,
navigationHelpButton: false,
baseLayerPicker: false,
navigationInstructionsInitiallyVisible: false,
animation: false,
timeline: false,
fullscreenButton: false,
selectionIndicator: false,
skyBox: false,
shouldAnimate: true,
terrain: Cesium.Terrain.fromWorldTerrain(),
});

//隐藏版权信息
viewer.cesiumWidget.creditContainer.style.display = "none";
//添加帧速显示
viewer.scene.debugShowFramesPerSecond = true;

// 根据太阳位置启用照明。
viewer.scene.globe.enableLighting = true;

// 启用深度测试
viewer.scene.globe.depthTestAgainstTerrain = true;

// 设定我们的模拟时间界限。
const start = Cesium.JulianDate.fromDate(new Date(2015, 2, 25, 16));
const duration = 8;
const stop = Cesium.JulianDate.addSeconds(
start,
duration,
new Cesium.JulianDate()
);

// 确保 viewer 位于所需的时间。
viewer.clock.startTime = start.clone();
viewer.clock.stopTime = stop.clone();
viewer.clock.currentTime = start.clone();
viewer.clock.multiplier = 1.0;
viewer.clock.clockRange = Cesium.ClockRange.LOOP_STOP;
viewer.clock.shouldAnimate = true;

// 将时间线设置为模拟边界(simulation bounds)。
viewer.timeline.zoomTo(start, stop);

// 准备时间样本。
const times = [0.0, 1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0];
const firstTime = times[0];
const lastTime = times[times.length - 1];
const delta = lastTime - firstTime;

// 准备点样本。前后点用于计算样条线的第一条切线和最后一条切线。
const before = Cesium.Cartesian3.fromDegrees(-112.87962, 36.27375, 620.01);
const points = [
Cesium.Cartesian3.fromDegrees(-112.87709, 36.27782, 620.01),
Cesium.Cartesian3.fromDegrees(-112.87351, 36.27992, 617.9),
Cesium.Cartesian3.fromDegrees(-112.87081, 36.2816, 617.6),
Cesium.Cartesian3.fromDegrees(-112.86539, 36.28239, 625.36),
Cesium.Cartesian3.fromDegrees(-112.86108, 36.28137, 627.82),
Cesium.Cartesian3.fromDegrees(-112.85551, 36.27967, 625.54),
Cesium.Cartesian3.fromDegrees(-112.848, 36.27732, 628.9),
Cesium.Cartesian3.fromDegrees(-112.84086, 36.27739, 638.81),
Cesium.Cartesian3.fromDegrees(-112.83682, 36.27995, 643.31),
];
const after = Cesium.Cartesian3.fromDegrees(-112.83506, 36.2822, 643.31);

// 计算第一条和最后一条切线。
const firstTangent = Cesium.Cartesian3.subtract(
points[0],
before,
new Cesium.Cartesian3()
);
const lastTangent = Cesium.Cartesian3.subtract(
after,
points[8],
new Cesium.Cartesian3()
);

/**
* 创建位置样条曲线。
* Catmull-Rom 样条函数是一种三次样条函数,
* 其控制点(除第一个和最后一个控制点外)的切线均使用前一个控制点和下一个控制点计算。
*/
const positionSpline = new Cesium.CatmullRomSpline({
times,
points,
firstTangent,
lastTangent,
});

// 创建CallbackPositionProperty并使其返回样条曲线评估结果。
const position = new Cesium.CallbackPositionProperty(function (time, result) {
const splineTime =
(delta * Cesium.JulianDate.secondsDifference(time, start)) / duration;
if (splineTime < firstTime || splineTime > lastTime) {
return undefined;
}
//返回给定时间的样条曲线上的点
return positionSpline.evaluate(splineTime, result);
}, false);

const orientation = new Cesium.VelocityOrientationProperty(position);

// 添加一些路径点
for (let i = 0; i < points.length; ++i) {
viewer.entities.add({
position: points[i],
//黄色空心圆点
point: {
pixelSize: 8,
color: Cesium.Color.TRANSPARENT,
outlineColor: Cesium.Color.YELLOW,
outlineWidth: 3,
},
});
}

// 创建实体并将其位置绑定到CallbackPositionProperty。
const entity = viewer.entities.add({
availability: new Cesium.TimeIntervalCollection([
new Cesium.TimeInterval({
start: start,
stop: stop,
}),
]),
position,
orientation,
model: {
uri: "../SampleData/models/CesiumDrone/CesiumDrone.glb",
minimumPixelSize: 64,
maximumScale: 20000,
},
path: {
material: new Cesium.PolylineGlowMaterialProperty({
glowPower: 0.1, // 发光强度,以占总线宽的百分比表示
color: Cesium.Color.YELLOW,
}),
width: 10,
resolution: 0.01,
leadTime: 1,//前导时间,这里表示显示未来1秒时间的路径
trailTime: 0.1,//尾随时间,这里表示路径会保留过去0.1秒内的轨迹,较早的部分自动淡出。
},
trackingReferenceFrame: Cesium.TrackingReferenceFrame.INERTIAL,
viewFrom: new Cesium.Cartesian3(-100, 0, 10),
});

viewer.trackedEntity = entity;