@jorgmoritz/gis-manager 0.1.43 → 0.1.45
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/dist/index.cjs +524 -58
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +138 -1
- package/dist/index.d.ts +138 -1
- package/dist/index.js +520 -59
- package/dist/index.js.map +1 -1
- package/dist/vue/index.cjs +341 -55
- package/dist/vue/index.cjs.map +1 -1
- package/dist/vue/index.js +341 -55
- package/dist/vue/index.js.map +1 -1
- package/package.json +1 -1
package/dist/vue/index.js
CHANGED
|
@@ -1909,14 +1909,15 @@ var HeightMarker = class {
|
|
|
1909
1909
|
polyline: {
|
|
1910
1910
|
positions: [C.Cartesian3.ZERO, C.Cartesian3.ZERO],
|
|
1911
1911
|
width: this.opts.width ?? 2,
|
|
1912
|
-
material:
|
|
1912
|
+
material: C.Color.YELLOW.withAlpha(0.4),
|
|
1913
|
+
// 黄色半透明垂直线
|
|
1913
1914
|
clampToGround: false
|
|
1914
1915
|
// vertical line in 3D space
|
|
1915
1916
|
},
|
|
1916
1917
|
ellipse: {
|
|
1917
|
-
semiMajorAxis: this.opts.circleRadius ??
|
|
1918
|
-
semiMinorAxis: this.opts.circleRadius ??
|
|
1919
|
-
material: color.withAlpha ? color.withAlpha(0.
|
|
1918
|
+
semiMajorAxis: this.opts.circleRadius ?? 3,
|
|
1919
|
+
semiMinorAxis: this.opts.circleRadius ?? 3,
|
|
1920
|
+
material: color.withAlpha ? color.withAlpha(0.45) : color,
|
|
1920
1921
|
outline: true,
|
|
1921
1922
|
outlineColor: color,
|
|
1922
1923
|
heightReference: C.HeightReference.CLAMP_TO_GROUND
|
|
@@ -1927,12 +1928,13 @@ var HeightMarker = class {
|
|
|
1927
1928
|
position: C.Cartesian3.ZERO,
|
|
1928
1929
|
label: {
|
|
1929
1930
|
text: "",
|
|
1930
|
-
font: "
|
|
1931
|
+
font: "10px sans-serif",
|
|
1932
|
+
// 字体改小
|
|
1931
1933
|
style: C.LabelStyle.FILL_AND_OUTLINE,
|
|
1932
1934
|
fillColor: C.Color.BLACK,
|
|
1933
1935
|
outlineColor: C.Color.WHITE,
|
|
1934
|
-
outlineWidth:
|
|
1935
|
-
pixelOffset: new C.Cartesian2(0, -
|
|
1936
|
+
outlineWidth: 2,
|
|
1937
|
+
pixelOffset: new C.Cartesian2(0, -4),
|
|
1936
1938
|
showBackground: false,
|
|
1937
1939
|
horizontalOrigin: C.HorizontalOrigin.CENTER,
|
|
1938
1940
|
verticalOrigin: C.VerticalOrigin.BOTTOM,
|
|
@@ -3458,6 +3460,10 @@ var AirplaneCursor = class {
|
|
|
3458
3460
|
__publicField(this, "cachedScaleFactor", 1);
|
|
3459
3461
|
// 相机变化事件监听器
|
|
3460
3462
|
__publicField(this, "cameraChangedListener");
|
|
3463
|
+
/** 飞机游标模型可见性,默认 false */
|
|
3464
|
+
__publicField(this, "visible", false);
|
|
3465
|
+
/** 是否显示视锥体,默认 true */
|
|
3466
|
+
__publicField(this, "showFrustum", true);
|
|
3461
3467
|
const C = this.CesiumNS;
|
|
3462
3468
|
this.opts = opts;
|
|
3463
3469
|
this.pose = { position: startPosition, heading: 0, pitch: -10, roll: 0 };
|
|
@@ -3465,6 +3471,8 @@ var AirplaneCursor = class {
|
|
|
3465
3471
|
this.angleStep = opts.angleStepDeg ?? 1;
|
|
3466
3472
|
this.fastFactor = opts.fastFactor ?? 5;
|
|
3467
3473
|
this.currentFOV = opts.fovDeg ?? DEFAULT_FOV;
|
|
3474
|
+
this.visible = opts.visible ?? false;
|
|
3475
|
+
this.showFrustum = opts.showFrustum ?? true;
|
|
3468
3476
|
this.ensureEntity(opts.color ?? C.Color.CYAN.withAlpha(0.9));
|
|
3469
3477
|
this.attachKeyboard(opts);
|
|
3470
3478
|
this.setupFOVListener();
|
|
@@ -3519,6 +3527,8 @@ var AirplaneCursor = class {
|
|
|
3519
3527
|
runAnimations: true,
|
|
3520
3528
|
clampAnimations: false
|
|
3521
3529
|
},
|
|
3530
|
+
show: this.visible,
|
|
3531
|
+
// 根据 visible 设置初始显示状态
|
|
3522
3532
|
properties: { _type: "airplane-cursor" }
|
|
3523
3533
|
});
|
|
3524
3534
|
this.entity = this.modelEntity;
|
|
@@ -3696,6 +3706,7 @@ var AirplaneCursor = class {
|
|
|
3696
3706
|
* - 后续只依赖回调读取 pose 与 currentFOV 即可自动更新
|
|
3697
3707
|
*/
|
|
3698
3708
|
updateFrustum() {
|
|
3709
|
+
if (!this.showFrustum) return;
|
|
3699
3710
|
try {
|
|
3700
3711
|
if (!this.frustum) {
|
|
3701
3712
|
let layer = this.viewer.dataSources?._dataSources?.[0];
|
|
@@ -3746,6 +3757,18 @@ var AirplaneCursor = class {
|
|
|
3746
3757
|
altitude
|
|
3747
3758
|
};
|
|
3748
3759
|
}
|
|
3760
|
+
/** 设置飞机游标可见性 */
|
|
3761
|
+
setVisible(visible) {
|
|
3762
|
+
this.visible = visible;
|
|
3763
|
+
if (this.modelEntity) {
|
|
3764
|
+
this.modelEntity.show = visible;
|
|
3765
|
+
}
|
|
3766
|
+
this.viewer.scene?.requestRender?.();
|
|
3767
|
+
}
|
|
3768
|
+
/** 获取当前可见性状态 */
|
|
3769
|
+
isVisible() {
|
|
3770
|
+
return this.visible;
|
|
3771
|
+
}
|
|
3749
3772
|
/** 获取内部实体(用于拾取识别) */
|
|
3750
3773
|
getEntity() {
|
|
3751
3774
|
return this.entity;
|
|
@@ -4936,6 +4959,34 @@ function calculateRelativeHeight(altitudeMode, absoluteHeight, startPointAltitud
|
|
|
4936
4959
|
}
|
|
4937
4960
|
}
|
|
4938
4961
|
|
|
4962
|
+
// src/utils/geometryUtils.ts
|
|
4963
|
+
function calculateDistanceAndMidpoint(CesiumNS, point1, point2) {
|
|
4964
|
+
const C = CesiumNS;
|
|
4965
|
+
const distance = C.Cartesian3.distance(point1, point2);
|
|
4966
|
+
const midpoint = new C.Cartesian3();
|
|
4967
|
+
C.Cartesian3.midpoint(point1, point2, midpoint);
|
|
4968
|
+
return { distance, midpoint };
|
|
4969
|
+
}
|
|
4970
|
+
function calculateHeadingBetweenPoints(CesiumNS, point1, point2) {
|
|
4971
|
+
const C = CesiumNS;
|
|
4972
|
+
try {
|
|
4973
|
+
const fromCarto = C.Cartographic.fromCartesian(point1);
|
|
4974
|
+
const toCarto = C.Cartographic.fromCartesian(point2);
|
|
4975
|
+
const deltaLon = toCarto.longitude - fromCarto.longitude;
|
|
4976
|
+
let heading = Math.atan2(
|
|
4977
|
+
Math.sin(deltaLon) * Math.cos(toCarto.latitude),
|
|
4978
|
+
Math.cos(fromCarto.latitude) * Math.sin(toCarto.latitude) - Math.sin(fromCarto.latitude) * Math.cos(toCarto.latitude) * Math.cos(deltaLon)
|
|
4979
|
+
);
|
|
4980
|
+
heading = C.Math.toDegrees(heading);
|
|
4981
|
+
if (heading > 180) heading -= 360;
|
|
4982
|
+
if (heading < -180) heading += 360;
|
|
4983
|
+
return heading;
|
|
4984
|
+
} catch (error) {
|
|
4985
|
+
console.error("[calculateHeadingBetweenPoints] Error:", error);
|
|
4986
|
+
return 0;
|
|
4987
|
+
}
|
|
4988
|
+
}
|
|
4989
|
+
|
|
4939
4990
|
// src/core/path-manager/editing/PathEditingEventHandler.ts
|
|
4940
4991
|
var PathEditingEventHandler = class {
|
|
4941
4992
|
constructor(options, callbacks) {
|
|
@@ -4996,36 +5047,14 @@ var PathEditingEventHandler = class {
|
|
|
4996
5047
|
if (typeof index === "number") {
|
|
4997
5048
|
if (currentActiveIndex === index) {
|
|
4998
5049
|
this.vertexDragHandler.startDrag(index, movement.position);
|
|
4999
|
-
} else {
|
|
5000
|
-
if (this.callbacks.onVertexSelect) {
|
|
5001
|
-
this.callbacks.onVertexSelect(index);
|
|
5002
|
-
}
|
|
5003
|
-
console.log("[PathEditingEventHandler] \u9876\u70B9\u88AB\u70B9\u51FB\uFF0C\u7D22\u5F15:", index, "\u56DE\u8C03\u5B58\u5728:", !!this.callbacks.onVertexSelectDetail);
|
|
5004
|
-
if (this.callbacks.onVertexSelectDetail) {
|
|
5005
|
-
try {
|
|
5006
|
-
const detailInfo = this.buildVertexDetailInfo(index);
|
|
5007
|
-
console.log("[PathEditingEventHandler] \u8C03\u7528 onVertexSelectDetail \u56DE\u8C03");
|
|
5008
|
-
this.callbacks.onVertexSelectDetail(detailInfo);
|
|
5009
|
-
} catch (error) {
|
|
5010
|
-
console.error("[PathEditingEventHandler] Error building vertex detail info:", error);
|
|
5011
|
-
}
|
|
5012
|
-
}
|
|
5013
5050
|
}
|
|
5014
5051
|
return;
|
|
5015
5052
|
}
|
|
5016
5053
|
}
|
|
5017
5054
|
const idx = pickVertexIndex(this.viewer, movement.position, this.hiddenClimbIndex);
|
|
5018
5055
|
if (typeof idx === "number") {
|
|
5019
|
-
if (
|
|
5020
|
-
this.
|
|
5021
|
-
}
|
|
5022
|
-
if (this.callbacks.onVertexSelectDetail) {
|
|
5023
|
-
try {
|
|
5024
|
-
const detailInfo = this.buildVertexDetailInfo(idx);
|
|
5025
|
-
this.callbacks.onVertexSelectDetail(detailInfo);
|
|
5026
|
-
} catch (error) {
|
|
5027
|
-
console.error("Error building vertex detail info:", error);
|
|
5028
|
-
}
|
|
5056
|
+
if (currentActiveIndex === idx) {
|
|
5057
|
+
this.vertexDragHandler.startDrag(idx, movement.position);
|
|
5029
5058
|
}
|
|
5030
5059
|
}
|
|
5031
5060
|
}, C.ScreenSpaceEventType.LEFT_DOWN);
|
|
@@ -5044,6 +5073,26 @@ var PathEditingEventHandler = class {
|
|
|
5044
5073
|
if (this.vertexDragHandler.isDragging()) {
|
|
5045
5074
|
return;
|
|
5046
5075
|
}
|
|
5076
|
+
const scene = this.viewer.scene;
|
|
5077
|
+
const picked = scene.pick?.(movement.position);
|
|
5078
|
+
const entity = picked?.id;
|
|
5079
|
+
if (entity?.properties?._type?.getValue?.() === "vertex-label") {
|
|
5080
|
+
const labelIndex = entity.properties._vertexIndex?.getValue?.();
|
|
5081
|
+
if (typeof labelIndex === "number") {
|
|
5082
|
+
if (this.callbacks.onVertexSelect) {
|
|
5083
|
+
this.callbacks.onVertexSelect(labelIndex);
|
|
5084
|
+
}
|
|
5085
|
+
if (this.callbacks.onVertexSelectDetail) {
|
|
5086
|
+
try {
|
|
5087
|
+
const detailInfo = this.buildVertexDetailInfo(labelIndex);
|
|
5088
|
+
this.callbacks.onVertexSelectDetail(detailInfo);
|
|
5089
|
+
} catch (error) {
|
|
5090
|
+
console.error("Error building vertex detail info:", error);
|
|
5091
|
+
}
|
|
5092
|
+
}
|
|
5093
|
+
return;
|
|
5094
|
+
}
|
|
5095
|
+
}
|
|
5047
5096
|
const idx = pickVertexIndex(this.viewer, movement.position, this.hiddenClimbIndex);
|
|
5048
5097
|
if (typeof idx === "number") {
|
|
5049
5098
|
if (this.callbacks.onVertexSelect) {
|
|
@@ -5059,6 +5108,45 @@ var PathEditingEventHandler = class {
|
|
|
5059
5108
|
}
|
|
5060
5109
|
return;
|
|
5061
5110
|
}
|
|
5111
|
+
const CLICK_THRESHOLD_PIXELS = 25;
|
|
5112
|
+
const positions = this.callbacks.getPositions?.() || [];
|
|
5113
|
+
if (positions.length > 0) {
|
|
5114
|
+
const clickPos = movement.position;
|
|
5115
|
+
let minDistance = Infinity;
|
|
5116
|
+
let nearestIndex = -1;
|
|
5117
|
+
for (let i = 0; i < positions.length; i++) {
|
|
5118
|
+
try {
|
|
5119
|
+
const screenPos = C.SceneTransforms.wgs84ToWindowCoordinates(
|
|
5120
|
+
scene,
|
|
5121
|
+
positions[i]
|
|
5122
|
+
);
|
|
5123
|
+
if (screenPos) {
|
|
5124
|
+
const dx = screenPos.x - clickPos.x;
|
|
5125
|
+
const dy = screenPos.y - clickPos.y;
|
|
5126
|
+
const distance = Math.sqrt(dx * dx + dy * dy);
|
|
5127
|
+
if (distance < minDistance) {
|
|
5128
|
+
minDistance = distance;
|
|
5129
|
+
nearestIndex = i;
|
|
5130
|
+
}
|
|
5131
|
+
}
|
|
5132
|
+
} catch {
|
|
5133
|
+
}
|
|
5134
|
+
}
|
|
5135
|
+
if (minDistance < CLICK_THRESHOLD_PIXELS && nearestIndex >= 0) {
|
|
5136
|
+
if (this.callbacks.onVertexSelect) {
|
|
5137
|
+
this.callbacks.onVertexSelect(nearestIndex);
|
|
5138
|
+
}
|
|
5139
|
+
if (this.callbacks.onVertexSelectDetail) {
|
|
5140
|
+
try {
|
|
5141
|
+
const detailInfo = this.buildVertexDetailInfo(nearestIndex);
|
|
5142
|
+
this.callbacks.onVertexSelectDetail(detailInfo);
|
|
5143
|
+
} catch (error) {
|
|
5144
|
+
console.error("Error building vertex detail info:", error);
|
|
5145
|
+
}
|
|
5146
|
+
}
|
|
5147
|
+
return;
|
|
5148
|
+
}
|
|
5149
|
+
}
|
|
5062
5150
|
const quickEditEnabled = this.callbacks.getQuickEditEnabled?.();
|
|
5063
5151
|
if (quickEditEnabled) {
|
|
5064
5152
|
this.handleQuickEditClick(movement);
|
|
@@ -5162,6 +5250,14 @@ var PathEditingEventHandler = class {
|
|
|
5162
5250
|
this.handleInsertVertex(activeIndex + 1, pose, "after");
|
|
5163
5251
|
}
|
|
5164
5252
|
});
|
|
5253
|
+
if (activeIndex < positions.length - 1) {
|
|
5254
|
+
menuItems.push({
|
|
5255
|
+
label: "\u5728\u4E2D\u95F4\u63D2\u5165\u822A\u70B9",
|
|
5256
|
+
action: () => {
|
|
5257
|
+
this.handleInsertMidpoint(activeIndex);
|
|
5258
|
+
}
|
|
5259
|
+
});
|
|
5260
|
+
}
|
|
5165
5261
|
} else if (pose && visibleVertexCount <= 1) {
|
|
5166
5262
|
menuItems.push({
|
|
5167
5263
|
label: "\u6DFB\u52A0\u7B2C\u4E00\u4E2A\u822A\u70B9",
|
|
@@ -5308,6 +5404,27 @@ var PathEditingEventHandler = class {
|
|
|
5308
5404
|
});
|
|
5309
5405
|
}
|
|
5310
5406
|
}
|
|
5407
|
+
/**
|
|
5408
|
+
* 🆕 在选中航点和下一个航点中间插入新航点
|
|
5409
|
+
*/
|
|
5410
|
+
handleInsertMidpoint(activeIndex) {
|
|
5411
|
+
const positions = this.callbacks.getPositions?.() || [];
|
|
5412
|
+
const poseData = this.callbacks.getPoseData?.();
|
|
5413
|
+
if (activeIndex >= positions.length - 1) {
|
|
5414
|
+
console.warn("[handleInsertMidpoint] \u9009\u4E2D\u822A\u70B9\u662F\u6700\u540E\u4E00\u4E2A\uFF0C\u65E0\u6CD5\u63D2\u5165\u4E2D\u70B9");
|
|
5415
|
+
return;
|
|
5416
|
+
}
|
|
5417
|
+
const point1 = positions[activeIndex];
|
|
5418
|
+
const point2 = positions[activeIndex + 1];
|
|
5419
|
+
const { midpoint } = calculateDistanceAndMidpoint(this.CesiumNS, point1, point2);
|
|
5420
|
+
const heading = calculateHeadingBetweenPoints(this.CesiumNS, point1, point2);
|
|
5421
|
+
const pitch = poseData?.pitches[activeIndex] ?? -10;
|
|
5422
|
+
const roll = poseData?.rolls[activeIndex] ?? 0;
|
|
5423
|
+
console.log("[handleInsertMidpoint] \u5728\u7D22\u5F15", activeIndex, "\u548C", activeIndex + 1, "\u4E4B\u95F4\u63D2\u5165\u4E2D\u70B9");
|
|
5424
|
+
if (this.callbacks.onInsertVertex) {
|
|
5425
|
+
this.callbacks.onInsertVertex(activeIndex + 1, midpoint, { heading, pitch, roll });
|
|
5426
|
+
}
|
|
5427
|
+
}
|
|
5311
5428
|
/**
|
|
5312
5429
|
* 处理删除顶点
|
|
5313
5430
|
*/
|
|
@@ -5756,23 +5873,37 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
5756
5873
|
while (useGlobalHeightFlags.length < positions.length) {
|
|
5757
5874
|
useGlobalHeightFlags.push(false);
|
|
5758
5875
|
}
|
|
5759
|
-
|
|
5876
|
+
const waypointIds = [];
|
|
5877
|
+
if (options?.waypointIds && Array.isArray(options.waypointIds)) {
|
|
5878
|
+
const offset = 0;
|
|
5879
|
+
for (let i = 0; i < offset; i++) {
|
|
5880
|
+
waypointIds[i] = void 0;
|
|
5881
|
+
}
|
|
5882
|
+
options.waypointIds.forEach((id, idx) => {
|
|
5883
|
+
waypointIds[offset + idx] = id;
|
|
5884
|
+
});
|
|
5885
|
+
}
|
|
5886
|
+
while (waypointIds.length < positions.length) {
|
|
5887
|
+
waypointIds.push(void 0);
|
|
5888
|
+
}
|
|
5889
|
+
let quickEditEnabled = true;
|
|
5760
5890
|
let quickEditOptions = {
|
|
5761
|
-
enabled:
|
|
5891
|
+
enabled: true,
|
|
5762
5892
|
climbHeight: currentDefaultAltitude,
|
|
5763
5893
|
// 使用当前默认高度
|
|
5764
5894
|
altitudeMode: currentAltitudeMode
|
|
5765
5895
|
// 使用当前高度模式
|
|
5766
5896
|
};
|
|
5767
|
-
if (options?.quickEdit) {
|
|
5897
|
+
if (options?.quickEdit !== void 0) {
|
|
5768
5898
|
if (typeof options.quickEdit === "boolean") {
|
|
5769
5899
|
quickEditEnabled = options.quickEdit;
|
|
5770
5900
|
quickEditOptions.enabled = options.quickEdit;
|
|
5771
5901
|
} else {
|
|
5772
|
-
quickEditEnabled = options.quickEdit.enabled ??
|
|
5902
|
+
quickEditEnabled = options.quickEdit.enabled ?? true;
|
|
5773
5903
|
quickEditOptions = {
|
|
5774
5904
|
...quickEditOptions,
|
|
5775
|
-
...options.quickEdit
|
|
5905
|
+
...options.quickEdit,
|
|
5906
|
+
enabled: options.quickEdit.enabled ?? true
|
|
5776
5907
|
};
|
|
5777
5908
|
}
|
|
5778
5909
|
}
|
|
@@ -5867,6 +5998,8 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
5867
5998
|
const stateManager = new PathStateManager(entity, positions, headings, pitches, rolls, fovs);
|
|
5868
5999
|
let activeIndex;
|
|
5869
6000
|
let editedIndices = /* @__PURE__ */ new Set();
|
|
6001
|
+
let isUpdatingFromCursor = false;
|
|
6002
|
+
let isUpdatingFromDrag = false;
|
|
5870
6003
|
const handleStyleManager = new VertexHandleStyleManager(CesiumNS);
|
|
5871
6004
|
const setActiveIndex = (idx) => {
|
|
5872
6005
|
if (activeIndex !== void 0 && handles[activeIndex]) {
|
|
@@ -5972,6 +6105,7 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
5972
6105
|
useGlobalHeightFlags
|
|
5973
6106
|
// 🆕 传递 useGlobalHeightFlags
|
|
5974
6107
|
);
|
|
6108
|
+
waypointIds.splice(actualIndex, 0, void 0);
|
|
5975
6109
|
console.log("[PathEditing] \u63D2\u5165\u9876\u70B9\u540E positions \u957F\u5EA6:", positions.length, "actualIndex:", actualIndex);
|
|
5976
6110
|
entity.polyline.positions = new C.CallbackProperty(() => positions.slice(), false);
|
|
5977
6111
|
setActiveIndex(actualIndex);
|
|
@@ -6004,6 +6138,7 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
6004
6138
|
fovs.splice(deleteAt, 1);
|
|
6005
6139
|
heightMarkers.splice(deleteAt, 1);
|
|
6006
6140
|
useGlobalHeightFlags.splice(deleteAt, 1);
|
|
6141
|
+
waypointIds.splice(deleteAt, 1);
|
|
6007
6142
|
console.log("[PathEditing] \u5220\u9664\u9876\u70B9\u540E positions \u957F\u5EA6:", positions.length);
|
|
6008
6143
|
entity.polyline.positions = new C.CallbackProperty(() => positions.slice(), false);
|
|
6009
6144
|
const newEditedIndices = /* @__PURE__ */ new Set();
|
|
@@ -6090,12 +6225,36 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
6090
6225
|
}
|
|
6091
6226
|
airplaneCursor.updateOptions({
|
|
6092
6227
|
onPose: (pose) => {
|
|
6228
|
+
if (isUpdatingFromDrag) return;
|
|
6093
6229
|
try {
|
|
6094
6230
|
if (preview) {
|
|
6095
6231
|
preview.setPose(pose.position, pose.heading, pose.pitch, pose.roll, 50);
|
|
6096
6232
|
}
|
|
6097
6233
|
} catch {
|
|
6098
6234
|
}
|
|
6235
|
+
if (activeIndex !== void 0 && !isUpdatingFromCursor) {
|
|
6236
|
+
isUpdatingFromCursor = true;
|
|
6237
|
+
try {
|
|
6238
|
+
positions[activeIndex] = pose.position;
|
|
6239
|
+
headings[activeIndex] = pose.heading;
|
|
6240
|
+
pitches[activeIndex] = pose.pitch;
|
|
6241
|
+
rolls[activeIndex] = pose.roll;
|
|
6242
|
+
if (handles[activeIndex]) {
|
|
6243
|
+
handles[activeIndex].position = pose.position;
|
|
6244
|
+
}
|
|
6245
|
+
vertexLabelManager.updateLabelPosition(activeIndex, pose.position);
|
|
6246
|
+
createOrUpdateMarkerForIndex(activeIndex);
|
|
6247
|
+
editedIndices.add(activeIndex);
|
|
6248
|
+
useGlobalHeightFlags[activeIndex] = false;
|
|
6249
|
+
try {
|
|
6250
|
+
entity.polyline.positions = positions.slice();
|
|
6251
|
+
} catch {
|
|
6252
|
+
}
|
|
6253
|
+
viewer.scene?.requestRender?.();
|
|
6254
|
+
} finally {
|
|
6255
|
+
isUpdatingFromCursor = false;
|
|
6256
|
+
}
|
|
6257
|
+
}
|
|
6099
6258
|
}
|
|
6100
6259
|
});
|
|
6101
6260
|
}
|
|
@@ -6171,24 +6330,38 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
6171
6330
|
},
|
|
6172
6331
|
onVertexDragMove: (index, newPosition) => {
|
|
6173
6332
|
console.log("[PathEditing] onVertexDragMove \u88AB\u8C03\u7528, index:", index);
|
|
6174
|
-
|
|
6175
|
-
|
|
6333
|
+
if (isUpdatingFromCursor) return;
|
|
6334
|
+
isUpdatingFromDrag = true;
|
|
6335
|
+
try {
|
|
6336
|
+
positions[index] = newPosition;
|
|
6337
|
+
if (handles[index]) {
|
|
6338
|
+
try {
|
|
6339
|
+
handles[index].position = newPosition;
|
|
6340
|
+
} catch {
|
|
6341
|
+
}
|
|
6342
|
+
}
|
|
6176
6343
|
try {
|
|
6177
|
-
|
|
6344
|
+
vertexLabelManager.updateLabelPosition(index, newPosition);
|
|
6178
6345
|
} catch {
|
|
6179
6346
|
}
|
|
6180
|
-
|
|
6181
|
-
|
|
6182
|
-
|
|
6183
|
-
|
|
6184
|
-
|
|
6185
|
-
|
|
6186
|
-
|
|
6187
|
-
|
|
6188
|
-
|
|
6189
|
-
|
|
6190
|
-
|
|
6191
|
-
|
|
6347
|
+
try {
|
|
6348
|
+
entity.polyline.positions = positions.slice();
|
|
6349
|
+
} catch {
|
|
6350
|
+
}
|
|
6351
|
+
try {
|
|
6352
|
+
viewer.scene.requestRender();
|
|
6353
|
+
} catch {
|
|
6354
|
+
}
|
|
6355
|
+
if (airplaneCursor && index === activeIndex) {
|
|
6356
|
+
airplaneCursor.setPose(
|
|
6357
|
+
newPosition,
|
|
6358
|
+
headings[index] ?? 0,
|
|
6359
|
+
pitches[index] ?? -10,
|
|
6360
|
+
rolls[index] ?? 0
|
|
6361
|
+
);
|
|
6362
|
+
}
|
|
6363
|
+
} finally {
|
|
6364
|
+
isUpdatingFromDrag = false;
|
|
6192
6365
|
}
|
|
6193
6366
|
if (options?.onVertexDragMoveDetail) {
|
|
6194
6367
|
try {
|
|
@@ -6392,6 +6565,55 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
6392
6565
|
// 🆕 添加相对高度
|
|
6393
6566
|
};
|
|
6394
6567
|
};
|
|
6568
|
+
if (options?.initialClickPosition && positions.length === 0) {
|
|
6569
|
+
console.log("[PathEditing] \u5904\u7406\u521D\u59CB\u70B9\u51FB\u4F4D\u7F6E\uFF0C\u7ACB\u5373\u6DFB\u52A0\u7B2C\u4E00\u4E2A\u822A\u70B9");
|
|
6570
|
+
let finalPosition = options.initialClickPosition;
|
|
6571
|
+
try {
|
|
6572
|
+
const cartographic = C.Cartographic.fromCartesian(options.initialClickPosition);
|
|
6573
|
+
const lon = C.Math.toDegrees(cartographic.longitude);
|
|
6574
|
+
const lat = C.Math.toDegrees(cartographic.latitude);
|
|
6575
|
+
let finalHeight;
|
|
6576
|
+
if (currentAltitudeMode === "absolute") {
|
|
6577
|
+
finalHeight = currentDefaultAltitude;
|
|
6578
|
+
} else if (currentAltitudeMode === "relativeToGround") {
|
|
6579
|
+
const terrainHeight = queryTerrainHeightSync(CesiumNS, viewer, options.initialClickPosition);
|
|
6580
|
+
finalHeight = terrainHeight + currentDefaultAltitude;
|
|
6581
|
+
} else if (currentAltitudeMode === "relativeToStart") {
|
|
6582
|
+
finalHeight = currentDefaultAltitude;
|
|
6583
|
+
} else {
|
|
6584
|
+
finalHeight = currentDefaultAltitude;
|
|
6585
|
+
}
|
|
6586
|
+
finalPosition = C.Cartesian3.fromDegrees(lon, lat, finalHeight);
|
|
6587
|
+
console.log("[PathEditing] \u521D\u59CB\u822A\u70B9\u9AD8\u5EA6\u8BA1\u7B97:", {
|
|
6588
|
+
altitudeMode: currentAltitudeMode,
|
|
6589
|
+
defaultAltitude: currentDefaultAltitude,
|
|
6590
|
+
finalHeight
|
|
6591
|
+
});
|
|
6592
|
+
} catch (error) {
|
|
6593
|
+
console.warn("[PathEditing] \u8BA1\u7B97\u521D\u59CB\u822A\u70B9\u9AD8\u5EA6\u5931\u8D25:", error);
|
|
6594
|
+
}
|
|
6595
|
+
const totalBefore = positions.length;
|
|
6596
|
+
insertVertex(0, finalPosition, { heading: 0, pitch: -10, roll: 0 });
|
|
6597
|
+
if (options?.onVertexInsertDetail) {
|
|
6598
|
+
try {
|
|
6599
|
+
const totalAfter = positions.length;
|
|
6600
|
+
const newVertex = buildVertexDetailInfo(0);
|
|
6601
|
+
const operationInfo = {
|
|
6602
|
+
type: "insert",
|
|
6603
|
+
index: 0,
|
|
6604
|
+
displayNumber: newVertex.displayNumber,
|
|
6605
|
+
totalVerticesBefore: totalBefore,
|
|
6606
|
+
totalVerticesAfter: totalAfter,
|
|
6607
|
+
newVertex,
|
|
6608
|
+
timestamp: /* @__PURE__ */ new Date(),
|
|
6609
|
+
totalDistance: getTotalDistance()
|
|
6610
|
+
};
|
|
6611
|
+
options.onVertexInsertDetail(operationInfo);
|
|
6612
|
+
} catch (error) {
|
|
6613
|
+
console.error("[PathEditing] \u89E6\u53D1 onVertexInsertDetail \u56DE\u8C03\u5931\u8D25:", error);
|
|
6614
|
+
}
|
|
6615
|
+
}
|
|
6616
|
+
}
|
|
6395
6617
|
return {
|
|
6396
6618
|
/** 保存并退出编辑模式 */
|
|
6397
6619
|
saveAndStop: () => {
|
|
@@ -6433,8 +6655,10 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
6433
6655
|
distance: calculatePathDistance(CesiumNS, positions, index),
|
|
6434
6656
|
ellipsoidHeight,
|
|
6435
6657
|
relativeHeight,
|
|
6436
|
-
useGlobalHeight: useGlobalHeightFlags[index] ?? false
|
|
6658
|
+
useGlobalHeight: useGlobalHeightFlags[index] ?? false,
|
|
6437
6659
|
// 🆕 添加 useGlobalHeight
|
|
6660
|
+
waypointId: waypointIds[index]
|
|
6661
|
+
// 🆕 添加 waypointId(原有航点保留ID,新插入航点为 undefined)
|
|
6438
6662
|
};
|
|
6439
6663
|
});
|
|
6440
6664
|
cleanupSession();
|
|
@@ -6817,6 +7041,67 @@ function startPathEditing(CesiumNS, viewer, entityOrId, options) {
|
|
|
6817
7041
|
options2?.onProgress?.("error");
|
|
6818
7042
|
return { success: false, error: String(error) };
|
|
6819
7043
|
}
|
|
7044
|
+
},
|
|
7045
|
+
/**
|
|
7046
|
+
* 🆕 获取当前选中航点索引
|
|
7047
|
+
* @returns 当前选中的航点索引,如果没有选中则返回 undefined
|
|
7048
|
+
*/
|
|
7049
|
+
getActiveIndex: () => {
|
|
7050
|
+
return activeIndex;
|
|
7051
|
+
},
|
|
7052
|
+
/**
|
|
7053
|
+
* 🆕 在选中航点和下一个航点中间插入新航点
|
|
7054
|
+
* @param index 选中航点的索引(如果不传则使用当前选中的航点)
|
|
7055
|
+
* @returns 是否插入成功
|
|
7056
|
+
*/
|
|
7057
|
+
insertMidpoint: (index) => {
|
|
7058
|
+
const targetIndex = index ?? activeIndex;
|
|
7059
|
+
if (targetIndex === void 0) {
|
|
7060
|
+
console.warn("[insertMidpoint] \u6CA1\u6709\u9009\u4E2D\u822A\u70B9");
|
|
7061
|
+
return false;
|
|
7062
|
+
}
|
|
7063
|
+
if (targetIndex >= positions.length - 1) {
|
|
7064
|
+
console.warn("[insertMidpoint] \u9009\u4E2D\u822A\u70B9\u662F\u6700\u540E\u4E00\u4E2A\uFF0C\u65E0\u6CD5\u63D2\u5165\u4E2D\u70B9");
|
|
7065
|
+
return false;
|
|
7066
|
+
}
|
|
7067
|
+
const point1 = positions[targetIndex];
|
|
7068
|
+
const point2 = positions[targetIndex + 1];
|
|
7069
|
+
const midpoint = C.Cartesian3.midpoint(point1, point2, new C.Cartesian3());
|
|
7070
|
+
const carto1 = C.Cartographic.fromCartesian(point1);
|
|
7071
|
+
const carto2 = C.Cartographic.fromCartesian(point2);
|
|
7072
|
+
const deltaLon = carto2.longitude - carto1.longitude;
|
|
7073
|
+
let heading = Math.atan2(
|
|
7074
|
+
Math.sin(deltaLon) * Math.cos(carto2.latitude),
|
|
7075
|
+
Math.cos(carto1.latitude) * Math.sin(carto2.latitude) - Math.sin(carto1.latitude) * Math.cos(carto2.latitude) * Math.cos(deltaLon)
|
|
7076
|
+
);
|
|
7077
|
+
heading = C.Math.toDegrees(heading);
|
|
7078
|
+
if (heading > 180) heading -= 360;
|
|
7079
|
+
if (heading < -180) heading += 360;
|
|
7080
|
+
const pitch = pitches[targetIndex] ?? -10;
|
|
7081
|
+
const roll = rolls[targetIndex] ?? 0;
|
|
7082
|
+
console.log("[insertMidpoint] \u5728\u7D22\u5F15", targetIndex, "\u548C", targetIndex + 1, "\u4E4B\u95F4\u63D2\u5165\u4E2D\u70B9");
|
|
7083
|
+
const totalBefore = positions.length;
|
|
7084
|
+
insertVertex(targetIndex + 1, midpoint, { heading, pitch, roll });
|
|
7085
|
+
if (options?.onVertexInsertDetail) {
|
|
7086
|
+
try {
|
|
7087
|
+
const totalAfter = positions.length;
|
|
7088
|
+
const newVertex = buildVertexDetailInfo(targetIndex + 1);
|
|
7089
|
+
const operationInfo = {
|
|
7090
|
+
type: "insert",
|
|
7091
|
+
index: targetIndex + 1,
|
|
7092
|
+
displayNumber: newVertex.displayNumber,
|
|
7093
|
+
totalVerticesBefore: totalBefore,
|
|
7094
|
+
totalVerticesAfter: totalAfter,
|
|
7095
|
+
newVertex,
|
|
7096
|
+
timestamp: /* @__PURE__ */ new Date(),
|
|
7097
|
+
totalDistance: getTotalDistance()
|
|
7098
|
+
};
|
|
7099
|
+
options.onVertexInsertDetail(operationInfo);
|
|
7100
|
+
} catch (error) {
|
|
7101
|
+
console.error("Error in onVertexInsertDetail:", error);
|
|
7102
|
+
}
|
|
7103
|
+
}
|
|
7104
|
+
return true;
|
|
6820
7105
|
}
|
|
6821
7106
|
};
|
|
6822
7107
|
}
|
|
@@ -6898,8 +7183,8 @@ function startPathDrawing(CesiumNS, viewer, options, onComplete) {
|
|
|
6898
7183
|
try {
|
|
6899
7184
|
const auto = options?.autoStartEditing;
|
|
6900
7185
|
const editOptions = {
|
|
6901
|
-
//
|
|
6902
|
-
quickEdit:
|
|
7186
|
+
// 🔧 修复:默认使用快速编辑模式,用户点击地图即可添加航点
|
|
7187
|
+
quickEdit: true
|
|
6903
7188
|
};
|
|
6904
7189
|
if (typeof auto === "object" && auto.preview) {
|
|
6905
7190
|
editOptions.preview = auto.preview;
|
|
@@ -6925,8 +7210,9 @@ function startPathDrawing(CesiumNS, viewer, options, onComplete) {
|
|
|
6925
7210
|
editOptions.altitudeMode = altitudeMode;
|
|
6926
7211
|
editOptions.defaultAltitude = defaultAltitude;
|
|
6927
7212
|
editOptions.climbHeight = climbHeight;
|
|
7213
|
+
editOptions.initialClickPosition = picked;
|
|
6928
7214
|
editSession = startPathEditing(CesiumNS, viewer, created, editOptions);
|
|
6929
|
-
console.log("[startPathDrawing] \u7F16\u8F91\u6A21\u5F0F\u5DF2\u542F\u52A8\uFF0C\
|
|
7215
|
+
console.log("[startPathDrawing] \u7F16\u8F91\u6A21\u5F0F\u5DF2\u542F\u52A8\uFF0C\u5FEB\u901F\u7F16\u8F91\u6A21\u5F0F\uFF0C\u70B9\u51FB\u5730\u56FE\u6DFB\u52A0\u822A\u70B9");
|
|
6930
7216
|
if (editSession && options?.onEditingStarted) {
|
|
6931
7217
|
try {
|
|
6932
7218
|
options.onEditingStarted(editSession);
|