| | |
| | | } else if (grassType == 2) { |
| | | // 异形地块,有障碍物 -> 调用 YixinglujingHaveObstacel |
| | | // 传入参数:boundary(A), obstacles(B), plannerWidth(C), safetyMarginStr(D) |
| | | // 注意:YixinglujingHaveObstacel.planPath 返回 String |
| | | generated = YixinglujingHaveObstacel.planPath(boundary, obstacles, plannerWidth, safetyMarginStr); |
| | | List<YixinglujingHaveObstacel.PathSegment> segments = |
| | | YixinglujingHaveObstacel.planPath(boundary, obstacles, plannerWidth, safetyMarginStr); |
| | | generated = formatYixingHaveObstaclePathSegments(segments); |
| | | } else { |
| | | // 无法判断地块类型,默认按凸形处理或提示 |
| | | if (showMessages) { |
| | |
| | | } |
| | | |
| | | /** |
| | | * 格式化 YixinglujingHaveObstacel.PathSegment 列表为坐标字符串 |
| | | */ |
| | | private String formatYixingHaveObstaclePathSegments(List<YixinglujingHaveObstacel.PathSegment> segments) { |
| | | if (segments == null || segments.isEmpty()) { |
| | | return ""; |
| | | } |
| | | StringBuilder sb = new StringBuilder(); |
| | | YixinglujingHaveObstacel.Point last = null; |
| | | for (YixinglujingHaveObstacel.PathSegment segment : segments) { |
| | | // 如果是第一段,或者当前段起点与上一段终点不连续,则添加起点 |
| | | if (last == null || !equalsYixingHaveObstaclePoint(last, segment.start)) { |
| | | appendYixingHaveObstaclePoint(sb, segment.start); |
| | | } |
| | | // 添加终点 |
| | | appendYixingHaveObstaclePoint(sb, segment.end); |
| | | last = segment.end; |
| | | } |
| | | return sb.toString(); |
| | | } |
| | | |
| | | private boolean equalsYixingHaveObstaclePoint(YixinglujingHaveObstacel.Point p1, YixinglujingHaveObstacel.Point p2) { |
| | | if (p1 == null || p2 == null) return false; |
| | | double tolerance = 1e-6; |
| | | return Math.abs(p1.x - p2.x) < tolerance && Math.abs(p1.y - p2.y) < tolerance; |
| | | } |
| | | |
| | | private void appendYixingHaveObstaclePoint(StringBuilder sb, YixinglujingHaveObstacel.Point point) { |
| | | if (sb.length() > 0) { |
| | | sb.append(";"); |
| | | } |
| | | sb.append(String.format(Locale.US, "%.6f,%.6f", point.x, point.y)); |
| | | } |
| | | |
| | | /** |
| | | * 比较两个点是否相同(使用小的容差) |
| | | */ |
| | | private boolean equals2D(AoxinglujingNoObstacle.Point p1, AoxinglujingNoObstacle.Point p2) { |