Cesium 中拾取 3DTiles 交点坐标

javascript 复制代码
   this.handler.setInputAction(
          (e: Cesium.ScreenSpaceEventHandler.PositionedEvent) => {
            this.CloseDelete()
            this.MapLeftClick(e)
          },
          Cesium.ScreenSpaceEventType.LEFT_CLICK,
        )
javascript 复制代码
 private MapLeftClick(e: Cesium.ScreenSpaceEventHandler.PositionedEvent) {
    const r = this.GetPickAndPosition(e.position)
 // var cartesian2Coordinates = e.position;//获取鼠标位置的屏幕坐标
        // var ray = this.viewer.camera.getPickRay(cartesian2Coordinates);//生成射线:
        // var pickedObject = this.viewer.scene.pick(ray);//该方法会返回射线与场景中对象的交点信息
        // 方法2:直接拾取3DTiles特征
        const pickedFeature = this.viewer.scene.pick(e.position);
        let earthPosition = null
        if (pickedFeature && pickedFeature.primitive instanceof Cesium.Cesium3DTileset) {
          // 获取点击位置的世界坐标
           earthPosition = this.viewer.scene.pickPosition(e.position);
          // this.pointsList.push(earthPosition)
          console.log('earthPosition', earthPosition);
          if (Cesium.defined(earthPosition)) {
            console.log('ooooookkkkkk', earthPosition);
          }
          if (earthPosition) {
            // 转换为经纬度
            const cartographic = Cesium.Cartographic.fromCartesian(earthPosition);
            const longitude = Cesium.Math.toDegrees(cartographic.longitude).toFixed(6);
            const latitude = Cesium.Math.toDegrees(cartographic.latitude).toFixed(6);
            const height = cartographic.height.toFixed(2);

            console.log(`交点坐标: 经度 ${longitude}°, 纬度 ${latitude}°, 高度 ${height}米`);

            // 在点击位置添加点标记
            this.viewer.entities.add({
              position: cartesian,
              point: {
                pixelSize: 10,
                color: Cesium.Color.RED,
                outlineColor: Cesium.Color.WHITE,
                outlineWidth: 2
              },
              label: {
                text: `(${longitude}, ${latitude}, ${height})`,
                font: '14pt monospace',
                style: Cesium.LabelStyle.FILL_AND_OUTLINE,
                outlineWidth: 2,
                verticalOrigin: Cesium.VerticalOrigin.BOTTOM,
                pixelOffset: new Cesium.Cartesian2(0, -10)
              }
            });
}
  1. Cesium.defined():

    • 这是 Cesium 提供的一个工具函数,用于安全地检查变量是否已定义且不为 nullundefined

    • 相当于 earthPosition !== undefined && earthPosition !== null 的简写

    • 更健壮,可以避免 JavaScript 的某些边缘情况

  2. 判断逻辑:

    • 只有当 earthPosition 存在(已定义且非 null)时,才会执行花括号内的代码

    • 如果 earthPositionundefinednull 或未声明,条件判断会返回 false

方法 适用对象 特点 典型场景
viewer.scene.pick(ray) 场景中所有可拾取对象(3D Tiles、模型、实体等) 返回包含对象信息的PickedObject(含位置、对象类型等) 需区分拾取的是 3D 模型、实体还是其他对象时
viewer.scene.pickPosition(ray) 场景中所有可交互对象(包括 3D Tiles、地球表面等) 直接返回交点坐标(Cartesian3),不区分对象类型 仅需坐标,不关心拾取的是模型还是地表时
viewer.scene.globe.pick(ray, scene) 仅地球表面(globe) 强制拾取地表坐标,忽略 3D 模型遮挡(除非模型在地下) 专门需要获取地表坐标时(如地形测量)
javascript 复制代码
  private GetPickAndPosition(sp: Cesium.Cartesian2) {
    const pick = this.viewer.scene.pick(sp)//场景中所有可拾取对象(3D Tiles、模型、实体等)返回包含对象信息的PickedObject(含位置、对象类型等)
    let ray = this.viewer.camera.getPickRay(sp) as any;//场景中所有可交互对象(包括 3D Tiles、地球表面等)
    let tp = this.viewer.scene.globe.pick(ray, this.viewer.scene);//仅地球表面(globe)
    return { pick, tp }

  }
相关推荐
excel几秒前
深度解析:Vue <script setup> 中的 defineModel 处理逻辑源码剖析
前端
excel2 分钟前
🧩 深入理解 Vue 宏编译:processDefineOptions() 源码解析
前端
excel3 分钟前
Vue 宏编译源码深度解析:processDefineProps 全流程解读
前端
excel6 分钟前
Vue SFC 编译器源码深度解析:processDefineEmits 与运行时事件生成机制
前端
excel9 分钟前
Vue 3 深度解析:defineModel() 与 defineProps() 的区别与底层机制
前端
excel10 分钟前
深入解析 processDefineExpose:Vue SFC 编译阶段的辅助函数
前端
dcloud_jibinbin10 分钟前
【uniapp】小程序体积优化,分包异步化
前端·vue.js·webpack·性能优化·微信小程序·uni-app
桜吹雪11 分钟前
自定义instanceof运算符行为API: Symbol.hasInstance
前端
qq_4275060812 分钟前
基于Vue 3和Element Plus实现简单的钩子函数管理各类弹窗操作
前端·javascript·vue.js
excel15 分钟前
深入解析:ScriptCompileContext —— Vue SFC 脚本编译上下文的核心机制
前端