张世豪
10 小时以前 13d032241e1a2938a8be4f64c9171e1240e9ea1e
src/zhangaiwu/AddDikuai.java
@@ -27,12 +27,13 @@
import dikuai.Dikuaiguanli;
import bianjie.bianjieguihua2;
import lujing.Lunjingguihua;
import publicway.buttonset;
import set.Setsys;
import ui.UIConfig;
import zhuye.MowerLocationData;
import zhuye.Shouye;
import zhuye.Coordinate;
import zhuye.buttonset;
import gecaoji.Device;
/**
 * 新增地块对话框 - 多步骤表单设计
@@ -67,6 +68,7 @@
    private JComboBox<String> mowingPatternCombo;
    private JTextField mowingWidthField; // 割草机割刀宽度
    private JTextField overlapDistanceField; // 相邻行重叠距离
    private JTextField mowingSafetyDistanceField; // 割草安全距离
    private JLabel calculatedMowingWidthLabel; // 计算后的割草宽度显示
    private JPanel previewPanel;
    private Map<String, JPanel> drawingOptionPanels = new HashMap<>();
@@ -101,6 +103,7 @@
        final boolean success;
        final String errorMessage;
        final String originalBoundary;
        final String originalBoundaryXY;
        final String optimizedBoundary;
        final String areaSqMeters;
        final String baseStationCoordinates;
@@ -109,6 +112,7 @@
        private BoundarySnapshotResult(boolean success,
                                       String errorMessage,
                                       String originalBoundary,
                                       String originalBoundaryXY,
                                       String optimizedBoundary,
                                       String areaSqMeters,
                                       String baseStationCoordinates,
@@ -116,18 +120,19 @@
            this.success = success;
            this.errorMessage = errorMessage;
            this.originalBoundary = originalBoundary;
            this.originalBoundaryXY = originalBoundaryXY;
            this.optimizedBoundary = optimizedBoundary;
            this.areaSqMeters = areaSqMeters;
            this.baseStationCoordinates = baseStationCoordinates;
            this.messageType = messageType;
        }
        static BoundarySnapshotResult success(String original, String optimized, String area, String baseStation) {
            return new BoundarySnapshotResult(true, null, original, optimized, area, baseStation, JOptionPane.INFORMATION_MESSAGE);
        static BoundarySnapshotResult success(String original, String originalXY, String optimized, String area, String baseStation) {
            return new BoundarySnapshotResult(true, null, original, originalXY, optimized, area, baseStation, JOptionPane.INFORMATION_MESSAGE);
        }
        static BoundarySnapshotResult failure(String message, int messageType) {
            return new BoundarySnapshotResult(false, message, null, null, null, null, messageType);
            return new BoundarySnapshotResult(false, message, null, null, null, null, null, messageType);
        }
    }
@@ -1044,6 +1049,65 @@
        
        calculatedWidthPanel.add(calculatedWidthDisplayPanel);
        settingsPanel.add(calculatedWidthPanel);
        settingsPanel.add(Box.createRigidArea(new Dimension(0, 10)));
        // 割草安全距离
        JPanel safetyDistancePanel = createFormGroupWithoutHint("割草安全距离");
        JPanel safetyDistanceInputPanel = new JPanel(new BorderLayout());
        safetyDistanceInputPanel.setBackground(WHITE);
        safetyDistanceInputPanel.setMaximumSize(new Dimension(Integer.MAX_VALUE, 48));
        safetyDistanceInputPanel.setAlignmentX(Component.LEFT_ALIGNMENT);
        // 获取默认值
        String defaultSafetyDistance = "0.5"; // 默认值
        try {
            Device device = Device.getGecaoji();
            if (device != null) {
                String safetyDistance = device.getMowingSafetyDistance();
                if (safetyDistance != null && !safetyDistance.trim().isEmpty() && !"-1".equals(safetyDistance.trim())) {
                    defaultSafetyDistance = safetyDistance.trim();
                }
            }
        } catch (Exception e) {
            // 如果获取失败,使用默认值
        }
        mowingSafetyDistanceField = new JTextField(defaultSafetyDistance);
        mowingSafetyDistanceField.setFont(new Font("微软雅黑", Font.PLAIN, 16));
        mowingSafetyDistanceField.setBorder(BorderFactory.createCompoundBorder(
            BorderFactory.createLineBorder(BORDER_COLOR, 2),
            BorderFactory.createEmptyBorder(10, 12, 10, 12)
        ));
        // 添加文本框焦点效果
        mowingSafetyDistanceField.addFocusListener(new FocusAdapter() {
            @Override
            public void focusGained(FocusEvent e) {
                mowingSafetyDistanceField.setBorder(BorderFactory.createCompoundBorder(
                    BorderFactory.createLineBorder(PRIMARY_COLOR, 2),
                    BorderFactory.createEmptyBorder(10, 12, 10, 12)
                ));
            }
            @Override
            public void focusLost(FocusEvent e) {
                mowingSafetyDistanceField.setBorder(BorderFactory.createCompoundBorder(
                    BorderFactory.createLineBorder(BORDER_COLOR, 2),
                    BorderFactory.createEmptyBorder(10, 12, 10, 12)
                ));
            }
        });
        JLabel safetyDistanceUnitLabel = new JLabel("米");
        safetyDistanceUnitLabel.setFont(new Font("微软雅黑", Font.PLAIN, 14));
        safetyDistanceUnitLabel.setForeground(LIGHT_TEXT);
        safetyDistanceUnitLabel.setBorder(BorderFactory.createEmptyBorder(0, 15, 0, 0));
        safetyDistanceInputPanel.add(mowingSafetyDistanceField, BorderLayout.CENTER);
        safetyDistanceInputPanel.add(safetyDistanceUnitLabel, BorderLayout.EAST);
        safetyDistancePanel.add(safetyDistanceInputPanel);
        settingsPanel.add(safetyDistancePanel);
        settingsPanel.add(Box.createRigidArea(new Dimension(0, 25)));
        
        stepPanel.add(settingsPanel);
@@ -1614,6 +1678,7 @@
        Dikuai dikuai = getOrCreatePendingDikuai();
        if (dikuai != null) {
            dikuai.setBoundaryOriginalCoordinates(snapshot.originalBoundary);
            dikuai.setBoundaryOriginalXY(snapshot.originalBoundaryXY);
            dikuai.setBoundaryCoordinates(snapshot.optimizedBoundary);
            dikuai.setLandArea(snapshot.areaSqMeters);
            dikuai.setBaseStationCoordinates(snapshot.baseStationCoordinates);
@@ -1622,11 +1687,13 @@
        }
        dikuaiData.put("boundaryOriginalCoordinates", snapshot.originalBoundary);
        dikuaiData.put("boundaryOriginalXY", snapshot.originalBoundaryXY);
        dikuaiData.put("boundaryCoordinates", snapshot.optimizedBoundary);
        dikuaiData.put("landArea", snapshot.areaSqMeters);
        dikuaiData.put("baseStationCoordinates", snapshot.baseStationCoordinates);
        if (activeSession != null) {
            activeSession.data.put("boundaryOriginalCoordinates", snapshot.originalBoundary);
            activeSession.data.put("boundaryOriginalXY", snapshot.originalBoundaryXY);
            activeSession.data.put("boundaryCoordinates", snapshot.optimizedBoundary);
            activeSession.data.put("landArea", snapshot.areaSqMeters);
            activeSession.data.put("baseStationCoordinates", snapshot.baseStationCoordinates);
@@ -1682,6 +1749,47 @@
        }
        return sb.toString();
    }
    /**
     * 构建原始边界XY坐标字符串(相对于基准站的XY坐标)
     */
    private static String buildOriginalBoundaryXYString(List<Coordinate> coordinates, String baseStationCoordinates) {
        if (coordinates == null || coordinates.isEmpty()) {
            return "-1";
        }
        if (baseStationCoordinates == null || baseStationCoordinates.trim().isEmpty() || "-1".equals(baseStationCoordinates.trim())) {
            return "-1";
        }
        try {
            // 解析基准站坐标
            String[] baseParts = baseStationCoordinates.split(",");
            if (baseParts.length < 4) {
                return "-1";
            }
            double baseLat = publicway.Gpstoxuzuobiao.parseDMToDecimal(baseParts[0], baseParts[1]);
            double baseLon = publicway.Gpstoxuzuobiao.parseDMToDecimal(baseParts[2], baseParts[3]);
            StringBuilder sb = new StringBuilder();
            DecimalFormat xyFormat = new DecimalFormat("0.00");
            for (Coordinate coord : coordinates) {
                double lat = convertToDecimalDegree(coord.getLatitude(), coord.getLatDirection());
                double lon = convertToDecimalDegree(coord.getLongitude(), coord.getLonDirection());
                // 转换为XY坐标
                double[] xy = publicway.Gpstoxuzuobiao.convertLatLonToLocal(lat, lon, baseLat, baseLon);
                if (sb.length() > 0) {
                    sb.append(";");
                }
                sb.append(xyFormat.format(xy[0])).append(",").append(xyFormat.format(xy[1]));
            }
            return sb.toString();
        } catch (Exception e) {
            e.printStackTrace();
            return "-1";
        }
    }
    private static double convertToDecimalDegree(String dmm, String direction) {
        if (dmm == null || dmm.isEmpty()) {
@@ -1804,10 +1912,11 @@
        }
    String originalBoundary = buildOriginalBoundaryString(uniqueCoordinates);
        String originalBoundaryXY = buildOriginalBoundaryXYString(uniqueCoordinates, baseStationCoordinates);
        DecimalFormat areaFormat = new DecimalFormat("0.00");
        String areaString = areaFormat.format(area);
        return BoundarySnapshotResult.success(originalBoundary, optimizedBoundary, areaString, baseStationCoordinates);
        return BoundarySnapshotResult.success(originalBoundary, originalBoundaryXY, optimizedBoundary, areaString, baseStationCoordinates);
    }
    private String resolvePlannerMode(String patternDisplay) {
@@ -2346,6 +2455,7 @@
        BoundarySnapshotResult snapshot = computeBoundarySnapshot();
        if (snapshot.success && activeSession != null) {
            activeSession.data.put("boundaryOriginalCoordinates", snapshot.originalBoundary);
            activeSession.data.put("boundaryOriginalXY", snapshot.originalBoundaryXY);
            activeSession.data.put("boundaryCoordinates", snapshot.optimizedBoundary);
            activeSession.data.put("landArea", snapshot.areaSqMeters);
            activeSession.data.put("baseStationCoordinates", snapshot.baseStationCoordinates);
@@ -2405,6 +2515,9 @@
        if (dikuaiData.containsKey("boundaryOriginalCoordinates")) {
            dikuai.setBoundaryOriginalCoordinates(dikuaiData.get("boundaryOriginalCoordinates"));
        }
        if (dikuaiData.containsKey("boundaryOriginalXY")) {
            dikuai.setBoundaryOriginalXY(dikuaiData.get("boundaryOriginalXY"));
        }
        if (dikuaiData.containsKey("boundaryCoordinates")) {
            dikuai.setBoundaryCoordinates(dikuaiData.get("boundaryCoordinates"));
        }
@@ -2478,6 +2591,21 @@
        if (isMeaningfulValue(plannedPath)) {
            dikuai.setPlannedPath(plannedPath);
        }
        // 保存割草安全距离(优先从dikuaiData获取,否则从TextField获取)
        if (dikuaiData.containsKey("mowingSafetyDistance")) {
            dikuai.setMowingSafetyDistance(dikuaiData.get("mowingSafetyDistance"));
        } else if (mowingSafetyDistanceField != null) {
            String safetyDistanceText = mowingSafetyDistanceField.getText().trim();
            if (!safetyDistanceText.isEmpty()) {
                try {
                    double safetyDistanceMeters = Double.parseDouble(safetyDistanceText);
                    dikuai.setMowingSafetyDistance(String.format(Locale.US, "%.2f", safetyDistanceMeters));
                } catch (NumberFormatException e) {
                    dikuai.setMowingSafetyDistance(safetyDistanceText);
                }
            }
        }
        Dikuai.putDikuai(landNumber, dikuai);
        Dikuai.saveToProperties();