drone-camera 0.0.0-stage → 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +155 -2
- package/index.d.ts +51 -0
- package/index.d.ts.map +1 -0
- package/index.js +20474 -0
- package/index.js.map +1 -0
- package/index.umd.cjs +1361 -0
- package/index.umd.cjs.map +1 -0
- package/lib/drone-capture-manifest.d.ts +169 -0
- package/lib/drone-capture-manifest.d.ts.map +1 -0
- package/lib/drone-capture-panel.d.ts +135 -0
- package/lib/drone-capture-panel.d.ts.map +1 -0
- package/lib/drone-capture.d.ts +380 -0
- package/lib/drone-capture.d.ts.map +1 -0
- package/lib/drone-cesium-mission.d.ts +120 -0
- package/lib/drone-cesium-mission.d.ts.map +1 -0
- package/lib/drone-cesium-rig.d.ts +50 -0
- package/lib/drone-cesium-rig.d.ts.map +1 -0
- package/lib/drone-cesium.d.ts +519 -0
- package/lib/drone-cesium.d.ts.map +1 -0
- package/lib/drone-control.d.ts +188 -0
- package/lib/drone-control.d.ts.map +1 -0
- package/lib/drone-engine.d.ts +70 -0
- package/lib/drone-engine.d.ts.map +1 -0
- package/lib/drone-exif.d.ts +64 -0
- package/lib/drone-exif.d.ts.map +1 -0
- package/lib/drone-fly.d.ts +545 -0
- package/lib/drone-fly.d.ts.map +1 -0
- package/lib/drone-gallery.d.ts +146 -0
- package/lib/drone-gallery.d.ts.map +1 -0
- package/lib/drone-husky-model.d.ts +22 -0
- package/lib/drone-husky-model.d.ts.map +1 -0
- package/lib/drone-image-utils.d.ts +67 -0
- package/lib/drone-image-utils.d.ts.map +1 -0
- package/lib/drone-image-viewer.d.ts +97 -0
- package/lib/drone-image-viewer.d.ts.map +1 -0
- package/lib/drone-lights.d.ts +194 -0
- package/lib/drone-lights.d.ts.map +1 -0
- package/lib/drone-minimap.d.ts +155 -0
- package/lib/drone-minimap.d.ts.map +1 -0
- package/lib/drone-panel.d.ts +265 -0
- package/lib/drone-panel.d.ts.map +1 -0
- package/lib/drone-panorama-viewer.d.ts +162 -0
- package/lib/drone-panorama-viewer.d.ts.map +1 -0
- package/lib/drone-panorama.d.ts +242 -0
- package/lib/drone-panorama.d.ts.map +1 -0
- package/lib/drone-photogrammetry.d.ts +207 -0
- package/lib/drone-photogrammetry.d.ts.map +1 -0
- package/lib/drone-radar.d.ts +136 -0
- package/lib/drone-radar.d.ts.map +1 -0
- package/lib/drone-reconstruction-preview.d.ts +84 -0
- package/lib/drone-reconstruction-preview.d.ts.map +1 -0
- package/lib/drone-rig.d.ts +385 -0
- package/lib/drone-rig.d.ts.map +1 -0
- package/lib/drone-sim.d.ts +883 -0
- package/lib/drone-sim.d.ts.map +1 -0
- package/lib/drone-stitch.d.ts +84 -0
- package/lib/drone-stitch.d.ts.map +1 -0
- package/lib/drone-world.d.ts +194 -0
- package/lib/drone-world.d.ts.map +1 -0
- package/lib/mission-editor.d.ts +116 -0
- package/lib/mission-editor.d.ts.map +1 -0
- package/lib/mission-panel.d.ts +173 -0
- package/lib/mission-panel.d.ts.map +1 -0
- package/package.json +61 -4
|
@@ -0,0 +1,188 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 渲染器无关的「飞行控制」抽象层。
|
|
3
|
+
*
|
|
4
|
+
* 库里所有 UI 模块(控制面板 / 航线面板 / 鹰眼图)都只依赖这一层接口,不依赖具体引擎实现,
|
|
5
|
+
* 于是同一套面板既能挂在 three.js 的 DroneFly 上,也能挂在 Cesium 之类的其他渲染器上
|
|
6
|
+
* (见 demo 的 Cesium 适配器)。
|
|
7
|
+
*
|
|
8
|
+
* 为什么必须显式抽出接口:DroneFly 含 private 成员,按 TypeScript 的类兼容规则,
|
|
9
|
+
* 只要目标类型带 private/protected,就只有同一条继承链上的对象才能赋值给它 ——
|
|
10
|
+
* 外部渲染器的控制器无论长得多像,都无法"伪装"成 DroneFly。
|
|
11
|
+
* 因此把「面板真正用到的那部分能力」提成公开接口,由各渲染器各自实现。
|
|
12
|
+
*
|
|
13
|
+
* 约定:接口只描述能力,不描述实现 —— 实现方自行决定真值来自 three 场景还是地理坐标系。
|
|
14
|
+
*/
|
|
15
|
+
import type { CameraMode, PhotoShot } from './drone-fly';
|
|
16
|
+
import type { CaptureCameraState, CaptureViewOverride } from './drone-capture';
|
|
17
|
+
import type { ChecklistItem, DroneSim, DroneSnapshot, FlightMode, FlightPhase, MissionConfig, MissionExport, MissionExportFormat, MissionWaypoint, StickState } from './drone-sim';
|
|
18
|
+
import type { MissionEditState } from './mission-editor';
|
|
19
|
+
/**
|
|
20
|
+
* 航点的地理坐标(经纬高,WGS84 椭球),由支持地理坐标系的后端(如 Cesium)提供。
|
|
21
|
+
*
|
|
22
|
+
* 与航点列表里的本地米坐标(x 东 / z 南 / altitude AGL,相对返航点)是同一位置的两种表示:
|
|
23
|
+
* 经纬高是同一位置在地球上的绝对坐标(海拔 = 地形高度 + AGL),面板可切换显示哪种。
|
|
24
|
+
*/
|
|
25
|
+
export interface WaypointGeo {
|
|
26
|
+
/** 经度(度) */
|
|
27
|
+
lon: number;
|
|
28
|
+
/** 纬度(度) */
|
|
29
|
+
lat: number;
|
|
30
|
+
/** 海拔(米,绝对高程 = 地形 + AGL) */
|
|
31
|
+
height: number;
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* 控制面板 / 航线面板 / 鹰眼图所需的最小飞行控制能力集。
|
|
35
|
+
*
|
|
36
|
+
* `DroneFly`(three.js 实现)与各渲染器适配器均实现本接口;面板只读真值、只调方法,
|
|
37
|
+
* 不触碰任何引擎对象,所以换渲染器时面板一行都不用改。
|
|
38
|
+
*/
|
|
39
|
+
export interface DronePanelHost {
|
|
40
|
+
/** 飞行内核:面板直接读取 gimbalPitch / photoCount / recordSeconds / stick 等真值 */
|
|
41
|
+
readonly sim: DroneSim;
|
|
42
|
+
/** 当前飞行阶段(自检 / 待机 / 起飞 / 悬停 / 返航 / 降落 ...) */
|
|
43
|
+
readonly phase: FlightPhase;
|
|
44
|
+
/** 是否已离地 */
|
|
45
|
+
readonly airborne: boolean;
|
|
46
|
+
/** 当前飞行挡位 */
|
|
47
|
+
readonly flightMode: FlightMode;
|
|
48
|
+
/** 相对起飞点的高度(米,AGL) */
|
|
49
|
+
readonly altitude: number;
|
|
50
|
+
/** 起飞前检查项(面板据此禁用起飞按钮并列出阻塞项) */
|
|
51
|
+
readonly preflightChecks: ChecklistItem[];
|
|
52
|
+
/** 机臂是否处于收拢状态 */
|
|
53
|
+
readonly armsFolded: boolean;
|
|
54
|
+
/** 是否正在录像 */
|
|
55
|
+
readonly isRecording: boolean;
|
|
56
|
+
/** 当前视角模式(orbit / follow / fpv) */
|
|
57
|
+
readonly cameraMode: CameraMode;
|
|
58
|
+
/** 上电(走自检 → 预热 → 待机) */
|
|
59
|
+
powerOn(): void;
|
|
60
|
+
/** 起飞 */
|
|
61
|
+
takeOff(): boolean;
|
|
62
|
+
/** 降落 */
|
|
63
|
+
land(): boolean;
|
|
64
|
+
/** 一键返航 */
|
|
65
|
+
returnHome(reason?: string): boolean;
|
|
66
|
+
/** 写入摇杆连续量(面板摇杆与键盘都走这里) */
|
|
67
|
+
setStick(stick: Partial<StickState>): void;
|
|
68
|
+
/** 切换飞行挡位 */
|
|
69
|
+
setMode(mode: FlightMode): void;
|
|
70
|
+
/** 展开 / 收拢机臂 */
|
|
71
|
+
setArmsFolded(folded: boolean): void;
|
|
72
|
+
/** 切换视角模式 */
|
|
73
|
+
setCameraMode(mode: CameraMode): void;
|
|
74
|
+
/** 设置云台俯仰角(度) */
|
|
75
|
+
setGimbalPitch(pitch: number): void;
|
|
76
|
+
/** 视角复位 */
|
|
77
|
+
resetCamera(): void;
|
|
78
|
+
/** 直接把无人机移动到目标位置(本地坐标 / 绝对姿态) */
|
|
79
|
+
flyTo(target: {
|
|
80
|
+
x?: number;
|
|
81
|
+
y?: number;
|
|
82
|
+
z?: number;
|
|
83
|
+
heading?: number;
|
|
84
|
+
pitch?: number;
|
|
85
|
+
roll?: number;
|
|
86
|
+
}): void;
|
|
87
|
+
/** 设定镜头/云台变焦倍数(1~4x) */
|
|
88
|
+
zoomTo(zoom: number): void;
|
|
89
|
+
/** 拍一张照片(取景位由实现方决定) */
|
|
90
|
+
requestPhoto(): Promise<PhotoShot | null>;
|
|
91
|
+
/**
|
|
92
|
+
* 取景相机(云台镜头)的位姿与内参快照 —— 与采集服务同源;未就绪返回 null。
|
|
93
|
+
* 全景拍摄要用它把每张照片的取景方位写进元数据。
|
|
94
|
+
*/
|
|
95
|
+
getCaptureCamera(): CaptureCameraState | null;
|
|
96
|
+
/**
|
|
97
|
+
* 设置取景**俯仰**覆盖(全景分层用):俯仰替代云台俯仰;传 `null` 复位。
|
|
98
|
+
* 只影响取景相机,不动机体与飞控。
|
|
99
|
+
*
|
|
100
|
+
* 没有水平偏航是有意的 —— 全景的水平覆盖靠 `spinBodyTo` 转机体(云台 Pan 行程不够)。
|
|
101
|
+
*/
|
|
102
|
+
setCaptureView(override: CaptureViewOverride | null): void;
|
|
103
|
+
/** 让机体原地自转到绝对方位角(度,罗盘角);`null` 停止自转。全景水平网格靠它 */
|
|
104
|
+
spinBodyTo(headingDeg: number | null): void;
|
|
105
|
+
/** 机体当前方位角(度,罗盘角) */
|
|
106
|
+
getBodyHeading(): number;
|
|
107
|
+
/** 开始录像 */
|
|
108
|
+
startRecording(): boolean;
|
|
109
|
+
/** 结束录像并返回产物 */
|
|
110
|
+
stopRecording(): Promise<Blob | null>;
|
|
111
|
+
}
|
|
112
|
+
/**
|
|
113
|
+
* 航线规划面板(MissionPanel)所需的最小飞行控制能力集。
|
|
114
|
+
*
|
|
115
|
+
* 与 `DronePanelHost` 同一设计:`DroneFly`(three 实现)与 `CesiumDroneAdapter`
|
|
116
|
+
* (Cesium 实现)都满足本接口,面板只读真值、只调方法,换渲染器时一行都不用改。
|
|
117
|
+
*
|
|
118
|
+
* 覆盖四类能力:
|
|
119
|
+
* - 执行控制:开始 / 暂停 / 继续 / 停止(语义全部由 DroneSim 内核定义,与后端无关);
|
|
120
|
+
* - 航点与参数:整表下发、单点更新、增删、参数修改、恢复默认;
|
|
121
|
+
* - 序列化:导出数据与 JSON / CSV 文本(实现下沉在 drone-sim,两后端共用);
|
|
122
|
+
* - 场景内编辑:编辑开关、选中、显隐、框住航线 —— 面板只展示结果,
|
|
123
|
+
* 「当前是否可编辑」由实现方判定(three 版=观察者视角且任务未执行)。
|
|
124
|
+
*/
|
|
125
|
+
export interface MissionPanelHost {
|
|
126
|
+
/** 飞行内核:面板直接读取 mission / missionConfig / homePosition 等真值 */
|
|
127
|
+
readonly sim: DroneSim;
|
|
128
|
+
/** 是否处于观察者(自由)视角 —— 场景内编辑的前置条件 */
|
|
129
|
+
readonly isOrbitView: boolean;
|
|
130
|
+
/** 全量真值快照(位置/姿态/电池/云台/任务…,面板据此渲染) */
|
|
131
|
+
getSnapshot(): DroneSnapshot;
|
|
132
|
+
/** 启动航线任务(地面时先自动起飞,到 1.2 米后自动接上航线) */
|
|
133
|
+
startMission(): boolean;
|
|
134
|
+
/** 暂停执行中的航线(原地悬停,可再续飞) */
|
|
135
|
+
pauseMission(reason?: string): boolean;
|
|
136
|
+
/** 续飞被暂停的航线 */
|
|
137
|
+
resumeMission(): boolean;
|
|
138
|
+
/** 中止航线并留在原地悬停 */
|
|
139
|
+
stopMission(reason?: string): boolean;
|
|
140
|
+
/** 下发航点列表(执行中会被拒绝,与真机"上传后不可改"一致) */
|
|
141
|
+
setMission(waypoints: Array<Partial<MissionWaypoint>>): boolean;
|
|
142
|
+
/** 改航线参数(速度/航向模式/过点方式/完成动作/循环) */
|
|
143
|
+
setMissionConfig(patch: Partial<MissionConfig>): void;
|
|
144
|
+
/** 航线参数与航点恢复出厂默认 */
|
|
145
|
+
resetMissionToDefault(): void;
|
|
146
|
+
/** 原位更新一个航点(场景拖拽每帧调用);返回夹紧后的航点,越界时 null */
|
|
147
|
+
updateMissionWaypoint(index: number, patch: Partial<MissionWaypoint>): MissionWaypoint | null;
|
|
148
|
+
/** 场景编辑:按索引删除一个航点 */
|
|
149
|
+
deleteMissionWaypoint(index: number): boolean;
|
|
150
|
+
/** 场景编辑:以飞机当前位置新增一个航点(高度取飞机当前高度) */
|
|
151
|
+
addMissionWaypointAtDrone(): number;
|
|
152
|
+
/** 把当前航线整理成可序列化的导出数据 */
|
|
153
|
+
getMissionExport(): MissionExport;
|
|
154
|
+
/** 导出航线文本(`json` 完整存档 / `csv` 纯航点表) */
|
|
155
|
+
exportMission(format?: MissionExportFormat): string;
|
|
156
|
+
/** 场景内编辑状态(开关/是否激活/选中/悬停/拖拽中) */
|
|
157
|
+
getMissionEditState(): MissionEditState;
|
|
158
|
+
/** 场景内编辑开关(开启仍需"当前确实可编辑"才生效) */
|
|
159
|
+
setMissionEditEnabled(enabled: boolean): void;
|
|
160
|
+
/** 场景内编辑开关当前是否开着 */
|
|
161
|
+
isMissionEditEnabled(): boolean;
|
|
162
|
+
/** 当前选中的航点索引(无选中 -1) */
|
|
163
|
+
getMissionSelected(): number;
|
|
164
|
+
/** 同步选中航点(列表与场景双向联动) */
|
|
165
|
+
setMissionSelected(index: number): void;
|
|
166
|
+
/** 航点标记显隐(不影响任务执行) */
|
|
167
|
+
setMissionWaypointsVisible(visible: boolean): void;
|
|
168
|
+
isMissionWaypointsVisible(): boolean;
|
|
169
|
+
/** 航线折线显隐 */
|
|
170
|
+
setMissionPathVisible(visible: boolean): void;
|
|
171
|
+
isMissionPathVisible(): boolean;
|
|
172
|
+
/** 把视角拉到"一眼看全整条航线"的位置;成功返回 true */
|
|
173
|
+
frameMission(): boolean;
|
|
174
|
+
/**
|
|
175
|
+
* 后端是否支持地理坐标(经纬高)。Cesium 等地理渲染器返回 true,three 等本地米坐标系返回 false。
|
|
176
|
+
* 面板据此决定是否显示"经纬度 / XYZ"坐标切换开关。
|
|
177
|
+
*/
|
|
178
|
+
supportsGeoCoordinates(): boolean;
|
|
179
|
+
/** 取某航点的地理坐标(经纬高);不支持或越界返回 null */
|
|
180
|
+
getWaypointGeo(index: number): WaypointGeo | null;
|
|
181
|
+
/**
|
|
182
|
+
* 用地理坐标原地改写一个航点(经纬高 → 本地米坐标的逆向换算由实现方完成)。
|
|
183
|
+
* Cesium 后端可写;three 等本地米坐标系无地理锚点,返回 false(面板仅在 geo 模式且
|
|
184
|
+
* supportsGeoCoordinates() 为 true 时才调用,故 three 不会走到这里)。
|
|
185
|
+
*/
|
|
186
|
+
setWaypointGeo(index: number, geo: WaypointGeo): boolean;
|
|
187
|
+
}
|
|
188
|
+
//# sourceMappingURL=drone-control.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"drone-control.d.ts","sourceRoot":"","sources":["../../src/lib/drone-camera/drone-control.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 引擎装配层 —— 用 `engine` 字段选择渲染后端,一处配置换整套渲染实现。
|
|
3
|
+
*
|
|
4
|
+
* 库里有两套完整的飞行控制器,都实现同一个 `DronePanelHost` 接口:
|
|
5
|
+
*
|
|
6
|
+
* engine: 'three' → DroneFly three.js + WebGPURenderer 的飞行沙盒
|
|
7
|
+
* engine: 'cesium' → CesiumDroneAdapter 地球(ENU/ECEF)坐标系下的飞行
|
|
8
|
+
*
|
|
9
|
+
* 两者的差别只在"真值怎么变成画面":飞行内核都是同一个 DroneSim,控制面板 /
|
|
10
|
+
* 航线面板 / 鹰眼图 / 键盘控制完全不区分后端。所以选后端这件事只该发生一次 ——
|
|
11
|
+
* 就在本工厂里,调用方拿到实例后只管用,不需要知道下面挂的是谁。
|
|
12
|
+
*
|
|
13
|
+
* ```ts
|
|
14
|
+
* // three(自带场景)
|
|
15
|
+
* const drone = await createDroneControl({
|
|
16
|
+
* engine: 'three', scene, camera, renderer, controls, modelUrl: '/models/dji_mini4_pro.glb',
|
|
17
|
+
* })
|
|
18
|
+
*
|
|
19
|
+
* // Cesium(先确保 /Cesium/Cesium.js 已就绪)
|
|
20
|
+
* await loadCesiumScript('/Cesium/Cesium.js')
|
|
21
|
+
* const drone = await createDroneControl({ engine: 'cesium', viewer, lon: 116.391, lat: 39.906 })
|
|
22
|
+
*
|
|
23
|
+
* // 之后再靠判别字段访问引擎特有成员
|
|
24
|
+
* if (drone.engine === 'three') drone.setGimbalStabilization('physical')
|
|
25
|
+
* ```
|
|
26
|
+
*
|
|
27
|
+
* `engine` 缺省为 `'three'`(与历史 API 一致:`new DroneFly(...)` + `initialize()`)。
|
|
28
|
+
*/
|
|
29
|
+
import type * as THREE from 'three';
|
|
30
|
+
import type { OrbitControls } from 'three/examples/jsm/controls/OrbitControls.js';
|
|
31
|
+
import type { WebGPURenderer } from 'three/webgpu';
|
|
32
|
+
import type { DronePanelHost } from './drone-control';
|
|
33
|
+
import { DroneFly, type DroneFlyInitializeOptions } from './drone-fly';
|
|
34
|
+
import { CesiumDroneAdapter, type CesiumDroneOptions } from './drone-cesium';
|
|
35
|
+
/** 渲染后端标识 */
|
|
36
|
+
export type DroneEngine = 'three' | 'cesium';
|
|
37
|
+
/**
|
|
38
|
+
* three 后端参数:场景四件套 + `DroneFly.initialize()` 的全部选项
|
|
39
|
+
* (modelUrl / obstacles)。
|
|
40
|
+
*/
|
|
41
|
+
export interface ThreeDroneEngineOptions extends DroneFlyInitializeOptions {
|
|
42
|
+
/** 后端标识;缺省 'three' */
|
|
43
|
+
engine?: 'three';
|
|
44
|
+
scene: THREE.Scene<THREE.Object3DEventMap>;
|
|
45
|
+
camera: THREE.PerspectiveCamera;
|
|
46
|
+
renderer: WebGPURenderer;
|
|
47
|
+
controls?: OrbitControls<THREE.Camera> | null;
|
|
48
|
+
}
|
|
49
|
+
/** Cesium 后端参数:本质就是 CesiumDroneOptions,只多一个必需的 engine 判别字段 */
|
|
50
|
+
export interface CesiumDroneEngineOptions extends CesiumDroneOptions {
|
|
51
|
+
engine: 'cesium';
|
|
52
|
+
}
|
|
53
|
+
/** `createDroneControl()` 的参数(判别联合) */
|
|
54
|
+
export type DroneControlOptions = ThreeDroneEngineOptions | CesiumDroneEngineOptions;
|
|
55
|
+
/**
|
|
56
|
+
* 引擎无关的控制器句柄 —— 两套实现都满足。
|
|
57
|
+
*
|
|
58
|
+
* 它是 `DronePanelHost`(面板 / 航线面板 / 鹰眼图真正依赖的那 22 项能力)
|
|
59
|
+
* 加上一个 `engine` 判别字段,于是:
|
|
60
|
+
* - 只做通用控制时,写 `(drone: DroneEngineHost) => void` 就够了,不必写联合类型;
|
|
61
|
+
* - 需要引擎特有成员时,再用 `engine` 收窄到具体类。
|
|
62
|
+
*/
|
|
63
|
+
export interface DroneEngineHost extends DronePanelHost {
|
|
64
|
+
readonly engine: DroneEngine;
|
|
65
|
+
}
|
|
66
|
+
/** 按 `engine` 装配并初始化:three 走 DroneFly.initialize,Cesium 走 CesiumDroneAdapter.start */
|
|
67
|
+
export declare function createDroneControl(options: ThreeDroneEngineOptions): Promise<DroneFly>;
|
|
68
|
+
export declare function createDroneControl(options: CesiumDroneEngineOptions): Promise<CesiumDroneAdapter>;
|
|
69
|
+
export declare function createDroneControl(options: DroneControlOptions): Promise<DroneEngineHost>;
|
|
70
|
+
//# sourceMappingURL=drone-engine.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"drone-engine.d.ts","sourceRoot":"","sources":["../../src/lib/drone-camera/drone-engine.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,OAAO,KAAK,KAAK,KAAK,MAAM,OAAO,CAAA;AACnC,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,8CAA8C,CAAA;AACjF,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,cAAc,CAAA;AAElD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAA;AACrD,OAAO,EAAE,QAAQ,EAAE,KAAK,yBAAyB,EAAE,MAAM,aAAa,CAAA;AACtE,OAAO,EAAE,kBAAkB,EAAE,KAAK,kBAAkB,EAAE,MAAM,gBAAgB,CAAA;AAE5E,aAAa;AACb,MAAM,MAAM,WAAW,GAAG,OAAO,GAAG,QAAQ,CAAA;AAE5C;;;GAGG;AACH,MAAM,WAAW,uBAAwB,SAAQ,yBAAyB;IACxE,sBAAsB;IACtB,MAAM,CAAC,EAAE,OAAO,CAAA;IAChB,KAAK,EAAE,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,gBAAgB,CAAC,CAAA;IAC1C,MAAM,EAAE,KAAK,CAAC,iBAAiB,CAAA;IAC/B,QAAQ,EAAE,cAAc,CAAA;IACxB,QAAQ,CAAC,EAAE,aAAa,CAAC,KAAK,CAAC,MAAM,CAAC,GAAG,IAAI,CAAA;CAC9C;AAED,8DAA8D;AAC9D,MAAM,WAAW,wBAAyB,SAAQ,kBAAkB;IAClE,MAAM,EAAE,QAAQ,CAAA;CACjB;AAED,uCAAuC;AACvC,MAAM,MAAM,mBAAmB,GAAG,uBAAuB,GAAG,wBAAwB,CAAA;AAEpF;;;;;;;GAOG;AACH,MAAM,WAAW,eAAgB,SAAQ,cAAc;IACrD,QAAQ,CAAC,MAAM,EAAE,WAAW,CAAA;CAC7B;AAED,sFAAsF;AACtF,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,uBAAuB,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAA;AACvF,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,wBAAwB,GAAG,OAAO,CAAC,kBAAkB,CAAC,CAAA;AAClG,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,mBAAmB,GAAG,OAAO,CAAC,eAAe,CAAC,CAAA"}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 零依赖 JPEG EXIF / GPS 解析器。
|
|
3
|
+
*
|
|
4
|
+
* 用途:真实无人机照片导入时,把「拍摄时间 / 机型 / 焦距 / 图像尺寸 / GPS 经纬高」
|
|
5
|
+
* 从文件里读出来,填进统一的 `CapturedImage.metadata`(见 drone-capture)。
|
|
6
|
+
*
|
|
7
|
+
* 为什么自己写而不引三方库:本库除 `three` 外不接受运行时依赖(见 lib/index.ts 的设计约定),
|
|
8
|
+
* 而 V1 只需要 JPEG 的 EXIF 基本项 —— 一个 APP1/TIFF 顺序读就够了,不值得为它挂一个包。
|
|
9
|
+
*
|
|
10
|
+
* 覆盖范围(够用即止,不做全谱):
|
|
11
|
+
* - 只认 JPEG(SOI 0xFFD8 → APP1 0xFFE1 "Exif\0\0" → TIFF),PNG / HEIC 一律返回 null;
|
|
12
|
+
* - IFD0:Make / Model / Orientation / DateTime / ExifIFD 指针 / GPSIFD 指针;
|
|
13
|
+
* - Exif IFD:曝光时间 / 光圈 / ISO / 原始拍摄时间 / 焦距 / 35mm 等效焦距 / 像素宽高;
|
|
14
|
+
* - GPS IFD:纬度(度分秒 + N/S)/ 经度(度分秒 + E/W)/ 海拔(含海平面下标志);
|
|
15
|
+
* - 字节序 II(小端)/ MM(大端)都支持;值内联(≤4 字节)与偏移两种存放方式都处理。
|
|
16
|
+
*
|
|
17
|
+
* 解析策略是**尽力而为、绝不抛错**:任何一段越界或类型不认识都只记进 `warnings` 并跳过,
|
|
18
|
+
* 已经读到的字段原样保留 —— 因为「元数据缺失」本身就是需要展示给用户的信息,
|
|
19
|
+
* 不该因为某个 tag 坏了就让整张照片导入失败。
|
|
20
|
+
*/
|
|
21
|
+
/** EXIF GPS 信息(已转成十进制度) */
|
|
22
|
+
export interface ExifGps {
|
|
23
|
+
/** 十进制度,北纬为正 */
|
|
24
|
+
latitude?: number;
|
|
25
|
+
/** 十进制度,东经为正 */
|
|
26
|
+
longitude?: number;
|
|
27
|
+
/** 海拔(米);altitudeRef = 1 表示海平面以下,此处已取负 */
|
|
28
|
+
altitude?: number;
|
|
29
|
+
/** 原始海拔标志:0 = 海平面以上,1 = 海平面以下 */
|
|
30
|
+
altitudeRef?: number;
|
|
31
|
+
}
|
|
32
|
+
/** EXIF 解析结果(字段全部可选 —— 缺失就是缺失,不填默认值) */
|
|
33
|
+
export interface ExifData {
|
|
34
|
+
make?: string;
|
|
35
|
+
model?: string;
|
|
36
|
+
lensModel?: string;
|
|
37
|
+
/** 原始拍摄时间(相机本地时间,无时区),格式 `YYYY-MM-DDTHH:MM:SS` */
|
|
38
|
+
dateTimeOriginal?: string;
|
|
39
|
+
/** 文件修改时间(EXIF DateTime) */
|
|
40
|
+
dateTime?: string;
|
|
41
|
+
/** 拍照方向(1~8,见 EXIF 规范;1 = 正常) */
|
|
42
|
+
orientation?: number;
|
|
43
|
+
focalLengthMm?: number;
|
|
44
|
+
/** 35mm 等效焦距 —— 换算内参的关键字段 */
|
|
45
|
+
focalLength35mm?: number;
|
|
46
|
+
exposureTimeSeconds?: number;
|
|
47
|
+
fNumber?: number;
|
|
48
|
+
isoSpeed?: number;
|
|
49
|
+
/** 图像宽高(EXIF 里记录的原始像素尺寸) */
|
|
50
|
+
pixelXDimension?: number;
|
|
51
|
+
pixelYDimension?: number;
|
|
52
|
+
gps?: ExifGps;
|
|
53
|
+
/** 解析过程中的异常/缺失说明(诊断用) */
|
|
54
|
+
warnings: string[];
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* 解析 JPEG 的 EXIF 段。
|
|
58
|
+
*
|
|
59
|
+
* @returns 解析结果;不是 JPEG / 没有 EXIF 段 / 结构不可识别时返回 `null`。
|
|
60
|
+
*/
|
|
61
|
+
export declare function parseJpegExif(bytes: Uint8Array): ExifData | null;
|
|
62
|
+
/** 从 Blob / File 读前若干字节解析 EXIF(只取头部,不必读整张图) */
|
|
63
|
+
export declare function readJpegExif(file: Blob, maxBytes?: number): Promise<ExifData | null>;
|
|
64
|
+
//# sourceMappingURL=drone-exif.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"drone-exif.d.ts","sourceRoot":"","sources":["../../src/lib/drone-camera/drone-exif.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AACH,2BAA2B;AAC3B,MAAM,WAAW,OAAO;IACtB,gBAAgB;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,gBAAgB;IAChB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,0CAA0C;IAC1C,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,iCAAiC;IACjC,WAAW,CAAC,EAAE,MAAM,CAAA;CACrB;AAED,wCAAwC;AACxC,MAAM,WAAW,QAAQ;IACvB,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,kDAAkD;IAClD,gBAAgB,CAAC,EAAE,MAAM,CAAA;IACzB,4BAA4B;IAC5B,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,iCAAiC;IACjC,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,aAAa,CAAC,EAAE,MAAM,CAAA;IACtB,6BAA6B;IAC7B,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,mBAAmB,CAAC,EAAE,MAAM,CAAA;IAC5B,OAAO,CAAC,EAAE,MAAM,CAAA;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,4BAA4B;IAC5B,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,GAAG,CAAC,EAAE,OAAO,CAAA;IACb,yBAAyB;IACzB,QAAQ,EAAE,MAAM,EAAE,CAAA;CACnB;AA6RD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,UAAU,GAAG,QAAQ,GAAG,IAAI,CAkChE;AAED,+CAA+C;AAC/C,wBAAsB,YAAY,CAAC,IAAI,EAAE,IAAI,EAAE,QAAQ,SAAa,GAAG,OAAO,CAAC,QAAQ,GAAG,IAAI,CAAC,CAa9F"}
|