SuperMap iClient3D for Cesium 自定义飞行站点
前言
前端飞行漫游的时候大多是使用在桌面创建好的飞行路线文件进行漫游。而有的项目由于项目需要需要在前端自定义这个飞行路线,这种情况怎么做呢?
一、创建一个空的飞行路线文件
在SuperMap iDesktopX中创建一个三维场景,然后再飞行管理下点击新建,新建之后点击保存.保存一个没有飞行节点的customFly.fpf文件。
二、添加自定义飞行站点
1. 创建飞行站点
定义一个handlerAddStopArr()方法用于创建飞行站点,并将站点保存到stopArray的数组中
handlerAddStopArr(lon, lat, height) {
// 添加自定义飞行站点并把站点数据存在数组中
let position = new Cesium.Cartesian3.fromDegrees(lon, lat, height)
let len = this.stopArray.length = undefined ? 0 : this.stopArray.length
let routeStop = new Cesium.RouteStop({
index: 1,
duration: 2,
waitTime: 5,
point: position,
heading: 6.260995919619558,
tilt: -0.40668579780875524,
speed: 20,
distanceToNext: 20,
stopName: "ggbon" + len,
})
this.stopArray.push(routeStop)
return this.stopArray
},
2. 动态传入站点坐标
初始化一个绘制线的hanlder,然后将handler拿到点数组转为经纬度坐标
后传给handlerAddStopArr以创建飞行站点.
addFlyRoute() {
// 点击按钮触发自定义事件
// 初始化绘线的hanlder
let vm = this
let tooltip = createTooltip(document.body);
let handler = new Cesium.DrawHandler(viewer, Cesium.DrawMode.Line, 0)
$("#addFlyRoute").click(() => {
if (vm.stopArray.length > 0) {
let routes = new Cesium.RouteCollection(viewer.entities);
routes.removeAll()
vm.stopArray = []
}
handler.activeEvt.addEventListener(function (isActive) {
if (isActive == true) {
viewer.enableCursorStyle = false;
viewer._element.style.cursor = '';
$('body').removeClass('drawCur').addClass('drawCur');
} else {
viewer.enableCursorStyle = true;
$('body').removeClass('drawCur');
}
});
handler.movingEvt.addEventListener(function (windowPosition) {
tooltip.showAt(windowPosition, '<p>点击绘制自定义飞行路线,右击绘制结束</p>');
});
// 通过handler拿到点数组创建飞行route
handler.drawEvt.addEventListener(function (result) {
console.log("result", result)
// 隐藏绘制的线
result.object._show = false
// result.positions
// 转换笛卡尔坐标为经纬度坐标传给创建站点的方法创建站点
for (let i in result.positions) {
console.log("坐标dikaer", result.positions[i])
let cartographic = Cesium.Cartographic.fromCartesian(result.positions[i]);
let lon = Cesium.Math.toDegrees(cartographic.longitude);
let lat = Cesium.Math.toDegrees(cartographic.latitude);
let height = cartographic.height;
console.log("坐标", lon, lat, height)
vm.handlerAddStopArr(lon, lat, height)
}
tooltip.setVisible(false);
console.log("stopArray", vm.stopArray)
// 触发初始化飞行路线的方法
vm.flyRoute()
});
handler.activate();
})
},
三、初始化飞行路线
初始化flyManager,在初始完成的回调中向routes飞行站点列表传入之前添加的飞行站点.并设置启动停止飞行路线的按钮.
flyRoute() {
let vm = this
// 添加飞行路线
var routes = new Cesium.RouteCollection(viewer.entities);
//添加fpf飞行文件,fpf由SuperMap iDesktop生成
var fpfUrl = '/static/SampleData/fpf/customFly.fpf';
routes.fromFile(fpfUrl);
//初始化飞行管理
var flyManager = new Cesium.FlyManager({
scene: scene,
routes: routes
});
//注册站点到达事件
flyManager.stopArrived.addEventListener(function (routeStop) {
routeStop.waitTime = 1; // 在每个站点处停留1s
});
flyManager.readyPromise.then(function () { // 飞行路线就绪
// 添加自定义的站点
vm.stopArray.map(el => {
routes.get(0).addStop(el)
})
// routes.get(0).addStop(vm.routeStop);
var currentRoute = flyManager.currentRoute;
currentRoute.isLineVisible = true;
currentRoute.isStopVisible = true;
//生成飞行文件中的所有站点列表
var allStops = flyManager.getAllRouteStops();
// 修正方位角开始 修正方位角没用
for (var index = 0; index < allStops.length - 1; index++) {
var currentRouteStop = allStops[index];
var nextRouteStop = allStops[index + 1];
var direction = new Cesium.Cartesian3(
nextRouteStop.point.x - currentRouteStop.point.x,
nextRouteStop.point.y - currentRouteStop.point.y,
nextRouteStop.point.z - currentRouteStop.point.z
);
Cesium.Cartesian3.normalize(direction, direction);
currentRouteStop.direction = direction;
}
// 最后一个站点的方向和倒数第二个相同
var lastRouteStop = allStops[allStops.length - 1];
lastRouteStop.direction = currentRouteStop.direction;
// 修正方位角结束
var menu = document.getElementById('stopList');
for (var i = 0, j = allStops.length; i < j; i++) {
var option = document.createElement('option');
option.innerHTML = "站点 " + (i + 1);
option.value = allStops[i].index;
menu.appendChild(option);
}
$('#stopList').change(function () { //注册站点切换事件
flyManager && flyManager.stop();
var index = parseInt($(this).val()); // 站点的索引
var route = flyManager.currentRoute;
var stop = route.get(index);
flyManager.currentStopIndex = index;
flyManager.viewToStop(stop);
});
$('#play').click(function () {
flyManager && flyManager.play();
});
$('#pause').click(function () {
flyManager && flyManager.pause();
});
$('#stop').click(function () {
flyManager && flyManager.stop();
});
$('#show-line').change(function () {
currentRoute.isLineVisible = $(this).prop('checked');
});
$('#show-stop').change(function () {
currentRoute.isStopVisible = $(this).prop('checked');
});
$('#toolbar').show();
$('#loadingbar').remove();
});
}
最终效果如下:
自定义飞行站点