这一节课程讲解CallbackProperty机制,官方解释为由回调函数延迟计算其值的属性。小编个人的理解为,该机制为间隔时间执行指定的方法返回属性值,用于对属性进行赋值。该机制可以可以说非常强大,可以实现许多动态效果。
首先来看下CallbackProperty的实例化参数
let CallbackProperty=new Cesium.CallbackProperty(callback, isConstant)
callback:回调函数,用于计算并返回属性值
isConstant:返回值是否变化
在Cesium原生范例中提供了一个线生长并计算线长度的范例,
callback
可以看到线非常平滑的在生长,同步的文本也在变化,下面来看下示例代码
var startLatitude = 35;
var startLongitude = -120;
var endLongitude;
var startTime = Cesium.JulianDate.now();
// Add a polyline to the scene. Positions are dynamic.
var isConstant = false;
var redLine = viewer.entities.add({
polyline : {
// This callback updates positions each frame.
positions : new Cesium.CallbackProperty(function(time, result) {
endLongitude = startLongitude + 0.001 * Cesium.JulianDate.secondsDifference(time, startTime);
return Cesium.Cartesian3.fromDegreesArray([startLongitude, startLatitude, endLongitude, startLatitude], Cesium.Ellipsoid.WGS84, result);
}, isConstant),
width : 5,
material : Cesium.Color.RED
}
});
可以看到在polyline的position设置时,使用CallbackProperty,通过计算线的结束点,不断返回位置坐标。
对于CallbackProperty有了初步的了解之后,这个时候会产生疑问,在什么情况下可以使用CallbackProperty?
根据小编的测试发现,在添加所有的entity时只要属性为property的都可以使用CallbackProperty。
下面来看下小编实现的一些效果:
交互绘制
高程量算
交互绘制和高程量算利用对鼠标事件的封装组合,形成常用的一些工具。以高程量算为例,示例代码如下
/**
* 作者:ljw20190619
*/
define([], function () {
Cesium.measureHeighthandler = function (viewer) {
this._viewer = viewer
this._dislabel
this._disline
this._startposition
this._endposition
this._startpoint
this._endpoint
this._startHeight
this._endHeight
this._height
this._circledis = 0
this._circle
this._customdatasoure = new Cesium.CustomDataSource('myData');
this._handler = new Cesium.ScreenSpaceEventHandler(this._viewer.scene.canvas);
this._viewer.dataSources.add(this._customdatasoure)
let _that = this
this.active = function () {
//设置鼠标左键单击回调事件
_that._handler.setInputAction(function (e) {
//获取点击位置笛卡尔坐标
let position = _that._viewer.scene.pickPosition(e.position);
_that._startposition = position
//将笛卡尔坐标转化为经纬度坐标
let cartographic = Cesium.Cartographic.fromCartesian(position);
let startheight = cartographic.height;
_that._startHeight = startheight
//在点击位置添加对应点
if (!_that._startpoint) {
_that._startpoint = _that._customdatasoure.entities.add({
point: {
color: new Cesium.Color(1, 1, 0),
pixelSize: 5,
outlineColor: new Cesium.Color(0, 1, 1),
disableDepthTestDistance: Number.POSITIVE_INFINITY
},
position: new Cesium.CallbackProperty(function () {
return _that._startposition
}, false),
});
}
_that._handler.removeInputAction(Cesium.ScreenSpaceEventType.LEFT_CLICK)
_that._handler.setInputAction(function (e) {
let position = _that._viewer.scene.pickPosition(e.endPosition);
_that._endposition = position
//将笛卡尔坐标转化为经纬度坐标
let cartographic = Cesium.Cartographic.fromCartesian(position);
let endheight = cartographic.height;
_that._endHeight = endheight
_that._height = _that._endHeight - _that._startHeight
_that._circledis = Cesium.Cartesian3.distance(_that._startposition, Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, _that._startHeight))
if (!_that._endpoint) {
_that._endpoint = _that._customdatasoure.entities.add({
point: {
color: new Cesium.Color(1, 1, 0),
pixelSize: 5,
outlineColor: new Cesium.Color(0, 1, 1),
disableDepthTestDistance: Number.POSITIVE_INFINITY
},
position: new Cesium.CallbackProperty(function () {
let cartographic = Cesium.Cartographic.fromCartesian(_that._startposition);
return Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, _that._endHeight)
}, false),
});
}
//绘制结果文本
if (!_that._dislabel) {
_that._dislabel = _that._customdatasoure.entities.add({
position: new Cesium.CallbackProperty(function () {
let cartographic = Cesium.Cartographic.fromCartesian(_that._startposition);
return Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, (cartographic.height + _that._endHeight) / 2)
}, false),
label: {
text: new Cesium.CallbackProperty(function () {
return Math.abs(_that._height).toFixed(2) + '米'
}, false),
font: '24px Helvetica',
// fillColor: Cesium.Color.SKYBLUE,
// outlineColor: Cesium.Color.BLACK,
outlineWidth: 2,
pixelOffset: new Cesium.Cartesian2(60, 0),
showBackground: true,
// style: Cesium.LabelStyle.FILL_AND_OUTLINE,
disableDepthTestDistance: Number.POSITIVE_INFINITY
}
})
}
//绘制结果线
if (!_that._disline) {
_that._disline = _that._customdatasoure.entities.add({
polyline: {
positions: new Cesium.CallbackProperty(function () {
let cartographic = Cesium.Cartographic.fromCartesian(_that._startposition);
return Cesium.Cartesian3.fromRadiansArrayHeights([cartographic.longitude, cartographic.latitude, cartographic.height, cartographic.longitude, cartographic.latitude, _that._endHeight])
}, false),
width: 2,
material: Cesium.Color.ORANGERED.withAlpha(0.5),
//depthFailMaterial: Cesium.Color.ORANGERED.withAlpha(0.5)
depthFailMaterial: new Cesium.ColorMaterialProperty(Cesium.Color.ORANGERED.withAlpha(0.5))
}
})
}
//绘制圆面
if (!_that._circle) {
_that._circle = _that._customdatasoure.entities.add({
position: new Cesium.CallbackProperty(function () {
let cartographic = Cesium.Cartographic.fromCartesian(_that._startposition);
return Cesium.Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, _that._endHeight)
}, false),
ellipse: {
semiMajorAxis: new Cesium.CallbackProperty(function () {
return _that._circledis
}, false),
semiMinorAxis: new Cesium.CallbackProperty(function () {
return _that._circledis
}, false),
height: new Cesium.CallbackProperty(function () {
return _that._endHeight
}, false),
material: Cesium.Color.YELLOW.withAlpha(0.2),
outline: true,
outlineColor: Cesium.Color.WHITE.withAlpha(0.5)
}
})
}
_that._handler.setInputAction(function (e) {
if (_that._circle) {
_that._customdatasoure.entities.remove(_that._circle)
}
_that._circle = undefined
_that._handler.removeInputAction(Cesium.ScreenSpaceEventType.MOUSE_MOVE)
_that._handler.removeInputAction(Cesium.ScreenSpaceEventType.RIGHT_CLICK)
}, Cesium.ScreenSpaceEventType.RIGHT_CLICK)
}, Cesium.ScreenSpaceEventType.MOUSE_MOVE)
}, Cesium.ScreenSpaceEventType.LEFT_CLICK);
}
this.disactive = function () {
_that._customdatasoure.entities.removeAll()
_that._dislabel=undefined
_that._disline = undefined
_that._startposition = undefined
_that._endposition = undefined
_that._startpoint = undefined
_that._endpoint = undefined
_that._startHeight = undefined
_that._endHeight = undefined
_that._height = undefined
_that._circledis = 0
_that._circle = undefined
}
}
return Cesium.measureHeighthandler
})
旋转
旋转相对比较简单,利用对圆面设置旋转实现,代码如下:
var addRoatePOI = function(POIObjs) {
POIObjs.forEach(function(value, index, array) {
var POIEntity = viewer.entities.add({
name: value[2],
position: Cesium.Cartesian3.fromDegrees(value[0], value[1], 180000),
ellipse: {
semiMinorAxis: 100000,
semiMajorAxis: 100000,
height: 180000,
material: new Cesium.ImageMaterialProperty({
image: 'images/Oval.png',
repeat: new Cesium.Cartesian2(1, 1),
transparent: true
}),
rotation: new Cesium.CallbackProperty(getRotationValue, false),
stRotation: new Cesium.CallbackProperty(getRotationValue, false),
outline: false, // height must be set for outline to display
numberOfVerticalLines: 100
},
description: '测试数据'
});
})
var rotation = Cesium.Math.toRadians(30);
function getRotationValue() {
rotation += 0.002;
return rotation;
}
}
本节教程就到这里,欢迎转发、留言、讨论。