void DrawDots() { if (shapeCreator == null) { return; } if (shapeCreator.NeigthborList == null) { return; } for (int i = 0; i < shapeCreator.NeigthborList.Count; i++) { RoadPoint pointA = shapeCreator.NeigthborList[i][0]; RoadPoint pointB = shapeCreator.NeigthborList[i][1]; if (pointA == null || pointB == null) { return; } Handles.DrawDottedLine(pointA.transform.position, pointB.transform.position, 4); } }
private void AddNeightbors(RoadPoint pointA) { if (lastSelected == null) { return; } if (lastSelected == pointA) { return; } for (int i = 0; i < shapeCreator.NeigthborList.Count; i++) { if (shapeCreator.NeigthborList[i].Contains(lastSelected) && shapeCreator.NeigthborList[i].Contains(pointA)) { return; } } List <RoadPoint> connection = new List <RoadPoint>(); connection.Add(pointA); connection.Add(lastSelected); shapeCreator.NeigthborList.Add(connection); }
public void StartGeneratingRoad(float widthMin, float widthMax, float estimatedLength, float spacing, float resolution, RoadTile tileBefore = null) { Setted = false; _spacing = spacing; _resolution = resolution; float pointPosX = Random.Range(widthMin, widthMax) * (Random.Range(0, 100) > 50 ? -1 : 1); float pointPosY = estimatedLength; EndPoint = new RoadPoint(new Vector2(pointPosX, pointPosY)); RoadPoint tileBeforeEndPoint; if (tileBefore != null) { transform.position = tileBefore.transform.position + (Vector3)tileBefore.EndPoint.position; tileBeforeEndPoint = tileBefore.EndPoint; } else { transform.position = Vector3.zero; tileBeforeEndPoint = new RoadPoint(Vector2.zero); } Vector2[] segmentPoints = new Vector2[4]; segmentPoints[0] = new Vector2(0, 0); segmentPoints[1] = tileBeforeEndPoint.Direction * tileBeforeEndPoint.strength * estimatedLength / 2; segmentPoints[2] = EndPoint.position - EndPoint.Direction * EndPoint.strength * estimatedLength / 2; segmentPoints[3] = EndPoint.position; Path.Initialize(segmentPoints, resolution); Calculate = true; }
// Update is called once per frame void FixedUpdate() { //测试结果,每秒50次 if (nextPoint != null) { //向下一个点走 Vector3 target = nextPoint.transform.position; target.y = ignoreY ? transform.position.y : target.y; transform.position = Vector3.MoveTowards(transform.position, target, step); if (Vector3.Distance(transform.position, target) < 0.05) { //到了终点附近逻辑等价于已经到达 RoadPoint tempp = nextPoint; nextPoint = nextPoint.getNextPoint(this); fromPoint = tempp; lookFront(nextPoint.transform.position); } } }
public void RemoveNeightbor(RoadPoint neightbor) { if (neightborList.Contains(neightbor)) { neightborList.Remove(neightbor); } }
//If BOT collision he's target void OnTriggerEnter2D(Collider2D coll) { if (coll.gameObject.tag == TagsManager.GetTag(Tag.RoadPoint)) { //UnityEngine.Debug.Log("<color=blue>BOT</color>: idę za Kolejnym punktem ścieżki"); RoadPoint roadPoint = coll.gameObject.GetComponent <RoadPoint>(); roadPoint.ResetCollider(); int bezpiecznik = 0; while (true) { int index = Random.Range(0, roadPoint.punktyDrogiObok.Length); if (roadPoint.punktyDrogiObok[index] != tempTargetRoad) { tempTargetRoad = target; target = roadPoint.punktyDrogiObok[index]; break; } else { bezpiecznik++; if (bezpiecznik > 10) { //UnityEngine.Debug.Log("<color=blue>BOT</color>: koniec ścieżki"); tempTargetRoad = target; target = roadPoint.punktyDrogiObok[index]; break; } } } } }
bool ISRoadBehind(RoadPoint thisroad, RoadPoint otherroad) { bool isBehind = false; if (thisroad.transform.position.z == otherroad.transform.position.z) { float x = Mathf.Abs(thisroad.transform.position.x - otherroad.transform.position.x); if (x == 3.0f) { isBehind = true; } } else if (thisroad.transform.position.x == otherroad.transform.position.x) { float z = Mathf.Abs(thisroad.transform.position.z - otherroad.transform.position.z); if (z == 3.0f) { isBehind = true; } } return(isBehind); }
public IEnumerator Start_WillInitializeArPathAndMapPath() { var start = new RoadPoint(0, new Marker("Start", 30f, -2)); var end = new RoadPoint(2, new Marker("End", 10f, -4)); var corner = new RoadPoint(1, new Marker("Corner 1", 24, -3)); var mockRoad = new Road(new [] { start, corner, end }); Repositories.RoadRepository.Save(new [] { mockRoad }); Repositories.LocationsRepository.Save(new [] { new Location("", "ChicagoMap") }); Repositories.SyncPointRepository.Save(new [] { new SyncPoint("test", 10, 10, 0), }); SceneManager.LoadScene("ARView"); yield return(null); var roads = GameObject.FindGameObjectsWithTag("Road"); Assert.AreEqual(2, roads.Length); foreach (var road in roads) { var roadRenderer = road.GetComponent <LineRenderer>(); Assert.AreEqual(3, roadRenderer.positionCount); Assert.AreEqual(start.Vector, roadRenderer.GetPosition(0)); Assert.AreEqual(corner.Vector, roadRenderer.GetPosition(1)); Assert.AreEqual(end.Vector, roadRenderer.GetPosition(2)); } }
// inSegment(): determine if a point is inside a segment // Input: a point P, and a collinear segment S // Return: 1 = P is inside S // 0 = P is not inside S int inSegment(RoadPoint P, RoadSegment S) { if (S.PointA.point.x != S.PointB.point.x) // S is not vertical { if (S.PointA.point.x <= P.point.x && P.point.x <= S.PointB.point.x) { return(1); } if (S.PointA.point.x >= P.point.x && P.point.x >= S.PointB.point.x) { return(1); } } else // S is vertical, so test y coordinate { if (S.PointA.point.y <= P.point.y && P.point.y <= S.PointB.point.y) { return(1); } if (S.PointA.point.y >= P.point.y && P.point.y >= S.PointB.point.y) { return(1); } } return(0); }
private void initRoad() { //初始先找个最近的点,Tag相同 GameObject[] objs = GameObject.FindGameObjectsWithTag(Tags.RAILWAY_POINT); float d = float.MaxValue; GameObject temp = null; foreach (GameObject o in objs) { float d_temp = Vector3.Distance(o.transform.position, transform.position); if (d > d_temp) { //找最近的点 temp = o; d = d_temp; } } if (temp != null) { //找到最近点 nextPoint = temp.GetComponent <RoadPoint>(); } else { nextPoint = objs[0].GetComponent <RoadPoint>(); } }
public RoadSegment(RoadPoint a, RoadPoint b, int level) { this.PointA = new RoadPoint(a.point, this); this.PointB = new RoadPoint(b.point, this); this.Level = level; }
public RoadPoint GetRoadById(int id) { RoadPoint road = null; dict_Road.TryGetValue(id, out road); return(road); }
/// <summary> /// 创建封闭路径 /// </summary> void CreatePath() { for (int i = 0; i < 2; i++) { list_Road[i].Id = i; list_Road[i].name = "RoadPoint" + list_Road[i].Id; dict_Road.Add(list_Road[i].Id, list_Road[i]); list_restRoad.Remove(list_Road[i]); list_lastRoad.Add(list_Road[i]); } RoadPoint tempRoad = list_Road[1]; int temp = 1; while (temp != list_Road.Count - 1) { tempRoad = CompileToRelistRoad(tempRoad); if (tempRoad != null) { temp++; tempRoad.Id = temp; tempRoad.name = "RoadPoint" + tempRoad.Id; dict_Road.Add(tempRoad.Id, tempRoad); list_restRoad.Remove(tempRoad); list_lastRoad.Add(tempRoad); } } }
// Shows the developer how the vehicles slow down at corners and obstructions private void OnDrawGizmos() { if (Application.isPlaying && road != null) { Gizmos.color = Color.blue; Gizmos.DrawLine(path[currentPoint].Position, path[currentPoint].Position + path[currentPoint].Forward * 3f); Gizmos.color = Color.red; int numberOfPoints = Mathf.FloorToInt(Mathf.Max(5f, velocity / topSpeed * speedCheckDistance / pointDistance)); for (int i = 0; i < numberOfPoints; i++) { RoadPoint roadPoint = path[(path.Length + currentPoint + (lane == Lane.LEFT ? i : -i)) % path.Length]; // Shows the collision boxes for each point the vehicle is checking if (showCollisionBounds) { Gizmos.color = new Color(0f, 1f, 0f, 0.1f); Gizmos.matrix = Matrix4x4.TRS(roadPoint.Position + vehicleCollider.center, roadPoint.Rotation, vehicleCollider.size); Gizmos.DrawWireCube(Vector3.zero, Vector3.one); Gizmos.matrix = Matrix4x4.identity; } float magnitude = (roadPoint.Forward - path[currentPoint].Forward).magnitude; Gizmos.color = new Gradient() { colorKeys = new GradientColorKey[] { new GradientColorKey(Color.white, 0f), new GradientColorKey(Color.yellow, 0.6f), new GradientColorKey(Color.red, 1f) }, }.Evaluate(Mathf.Clamp(magnitude, 0f, 1f)); Gizmos.DrawLine(roadPoint.Position, roadPoint.Position + (roadPoint.Forward - path[currentPoint].Forward)); } } }
public void AddNeightbor(RoadPoint neightbor) { if (!neightborList.Contains(neightbor)) { neightborList.Add(neightbor); } }
/// <summary> /// starting city blueprint O-type /// </summary> /// <param name="center"></param> /// <param name="angle"></param> public void AddCityCentreO(Vector2 center, float angle) { angle = 360f / 8f; RoadSegment last = null; RoadSegment first = null; for (int i=0; i<8; i++) { Quaternion rotationA = Quaternion.Euler (0, 0, angle * i); Quaternion rotationB = Quaternion.Euler (0, 0, angle * (i + 1)); RoadPoint a = new RoadPoint (); a.point = rotationA * (new Vector2 (this.scale / 2.5f, 0) + center); RoadPoint b = new RoadPoint (); b.point = rotationB * (new Vector2 (this.scale / 2.5f, 0) + center); RoadSegment rA = new RoadSegment (a, b, 0); this.RoadSegments.Add(rA); if(first == null) first = rA; if(last != null) { Intersection iA = new Intersection (new List<RoadPoint> (){rA.PointA,last.PointA}); this.RoadIntersections.Add (iA); } last = rA; } Intersection iB = new Intersection (new List<RoadPoint> (){first.PointA,last.PointA}); this.RoadIntersections.Add (iB); }
partial void PointsCustomParse(OverlayStream stream, long finalPos, int offset, RecordType type, PreviousParse lastParsed) { if (stream.Complete) { return; } var subMeta = stream.GetSubrecord(); if (subMeta.RecordType != RecordTypes.PGRP) { return; } stream.Position += subMeta.HeaderLength; var pointBytes = stream.ReadMemory(subMeta.ContentLength); subMeta = stream.GetSubrecord(); switch (subMeta.RecordTypeInt) { case 0x52524750: // "PGRR": stream.Position += subMeta.HeaderLength; var connBytes = stream.ReadMemory(subMeta.ContentLength); this.Points = BinaryOverlayList.FactoryByLazyParse <IRoadPointGetter>( pointBytes, _package, getter: (s, p) => { int numPts = pointBytes.Length / RoadBinaryCreateTranslation.POINT_LEN; RoadPoint[] points = new RoadPoint[numPts]; var connFloats = connBytes.Span.AsFloatSpan(); for (int i = 0; i < numPts; i++) { var pt = RoadBinaryCreateTranslation.ReadPathGridPoint(s, out var numConn); s = s.Slice(RoadBinaryCreateTranslation.POINT_LEN); P3Float[] conns = new P3Float[numConn]; for (int j = 0; j < numConn; j++) { conns[j] = new P3Float( x: connFloats[0], y: connFloats[1], z: connFloats[2]); connFloats = connFloats.Slice(3); } pt.Connections.AddRange(conns); points[i] = pt; } return(points); }); break; default: this.Points = BinaryOverlayList.FactoryByStartIndex <IRoadPointGetter>( pointBytes, _package, itemLength: RoadBinaryCreateTranslation.POINT_LEN, getter: (s, p) => RoadBinaryCreateTranslation.ReadPathGridPoint(s, out var numConn)); break; } }
public void Enqueue(Car car, RoadPoint nextPoint, bool isRestrictedByRedLight, bool isNS) { if (isNS) { queueNS.Enqueue(new CarInfo(car, nextPoint, isRestrictedByRedLight)); return; } queueWE.Enqueue(new CarInfo(car, nextPoint, isRestrictedByRedLight)); }
void MoveToRoad(int id) { footRoad = RoadManager._Instance.GetRoadById(id); //目标位置 targetPos = footRoad.transform.position + new Vector3(0, 0.5f, 0); FaceToPos(targetPos); isMoveing = true; gameObject.GetComponent <Player>().Count = footRoad.MapBlock.Count; }
void HandleRightMouseDown(Vector3 mousePosition, RoadPoint roadPoint) { if (lastSelected == null) { return; } lastSelected.gameObject.GetComponent <Renderer>().sharedMaterial = shapeCreator.whiteMat; lastSelected = null; }
void HandleLeftMouseDrag(Vector3 mousePosition, RoadPoint roadPoint) { if (lastSelected == null) { return; } lastSelected.transform.position = mousePosition; }
public RoadPoint(Vector3 c_pos, RoadPoint c_previousSelected = null) { pos = c_pos; sphere.transform.position = c_pos; if (c_previousSelected != null) { AddNeightbor(c_previousSelected); } sphere.transform.tag = "RoadPoint"; neightborList = new List <RoadPoint>(); }
FindPaths( RoadPoint source, IEnumerable <RoadPoint> targets, Func <Road, double> cost, Func <Road, double> bound, double maxRadius) { var dijkstraRouter = new DijkstraRouter <Road, RoadPoint>(); var precomputedRouter = new PrecomputedDijkstraRouter <Road, RoadPoint>(_map, cost, bound, maxRadius); var expectedPath = dijkstraRouter.Route(source, targets, cost, bound, maxRadius); var actualPath = precomputedRouter.Route(source, targets, cost, bound, maxRadius); return(expectedPath, actualPath); }
/// <summary> /// 更新堵塞铁路信息 /// </summary> private void updateblockRoad() { foreach (RoadPoint p in edge) { if (!p.active) { blockPoint = p; } } updateBlock(); }
private RoadSegment[] patchSegment(RoadSegment segment, RoadPoint newPoint) { this.RoadSegments.RemoveAll(p => p.IsEqual(segment)); RoadSegment left = new RoadSegment(segment.PointA, new RoadPoint(newPoint.point), segment.Level); RoadSegment right = new RoadSegment(segment.PointB, new RoadPoint(newPoint.point), segment.Level); this.RoadSegments.Add(left); this.RoadSegments.Add(right); return(new RoadSegment[] { left, right }); }
public static RoadPoint ReadPathGridPoint(ReadOnlySpan <byte> reader, out byte numConn) { var pt = new RoadPoint(); pt.Point = new Noggog.P3Float( reader.Float(), reader.Slice(4).Float(), reader.Slice(8).Float()); numConn = reader[12]; pt.NumConnectionsFluffBytes = reader.Slice(13, 3).ToArray(); return(pt); }
public void GivenMarkerArrayReturnListOfMarkers() { var point1 = new RoadPoint(0, new Marker("Thing1", 20, -2)); var point2 = new RoadPoint(0, new Marker("Thing2", 20, -8)); var road = new Road(new[] { point1, point2 }); Assert.AreEqual("Road", road.Tag); Assert.AreEqual(2, road.Points.Length); Assert.AreEqual(point1, road.Points[0]); Assert.AreEqual(0, point1.Vector.y); Assert.AreEqual(point2, road.Points[1]); Assert.AreEqual(0, point2.Vector.y); }
/// <summary> /// 获得与此路相邻的路 /// </summary> /// <param name="road"></param> /// <returns></returns> RoadPoint CompileToRelistRoad(RoadPoint road) { for (int i = 0; i < list_restRoad.Count; i++) { if (ISRoadBehind(road, list_restRoad[i])) { return(list_restRoad[i]); } } return(null); }
public static partial void FillBinaryPointsCustom(MutagenFrame frame, IRoadInternal item) { if (!frame.Reader.TryReadSubrecord(PGRP, out var subMeta)) { return; } var pointBytes = frame.Reader.ReadSpan(subMeta.ContentLength); subMeta = frame.ReadSubrecord(); switch (subMeta.RecordType.TypeInt) { case 0x52524750: // "PGRR": var connBytes = frame.Reader.ReadSpan(subMeta.ContentLength); var connFloats = connBytes.AsFloatSpan(); int numPts = pointBytes.Length / POINT_LEN; RoadPoint[] points = new RoadPoint[numPts]; for (int i = 0; i < numPts; i++) { var pt = ReadPathGridPoint(pointBytes, out var numConn); pointBytes = pointBytes.Slice(16); P3Float[] conns = new P3Float[numConn]; for (int j = 0; j < numConn; j++) { conns[j] = new P3Float( x: connFloats[0], y: connFloats[1], z: connFloats[2]); connFloats = connFloats.Slice(3); } pt.Connections.AddRange(conns); points[i] = pt; } item.Points = points.ToExtendedList(); if (connFloats.Length > 0) { throw new ArgumentException("Connection reader did not complete as expected."); } break; default: frame.Reader.Position -= subMeta.HeaderLength; item.Points = new ExtendedList <RoadPoint>(); while (pointBytes.Length > 0) { item.Points.Add( ReadPathGridPoint(pointBytes, out var numConn)); pointBytes = pointBytes.Slice(16); } break; } }
private bool canReach(Vector3 startP, Vector3 v) { int time = 3; RoadPoint start = getStartPoint(startP); obj.transform.position = start.transform.position; objend.transform.position = v; //我们假设这个是车 rm.fromPoint = start; rm.nextPoint = start; RoadPoint temp; bool flag = false; while (true) { temp = rm.nextPoint; rm.nextPoint = rm.nextPoint.getNextPoint(rm, out flag); rm.fromPoint = temp; int i = (Mathf.FloorToInt(Mathf.Abs(Vector3.Distance(rm.nextPoint.transform.position, rm.fromPoint.transform.position)) / roadW) + 1); Vector3 nv = (rm.fromPoint.transform.position - rm.nextPoint.transform.position) / i; for (; i >= 0; i--) { Bounds bs = new Bounds(rm.fromPoint.transform.position - nv * i, new Vector3(roadW, 0.1f, roadW)); if (bs.Contains(v)) { return(true); } } if (Mathf.Abs(Vector3.Distance(v, rm.nextPoint.transform.position)) < 0.5) { return(true); } if (!flag) { time--; } if (time < 0) { return(false); } } }
public void TestSimpleShortestPath() { var maxRadius = 200D; var start = new RoadPoint(_map.GetEdge(0), 0.3); var targets = new RoadPoint[] { new RoadPoint(_map.GetEdge(10), 0.5), new RoadPoint(_map.GetEdge(17), 0.6), }; Func <Road, double> cost = r => r.Weight; var paths = this.FindPaths(start, targets, cost, cost, maxRadius); Assert.Single(paths.actual); Assert.Equal(paths.expected, paths.actual); }
/// <summary> /// Adds the city centre x. /// </summary> /// <param name="center">Center.</param> /// <param name="angle">Angle.</param> public void AddCityCentreX(Vector2 center, float angle) { Quaternion rotation = Quaternion.Euler (0, 0, angle); RoadPoint a = new RoadPoint (); a.point = rotation * center; RoadPoint b = new RoadPoint (); b.point = rotation * (new Vector2 (this.scale, 0) + center); RoadPoint c = new RoadPoint (); c.point = rotation * center; RoadPoint d = new RoadPoint (); d.point = rotation * (new Vector2 (0, this.scale) + center); RoadPoint e = new RoadPoint (); e.point = rotation * center; RoadPoint f = new RoadPoint (); f.point = rotation * (new Vector2 (-this.scale, 0) + center); RoadPoint g = new RoadPoint (); g.point = rotation * center; RoadPoint h = new RoadPoint (); h.point = rotation * (new Vector2 (0, -this.scale) + center); RoadSegment rA = new RoadSegment (a, b, 0); RoadSegment rB = new RoadSegment (c, d, 0); RoadSegment rC = new RoadSegment (e, f, 0); RoadSegment rD = new RoadSegment (g, h, 0); this.RoadSegments.AddRange (new RoadSegment[]{rA,rB,rC,rD}); Intersection iA = new Intersection (new List<RoadPoint> (){rA.PointA,rB.PointA,rC.PointA,rD.PointA}); this.RoadIntersections.Add (iA); }
/// <summary> /// starting city blueprint Y-type /// </summary> /// <param name="center"></param> /// <param name="angle"></param> public void AddCityCentreY(Vector2 center, float angle) { Quaternion rotation = Quaternion.Euler (0, 0, angle); RoadPoint a = new RoadPoint (); a.point = rotation * center; RoadPoint b = new RoadPoint (); b.point = rotation * (new Vector2 (this.scale, 0) + center); Quaternion localA = Quaternion.Euler (0, 0, 120f); RoadPoint c = new RoadPoint (); c.point = rotation * center; RoadPoint d = new RoadPoint (); d.point = localA * rotation * (new Vector2 (this.scale, 0) + center); Quaternion localB = Quaternion.Euler (0, 0, 240f); RoadPoint e = new RoadPoint (); e.point = rotation * center; RoadPoint f = new RoadPoint (); f.point = localB * rotation * (new Vector2 (this.scale, 0) + center); RoadSegment rA = new RoadSegment (a, b, 0); RoadSegment rB = new RoadSegment (c, d, 0); RoadSegment rC = new RoadSegment (e, f, 0); this.RoadSegments.AddRange (new RoadSegment[]{rA,rB,rC}); Intersection iA = new Intersection (new List<RoadPoint> (){rA.PointA,rB.PointA,rC.PointA}); this.RoadIntersections.Add (iA); }
/// <summary> /// http://geomalgorithms.com/a02-_lines.html#Distance-to-Ray-or-Segment /// </summary> /// <returns>Distance between segments.</returns> /// <param name="P">P.</param> /// <param name="S">S.</param> private float distPointSegment( RoadPoint P, RoadSegment S) { Vector2 v = S.PointB.point - S.PointA.point; Vector2 w = P.point - S.PointA.point; float c1 = Vector2.Dot(w,v); if ( c1 <= 0 ) return Vector2.Distance(P.point, S.PointA.point); float c2 = Vector2.Dot(v,v); if ( c2 <= c1 ) return Vector2.Distance(P.point, S.PointB.point); float b = c1 / c2; Vector2 Pb = S.PointA.point + (v * b); return Vector2.Distance(P.point, Pb); }
// inSegment(): determine if a point is inside a segment // Input: a point P, and a collinear segment S // Return: 1 = P is inside S // 0 = P is not inside S int inSegment( RoadPoint P, RoadSegment S) { if (S.PointA.point.x != S.PointB.point.x) { // S is not vertical if (S.PointA.point.x <= P.point.x && P.point.x <= S.PointB.point.x) return 1; if (S.PointA.point.x >= P.point.x && P.point.x >= S.PointB.point.x) return 1; } else { // S is vertical, so test y coordinate if (S.PointA.point.y <= P.point.y && P.point.y <= S.PointB.point.y) return 1; if (S.PointA.point.y >= P.point.y && P.point.y >= S.PointB.point.y) return 1; } return 0; }
private RoadSegment[] patchSegment(RoadSegment segment, RoadPoint newPoint) { this.RoadSegments.RemoveAll(p => p.IsEqual(segment)); RoadSegment left = new RoadSegment (segment.PointA, new RoadPoint(newPoint.point), segment.Level); RoadSegment right = new RoadSegment (segment.PointB, new RoadPoint(newPoint.point), segment.Level); this.RoadSegments.Add (left); this.RoadSegments.Add (right); return new RoadSegment[] {left,right}; }
private bool PointWithin(RoadPoint point, float distance) { foreach (RoadSegment segment in this.RoadSegments) if (Vector2.Distance (point.point, segment.PointA.point) < distance) return true; else if (Vector2.Distance (point.point, segment.PointB.point) < distance) return true; return false; }
public RoadSegment(RoadPoint a, RoadPoint b, int level) { this.PointA = new RoadPoint (a.point, this); this.PointB = new RoadPoint (b.point, this); this.Level = level; }
/// <summary> /// get other segment point given one of them /// </summary> /// <param name="main"></param> /// <returns></returns> public RoadPoint GetOther(RoadPoint main) { return this.PointA.Equals(main) ? this.PointB : this.PointA; }