rootMeta coordinate 配置。Definition: TilesetHeader
3D Tiles rootMeta 字段中定义的坐标系元数据。
interface RootMeta {
/** 模型垂直轴向 (如 "Z", "-Y") */
upAxis?: string;
/** 坐标系转换矩阵信息 */
coordinate?: Coordinate;
}
描述 ECEF 与 ENU 之间的转换关系。
interface Coordinate {
/** 地面高度 */
ground_height?: number;
/** ECEF 到 ENU 的转换矩阵 (4x4 数组) */
pose_ecef_to_enu?: number[];
/** ENU 到 ECEF 的转换矩阵 (4x4 数组) */
pose_enu_to_ecef?: number[];
}
Five 中涉及多个坐标系,它们在不同场景下各有用途。理解它们的关系是正确使用 Five 的关键。
| 坐标系 | 上轴 | 适用场景 | 说明 |
|---|---|---|---|
| Local (Y-up) | Y | 渲染场景、前端开发 | Five 的 five.scene、Observer 位置、project2d 等均使用此坐标系。与 Three.js 默认一致。 |
| ENU (Z-up) | Z | 算法交互、后端接口、模型原始数据 | 测绘行业习惯。3D Tiles 数据源、loadGltf 等加载器默认输出 Z-up。 |
| ECEF | - | RTK 定位、地球坐标 | 地心地固坐标系,用于包含 RTK 信息的模型。 |
| World | Y | Three.js 世界坐标 | 通常等同于 Local,除非有 Object3D 层级嵌套偏移。 |
关键区分:
- 开发者在
five.scene中操作的所有对象(添加标签、射线检测结果、project2d输入等)都处于 Local (Y-up) 坐标系。- 模型数据源(3D Tiles、PLY、GLTF 等文件)通常以 ENU (Z-up) 存储。Five 在加载时会自动将其旋转对齐到 Local (Y-up)。
- 与后端/算法交互时,推荐使用 ENU (Z-up) 坐标系传输数据,通过
viewLayer.localToEnu()/viewLayer.enuToLocal()进行转换。
Five 的渲染场景 (five.scene) 和 Observers (观察点) 使用 Y-up (Y 轴向上) 的右手坐标系。
这与 Three.js 的默认坐标系一致,便于前端开发和场景渲染。
在本项目及相关算法交互中,ENU 指代 Z-up (Z 轴向上) 的坐标系。这是为了和测绘行业习惯保持一致。
地心地固坐标系 (Earth-Centered, Earth-Fixed)。
ecefToEnu 方法将 ECEF 坐标转换为 ENU 坐标。模型 (如 .at3d, 3D Tiles) 的加载逻辑遵循以下原则:
five.scene 中看到的所有模型都已处于统一的 Y-up 坐标系下。注意: 外部模型加载函数(如
loadGltf,loadPly等)的upAxis参数默认为'Z',表示输出的模型以 Z-up 存储。这是因为这些函数返回的是原始模型对象,尚未经过 Five 的自动对齐。当你通过five.load(work)加载 Work 数据时,Five 会自动完成 Z-up → Y-up 的转换。如果你手动使用loadGltf并添加到five.scene,需要自行处理坐标系旋转。详见 Load External Model。
在 3D Tiles 的 tileset.json 中,rootMeta 字段用于描述坐标系转换信息(没有该字段则默认 Z-up):
pose_ecef_to_enu 和 pose_enu_to_ecef 变换矩阵。在 model 的 coordinate 字段用于描述坐标系转换信息(没有该字段则默认 Z-up):
pose_ecef_to_enu 和 pose_enu_to_ecef 变换矩阵。ViewLayer (继承自 Tile3D) 提供了成套的坐标转换方法,用于在 Local, ENU, ECEF 和 World 之间进行转换。
| 方法名 | 说明 |
|---|---|
localToEnu(vector) |
Local (Y-up) -> ENU (Z-up) |
enuToLocal(vector) |
ENU (Z-up) -> Local (Y-up) |
enuToEcef(vector) |
ENU (Z-up) -> ECEF |
ecefToEnu(vector) |
ECEF -> ENU (Z-up) |
localToEcef(vector) |
Local (Y-up) -> ECEF |
ecefToLocal(vector) |
ECEF -> Local (Y-up) |
worldToEnu(vector) |
World -> ENU (Z-up) |
enuToWorld(vector) |
ENU (Z-up) -> World |
注:
World坐标系通常指 Three.js 的世界坐标 (即five.scene的坐标)。在未通过Object3D层级嵌套偏移的情况下,World等同于Local。
推荐在与后端或算法交互时,将 Local 坐标转换为 ENU 坐标。
import * as THREE from 'three';
import { ViewLayer } from '@realsee/five';
// 假设已加载 ViewLayer
const viewLayer: ViewLayer = ...;
// 1. 获取场景中某点的坐标 (Local Y-up)
const localPosition = new THREE.Vector3(10, 20, 30);
// 2. 转换为 ENU 坐标 (Z-up) 用于传输给后端/算法
const enuPosition = viewLayer.localToEnu(localPosition.clone());
console.log(`Local: ${localPosition.toArray()}`); // [x, y, z] (y-up)
console.log(`ENU: ${enuPosition.toArray()}`); // [x, y, z] (z-up)
// 3. 将 ECEF 坐标转换为 Local 坐标用于显示
const ecefPosition = new THREE.Vector3( ... );
const displayPosition = viewLayer.ecefToLocal(ecefPosition.clone());
upAxis, modelUpAxis)。tags: [坐标系, 坐标转换, 右手坐标系, 模型方向, 旋转, 地理坐标, coordinate-system, enu, ecef, z-up, y-up, transform, local, world, rtk]