xushiting 2 年之前
父節點
當前提交
395519c49c

+ 32 - 5
src/graphic/Controls/MoveRoad.js

@@ -8,7 +8,6 @@ import { edgeService } from "../Service/EdgeService";
 
 export default class MoveRoad {
   constructor() {
-    this.startMoving = false;
     this.moveFlag = false;
 
     //拖拽墙角的时候,墙角的父亲与其他墙角相交
@@ -18,10 +17,6 @@ export default class MoveRoad {
     this.splitRoadId = null;
   }
 
-  setStartMoving(value) {
-    this.startMoving = value;
-  }
-
   // 测试要考虑pointId拖拽到包含他的所有墙的另一头
   // 这个函数不会删除/拆分/合并墙或者点
   moveingRoadPoint(pointId, position, modifyPoint) {
@@ -989,6 +984,38 @@ export default class MoveRoad {
     }
   }
 
+  //需要更新:points,leftLanes,rightLanes,leftEdgeId,rightEdgeId
+  moveCurveRoad(curveRoadId, dx, dy) {
+    dx = dx;
+    dy = -dy;
+    const curveRoad = dataService.getCurveRoad(curveRoadId);
+    const leftCurveEdge = dataService.getCurveEdge(curveRoad.leftEdgeId);
+    const rightCurveEdge = dataService.getCurveEdge(curveRoad.rightEdgeId);
+
+    for (let i = 0; i < curveRoad.points.length; ++i) {
+      curveRoad.points[i].x += dx;
+      curveRoad.points[i].y += dy;
+      leftCurveEdge.points[i].x += dx;
+      leftCurveEdge.points[i].y += dy;
+      rightCurveEdge.points[i].x += dx;
+      rightCurveEdge.points[i].y += dy;
+    }
+
+    for (let i = 0; i < curveRoad.leftLanes.length; ++i) {
+      for (let j = 0; j < curveRoad.leftLanes[i].length; ++j) {
+        curveRoad.leftLanes[i][j].x += dx;
+        curveRoad.leftLanes[i][j].y += dy;
+      }
+    }
+
+    for (let i = 0; i < curveRoad.rightLanes.length; ++i) {
+      for (let j = 0; j < curveRoad.rightLanes[i].length; ++j) {
+        curveRoad.rightLanes[i][j].x += dx;
+        curveRoad.rightLanes[i][j].y += dy;
+      }
+    }
+  }
+
   // pointId1移动到pointId2
   // 如果有一堵墙(roadId)的两头是pointId1和pointId2,那么这堵墙会被删除
   moveTo(pointId1, pointId2) {

+ 2 - 0
src/graphic/Geometry/CurveRoad.js

@@ -7,6 +7,8 @@ export default class CurveRoad extends Road {
   constructor(startId, endId, vectorId) {
     super(startId, endId, vectorId);
     this.points = []; //中心线上一系列控制点。数组是从start到end。
+    this.leftLanesCurves = null; //左车道曲线
+    this.rightLanesCurves = null; //左车道曲线
     this.width = Constant.defaultRoadWidth; //默认宽度
     this.leftDrivewayCount = 2; //左边的车道个数
     this.rightDrivewayCount = 2; //右边的车道个数

+ 25 - 7
src/graphic/Layer.js

@@ -212,7 +212,6 @@ export default class Layer {
         break;
       case LayerEvents.MoveRoadPoint:
         point = dataService.getPoint(draggingItem.vectorId);
-        //listenLayer.start(position, draggingItem.vectorId, point.parent);
         listenLayer.start(position, draggingItem.vectorId, point.parent);
         if (listenLayer.modifyPoint) {
           position = {
@@ -315,9 +314,25 @@ export default class Layer {
 
         addRoad.setNewRoadPoint("start", position);
         break;
+      case LayerEvents.MoveCurveRoad:
+        needAutoRedraw = true;
+        moveRoad.moveCurveRoad(
+          draggingItem.vectorId,
+          (dx * coordinate.defaultZoom) / coordinate.zoom,
+          (dy * coordinate.defaultZoom) / coordinate.zoom
+        );
+        this.lastX = X;
+        this.lastY = Y;
+        break;
       case LayerEvents.MoveCurveRoadPoint:
         point = dataService.getCurvePoint(draggingItem.vectorId);
-        listenLayer.start(position, draggingItem.vectorId, null, point.parent);
+        listenLayer.start(
+          position,
+          draggingItem.vectorId,
+          null,
+          null,
+          point.parent
+        );
         if (listenLayer.modifyPoint) {
           position = {
             x: listenLayer.modifyPoint.x,
@@ -472,12 +487,15 @@ export default class Layer {
         break;
       case LayerEvents.MoveRoad:
         needAutoRedraw = true;
-        if (focusItem != null && focusItem.type == VectorType.Road) {
-          const road = dataService.getRoad(focusItem.vectorId);
-          this.uiControl.currentUI = focusItem.type;
-        }
         this.history.save();
-        moveRoad.setStartMoving(false);
+        break;
+      case LayerEvents.MoveCurveRoad:
+        needAutoRedraw = true;
+        this.history.save();
+        break;
+      case LayerEvents.MoveCurveRoadPoint:
+        needAutoRedraw = true;
+        this.history.save();
         break;
       case LayerEvents.MoveTag:
         needAutoRedraw = true;

+ 7 - 76
src/graphic/ListenLayer.js

@@ -289,7 +289,11 @@ export default class ListenLayer {
       }
       const curveRoad = dataService.getCurveRoad(curveRoadId);
       console.log("currentRoad", curveRoad.curves);
-      let joinInfo = this.distanceForBezier(position, curveRoad.curves);
+      let joinInfo = this.distanceForBezier(
+        position,
+        curveRoad.curves,
+        curveRoad.width
+      );
       if (joinInfo.distance < Constant.minAdsorbPix) {
         curveRoadInfo = {
           curveRoadId: curveRoadId,
@@ -420,83 +424,10 @@ export default class ListenLayer {
     } else {
       return true;
     }
-    // if (!flag1) {
-    //   stateService.setSelectItem(
-    //     this.curveRoadInfo.curveRoadId,
-    //     this.curveRoadInfo.type,
-    //     this.curveRoadInfo.state
-    //   );
-    // }
-    // if (!flag2) {
-    //   stateService.setSelectItem(
-    //     this.roadInfo.roadId,
-    //     this.roadInfo.type,
-    //     this.roadInfo.state
-    //   );
-    // }
-    // if (!flag3) {
-    //   stateService.setSelectItem(
-    //     this.curvePointInfo.curvePointId,
-    //     this.curvePointInfo.type,
-    //     this.curvePointInfo.state
-    //   );
-    // }
-    // if (!flag4) {
-    //   stateService.setSelectItem(
-    //     this.pointInfo.pointId,
-    //     this.pointInfo.type,
-    //     this.pointInfo.state
-    //   );
-    // }
-    // let selectItem = stateService.getSelectItem();
-    // if (selectItem != null) {
-    //   console.log("监听:" + JSON.stringify(selectItem));
-    // }
-    // return flag1 && flag2 && flag3 && flag4;
   }
 
-  // distanceForBezier(position, curves) {
-  //   let joinInfo = {
-  //     position: null,
-  //     distance: null,
-  //   };
-  //   for (let i = 0; i < curves.length; ++i) {
-  //     const curve = curves[i];
-  //     let bezierData = [];
-  //     bezierData.push(curve.start.x);
-  //     bezierData.push(curve.start.y);
-  //     bezierData.push(curve.control.x);
-  //     bezierData.push(curve.control.y);
-  //     bezierData.push(curve.end.x);
-  //     bezierData.push(curve.end.y);
-  //     const { isHit, getInfo } = bezierUtil.measureBezier(...bezierData);
-  //     const { point } = getInfo(position);
-  //     const distance = mathUtil.getDistance(position, {
-  //       x: point[0],
-  //       y: point[1],
-  //     });
-  //     if (joinInfo.distance == null || distance < joinInfo.distance) {
-  //       joinInfo.distance = mathUtil.getDistance(position, {
-  //         x: point[0],
-  //         y: point[1],
-  //       });
-  //       joinInfo.position = {
-  //         x: point[0],
-  //         y: point[1],
-  //       };
-  //     }
-  //   }
-  //   if (joinInfo.distance != null) {
-  //     console.log("离曲线距离:" + joinInfo.distance);
-  //     //position到joinInfo.position的线段
-  //     //draw.clear();
-  //     draw.drawTestLine(position, joinInfo.position);
-  //   }
-  //   return joinInfo;
-  // }
-
-  distanceForBezier(position, curves) {
-    return mathUtil.getHitInfoForCurves(position, curves);
+  distanceForBezier(position, curves, width) {
+    return mathUtil.getHitInfoForCurves(position, curves, width);
   }
 
   equalAndClone(info1, info2) {

+ 10 - 0
src/graphic/Service/CrossRoadService.js

@@ -0,0 +1,10 @@
+const roadLen = 500;
+//交叉路口
+export default class CrossRoadService {
+  constructor() {}
+
+  create(position, num) {}
+}
+
+const crossRoadService = new CrossRoadService();
+export { crossRoadService };

+ 3 - 3
src/graphic/Util/MathUtil.js

@@ -1325,13 +1325,13 @@ export default class MathUtil {
     };
   }
 
-  getHitInfoForCurves(pos, curves) {
+  getHitInfoForCurves(pos, curves, roadWidth) {
     let joinInfo;
     for (const curve of curves) {
       const tempJoinInfo =
         curve.controls.length === 2
-          ? mathUtil.getHitInfoForThreeBezier(pos, curve, 8)
-          : mathUtil.getHitInfoForTwoBezier(pos.x, curve);
+          ? mathUtil.getHitInfoForThreeBezier(pos, curve, roadWidth / 2)
+          : mathUtil.getHitInfoForTwoBezier(pos, curve);
 
       if (
         !joinInfo ||

+ 77 - 43
src/graphic/Util/bezierUtil.js

@@ -21,7 +21,11 @@ export function transformCoord(rotation, dx, dy) {
 
 export function createIsRoughHit(fromX, fromY, cpX, cpY, toX, toY) {
   var _a, _b, _c;
-  var transform = transformCoord(Math.atan2(toX - fromX, toY - fromY), (fromX + toX) / 2, (fromY + toY) / 2);
+  var transform = transformCoord(
+    Math.atan2(toX - fromX, toY - fromY),
+    (fromX + toX) / 2,
+    (fromY + toY) / 2
+  );
   var t_from = transform(fromX, fromY);
   var t_cp = transform(cpX, cpY);
   var t_to = transform(toX, toY);
@@ -33,14 +37,20 @@ export function createIsRoughHit(fromX, fromY, cpX, cpY, toX, toY) {
   if (t_cp.x >= t_from.x && t_cp.x <= t_to.y) {
     (_a = [t_from.x, t_to.x]), (left = _a[0]), (right = _a[1]);
   } else if (t_cp.x > 0) {
-    (_b = [t_from.x, 0.5 * (t_cp.x + (ratio * ratio) / t_cp.x)]), (left = _b[0]), (right = _b[1]);
+    (_b = [t_from.x, 0.5 * (t_cp.x + (ratio * ratio) / t_cp.x)]),
+      (left = _b[0]),
+      (right = _b[1]);
   } else {
-    (_c = [0.5 * (t_cp.x + (ratio * ratio) / t_cp.x), t_to.x]), (left = _c[0]), (right = _c[1]);
+    (_c = [0.5 * (t_cp.x + (ratio * ratio) / t_cp.x), t_to.x]),
+      (left = _c[0]),
+      (right = _c[1]);
   }
   return function isRoughtHit(x, y, distance) {
     var t_point = transform(x, y);
-    if (t_point.x < left - distance || t_point.x > right + distance) return false;
-    if (t_point.y < bottom - distance || t_point.y > top + distance) return false;
+    if (t_point.x < left - distance || t_point.x > right + distance)
+      return false;
+    if (t_point.y < bottom - distance || t_point.y > top + distance)
+      return false;
     return true;
   };
 }
@@ -50,28 +60,29 @@ export function baseMeasureBezier(fromX, fromY, cpX, cpY, toX, toY) {
     getDistance = _a.getDistance,
     getInfo = _a.getInfo;
   function baseIsHit(x, y, hitDistance) {
-    if (typeof hitDistance !== 'number') throw new Error('isHit params "hitDistance" must be a number');
+    if (typeof hitDistance !== "number")
+      throw new Error('isHit params "hitDistance" must be a number');
     // rough hit
     if (!isRoughHit(x, y, hitDistance)) return false;
     //  analyical
     return getDistance(x, y) <= hitDistance;
   }
   function isHit(a, b, c) {
-    if (typeof a === 'number') return baseIsHit(a, b, c);
+    if (typeof a === "number") return baseIsHit(a, b, c);
     if (Array.isArray(a)) return baseIsHit(a[0], a[1], b);
     return baseIsHit(a.x, a.y, b);
   }
   return {
     isHit: isHit,
     getInfo: function (a, b) {
-      if (typeof a === 'number') return getInfo(a, b);
+      if (typeof a === "number") return getInfo(a, b);
       if (Array.isArray(a)) return getInfo(a[0], a[1]);
       return getInfo(a.x, a.y);
     },
   };
 }
 export function measureBezier(a, b, c, d, e, f) {
-  if (typeof a === 'number') {
+  if (typeof a === "number") {
     // @ts-ignore
     return baseMeasureBezier(a, b, c, d, e, f);
   }
@@ -103,44 +114,67 @@ export function createCalDistanceToBezier(sX, sY, cpX, cpY, eX, eY) {
   var calBezierTValues =
     dot(b, b) === 0
       ? // bezier fallback to line or point
-      function calBezierTValues(d) {
-        return dot_a === 0 ? 0 : clamp(-dot(a, d) / 2 / dot_a, 0, 1);
-      }
-      : function calBezierTValues(d) {
-        var ky = (kk * (2.0 * dot_a + dot(d, b))) / 3.0;
-        var kz = kk * dot(d, a);
-        var p = ky - kx_2;
-        var p3 = p * p * p;
-        var q = kx * (2.0 * kx_2 - 3.0 * ky) + kz;
-        var h = q * q + 4.0 * p3;
-        if (h >= 0.0) {
-          h = sqrt(h);
-          var x_0 = (h - q) / 2.0;
-          var x_1 = (-h - q) / 2.0;
-          var t = clamp(sign(x_0) * pow(abs(x_0), 1 / 3) + sign(x_1) * pow(abs(x_1), 1 / 3) - kx, 0.0, 1.0);
-          return t;
-        } else {
-          var z = sqrt(-p);
-          var v = acos(q / (p * z * 2.0)) / 3.0;
-          var m = cos(v);
-          var n = sin(v) * SQRT_3;
-          return [clamp((m + m) * z - kx, 0, 1), clamp((-n - m) * z - kx, 0, 1)];
+        function calBezierTValues(d) {
+          return dot_a === 0 ? 0 : clamp(-dot(a, d) / 2 / dot_a, 0, 1);
         }
-      };
+      : function calBezierTValues(d) {
+          var ky = (kk * (2.0 * dot_a + dot(d, b))) / 3.0;
+          var kz = kk * dot(d, a);
+          var p = ky - kx_2;
+          var p3 = p * p * p;
+          var q = kx * (2.0 * kx_2 - 3.0 * ky) + kz;
+          var h = q * q + 4.0 * p3;
+          if (h >= 0.0) {
+            h = sqrt(h);
+            var x_0 = (h - q) / 2.0;
+            var x_1 = (-h - q) / 2.0;
+            var t = clamp(
+              sign(x_0) * pow(abs(x_0), 1 / 3) +
+                sign(x_1) * pow(abs(x_1), 1 / 3) -
+                kx,
+              0.0,
+              1.0
+            );
+            return t;
+          } else {
+            var z = sqrt(-p);
+            var v = acos(q / (p * z * 2.0)) / 3.0;
+            var m = cos(v);
+            var n = sin(v) * SQRT_3;
+            return [
+              clamp((m + m) * z - kx, 0, 1),
+              clamp((-n - m) * z - kx, 0, 1),
+            ];
+          }
+        };
   return {
     getDistance: function (pX, pY) {
       var d = [sX - pX, sY - pY];
       var t = calBezierTValues(d);
-      if (typeof t === 'number') return sqrt(dot2((c[0] + b[0] * t) * t + d[0], (c[1] + b[1] * t) * t + d[1]));
+      if (typeof t === "number")
+        return sqrt(
+          dot2((c[0] + b[0] * t) * t + d[0], (c[1] + b[1] * t) * t + d[1])
+        );
       var _a = t,
         t_0 = _a[0],
         t_1 = _a[1];
-      return sqrt(min(dot2(d[0] + (c[0] + b[0] * t_0) * t_0, d[1] + (c[1] + b[1] * t_0) * t_0), dot2(d[0] + (c[0] + b[0] * t_1) * t_1, d[1] + (c[1] + b[1] * t_1) * t_1)));
+      return sqrt(
+        min(
+          dot2(
+            d[0] + (c[0] + b[0] * t_0) * t_0,
+            d[1] + (c[1] + b[1] * t_0) * t_0
+          ),
+          dot2(
+            d[0] + (c[0] + b[0] * t_1) * t_1,
+            d[1] + (c[1] + b[1] * t_1) * t_1
+          )
+        )
+      );
     },
     getInfo: function (pX, pY) {
       var d = [sX - pX, sY - pY];
       var t = calBezierTValues(d);
-      if (typeof t === 'number') {
+      if (typeof t === "number") {
         var p_x = (c[0] + b[0] * t) * t + d[0];
         var p_y = (c[1] + b[1] * t) * t + d[1];
         return {
@@ -159,13 +193,13 @@ export function createCalDistanceToBezier(sX, sY, cpX, cpY, eX, eY) {
       var d_1 = dot2(p_1_x, p_1_y);
       return d_0 >= d_1
         ? {
-          distance: sqrt(d_1),
-          point: [p_1_x + pX, p_1_y + pY],
-        }
+            distance: sqrt(d_1),
+            point: [p_1_x + pX, p_1_y + pY],
+          }
         : {
-          distance: sqrt(d_0),
-          point: [p_0_x + pX, p_0_y + pY],
-        };
+            distance: sqrt(d_0),
+            point: [p_0_x + pX, p_0_y + pY],
+          };
     },
   };
 }
@@ -175,5 +209,5 @@ export default {
   createIsRoughHit,
   baseMeasureBezier,
   measureBezier,
-  createCalDistanceToBezier
-}
+  createCalDistanceToBezier,
+};