@fleet-frontend/mower-maps 0.0.9-beta.5 → 0.0.9-beta.6
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/config/constants.d.ts +1 -25
- package/dist/config/constants.d.ts.map +1 -1
- package/dist/config/styles.d.ts +1 -1
- package/dist/config/styles.d.ts.map +1 -1
- package/dist/index.d.ts +2 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.esm.js +278 -130
- package/dist/index.js +278 -130
- package/dist/processor/MapDataProcessor.d.ts +1 -1
- package/dist/processor/MapDataProcessor.d.ts.map +1 -1
- package/dist/processor/PathDataProcessor.d.ts +2 -21
- package/dist/processor/PathDataProcessor.d.ts.map +1 -1
- package/dist/processor/builder/AntennaDataBuilder.d.ts +2 -1
- package/dist/processor/builder/AntennaDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/BoundaryDataBuilder.d.ts +1 -1
- package/dist/processor/builder/BoundaryDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/ChannelDataBuilder.d.ts +1 -1
- package/dist/processor/builder/ChannelDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/ChargingPileDataBuilder.d.ts +1 -1
- package/dist/processor/builder/ChargingPileDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/ObstacleDataBuilder.d.ts +2 -1
- package/dist/processor/builder/ObstacleDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/PathDataBuilder.d.ts +1 -1
- package/dist/processor/builder/PathDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/PointDataBuilder.d.ts +2 -1
- package/dist/processor/builder/PointDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/SvgElementDataBuilder.d.ts +1 -1
- package/dist/processor/builder/SvgElementDataBuilder.d.ts.map +1 -1
- package/dist/processor/builder/VisionOffDataBuilder.d.ts +2 -1
- package/dist/processor/builder/VisionOffDataBuilder.d.ts.map +1 -1
- package/dist/processor/index.d.ts +2 -1
- package/dist/processor/index.d.ts.map +1 -1
- package/dist/render/BoundaryLabelsManager.d.ts +1 -1
- package/dist/render/BoundaryLabelsManager.d.ts.map +1 -1
- package/dist/render/MowerMapOverlay.d.ts +2 -2
- package/dist/render/MowerMapOverlay.d.ts.map +1 -1
- package/dist/render/MowerMapRenderer.d.ts.map +1 -1
- package/dist/render/MowerPositionManager.d.ts.map +1 -1
- package/dist/render/SvgMapView.d.ts.map +1 -1
- package/dist/render/layers/BoundaryBorderLayer.d.ts +2 -2
- package/dist/render/layers/BoundaryBorderLayer.d.ts.map +1 -1
- package/dist/render/layers/ChannelLayer.d.ts.map +1 -1
- package/dist/render/layers/DrawLayer.d.ts +1 -1
- package/dist/render/layers/DrawLayer.d.ts.map +1 -1
- package/dist/render/layers/PathLayer.d.ts.map +1 -1
- package/dist/render/layers/SvgElementLayer.d.ts.map +1 -1
- package/dist/render/layers/types.d.ts +1 -38
- package/dist/render/layers/types.d.ts.map +1 -1
- package/dist/store/processMowingState.d.ts +1 -5
- package/dist/store/processMowingState.d.ts.map +1 -1
- package/dist/store/useSubBoundaryBorderStore.d.ts +9 -5
- package/dist/store/useSubBoundaryBorderStore.d.ts.map +1 -1
- package/dist/types/constants.d.ts +38 -0
- package/dist/types/constants.d.ts.map +1 -0
- package/dist/types/index.d.ts +6 -0
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/layers.d.ts +50 -0
- package/dist/types/layers.d.ts.map +1 -0
- package/dist/types/processor.d.ts +26 -0
- package/dist/types/processor.d.ts.map +1 -0
- package/dist/types/realTime.d.ts +8 -1
- package/dist/types/realTime.d.ts.map +1 -1
- package/dist/types/renderer.d.ts +3 -3
- package/dist/types/renderer.d.ts.map +1 -1
- package/dist/types/store.d.ts +22 -0
- package/dist/types/store.d.ts.map +1 -0
- package/dist/types/utils.d.ts +102 -0
- package/dist/types/utils.d.ts.map +1 -0
- package/dist/utils/boundaryUtils.d.ts +1 -29
- package/dist/utils/boundaryUtils.d.ts.map +1 -1
- package/dist/utils/common.d.ts +1 -5
- package/dist/utils/common.d.ts.map +1 -1
- package/dist/utils/coordinates.d.ts +1 -7
- package/dist/utils/coordinates.d.ts.map +1 -1
- package/dist/utils/handleRealTime.d.ts +2 -7
- package/dist/utils/handleRealTime.d.ts.map +1 -1
- package/dist/utils/mapBounds.d.ts +1 -10
- package/dist/utils/mapBounds.d.ts.map +1 -1
- package/dist/utils/math.d.ts +2 -9
- package/dist/utils/math.d.ts.map +1 -1
- package/dist/utils/mower.d.ts +4 -4
- package/dist/utils/mower.d.ts.map +1 -1
- package/dist/utils/pathSegments.d.ts +1 -23
- package/dist/utils/pathSegments.d.ts.map +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -120,7 +120,7 @@ class SvgMapView {
|
|
|
120
120
|
* 设置自适应视图变换 - 让SVG刚好包裹住图形
|
|
121
121
|
*/
|
|
122
122
|
fitToView(bounds) {
|
|
123
|
-
const padding =
|
|
123
|
+
const padding = 20; // 添加一些边距以避免内容贴边
|
|
124
124
|
const boundWidth = bounds.maxX - bounds.minX;
|
|
125
125
|
const boundHeight = bounds.maxY - bounds.minY;
|
|
126
126
|
// 防止宽高为0的情况
|
|
@@ -143,9 +143,10 @@ class SvgMapView {
|
|
|
143
143
|
this.viewBox = {
|
|
144
144
|
x: bounds.minX - padding,
|
|
145
145
|
y: bounds.minY - padding,
|
|
146
|
-
width: boundWidth + padding,
|
|
147
|
-
height: boundHeight + padding,
|
|
146
|
+
width: boundWidth + padding * 2,
|
|
147
|
+
height: boundHeight + padding * 2,
|
|
148
148
|
};
|
|
149
|
+
console.log('viewbox->', this.viewBox);
|
|
149
150
|
// 根据宽高比选择合适的preserveAspectRatio设置
|
|
150
151
|
if (Math.abs(contentAspectRatio - containerAspectRatio) < 0.01) {
|
|
151
152
|
// 宽高比接近,使用slice填满容器
|
|
@@ -651,8 +652,6 @@ const create = (createState) => createState ? createImpl(createState) : createIm
|
|
|
651
652
|
|
|
652
653
|
const useSubBoundaryBorderStore = create((set, get) => ({
|
|
653
654
|
subBoundaryBorder: {},
|
|
654
|
-
// 覆盖所有数据
|
|
655
|
-
setSubBoundaryBorder: (subBoundaryBorder) => set({ subBoundaryBorder }),
|
|
656
655
|
// 追加单个数据
|
|
657
656
|
addSubBoundaryBorder: (key, element) => set((state) => ({
|
|
658
657
|
subBoundaryBorder: {
|
|
@@ -660,17 +659,69 @@ const useSubBoundaryBorderStore = create((set, get) => ({
|
|
|
660
659
|
[key]: element,
|
|
661
660
|
},
|
|
662
661
|
})),
|
|
663
|
-
// 追加多个数据
|
|
664
|
-
addMultipleSubBoundaryBorders: (borders) => set((state) => ({
|
|
665
|
-
subBoundaryBorder: {
|
|
666
|
-
...state.subBoundaryBorder,
|
|
667
|
-
...borders,
|
|
668
|
-
},
|
|
669
|
-
})),
|
|
670
662
|
// 清空所有数据
|
|
671
663
|
clearSubBoundaryBorder: () => set({ subBoundaryBorder: {} }),
|
|
664
|
+
// 障碍物
|
|
665
|
+
obstacles: {},
|
|
666
|
+
addObstacles: (key, element) => set((state) => ({
|
|
667
|
+
obstacles: {
|
|
668
|
+
...state.obstacles,
|
|
669
|
+
[key]: element,
|
|
670
|
+
},
|
|
671
|
+
})),
|
|
672
|
+
clearObstacles: () => set({ obstacles: {} }),
|
|
673
|
+
// svg数据
|
|
674
|
+
svgElements: {},
|
|
675
|
+
addSvgElements: (key, element) => set((state) => ({
|
|
676
|
+
svgElements: {
|
|
677
|
+
...state.svgElements,
|
|
678
|
+
[key]: element,
|
|
679
|
+
},
|
|
680
|
+
})),
|
|
681
|
+
clearSvgElements: () => set({ svgElements: {} }),
|
|
672
682
|
}));
|
|
673
683
|
|
|
684
|
+
/**
|
|
685
|
+
* 常量和枚举类型定义
|
|
686
|
+
*/
|
|
687
|
+
/**
|
|
688
|
+
* 机器人状态枚举
|
|
689
|
+
*/
|
|
690
|
+
var RobotStatus;
|
|
691
|
+
(function (RobotStatus) {
|
|
692
|
+
RobotStatus[RobotStatus["PARKED"] = 1] = "PARKED";
|
|
693
|
+
RobotStatus[RobotStatus["CHARGING"] = 2] = "CHARGING";
|
|
694
|
+
RobotStatus[RobotStatus["STANDBY"] = 3] = "STANDBY";
|
|
695
|
+
RobotStatus[RobotStatus["MOWING"] = 4] = "MOWING";
|
|
696
|
+
RobotStatus[RobotStatus["WORKING"] = 5] = "WORKING";
|
|
697
|
+
RobotStatus[RobotStatus["MAPPING"] = 6] = "MAPPING";
|
|
698
|
+
RobotStatus[RobotStatus["ERROR"] = 7] = "ERROR";
|
|
699
|
+
RobotStatus[RobotStatus["UPGRADING"] = 8] = "UPGRADING";
|
|
700
|
+
RobotStatus[RobotStatus["DISCONNECTED"] = 9] = "DISCONNECTED";
|
|
701
|
+
RobotStatus[RobotStatus["UNKNOWN"] = -1] = "UNKNOWN";
|
|
702
|
+
RobotStatus[RobotStatus["TASK_DELAY"] = 10] = "TASK_DELAY";
|
|
703
|
+
})(RobotStatus || (RobotStatus = {}));
|
|
704
|
+
/**
|
|
705
|
+
* RTK状态枚举
|
|
706
|
+
*/
|
|
707
|
+
var RTK_STATE;
|
|
708
|
+
(function (RTK_STATE) {
|
|
709
|
+
RTK_STATE[RTK_STATE["LOW_RTK"] = 1] = "LOW_RTK";
|
|
710
|
+
RTK_STATE[RTK_STATE["MIDDLE_RTK"] = 2] = "MIDDLE_RTK";
|
|
711
|
+
RTK_STATE[RTK_STATE["HIGH_RTK"] = 3] = "HIGH_RTK";
|
|
712
|
+
RTK_STATE[RTK_STATE["NO_POSTURE"] = 10] = "NO_POSTURE";
|
|
713
|
+
RTK_STATE[RTK_STATE["OUT_OF_RANGE"] = 11] = "OUT_OF_RANGE";
|
|
714
|
+
RTK_STATE[RTK_STATE["OFF_LINE"] = 19] = "OFF_LINE";
|
|
715
|
+
})(RTK_STATE || (RTK_STATE = {}));
|
|
716
|
+
/**
|
|
717
|
+
* 实时数据类型枚举
|
|
718
|
+
*/
|
|
719
|
+
var REAL_TIME_DATA_TYPE;
|
|
720
|
+
(function (REAL_TIME_DATA_TYPE) {
|
|
721
|
+
REAL_TIME_DATA_TYPE[REAL_TIME_DATA_TYPE["LOCATION"] = 1] = "LOCATION";
|
|
722
|
+
REAL_TIME_DATA_TYPE[REAL_TIME_DATA_TYPE["PROCESS"] = 2] = "PROCESS";
|
|
723
|
+
})(REAL_TIME_DATA_TYPE || (REAL_TIME_DATA_TYPE = {}));
|
|
724
|
+
|
|
674
725
|
/**
|
|
675
726
|
* 地图渲染相关常量配置
|
|
676
727
|
*/
|
|
@@ -723,36 +774,6 @@ const LAYER_DEFAULT_TYPE = {
|
|
|
723
774
|
VISION_OFF_AREA: 'vision_off_area',
|
|
724
775
|
ANTENNA: 'antenna',
|
|
725
776
|
};
|
|
726
|
-
var RobotStatus;
|
|
727
|
-
(function (RobotStatus) {
|
|
728
|
-
RobotStatus[RobotStatus["PARKED"] = 1] = "PARKED";
|
|
729
|
-
RobotStatus[RobotStatus["CHARGING"] = 2] = "CHARGING";
|
|
730
|
-
RobotStatus[RobotStatus["STANDBY"] = 3] = "STANDBY";
|
|
731
|
-
RobotStatus[RobotStatus["MOWING"] = 4] = "MOWING";
|
|
732
|
-
RobotStatus[RobotStatus["WORKING"] = 5] = "WORKING";
|
|
733
|
-
RobotStatus[RobotStatus["MAPPING"] = 6] = "MAPPING";
|
|
734
|
-
RobotStatus[RobotStatus["ERROR"] = 7] = "ERROR";
|
|
735
|
-
RobotStatus[RobotStatus["UPGRADING"] = 8] = "UPGRADING";
|
|
736
|
-
RobotStatus[RobotStatus["DISCONNECTED"] = 9] = "DISCONNECTED";
|
|
737
|
-
RobotStatus[RobotStatus["UNKNOWN"] = -1] = "UNKNOWN";
|
|
738
|
-
RobotStatus[RobotStatus["TASK_DELAY"] = 10] = "TASK_DELAY";
|
|
739
|
-
// WAITING = 'Waiting',
|
|
740
|
-
})(RobotStatus || (RobotStatus = {}));
|
|
741
|
-
// RTK状态
|
|
742
|
-
var RTK_STATE;
|
|
743
|
-
(function (RTK_STATE) {
|
|
744
|
-
RTK_STATE[RTK_STATE["LOW_RTK"] = 1] = "LOW_RTK";
|
|
745
|
-
RTK_STATE[RTK_STATE["MIDDLE_RTK"] = 2] = "MIDDLE_RTK";
|
|
746
|
-
RTK_STATE[RTK_STATE["HIGH_RTK"] = 3] = "HIGH_RTK";
|
|
747
|
-
RTK_STATE[RTK_STATE["NO_POSTURE"] = 10] = "NO_POSTURE";
|
|
748
|
-
RTK_STATE[RTK_STATE["OUT_OF_RANGE"] = 11] = "OUT_OF_RANGE";
|
|
749
|
-
RTK_STATE[RTK_STATE["OFF_LINE"] = 19] = "OFF_LINE";
|
|
750
|
-
})(RTK_STATE || (RTK_STATE = {}));
|
|
751
|
-
var REAL_TIME_DATA_TYPE;
|
|
752
|
-
(function (REAL_TIME_DATA_TYPE) {
|
|
753
|
-
REAL_TIME_DATA_TYPE[REAL_TIME_DATA_TYPE["LOCATION"] = 1] = "LOCATION";
|
|
754
|
-
REAL_TIME_DATA_TYPE[REAL_TIME_DATA_TYPE["PROCESS"] = 2] = "PROCESS";
|
|
755
|
-
})(REAL_TIME_DATA_TYPE || (REAL_TIME_DATA_TYPE = {}));
|
|
756
777
|
const ISOLATED_BOUNDARY_SVG = `<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
757
778
|
<g opacity="0.6">
|
|
758
779
|
<rect width="24" height="24" rx="12" fill="#1E1E1F" fill-opacity="0.5"/>
|
|
@@ -852,37 +873,66 @@ class ChannelLayer extends BaseLayer {
|
|
|
852
873
|
}
|
|
853
874
|
// 2. 再计算所有通道的边界
|
|
854
875
|
for (const element of this.elements) {
|
|
855
|
-
const tunnelConnection = element.originalData?.connection;
|
|
856
|
-
if (tunnelConnection && Array.isArray(tunnelConnection)) {
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
+
// const tunnelConnection = element.originalData?.connection;
|
|
877
|
+
// if (tunnelConnection && Array.isArray(tunnelConnection)) {
|
|
878
|
+
// const clipPathId = `channel-exclude-${
|
|
879
|
+
// element.originalData?.id || Math.random().toString(36).substr(2, 9)
|
|
880
|
+
// }`;
|
|
881
|
+
// // 检查是否已存在该 clipPath
|
|
882
|
+
// const existingClipPath = defs.querySelector(`#${clipPathId}`);
|
|
883
|
+
// if (existingClipPath) continue;
|
|
884
|
+
// // 创建 clipPath
|
|
885
|
+
// const clipPath = document.createElementNS('http://www.w3.org/2000/svg', 'clipPath');
|
|
886
|
+
// clipPath.setAttribute('id', clipPathId);
|
|
887
|
+
// clipPath.setAttribute('clipPathUnits', 'userSpaceOnUse');
|
|
888
|
+
// // === 合成一个 path ===
|
|
889
|
+
// let d = `M ${minX} ${minY} L ${maxX} ${minY} L ${maxX} ${maxY} L ${minX} ${maxY} Z`;
|
|
890
|
+
// for (const partitionId of tunnelConnection) {
|
|
891
|
+
// const boundaryData = subBoundaryBorder[partitionId];
|
|
892
|
+
// if (boundaryData && boundaryData.coordinates.length >= 3) {
|
|
893
|
+
// d += ` M ${boundaryData.coordinates[0][0]} ${boundaryData.coordinates[0][1]}`;
|
|
894
|
+
// for (let i = 1; i < boundaryData.coordinates.length; i++) {
|
|
895
|
+
// d += ` L ${boundaryData.coordinates[i][0]} ${boundaryData.coordinates[i][1]}`;
|
|
896
|
+
// }
|
|
897
|
+
// d += ' Z';
|
|
898
|
+
// }
|
|
899
|
+
// }
|
|
900
|
+
// const path = document.createElementNS('http://www.w3.org/2000/svg', 'path');
|
|
901
|
+
// path.setAttribute('d', d);
|
|
902
|
+
// path.setAttribute('clip-rule', 'evenodd'); // 关键
|
|
903
|
+
// clipPath.appendChild(path);
|
|
904
|
+
// defs.appendChild(clipPath);
|
|
905
|
+
// clipPathIdsMap[element.originalData?.id.toString()] = clipPathId;
|
|
906
|
+
// } else {
|
|
907
|
+
const clipPathId = `channel-exclude-all-${element.originalData?.id || Math.random().toString(36).substr(2, 9)}`;
|
|
908
|
+
// 检查是否已存在该 clipPath
|
|
909
|
+
const existingClipPath = defs.querySelector(`#${clipPathId}`);
|
|
910
|
+
if (existingClipPath)
|
|
911
|
+
continue;
|
|
912
|
+
// 创建 clipPath
|
|
913
|
+
const clipPath = document.createElementNS('http://www.w3.org/2000/svg', 'clipPath');
|
|
914
|
+
clipPath.setAttribute('id', clipPathId);
|
|
915
|
+
clipPath.setAttribute('clipPathUnits', 'userSpaceOnUse');
|
|
916
|
+
// === 合成一个 path ===
|
|
917
|
+
let d = `M ${minX} ${minY} L ${maxX} ${minY} L ${maxX} ${maxY} L ${minX} ${maxY} Z`;
|
|
918
|
+
for (const partitionId in subBoundaryBorder) {
|
|
919
|
+
const boundaryData = subBoundaryBorder[partitionId];
|
|
920
|
+
if (boundaryData && boundaryData.coordinates.length >= 3) {
|
|
921
|
+
d += ` M ${boundaryData.coordinates[0][0]} ${boundaryData.coordinates[0][1]}`;
|
|
922
|
+
for (let i = 1; i < boundaryData.coordinates.length; i++) {
|
|
923
|
+
d += ` L ${boundaryData.coordinates[i][0]} ${boundaryData.coordinates[i][1]}`;
|
|
876
924
|
}
|
|
925
|
+
d += ' Z';
|
|
877
926
|
}
|
|
878
|
-
const path = document.createElementNS('http://www.w3.org/2000/svg', 'path');
|
|
879
|
-
path.setAttribute('d', d);
|
|
880
|
-
path.setAttribute('clip-rule', 'evenodd'); // 关键
|
|
881
|
-
clipPath.appendChild(path);
|
|
882
|
-
defs.appendChild(clipPath);
|
|
883
|
-
clipPathIdsMap[element.originalData?.id.toString()] = clipPathId;
|
|
884
927
|
}
|
|
928
|
+
const path = document.createElementNS('http://www.w3.org/2000/svg', 'path');
|
|
929
|
+
path.setAttribute('d', d);
|
|
930
|
+
path.setAttribute('clip-rule', 'evenodd'); // 关键
|
|
931
|
+
clipPath.appendChild(path);
|
|
932
|
+
defs.appendChild(clipPath);
|
|
933
|
+
clipPathIdsMap[element.originalData?.id.toString()] = clipPathId;
|
|
885
934
|
}
|
|
935
|
+
// }
|
|
886
936
|
return clipPathIdsMap;
|
|
887
937
|
}
|
|
888
938
|
/**
|
|
@@ -953,7 +1003,7 @@ class PathLayer extends BaseLayer {
|
|
|
953
1003
|
* 创建所有分区并集的 clipPath
|
|
954
1004
|
*/
|
|
955
1005
|
createUnionClipPath(svgGroup) {
|
|
956
|
-
const { subBoundaryBorder } = useSubBoundaryBorderStore.getState();
|
|
1006
|
+
const { subBoundaryBorder, obstacles, svgElements } = useSubBoundaryBorderStore.getState();
|
|
957
1007
|
// 确保 defs 元素存在
|
|
958
1008
|
let defs = svgGroup.querySelector('defs');
|
|
959
1009
|
if (!defs) {
|
|
@@ -967,7 +1017,7 @@ class PathLayer extends BaseLayer {
|
|
|
967
1017
|
defs.removeChild(existing);
|
|
968
1018
|
// 合成所有分区的 path
|
|
969
1019
|
let d = '';
|
|
970
|
-
//
|
|
1020
|
+
// 1. 外圈(主边界,顺时针)
|
|
971
1021
|
Object.values(subBoundaryBorder).forEach((item) => {
|
|
972
1022
|
const bCoords = item.coordinates;
|
|
973
1023
|
if (bCoords.length >= 3) {
|
|
@@ -978,6 +1028,27 @@ class PathLayer extends BaseLayer {
|
|
|
978
1028
|
d += ' Z ';
|
|
979
1029
|
}
|
|
980
1030
|
});
|
|
1031
|
+
// 2. 内圈(禁区,逆时针)
|
|
1032
|
+
Object.values(obstacles).forEach((item) => {
|
|
1033
|
+
const bCoords = item.coordinates;
|
|
1034
|
+
if (bCoords.length >= 3) {
|
|
1035
|
+
d += `M ${bCoords[bCoords.length - 1][0]} ${bCoords[bCoords.length - 1][1]}`;
|
|
1036
|
+
for (let i = bCoords.length - 2; i >= 0; i--) {
|
|
1037
|
+
d += ` L ${bCoords[i][0]} ${bCoords[i][1]}`;
|
|
1038
|
+
}
|
|
1039
|
+
d += ' Z ';
|
|
1040
|
+
}
|
|
1041
|
+
});
|
|
1042
|
+
console.error('svgElements----', svgElements);
|
|
1043
|
+
// 3. svgElements(直接拼接path字符串,建议逆时针)
|
|
1044
|
+
if (Array.isArray(svgElements)) {
|
|
1045
|
+
svgElements.forEach((svgPath) => {
|
|
1046
|
+
const svgPathString = svgPath?.metadata?.svg;
|
|
1047
|
+
if (svgPathString && typeof svgPathString === 'string' && svgPathString.trim()) {
|
|
1048
|
+
d += svgPathString + ' ';
|
|
1049
|
+
}
|
|
1050
|
+
});
|
|
1051
|
+
}
|
|
981
1052
|
const path = document.createElementNS('http://www.w3.org/2000/svg', 'path');
|
|
982
1053
|
path.setAttribute('d', d);
|
|
983
1054
|
const clipPath = document.createElementNS('http://www.w3.org/2000/svg', 'clipPath');
|
|
@@ -1150,7 +1221,7 @@ class ObstacleLayer extends BaseLayer {
|
|
|
1150
1221
|
}
|
|
1151
1222
|
}
|
|
1152
1223
|
|
|
1153
|
-
var chargingPileImage = "data:image/png;base64,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";
|
|
1224
|
+
var chargingPileImage = "data:image/png;base64,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";
|
|
1154
1225
|
|
|
1155
1226
|
/**
|
|
1156
1227
|
* 充电桩图层
|
|
@@ -1340,7 +1411,7 @@ class SvgElementLayer extends BaseLayer {
|
|
|
1340
1411
|
// 在transformGroup上应用变换:平移到中心,旋转,缩放,然后居中SVG
|
|
1341
1412
|
const transform = [
|
|
1342
1413
|
`translate(${center[0]}, ${center[1]})`,
|
|
1343
|
-
`rotate(${(direction * 180) / Math.PI})`,
|
|
1414
|
+
`rotate(${-(direction * 180) / Math.PI})`,
|
|
1344
1415
|
`scale(${userScale})`,
|
|
1345
1416
|
`translate(${-originalWidth / 2}, ${-originalHeight / 2})`,
|
|
1346
1417
|
].join(' ');
|
|
@@ -1542,15 +1613,6 @@ function convertCoordinate(x, y) {
|
|
|
1542
1613
|
};
|
|
1543
1614
|
}
|
|
1544
1615
|
|
|
1545
|
-
/**
|
|
1546
|
-
* 路径段类型
|
|
1547
|
-
*/
|
|
1548
|
-
var PathSegmentType;
|
|
1549
|
-
(function (PathSegmentType) {
|
|
1550
|
-
PathSegmentType["EDGE"] = "edge";
|
|
1551
|
-
PathSegmentType["MOWING"] = "mowing";
|
|
1552
|
-
PathSegmentType["TRANS"] = "trans";
|
|
1553
|
-
})(PathSegmentType || (PathSegmentType = {}));
|
|
1554
1616
|
/**
|
|
1555
1617
|
* 按Python逻辑创建路径段:根据连续的两点之间的关系确定线段类型
|
|
1556
1618
|
*/
|
|
@@ -1879,6 +1941,14 @@ function generateBoundaryData(mapData, pathData) {
|
|
|
1879
1941
|
return boundaryData;
|
|
1880
1942
|
}
|
|
1881
1943
|
|
|
1944
|
+
var RealTimeDataType;
|
|
1945
|
+
(function (RealTimeDataType) {
|
|
1946
|
+
RealTimeDataType[RealTimeDataType["LOCATION"] = 1] = "LOCATION";
|
|
1947
|
+
RealTimeDataType[RealTimeDataType["PROCESS"] = 2] = "PROCESS";
|
|
1948
|
+
RealTimeDataType[RealTimeDataType["PARTITION"] = 3] = "PARTITION";
|
|
1949
|
+
RealTimeDataType[RealTimeDataType["STATUS"] = 4] = "STATUS";
|
|
1950
|
+
})(RealTimeDataType || (RealTimeDataType = {}));
|
|
1951
|
+
|
|
1882
1952
|
/**
|
|
1883
1953
|
* 射线法判断点是否在多边形内部
|
|
1884
1954
|
* @param x 点的x坐标
|
|
@@ -2048,7 +2118,7 @@ const getProcessMowingDataFromRealTimeData = ({ realTimeData, isMowing, pathData
|
|
|
2048
2118
|
let newMowingStatus = isMowing;
|
|
2049
2119
|
let newPathData = pathData || {};
|
|
2050
2120
|
// 找到返回的第一个实时进度的点
|
|
2051
|
-
const firstProcessData = realTimeData.find((item) => item.type ===
|
|
2121
|
+
const firstProcessData = realTimeData.find((item) => item.type === RealTimeDataType.PROCESS);
|
|
2052
2122
|
if (firstProcessData) {
|
|
2053
2123
|
// console.log('firstProcessData==', firstProcessData);
|
|
2054
2124
|
const { action, subAction, currentMowBoundary, currentMowProgress } = firstProcessData;
|
|
@@ -4596,6 +4666,36 @@ var merge = createAssigner(function(object, source, srcIndex) {
|
|
|
4596
4666
|
*/
|
|
4597
4667
|
var round = createRound('round');
|
|
4598
4668
|
|
|
4669
|
+
/**
|
|
4670
|
+
* 工具模块类型定义
|
|
4671
|
+
*/
|
|
4672
|
+
/**
|
|
4673
|
+
* 路径段类型枚举
|
|
4674
|
+
*/
|
|
4675
|
+
var PathSegmentType;
|
|
4676
|
+
(function (PathSegmentType) {
|
|
4677
|
+
PathSegmentType["EDGE"] = "edge";
|
|
4678
|
+
PathSegmentType["MOWING"] = "mowing";
|
|
4679
|
+
PathSegmentType["TRANS"] = "trans";
|
|
4680
|
+
})(PathSegmentType || (PathSegmentType = {}));
|
|
4681
|
+
/**
|
|
4682
|
+
* 单位类型枚举
|
|
4683
|
+
*/
|
|
4684
|
+
var UnitsType;
|
|
4685
|
+
(function (UnitsType) {
|
|
4686
|
+
UnitsType["Metric"] = "metric";
|
|
4687
|
+
UnitsType["Imperial"] = "imperial";
|
|
4688
|
+
})(UnitsType || (UnitsType = {}));
|
|
4689
|
+
/**
|
|
4690
|
+
* 面积单位类型枚举
|
|
4691
|
+
*/
|
|
4692
|
+
var UnitsAreaType;
|
|
4693
|
+
(function (UnitsAreaType) {
|
|
4694
|
+
UnitsAreaType["SQUARE_METER"] = "m\u00B2";
|
|
4695
|
+
UnitsAreaType["SQUARE_FOOT"] = "ft\u00B2";
|
|
4696
|
+
UnitsAreaType["ACRE"] = "ac";
|
|
4697
|
+
})(UnitsAreaType || (UnitsAreaType = {}));
|
|
4698
|
+
|
|
4599
4699
|
/**
|
|
4600
4700
|
* 默认航向相对于canvas的偏移角度: 航向默认是东
|
|
4601
4701
|
*/
|
|
@@ -4669,17 +4769,6 @@ function formatNumberWithMetricPrefix(value, round = true, decimals = 2) {
|
|
|
4669
4769
|
return `${mathFn(value / 1000000000, decimals)}B`;
|
|
4670
4770
|
}
|
|
4671
4771
|
}
|
|
4672
|
-
var UnitsType;
|
|
4673
|
-
(function (UnitsType) {
|
|
4674
|
-
UnitsType["Metric"] = "metric";
|
|
4675
|
-
UnitsType["Imperial"] = "imperial";
|
|
4676
|
-
})(UnitsType || (UnitsType = {}));
|
|
4677
|
-
var UnitsAreaType;
|
|
4678
|
-
(function (UnitsAreaType) {
|
|
4679
|
-
UnitsAreaType["SQUARE_METER"] = "m\u00B2";
|
|
4680
|
-
UnitsAreaType["SQUARE_FOOT"] = "ft\u00B2";
|
|
4681
|
-
UnitsAreaType["ACRE"] = "ac";
|
|
4682
|
-
})(UnitsAreaType || (UnitsAreaType = {}));
|
|
4683
4772
|
/**
|
|
4684
4773
|
* 转换割草面积的方法
|
|
4685
4774
|
* @param area 面积数值(单位:m²)
|
|
@@ -4875,7 +4964,12 @@ class BoundaryBorderLayer extends BaseLayer {
|
|
|
4875
4964
|
* 设置当前割草任务的边界
|
|
4876
4965
|
*/
|
|
4877
4966
|
setMowingBoundarys(mowingBoundarys) {
|
|
4878
|
-
|
|
4967
|
+
if (!mowingBoundarys) {
|
|
4968
|
+
this.mowingBoundarys = this.elements?.map(item => item?.originalData?.id);
|
|
4969
|
+
}
|
|
4970
|
+
else {
|
|
4971
|
+
this.mowingBoundarys = mowingBoundarys;
|
|
4972
|
+
}
|
|
4879
4973
|
}
|
|
4880
4974
|
/**
|
|
4881
4975
|
* SVG渲染方法
|
|
@@ -5303,6 +5397,14 @@ class BoundaryDataBuilder {
|
|
|
5303
5397
|
* 创建边界元素数据
|
|
5304
5398
|
*/
|
|
5305
5399
|
static create(type, coordinates, style) {
|
|
5400
|
+
const len = coordinates?.length || 0;
|
|
5401
|
+
const firstPoint = coordinates?.[0];
|
|
5402
|
+
const lastPoint = coordinates?.[len - 1];
|
|
5403
|
+
const isClosed = firstPoint?.[0] === lastPoint?.[0] && firstPoint?.[1] === lastPoint?.[1];
|
|
5404
|
+
// 如果地图没有闭合,则手动新增闭合点,避免border最后一部分没有闭合的情况
|
|
5405
|
+
if (!isClosed) {
|
|
5406
|
+
coordinates.push([firstPoint?.[0], firstPoint?.[1], lastPoint?.[2]]);
|
|
5407
|
+
}
|
|
5306
5408
|
return {
|
|
5307
5409
|
type,
|
|
5308
5410
|
coordinates,
|
|
@@ -5705,8 +5807,13 @@ class MapDataProcessor {
|
|
|
5705
5807
|
// 为ObstacleData创建兼容的MapElement接口
|
|
5706
5808
|
const mapElement = element;
|
|
5707
5809
|
const obstacleElement = ObstacleDataBuilder.fromMapElement(mapElement, this.mapConfig.obstacle);
|
|
5708
|
-
if (obstacleElement)
|
|
5810
|
+
if (obstacleElement) {
|
|
5709
5811
|
result.push(obstacleElement);
|
|
5812
|
+
const { addObstacles } = useSubBoundaryBorderStore.getState();
|
|
5813
|
+
addObstacles(`obstacle-${obstacleElement.originalData.id}`, {
|
|
5814
|
+
...obstacleElement,
|
|
5815
|
+
});
|
|
5816
|
+
}
|
|
5710
5817
|
}
|
|
5711
5818
|
catch (error) {
|
|
5712
5819
|
console.warn(`Error processing OBSTACLE element:`, element, error);
|
|
@@ -5767,8 +5874,13 @@ class MapDataProcessor {
|
|
|
5767
5874
|
element.direction !== undefined) {
|
|
5768
5875
|
const mapElement = element;
|
|
5769
5876
|
const svgElement = SvgElementDataBuilder.fromMapElement(mapElement, this.mapConfig.doodle);
|
|
5770
|
-
if (svgElement)
|
|
5877
|
+
if (svgElement) {
|
|
5771
5878
|
result.push(svgElement);
|
|
5879
|
+
const { addSvgElements } = useSubBoundaryBorderStore.getState();
|
|
5880
|
+
addSvgElements(`time-limit-obstacle-${svgElement.originalData.id}`, {
|
|
5881
|
+
...svgElement,
|
|
5882
|
+
});
|
|
5883
|
+
}
|
|
5772
5884
|
}
|
|
5773
5885
|
// 如果有points数据,按传统方式绘制
|
|
5774
5886
|
else if ('points' in element &&
|
|
@@ -5777,8 +5889,13 @@ class MapDataProcessor {
|
|
|
5777
5889
|
element.points.length >= 3) {
|
|
5778
5890
|
const mapElement = element;
|
|
5779
5891
|
const polygonElement = ObstacleDataBuilder.createTimeLimitObstacle(mapElement, this.mapConfig.obstacle);
|
|
5780
|
-
if (polygonElement)
|
|
5892
|
+
if (polygonElement) {
|
|
5781
5893
|
result.push(polygonElement);
|
|
5894
|
+
const { addObstacles } = useSubBoundaryBorderStore.getState();
|
|
5895
|
+
addObstacles(`time-limit-obstacle-${polygonElement.originalData.id}`, {
|
|
5896
|
+
...polygonElement,
|
|
5897
|
+
});
|
|
5898
|
+
}
|
|
5782
5899
|
}
|
|
5783
5900
|
}
|
|
5784
5901
|
catch (error) {
|
|
@@ -6115,7 +6232,6 @@ class BoundaryLabelsManager {
|
|
|
6115
6232
|
this.collapseOtherLabels(boundaryId);
|
|
6116
6233
|
// 展开当前标签
|
|
6117
6234
|
extendedContent.style.display = 'block';
|
|
6118
|
-
labelDiv.style.whiteSpace = 'normal';
|
|
6119
6235
|
this.currentExpandedBoundaryId = boundaryId;
|
|
6120
6236
|
}
|
|
6121
6237
|
/**
|
|
@@ -7175,9 +7291,10 @@ class MowerPositionManager {
|
|
|
7175
7291
|
return;
|
|
7176
7292
|
this.mowerPositionConfig = chargingPilesPositionConfig;
|
|
7177
7293
|
const lastPosition = this.lastPosition;
|
|
7178
|
-
const postureX = chargingPilesPositionConfig.postureX
|
|
7179
|
-
const postureY = chargingPilesPositionConfig.postureY
|
|
7180
|
-
const postureTheta = chargingPilesPositionConfig.postureTheta
|
|
7294
|
+
const postureX = chargingPilesPositionConfig.postureX || chargingPilesPositionConfig.lastPostureX || lastPosition?.x || 0;
|
|
7295
|
+
const postureY = chargingPilesPositionConfig.postureY || chargingPilesPositionConfig.lastPostureY || lastPosition?.y || 0;
|
|
7296
|
+
const postureTheta = chargingPilesPositionConfig.postureTheta || chargingPilesPositionConfig.lastPostureTheta || lastPosition?.rotation || 0;
|
|
7297
|
+
console.log('updatePositionByLastPosition->', postureX, postureY, postureTheta, chargingPilesPositionConfig);
|
|
7181
7298
|
// 检查是否需要更新图片
|
|
7182
7299
|
this.updateMowerImage(chargingPilesPositionConfig);
|
|
7183
7300
|
// 立即更新位置
|
|
@@ -7191,10 +7308,10 @@ class MowerPositionManager {
|
|
|
7191
7308
|
this.updateMowerImage(positionConfig);
|
|
7192
7309
|
// 更新配置
|
|
7193
7310
|
this.mowerPositionConfig = positionConfig;
|
|
7194
|
-
const postureX = positionConfig?.postureX
|
|
7195
|
-
const postureY = positionConfig?.postureY
|
|
7196
|
-
const postureTheta = positionConfig?.postureTheta
|
|
7197
|
-
console.log('updatePosition manager', positionConfig, this.lastPosition);
|
|
7311
|
+
const postureX = positionConfig?.postureX || this.lastPosition?.x || 0;
|
|
7312
|
+
const postureY = positionConfig?.postureY || this.lastPosition?.y || 0;
|
|
7313
|
+
const postureTheta = positionConfig?.postureTheta || this.lastPosition?.rotation || 0;
|
|
7314
|
+
console.log('updatePosition manager', JSON.stringify(this.currentPosition), this.currentPosition, !this.currentPosition, positionConfig, this.lastPosition, animationTime);
|
|
7198
7315
|
// 停止当前动画(如果有)
|
|
7199
7316
|
this.stopAnimation();
|
|
7200
7317
|
// 第一个点
|
|
@@ -7204,6 +7321,7 @@ class MowerPositionManager {
|
|
|
7204
7321
|
y: postureY,
|
|
7205
7322
|
rotation: postureTheta,
|
|
7206
7323
|
};
|
|
7324
|
+
console.log('updatePosition first->', this.currentPosition);
|
|
7207
7325
|
this.setElementPosition(this.currentPosition.x, this.currentPosition.y, this.currentPosition.rotation);
|
|
7208
7326
|
return;
|
|
7209
7327
|
}
|
|
@@ -7253,7 +7371,7 @@ class MowerPositionManager {
|
|
|
7253
7371
|
if (!positonOutOfRange && !positionValid) {
|
|
7254
7372
|
this.lastPosition = { x, y, rotation: theta };
|
|
7255
7373
|
}
|
|
7256
|
-
// console.log('setElementPosition', x, y, targetRotation, positonOutOfRange, positionValid, targetPixelPosition);
|
|
7374
|
+
// console.log('setElementPosition', x, y, theta, targetRotation, positonOutOfRange, positionValid, targetPixelPosition);
|
|
7257
7375
|
if (!this.mowerElement)
|
|
7258
7376
|
return;
|
|
7259
7377
|
this.mowerElement.style.left = `${targetPixelPosition?.x}px`;
|
|
@@ -7307,10 +7425,12 @@ class MowerPositionManager {
|
|
|
7307
7425
|
y: this.onlyUpdateTheta ? 0 : this.targetPosition.y - this.startPosition.y,
|
|
7308
7426
|
rotation: radNormalize(targetTheta - startTheta),
|
|
7309
7427
|
};
|
|
7428
|
+
console.log('startAnimationToPosition-->', this.deltaPosition, this.onlyUpdateTheta, this.targetPosition, this.startPosition);
|
|
7310
7429
|
// 开始动画循环
|
|
7311
7430
|
this.animateStep();
|
|
7312
7431
|
}
|
|
7313
7432
|
forceUpdatePosition() {
|
|
7433
|
+
console.log('forceUpdatePosition-->', this.currentPosition, this.targetPosition, this.startPosition);
|
|
7314
7434
|
this.animateStep();
|
|
7315
7435
|
}
|
|
7316
7436
|
/**
|
|
@@ -7337,6 +7457,7 @@ class MowerPositionManager {
|
|
|
7337
7457
|
vehicleState: this.mowerPositionConfig?.vehicleState,
|
|
7338
7458
|
});
|
|
7339
7459
|
}
|
|
7460
|
+
// console.log('animateStep-->', this.startPosition, this.deltaPosition, this.targetPosition, easedProgress)
|
|
7340
7461
|
// 继续动画或结束
|
|
7341
7462
|
if (progress < 1) {
|
|
7342
7463
|
// 设置当前位置
|
|
@@ -8623,13 +8744,6 @@ class MowerMapOverlay {
|
|
|
8623
8744
|
}
|
|
8624
8745
|
}
|
|
8625
8746
|
|
|
8626
|
-
var RealTimeDataType;
|
|
8627
|
-
(function (RealTimeDataType) {
|
|
8628
|
-
RealTimeDataType[RealTimeDataType["LOCATION"] = 1] = "LOCATION";
|
|
8629
|
-
RealTimeDataType[RealTimeDataType["PROCESS"] = 2] = "PROCESS";
|
|
8630
|
-
RealTimeDataType[RealTimeDataType["PARTITION"] = 3] = "PARTITION";
|
|
8631
|
-
})(RealTimeDataType || (RealTimeDataType = {}));
|
|
8632
|
-
|
|
8633
8747
|
// 获取车辆状态的中文文案
|
|
8634
8748
|
const getVehicleStateText = (vehicleState) => {
|
|
8635
8749
|
switch (vehicleState) {
|
|
@@ -8749,7 +8863,7 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
8749
8863
|
// const mapRef = useMap();
|
|
8750
8864
|
const [isGoogleMapsReady, setIsGoogleMapsReady] = React.useState(false);
|
|
8751
8865
|
const [hasInitializedBounds, setHasInitializedBounds] = React.useState(false);
|
|
8752
|
-
const { clearSubBoundaryBorder } = useSubBoundaryBorderStore();
|
|
8866
|
+
const { clearSubBoundaryBorder, clearObstacles } = useSubBoundaryBorderStore();
|
|
8753
8867
|
const currentProcessMowingStatusRef = React.useRef(false);
|
|
8754
8868
|
const { updateProcessStateIsMowing, processStateIsMowing } = useProcessMowingState();
|
|
8755
8869
|
const [mowPartitionData, setMowPartitionData] = React.useState(null);
|
|
@@ -8803,8 +8917,12 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
8803
8917
|
lastPostureTheta: currentPositionData?.lastPostureTheta
|
|
8804
8918
|
? Number(currentPositionData.lastPostureTheta)
|
|
8805
8919
|
: 0,
|
|
8806
|
-
lastPostureX: currentPositionData?.lastPostureX
|
|
8807
|
-
|
|
8920
|
+
lastPostureX: currentPositionData?.lastPostureX
|
|
8921
|
+
? Number(currentPositionData.lastPostureX)
|
|
8922
|
+
: 0,
|
|
8923
|
+
lastPostureY: currentPositionData?.lastPostureY
|
|
8924
|
+
? Number(currentPositionData.lastPostureY)
|
|
8925
|
+
: 0,
|
|
8808
8926
|
vehicleState: currentPositionData?.vehicleState || RobotStatus.CHARGING,
|
|
8809
8927
|
};
|
|
8810
8928
|
}, [realTimeData, modelType]);
|
|
@@ -8897,12 +9015,26 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
8897
9015
|
handleError(`初始化Google Maps叠加层失败: ${error instanceof Error ? error.message : String(error)}`);
|
|
8898
9016
|
}
|
|
8899
9017
|
};
|
|
9018
|
+
const resetInCharginPie = React.useCallback(() => {
|
|
9019
|
+
const elements = MapDataProcessor.processMapData(mapJson, mergedMapConfig);
|
|
9020
|
+
const chargingPiles = elements.find((element) => element.type === 'charging_pile');
|
|
9021
|
+
if (!overlayRef.current)
|
|
9022
|
+
return;
|
|
9023
|
+
// 如果在充电桩上,则直接更新位置到充电桩的位置
|
|
9024
|
+
overlayRef.current.updatePosition({
|
|
9025
|
+
...mowerPositionData,
|
|
9026
|
+
postureX: chargingPiles?.originalData.position[0],
|
|
9027
|
+
postureY: chargingPiles?.originalData.position[1],
|
|
9028
|
+
postureTheta: chargingPiles?.originalData.direction - Math.PI || 0,
|
|
9029
|
+
}, 0);
|
|
9030
|
+
}, [mapJson]);
|
|
8900
9031
|
// 初始化效果
|
|
8901
9032
|
React.useEffect(() => {
|
|
8902
9033
|
initializeGoogleMapsOverlay();
|
|
8903
9034
|
// 清理函数
|
|
8904
9035
|
return () => {
|
|
8905
9036
|
clearSubBoundaryBorder();
|
|
9037
|
+
clearObstacles();
|
|
8906
9038
|
updateProcessStateIsMowing(false);
|
|
8907
9039
|
currentProcessMowingStatusRef.current = false;
|
|
8908
9040
|
if (overlayRef.current) {
|
|
@@ -8999,12 +9131,12 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
8999
9131
|
// 计算左下角和右上角坐标
|
|
9000
9132
|
sw: {
|
|
9001
9133
|
x: viewBoxInfo.x / SCALE_FACTOR,
|
|
9002
|
-
y: viewBoxInfo.y / SCALE_FACTOR
|
|
9134
|
+
y: viewBoxInfo.y / SCALE_FACTOR,
|
|
9003
9135
|
},
|
|
9004
9136
|
ne: {
|
|
9005
9137
|
x: (viewBoxInfo.x + viewBoxInfo.width) / SCALE_FACTOR,
|
|
9006
|
-
y: (viewBoxInfo.y + viewBoxInfo.height) / SCALE_FACTOR
|
|
9007
|
-
}
|
|
9138
|
+
y: (viewBoxInfo.y + viewBoxInfo.height) / SCALE_FACTOR,
|
|
9139
|
+
},
|
|
9008
9140
|
};
|
|
9009
9141
|
}
|
|
9010
9142
|
}
|
|
@@ -9018,7 +9150,7 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
9018
9150
|
lastY: mowerPositionData.lastPostureY || 0,
|
|
9019
9151
|
lastTheta: mowerPositionData.lastPostureTheta || 0,
|
|
9020
9152
|
vehicleState: mowerPositionData.vehicleState || RobotStatus.UNKNOWN,
|
|
9021
|
-
vehicleStateText: getVehicleStateText(mowerPositionData.vehicleState || RobotStatus.UNKNOWN)
|
|
9153
|
+
vehicleStateText: getVehicleStateText(mowerPositionData.vehicleState || RobotStatus.UNKNOWN),
|
|
9022
9154
|
};
|
|
9023
9155
|
}
|
|
9024
9156
|
// 获取当前割草地块数据
|
|
@@ -9026,9 +9158,6 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
9026
9158
|
setDebugInfo(newDebugInfo);
|
|
9027
9159
|
};
|
|
9028
9160
|
updateDebugInfo();
|
|
9029
|
-
// 设置定时更新(仅在没有数据变化时使用)
|
|
9030
|
-
const interval = setInterval(updateDebugInfo, 1000);
|
|
9031
|
-
return () => clearInterval(interval);
|
|
9032
9161
|
}, [debug, mapJson, mowerPositionData, mowPartitionData, defaultTransform]);
|
|
9033
9162
|
// 当关键数据变化时立即更新debug信息
|
|
9034
9163
|
React.useEffect(() => {
|
|
@@ -9057,12 +9186,12 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
9057
9186
|
// 计算左下角和右上角坐标
|
|
9058
9187
|
sw: {
|
|
9059
9188
|
x: viewBoxInfo.x / SCALE_FACTOR,
|
|
9060
|
-
y: viewBoxInfo.y / SCALE_FACTOR
|
|
9189
|
+
y: viewBoxInfo.y / SCALE_FACTOR,
|
|
9061
9190
|
},
|
|
9062
9191
|
ne: {
|
|
9063
9192
|
x: (viewBoxInfo.x + viewBoxInfo.width) / SCALE_FACTOR,
|
|
9064
|
-
y: (viewBoxInfo.y + viewBoxInfo.height) / SCALE_FACTOR
|
|
9065
|
-
}
|
|
9193
|
+
y: (viewBoxInfo.y + viewBoxInfo.height) / SCALE_FACTOR,
|
|
9194
|
+
},
|
|
9066
9195
|
};
|
|
9067
9196
|
}
|
|
9068
9197
|
}
|
|
@@ -9076,7 +9205,7 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
9076
9205
|
lastY: mowerPositionData.lastPostureY || 0,
|
|
9077
9206
|
lastTheta: mowerPositionData.lastPostureTheta || 0,
|
|
9078
9207
|
vehicleState: mowerPositionData.vehicleState || RobotStatus.UNKNOWN,
|
|
9079
|
-
vehicleStateText: getVehicleStateText(mowerPositionData.vehicleState || RobotStatus.UNKNOWN)
|
|
9208
|
+
vehicleStateText: getVehicleStateText(mowerPositionData.vehicleState || RobotStatus.UNKNOWN),
|
|
9080
9209
|
};
|
|
9081
9210
|
}
|
|
9082
9211
|
// 获取当前割草地块数据
|
|
@@ -9096,6 +9225,24 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
9096
9225
|
setMowPartitionData(mowingPartition);
|
|
9097
9226
|
}
|
|
9098
9227
|
const curMowPartitionData = mowingPartition || mowPartitionData;
|
|
9228
|
+
const statusData = realTimeData?.find(item => item?.type === RealTimeDataType.STATUS);
|
|
9229
|
+
if (statusData) {
|
|
9230
|
+
// 车辆回桩不会回传最后的park的位置,所以根据实时数据的状态数据判断车辆回到桩上
|
|
9231
|
+
if ([RobotStatus.CHARGING, RobotStatus.PARKED].includes(statusData?.vehicleState || RobotStatus.UNKNOWN)) {
|
|
9232
|
+
resetInCharginPie();
|
|
9233
|
+
}
|
|
9234
|
+
else if (statusData?.vehicleState === RobotStatus.MOWING) {
|
|
9235
|
+
// 兜底收不到割草地块的实时数据,使用状态来兜底
|
|
9236
|
+
const partitionids = curMowPartitionData?.partitionIds;
|
|
9237
|
+
if (!partitionids) {
|
|
9238
|
+
overlayRef.current.setBorderLayerHighlight();
|
|
9239
|
+
}
|
|
9240
|
+
}
|
|
9241
|
+
else if (statusData?.vehicleState === RobotStatus.WORKING) {
|
|
9242
|
+
// 同上
|
|
9243
|
+
overlayRef.current.resetBorderLayerHighlight();
|
|
9244
|
+
}
|
|
9245
|
+
}
|
|
9099
9246
|
if (!mapJson ||
|
|
9100
9247
|
!pathJson ||
|
|
9101
9248
|
!overlayRef.current)
|
|
@@ -9211,8 +9358,9 @@ const MowerMapRenderer = React.forwardRef(({ mapConfig, modelType, mapRef, mapJs
|
|
|
9211
9358
|
fontFamily: 'monospace',
|
|
9212
9359
|
zIndex: 10000,
|
|
9213
9360
|
maxWidth: '300px',
|
|
9214
|
-
lineHeight: '1.4'
|
|
9215
|
-
}, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold', marginBottom: '8px' }, children: "\uD83D\uDC1B Debug Info" }), debugInfo.mapBounds && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDCCD Map GPS Bounds:" }), jsxRuntime.jsxs("div", { children: ["SW: [", debugInfo.mapBounds.sw[0].toFixed(6), ", ", debugInfo.mapBounds.sw[1].toFixed(6), "]"] }), jsxRuntime.jsxs("div", { children: ["NE: [", debugInfo.mapBounds.ne[0].toFixed(6), ", ", debugInfo.mapBounds.ne[1].toFixed(6), "]"] })] })), debugInfo.viewBox && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDCD0 SVG ViewBox (meters):" }), jsxRuntime.jsxs("div", { children: ["SW: [", debugInfo.viewBox.sw.x.toFixed(2), ", ", debugInfo.viewBox.sw.y.toFixed(2), "]"] }), jsxRuntime.jsxs("div", { children: ["NE: [", debugInfo.viewBox.ne.x.toFixed(2), ", ", debugInfo.viewBox.ne.y.toFixed(2), "]"] }), jsxRuntime.jsxs("div", { children: ["Size: ", debugInfo.viewBox.width.toFixed(2), "m \u00D7 ", debugInfo.viewBox.height.toFixed(2), "m"] }), jsxRuntime.jsxs("div", { children: ["Scale: 1:", debugInfo.viewBox.scale] })] })), debugInfo.mowerPosition && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDE9C Mower Position:" }), jsxRuntime.jsxs("div", { children: ["Current: X=", debugInfo.mowerPosition.x.toFixed(2), ", Y=", debugInfo.mowerPosition.y.toFixed(2)] }), jsxRuntime.jsxs("div", { children: ["Theta: ", (debugInfo.mowerPosition.theta * 180 / Math.PI).toFixed(1), "\u00B0"] }), jsxRuntime.jsxs("div", { children: ["Last: X=", debugInfo.mowerPosition.lastX.toFixed(2), ", Y=", debugInfo.mowerPosition.lastY.toFixed(2)] }), jsxRuntime.jsxs("div", { children: ["Last Theta: ", (debugInfo.mowerPosition.lastTheta * 180 / Math.PI).toFixed(1), "\u00B0"] }), jsxRuntime.jsxs("div", { children: ["Status: ", debugInfo.mowerPosition.vehicleStateText, " (", debugInfo.mowerPosition.vehicleState, ")"] })] })), debugInfo.partitionData && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDD32 Mow Partition Data:" }), jsxRuntime.jsxs("div", { children: ["Type: ", debugInfo.partitionData.type || 'N/A'] }), debugInfo.partitionData.partitionIds &&
|
|
9361
|
+
lineHeight: '1.4',
|
|
9362
|
+
}, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold', marginBottom: '8px' }, children: "\uD83D\uDC1B Debug Info" }), debugInfo.mapBounds && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDCCD Map GPS Bounds:" }), jsxRuntime.jsxs("div", { children: ["SW: [", debugInfo.mapBounds.sw[0].toFixed(6), ", ", debugInfo.mapBounds.sw[1].toFixed(6), "]"] }), jsxRuntime.jsxs("div", { children: ["NE: [", debugInfo.mapBounds.ne[0].toFixed(6), ", ", debugInfo.mapBounds.ne[1].toFixed(6), "]"] })] })), debugInfo.viewBox && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDCD0 SVG ViewBox (meters):" }), jsxRuntime.jsxs("div", { children: ["SW: [", debugInfo.viewBox.sw.x.toFixed(2), ", ", debugInfo.viewBox.sw.y.toFixed(2), "]"] }), jsxRuntime.jsxs("div", { children: ["NE: [", debugInfo.viewBox.ne.x.toFixed(2), ", ", debugInfo.viewBox.ne.y.toFixed(2), "]"] }), jsxRuntime.jsxs("div", { children: ["Size: ", debugInfo.viewBox.width.toFixed(2), "m \u00D7 ", debugInfo.viewBox.height.toFixed(2), "m"] }), jsxRuntime.jsxs("div", { children: ["Scale: 1:", debugInfo.viewBox.scale] })] })), debugInfo.mowerPosition && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDE9C Mower Position:" }), jsxRuntime.jsxs("div", { children: ["Current: X=", debugInfo.mowerPosition.x.toFixed(2), ", Y=", debugInfo.mowerPosition.y.toFixed(2)] }), jsxRuntime.jsxs("div", { children: ["Theta: ", ((debugInfo.mowerPosition.theta * 180) / Math.PI).toFixed(1), "\u00B0"] }), jsxRuntime.jsxs("div", { children: ["Last: X=", debugInfo.mowerPosition.lastX.toFixed(2), ", Y=", debugInfo.mowerPosition.lastY.toFixed(2)] }), jsxRuntime.jsxs("div", { children: ["Last Theta: ", ((debugInfo.mowerPosition.lastTheta * 180) / Math.PI).toFixed(1), "\u00B0"] }), jsxRuntime.jsxs("div", { children: ["Status: ", debugInfo.mowerPosition.vehicleStateText, " (", debugInfo.mowerPosition.vehicleState, ")"] })] })), debugInfo.partitionData && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDD32 Mow Partition Data:" }), jsxRuntime.jsxs("div", { children: ["Type: ", debugInfo.partitionData.type || 'N/A'] }), debugInfo.partitionData.partitionIds &&
|
|
9363
|
+
debugInfo.partitionData.partitionIds.length > 0 ? (jsxRuntime.jsxs("div", { children: ["Active IDs: [", debugInfo.partitionData.partitionIds.join(', '), "]"] })) : (jsxRuntime.jsx("div", { children: "No active partitions" })), debugInfo.partitionData.time && (jsxRuntime.jsxs("div", { children: ["Updated: ", new Date(debugInfo.partitionData.time).toLocaleTimeString()] }))] })), !debugInfo.partitionData && (jsxRuntime.jsxs("div", { style: { marginBottom: '6px' }, children: [jsxRuntime.jsx("div", { style: { fontWeight: 'bold' }, children: "\uD83D\uDD32 Mow Partition Data:" }), jsxRuntime.jsx("div", { style: { color: '#888' }, children: "No partition data available" })] }))] }));
|
|
9216
9364
|
};
|
|
9217
9365
|
// 错误显示
|
|
9218
9366
|
if (currentError) {
|