1、为什么要自定义Primitive
a、在飞机飞行过程中,如果使用entity同时绘制飞机和线的时候,会发现飞机的飞行位置和线的位置不统一,出现差距,出现脱线。
b、结合代码分析,cesium的线和飞机模型是分开渲染的,渲染的时段不一致,导致飞机在飞行过程的点位结合不上。
c、采用同批次渲染就不会发生这个问题
2、如何自定义Primitive
a、使用es6进行编码
b、使用class
c、提供update方法
d、将自定义的primitive加入到primitivecollection中进行渲染
3、实现代码
案例以初始实验为主,不以飞机案例来做。
案例以点和文字加入一个渲染队列进行数据渲染。
1、首先创建一个类CustomPrimitive
包括类名、构造函数,以及对应的参数
import { LabelCollection, PointPrimitiveCollection, Cartesian3 } from "cesium";
export default class CustomPrimitive {
/**
* 自定义对象
* @param options
* @param {Cartesian3} options.position 点位置
* @param {string} options.text 文本内容
* @param {number} options.pixelSize 点的像素大小
*/
constructor(options) {
this._position = options.position;
this._label = options.text;
this._pixelSize = options.pixelSize;
this._ready = false;
/**
* 渲染队列
* @type {[]}
* @private
*/
this._primitiveCollection = [];
}
}
2、编写update方法,当数据没有完成注册时,执行注册,初始化实体对象
/**
* 注册
* @param frameState
*/
init(frameState) {}
/**
* 更新
* @param frameState
*/
update(frameState) {
if (!this._ready) {
this._ready = true;
this.init(frameState);
}
this._primitiveCollection.forEach((primitive) => {
primitive && !primitive.isDestroyed() && primitive.update(frameState);
});
}
3、编写注册对象,包括点集合和文本渲染
/**
* 注册
* @param frameState
*/
init(frameState) {
const points = new PointPrimitiveCollection();
points.add({
position: this._position,
color: Color.fromCssColorString("#ff0000", new Color()),
disableDepthTestDistance: 5000,
outlineWidth: 1,
outlineColor: Color.fromCssColorString("#ffff00", new Color()),
pixelSize: this._pixelSize,
});
this._primitiveCollection.push(points);
let labels = new LabelCollection();
labels.add({
text: this._label,
position: this._position,
disableDepthTestDistance: 5000,
fillColor: Color.fromCssColorString("#ffffff", new Color()),
font: "32px sans-serif",
horizontalOrigin: HorizontalOrigin.CENTER,
verticalOrigin: VerticalOrigin.BOTTOM,
showBackground: true,
backgroundColor: Color.fromCssColorString("#0EE3F6C1", new Color()),
backgroundPadding: Cartesian2.fromArray([12, 7]),
});
this._primitiveCollection.push(labels);
}
4、渲染代码:将定义的Primitive对象加入到渲染队列
let origin2 = Cartesian3.fromDegrees(106, 26, 1600);
let origin21 = Cartesian3.fromDegrees(106, 26, 40);
viewer.camera.flyTo({
destination: origin2,
complete: () => {
let primitive = new CustomPrimitive({
position: origin21,
text: "测试",
pixelSize: 8,
});
viewer.scene.primitives.add(primitive);
},
});
4、渲染效果
全部代码
import {
LabelCollection,
PointPrimitiveCollection,
Cartesian3,
Color,
Cartesian2,
HorizontalOrigin,
VerticalOrigin,
} from "cesium";
export default class CustomPrimitive {
/**
* 自定义对象
* @param options
* @param {Cartesian3} options.position 点位置
* @param {string} options.text 文本内容
* @param {number} options.pixelSize 点的像素大小
*/
constructor(options) {
this._position = options.position;
this._label = options.text;
this._pixelSize = options.pixelSize;
this._ready = false;
/**
* 渲染队列
* @type {[]}
* @private
*/
this._primitiveCollection = [];
}
/**
* 注册
* @param frameState
*/
init(frameState) {
const points = new PointPrimitiveCollection();
points.add({
position: this._position,
color: Color.fromCssColorString("#ff0000", new Color()),
disableDepthTestDistance: 5000,
outlineWidth: 1,
outlineColor: Color.fromCssColorString("#ffff00", new Color()),
pixelSize: this._pixelSize,
});
this._primitiveCollection.push(points);
let labels = new LabelCollection();
labels.add({
text: this._label,
position: this._position,
disableDepthTestDistance: 5000,
fillColor: Color.fromCssColorString("#ffffff", new Color()),
font: "32px sans-serif",
horizontalOrigin: HorizontalOrigin.CENTER,
verticalOrigin: VerticalOrigin.BOTTOM,
showBackground: true,
backgroundColor: Color.fromCssColorString("#0EE3F6C1", new Color()),
backgroundPadding: Cartesian2.fromArray([12, 7]),
});
this._primitiveCollection.push(labels);
}
/**
* 更新
* @param frameState
*/
update(frameState) {
if (!this._ready) {
this._ready = true;
this.init(frameState);
}
this._primitiveCollection.forEach((primitive) => {
primitive && !primitive.isDestroyed() && primitive.update(frameState);
});
}
}