在官方例子中每个图形都是一个entity,官方例子提供了显示正方形、圆形、锥形、图片等多种案例!

// 初始花
var viewer = new Cesium.Viewer("cesiumContainer");
// 创建蓝色entity
var blueBox = viewer.entities.add({ // 添加到图形实体
// 名称
name: "Blue box",
// 位置 笛卡尔
position: Cesium.Cartesian3.fromDegrees(-114.0, 40.0, 300000.0),
// 形状,可以是盒子 线段 椎体等,当前是盒子
box: {
// 设置框的长度、宽度和高度 笛卡尔单位
dimensions: new Cesium.Cartesian3(400000.0, 300000.0, 500000.0),
// 颜色 还可以设置边框、阴影等
material: Cesium.Color.BLUE,
},
}); // 创建红色entity
var redBox = viewer.entities.add({
name: "Red box with black outline",
position: Cesium.Cartesian3.fromDegrees(-107.0, 40.0, 300000.0),
box: {
dimensions: new Cesium.Cartesian3(400000.0, 300000.0, 500000.0),
material: Cesium.Color.RED.withAlpha(0.5),
outline: true,
outlineColor: Cesium.Color.BLACK,
},
}); // 创建透明entity
var outlineOnly = viewer.entities.add({
name: "Yellow box outline",
position: Cesium.Cartesian3.fromDegrees(-100.0, 40.0, 300000.0),
box: {
dimensions: new Cesium.Cartesian3(400000.0, 300000.0, 500000.0),
fill: false,
outline: true,
outlineColor: Cesium.Color.YELLOW,
},
}); viewer.zoomTo(viewer.entities);

此外还可以通过加载czml文件来进行显示,其它例子也可通过 https://sandcastle.cesium.com/?src=Box.html&label=All 进行查看!

但是,这些例子都是根据固定的位置和形状进行显示的,如果我们要自己进行手动绘制呢?官方依然提供了一个例子:

该实例提供了手动绘制线段与多边形的方法,代码如下:

var viewer = new Cesium.Viewer("cesiumContainer", {
selectionIndicator: false,
infoBox: false,
/**
* 开启世界图形,防止图形错位
* 如果不开启则使用:
* 几何图形要依附于模型必须开启depthTestAgainstTerrain
* viewer.scene.globe.depthTestAgainstTerrain = true
* */
terrainProvider: Cesium.createWorldTerrain(),
});
// 防止双击放大球体
viewer.cesiumWidget.screenSpaceEventHandler.removeInputAction(
Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK
);
// 创建一个点
function createPoint(worldPosition) {
var point = viewer.entities.add({
position: worldPosition,
point: {
color: Cesium.Color.WHITE,
// 大小
pixelSize: 5,
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
},
});
return point;
}
var drawingMode = "line";
// 绘制
function drawShape(positionData) {
var shape;
if (drawingMode === "line") {
shape = viewer.entities.add({
// 线段
polyline: {
positions: positionData,
clampToGround: true,
width: 3,
},
});
} else if (drawingMode === "polygon") {
// 多边形
shape = viewer.entities.add({
polygon: {
hierarchy: positionData,
material: new Cesium.ColorMaterialProperty(
Cesium.Color.WHITE.withAlpha(0.7)
),
},
});
}
return shape;
}
// 所有活动点的实体
var activeShapePoints = [];
// 绘制图形
var activeShape;
// 第一个活动点
var floatingPoint;
// 创建鼠标事件
var handler = new Cesium.ScreenSpaceEventHandler(viewer.canvas);
handler.setInputAction(function (event) {
// 获取鼠标当前位置 viewer.scene.pickPosition 将位置转化为笛卡尔单位
var earthPosition = viewer.scene.pickPosition(event.position);
if (Cesium.defined(earthPosition)) {
if (activeShapePoints.length === 0) {
// 创建第一个点
floatingPoint = createPoint(earthPosition);
activeShapePoints.push(earthPosition);
// 最重要的一步,绘制过程中图形会动态跟着鼠标移动
// CallbackProperty返回一个回调函数 当activeShapePoints改变时会触发
// 不管activeShapePoints是增加还是删除都会动态改变图形的形状
// 在绘制结束必须重置activeShapePoints = [] 不然 CallbackProperty 一直处于回调中,严重消耗性能
var dynamicPositions = new Cesium.CallbackProperty(function () {
if (drawingMode === "polygon") {
// 多边形的position需要用 PolygonHierarchy进行转化
return new Cesium.PolygonHierarchy(activeShapePoints);
}
return activeShapePoints;
}, false);
activeShape = drawShape(dynamicPositions);
}
activeShapePoints.push(earthPosition);
createPoint(earthPosition);
}
// 鼠标左键点击事件 LEFT_CLICK
}, Cesium.ScreenSpaceEventType.LEFT_CLICK); handler.setInputAction(function (event) {
// 判断是否存在
if (Cesium.defined(floatingPoint)) {
var newPosition = viewer.scene.pickPosition(event.endPosition);
if (Cesium.defined(newPosition)) {
// 动态改变活动点的位置与鼠标当前位置保持一致
floatingPoint.position.setValue(newPosition);
activeShapePoints.pop();
activeShapePoints.push(newPosition);
}
}
// 鼠标左键移动事件 MOUSE_MOVE
}, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
// 重新绘制形状,使其不是动态的,然后删除动态形状.
function terminateShape() {
// 删除最后一个点
activeShapePoints.pop();
// 绘制完整的图形
drawShape(activeShapePoints);
// 删除创建的第一个点和处于活动状态的实体
viewer.entities.remove(floatingPoint);
viewer.entities.remove(activeShape);
// 格式化
floatingPoint = undefined;
activeShape = undefined;
activeShapePoints = [];
}
// 结束绘制
handler.setInputAction(function (event) {
terminateShape();
// 鼠标右键点击事件 RIGHT_CLICK
}, Cesium.ScreenSpaceEventType.RIGHT_CLICK); // Sandcastle 百度解决,不用也行,只是在cesium上挂载组件
var options = [
{
text: "Draw Lines",
onselect: function () {
if (!Cesium.Entity.supportsPolylinesOnTerrain(viewer.scene)) {
window.alert(
"This browser does not support polylines on terrain."
);
} terminateShape();
drawingMode = "line";
},
},
{
text: "Draw Polygons",
onselect: function () {
terminateShape();
drawingMode = "polygon";
},
},
]; Sandcastle.addToolbarMenu(options);
// Zoom in to an area with mountains
viewer.camera.lookAt(
Cesium.Cartesian3.fromDegrees(-122.2058, 46.1955, 1000.0),
new Cesium.Cartesian3(5000.0, 5000.0, 5000.0)
);
viewer.camera.lookAtTransform(Cesium.Matrix4.IDENTITY);

下面是自己封装的一个绘制多边形的代码:DrawPolygon.js

点击查看代码
/*
绘制面
*/
import * as Cesium from 'cesium'
import * as turf from '@turf/turf'
import Entity from './Entity' const LEFT_CLICK = Cesium.ScreenSpaceEventType.LEFT_CLICK
const RIGHT_CLICK = Cesium.ScreenSpaceEventType.RIGHT_CLICK
const MOUSE_MOVE = Cesium.ScreenSpaceEventType.MOUSE_MOVE
const LEFT_DOUBLE_CLICK = Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK // 绘制面
export default class DaChDraw {
// 初始化
constructor(viewer = null, options = { singleMode: false }) {
if (!viewer) {
throw new Error('请传入cesium实例!')
}
this.viewer = viewer
// 当前面所有点
this._position = []
// 最后一个活动点
this._positionLast = null
// 第一次绘制的图形
this._shape = null
// 绘制的所有实体
this._entityList = []
// 通过加载geojson显示的面
this._polygonJson = []
// 是否显示面积
this._isShowArea = false
// 通过加载geojson显示的图形
this._geoMap = new Map()
// 绘制的图形
this._drawMap = new Map()
this.entity = new Entity(viewer)
// 测量
this._resultTip = null
// 测量所保存的实体
this._resultTipArr = []
this.handler = new Cesium.ScreenSpaceEventHandler(this.viewer.canvas)
const _serf = this
// 是否开启单例模式,默认关闭 开启后在多个页面实例化都取到相同的DaChDraw 实例
_serf.singleMode = null
if (options.singleMode) {
if (!DaChDraw.singleMode) {
DaChDraw.singleMode = _serf
}
return DaChDraw.singleMode
}
}
// 结束
destroy() {
this._position = []
this._positionLast = null
this._shape = null
this._entityList = []
}
// 开始绘制
startDraw(showArea = this._isShowArea) {
const _serf = this
_serf._isShowArea = showArea
// 鼠标点击
_serf.handler.setInputAction(function(event) {
// 获取当前点击坐标
let earthPosition = _serf.viewer.scene.pickPosition(event.position)
if (Cesium.defined(earthPosition)) {
if (_serf._position.length === 0) {
// 创建点击的第一个点
_serf._positionLast = _serf.entity.createPoint(earthPosition)
_serf._position.push(earthPosition)
var dynamicPositions = new Cesium.CallbackProperty(function() {
// return new Cesium.PolygonHierarchy(_serf._position)
return _serf._position
}, false)
_serf._shape = _serf.entity.createLine(dynamicPositions)
_serf._entityList.push(_serf._positionLast)
_serf._entityList.push(_serf._shape)
}
_serf._position.push(earthPosition)
const pot = _serf.entity.createPoint(earthPosition)
_serf._entityList.push(pot)
}
}, LEFT_CLICK)
// 鼠标移动
this.handler.setInputAction(function(event) {
if (Cesium.defined(_serf._positionLast)) {
// 如果已经存在了一个点,说明当前处于绘制状态
// 获取移动后的最后一个位置 pickPosition获取笛卡尔坐标
let newPosition = _serf.viewer.scene.pickPosition(event.endPosition)
if (Cesium.defined(newPosition)) {
_serf._positionLast.position.setValue(newPosition)
_serf._position.pop()
_serf._position.push(newPosition)
}
}
}, MOUSE_MOVE)
// 鼠标双击绘制完成
_serf.handler.setInputAction(function(event) {
console.log(_serf._position)
if (_serf._position.length <= 4) {
_serf.breakDraw()
} else {
_serf.finishDraw()
}
}, LEFT_DOUBLE_CLICK)
// 鼠标右键结束绘制
_serf.handler.setInputAction(function(event) {
_serf.breakDraw()
}, RIGHT_CLICK)
}
// 绘制中断
breakDraw() {
const _serf = this
_serf._entityList.forEach((entity) => {
_serf.entity.remove(entity)
})
// 移除鼠标监听
this.handler.removeInputAction(LEFT_CLICK)
this.handler.removeInputAction(MOUSE_MOVE)
this.handler.removeInputAction(RIGHT_CLICK)
this.handler.removeInputAction(LEFT_DOUBLE_CLICK)
_serf.destroy()
}
// 绘制结束
finishDraw() {
const _serf = this
_serf.entity.remove(_serf._positionLast)
_serf.entity.remove(_serf._shape)
_serf._position.pop()
_serf._position.unshift(_serf._position[_serf._position.length - 1])
// _serf._polygonLast = _serf.entity.createPolygon(_serf._position)
_serf._polygonLast = _serf.entity.createLine(_serf._position)
const position = _serf.coordinates(
_serf._position,
_serf._position,
'Polygon'
)
// 绘制图形转geosjson
let geoJson = turf.polygon([position])
console.log(JSON.stringify(geoJson))
// 绘制完成后显示面积
if (_serf._isShowArea) {
let area = (turf.area(obj) / 1000000.0).toFixed(4) + '平方公里'
_serf.entity.createLabel(
area,
_serf._position[_serf._position.length - 1]
)
}
const { _id: id } = _serf._polygonLast
const polyObj = {
id,
geoJson,
}
this._drawMap.set(id, polyObj)
// 去掉所有绘制的点
_serf._entityList.forEach((entity) => {
_serf.entity.remove(entity)
})
this.destroy()
}
cartesian2Degrees(cartesian) {
const ellipsoid =
this.viewer.scene.globe.ellipsoid || Cesium.Ellipsoid.WGS84
let cartographic = Cesium.Cartographic.fromCartesian(cartesian, ellipsoid)
let lat = Cesium.Math.toDegrees(cartographic.latitude)
let lon = Cesium.Math.toDegrees(cartographic.longitude)
let height = cartographic.height
return {
lat,
lon,
height,
}
}
coordinates(position, positions, type) {
if (position instanceof Cesium.Cartesian3) {
const coor = this.cartesian2Degrees(position)
return [coor.lon, coor.lat, coor.height]
} else if (positions instanceof Array) {
const pts = []
for (let p of positions) {
const c = this.cartesian2Degrees(p)
pts.push([c.lon, c.lat, c.height])
}
if (type === 'Polygon') {
return pts
} else {
return [pts]
}
}
} // 加载geojson显示图形
getDraw(feat, style = {}) {
let positions = []
const coordinates = feat.geometry.coordinates[0]
for (let c of coordinates) {
positions.push({
lon: c[0],
lat: c[1],
height: c[2],
})
}
positions = positions.map((_) => {
return Cesium.Cartesian3.fromDegrees(_.lon, _.lat, _.height)
})
return this.entity.createPolygon(positions, style)
} }

Entity.js

点击查看代码
// 定义实体对象
import * as Cesium from 'cesium'
export default class Entitys {
constructor(core) {
this.entitys = core.entities
}
// 新增
add(entity) {
return this.entitys.add(entity)
}
// 删除
remove(entity) {
this.entitys.remove(entity)
}
// 移除所有
removeAll() {
this.entitys.removeAll()
}
// 创建实体类
create() {
return new Cesium.Entity()
}
// 根据ID获取实体类
withIdGainEntity(id) {
return this.entitys.getById(id)
}
getPoint() {
return new Cesium.PointGraphics({
pixelSize: 5,
color: Cesium.Color.BLUE,
outlineColor: Cesium.Color.WHITE,
outlineWidth: 1,
})
}
getLine(positions, color, width = 1) {
return new Cesium.PolylineGraphics({
show: true,
positions: positions,
material: color,
width,
clampToGround: true,
})
}
getPolygon(position) {
return new Cesium.PolygonGraphics({
show: true,
hierarchy: position,
material: Cesium.Color.RED.withAlpha(0.5),
})
}
// 创建点
createPoint(position, label = null, point = true, billboard = false) {
let entity = this.create()
entity.position = position
if (point) entity.point = this.getPoint()
if (label) entity.label = this.getLabel(label)
return this.add(entity)
}
// 创建线
createLine(positions, oid = '', color = Cesium.Color.BLUE) {
let entity = this.create()
entity.position = positions
entity.polyline = this.getLine(positions, color)
entity.oid = oid
return this.add(entity)
}
// 创建面
createPolygon(positions) {
const entity = this.create()
entity.polygon = this.getPolygon(positions)
return this.add(entity)
}
// 创建label
createLabel(text, positions) {
let entity = this.create()
entity.label = this.getLabel(text)
entity.position = positions
return this.add(entity)
}
getLabel(text, offset) {
return new Cesium.LabelGraphics({
//文字标签
text: text,
font: '16px sans-serif',
fillColor: Cesium.Color.GOLD,
style: Cesium.LabelStyle.FILL_AND_OUTLINE,
outlineWidth: 2,
showBackground: true,
verticalOrigin: Cesium.VerticalOrigin.BOTTOM,
pixelOffset: offset == undefined ? new Cesium.Cartesian2(10, 30) : offset,
})
}
}

vue + cesium开发(4) 绘制图形的更多相关文章

  1. vue + cesium开发(5) 搭建 vue + cesium开发环境(2)

    上vue+cesium开发(1)中,没有进行配置webpack,而是使用了插件进行代替,在使用过程中出现了一些未知BUG,影响体验,因此参考了官方文档对项目进行重新配置,使用了 copy-webpac ...

  2. Android OpenGL ES 开发:绘制图形

    OpenGL 绘制图形步骤 上一篇介绍了 OpenGL 的相关概念,今天来实际操作,使用 OpenGL 绘制出图形,对其过程有一个初步的了解. OpenGL 绘制图形主要概括成以下几个步骤: 创建程序 ...

  3. cesium开发(1)搭建 vue + cesium开发环境

    进入新公司一段时间了,新公司业务主要从事卫星方面等webgl的开发,主要使用了leafletjs和cesium,其中cesium难度较大,需求较多,再进行了一段时间的使用开发后依旧感到有些力不从心, ...

  4. vue + cesium开发(3) cesium1.87更新问题

    官方在2021年11月1号更新日志中记录了他们把zip.js升级到了2.3.12以适应webpack4中的关于import.meta不兼容的语法问题,但是经过实测,1.87版本依然没有解决这个问题,所 ...

  5. 在Android中使用OpenGL ES进行开发第(三)节:绘制图形

    一.前期基础知识储备笔者计划写三篇文章来详细分析OpenGL ES基础的同时也是入门关键的三个点: ①OpenGL ES是什么?与OpenGL的关系是什么?——概念部分 ②使用OpenGLES绘制2D ...

  6. Windows App开发之编辑文本与绘制图形

    编辑文本及键盘输入 相信大家都会使用TextBox,但假设要让文本在TextBox中换行该怎么做呢?将TextWrapping属性设置为Wrap,将AcceptsReturn属性设置为True就好咯. ...

  7. CSS 魔法系列:纯 CSS 绘制图形(心形、六边形等)

    <CSS 魔法系列>继续给大家带来 CSS 在网页中以及图形绘制中的使用.这篇文章给大家带来的是纯 CSS 绘制五角星.六角形.五边形.六边形.心形等等. 我们的网页因为 CSS 而呈现千 ...

  8. html5 Canvas绘制图形入门详解

    html5,这个应该就不需要多作介绍了,只要是开发人员应该都不会陌生.html5是「新兴」的网页技术标准,目前,除IE8及其以下版本的IE浏览器之外,几乎所有主流浏览器(FireFox.Chrome. ...

  9. vue前端开发那些事——vue组件开发

    vue的学习曲线不是很陡(相比其它框架,如anglarjs),官方文档比较全面,分为基础篇和高级篇.我们刚开始学习的时候,肯定像引用jquery那样,先把vue的js引进来,然后学习基础内容.如果仅仅 ...

随机推荐

  1. hexo配合github action 自动构建(多种形式)

    已经使用HEXO正常构建GitHub页面 根据github action 给hexo配置自动部署github page 前往墨抒颖的个人网站查看纯净版 1. 为仓库设置访问密钥 第一步先生成密钥,打开 ...

  2. TypeScript 条件类型精读与实践

    在大多数程序中,我们必须根据输入做出决策.TypeScript 也不例外,使用条件类型可以描述输入类型与输出类型之间的关系. 本文同步首发在个人博客中,欢迎订阅.交流. 用于条件判断时的 extend ...

  3. 12c slience dbca ORA-27125

    问题:12c slience dbca ORA-27125 解决办法:网上大部分方法是把dba组放在内核的,没有效果,可以尝试google找到一位大神的方案,成功解决https://oracle-ad ...

  4. 10.8 location

    创建一个前台站点 server { listen 80; server_name www.nginx.com; locaiton / { root /var/www/html/www; } } 创建一 ...

  5. Windows下的程序及热键监视神器——Spy++

    Windows下的程序及热键监视神器--Spy++ 背景 在使用Windows的时候,偶尔会发现某些应用程序的热键不生效了:又或是桌面弹出了弹框却并不知道这个弹框来自何处.例如,本人最近使用Vim的时 ...

  6. SphereEx 公司成立,推动 Apache ShardingSphere 社区加速发展

    近日,SphereEx 商业公司在中国红杉种子基金及初心资本助力下,已完成公司及团队组建.各大媒体平台及公众号已相继报道,并抢占新闻头条.作为以 Apache ShardingSphere 核心团队组 ...

  7. Java:并发笔记-02

    Java:并发笔记-02 说明:这是看了 bilibili 上 黑马程序员 的课程 java并发编程 后做的笔记 3. 共享模型之管程-1 本章内容-1 共享问题 synchronized 线程安全分 ...

  8. Java中类及方法的加载顺序

    1. 虚拟机在首次加载Java类时,会对静态代码块.静态成员变量.静态方法进行一次初始化(静态间按顺序执行). 2. 只有在调用new方法时才会创建类的实例. 3. 类实例创建过程:父子继承关系,先父 ...

  9. [no_code][Alpha]测试报告

    项目 内容 2020春季计算机学院软件工程(罗杰 任健) 2020春季计算机学院软件工程(罗杰 任健) 作业要求 测试报告 我们在这个课程的目标是 设计出一个OCR表单处理软件 这个作业在哪个具体方面 ...

  10. HITS算法简介

    1.算法名称 超文本敏感标题搜索 (Hyperlink-Induced Topic Search) 2.算法背景 HITS 算法是由康奈尔大学的Jon Kleinberg 博士于1997 年首先提出的 ...