///
/// 钳击
///
public class DoubleArrow : GMapPolygon, IPlot
{
protected string geo_type = string.Empty;
protected PointLatLng[] points;
private PlotTypes type;
private double headHeightFactor = 0.0;
private double headWidthFactor = 0.0;
private double neckHeightFactor = 0.15;
private double neckWidthFactor = 0.15;
private PointLatLng connPoint;
private PointLatLng tempPoint4;
private int fixPointCount = 0;
public DoubleArrow(PointLatLng[] points,string name= "DoubleArrow")
: base(points.ToList(), name)
{
this.points = points;
this.geo_type = "RootTest";
this.type = PlotTypes.DOUBLE_ARROW;
this.headHeightFactor = 0.25;
this.headWidthFactor = 0.3;
this.neckHeightFactor = 0.85;
this.neckWidthFactor = 0.15;
this.connPoint = PointLatLng.Empty;
this.tempPoint4 = PointLatLng.Empty; ;
this.fixPointCount = 4;
this.SetPoints(points);
}
public void FinishDrawing()
{
List pointList = points.ToList();
if (this.GetPointCount() == 3 && this.tempPoint4 != null)
pointList.Add(this.tempPoint4);
if (this.connPoint != null)
pointList.Add(this.connPoint);
this.points = pointList.ToArray();
}
public void Generate()
{
var count = this.GetPointCount();
if (count < 2)
{
return;
}
if (count == 2)
{
this.Points.Clear();
var temp=GeometryUtil.ConvertCoordinates(points.ToList(), ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.AddRange(temp);
return;
}
var pnt1 = this.points[0];
var pnt2 = this.points[1];
var pnt3 = this.points[2];
count = this.GetPointCount();
if (count == 3)
this.tempPoint4 = this.GetTempPoint4(pnt1, pnt2, pnt3);
else
this.tempPoint4 = this.points[3];
if (count == 3 || count == 4)
this.connPoint = PlotUtil.Mid(pnt1, pnt2);
else
this.connPoint = this.points[4];
PointLatLng[] leftArrowPnts;
PointLatLng[] rightArrowPnts;
if (PlotUtil.IsClockWise(pnt1, pnt2, pnt3))
{
leftArrowPnts = this.GetArrowPoints(pnt1, this.connPoint, this.tempPoint4, false);
rightArrowPnts = this.GetArrowPoints(this.connPoint, pnt2, pnt3, true);
}
else
{
leftArrowPnts = this.GetArrowPoints(pnt2, this.connPoint, pnt3, false);
rightArrowPnts = this.GetArrowPoints(this.connPoint, pnt1, this.tempPoint4, true);
}
var m = leftArrowPnts.Length;
var t = (m - 5) / 2;
var llBodyPnts = leftArrowPnts.Take(t).ToArray();
var lArrowPnts = leftArrowPnts.Skip(t).Take(5).ToArray();
var lrBodyPnts = leftArrowPnts.Skip(t + 5).Take(m - (t + 5)).ToArray();
var rlBodyPnts = rightArrowPnts.Take(t).ToArray();
var rArrowPnts = rightArrowPnts.Skip(t).Take(5).ToArray();
var rrBodyPnts = rightArrowPnts.Skip(t + 5).Take(m - (t + 5)).ToArray();
rlBodyPnts = PlotUtil.GetBezierPoints(rlBodyPnts).ToArray();
var bodyPnts = PlotUtil.GetBezierPoints(rrBodyPnts.Concat(llBodyPnts.Skip(1)).ToArray());
lrBodyPnts = PlotUtil.GetBezierPoints(lrBodyPnts).ToArray();
var pnts = rlBodyPnts.Concat(rArrowPnts.Concat(bodyPnts).Concat(lArrowPnts).Concat(lrBodyPnts).ToArray());
var temps = GeometryUtil.ConvertCoordinates(pnts.ToList(), ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temps);
}
private PointLatLng[] GetArrowPoints(PointLatLng pnt1, PointLatLng pnt2, PointLatLng pnt3, bool clockWise)
{
var midPnt = PlotUtil.Mid(pnt1, pnt2);
var len = PlotUtil.Distance(midPnt, pnt3);
var midPnt1 = PlotUtil.GetThirdPoint(pnt3, midPnt, 0, len * 0.3, true);
var midPnt2 = PlotUtil.GetThirdPoint(pnt3, midPnt, 0, len * 0.5, true);
//var midPnt3=PlotUtils.getThirdPoint(pnt3, midPnt, 0, len * 0.7, true);
midPnt1 = PlotUtil.GetThirdPoint(midPnt, midPnt1, Constants.HALF_PI, len / 5, clockWise);
midPnt2 = PlotUtil.GetThirdPoint(midPnt, midPnt2, Constants.HALF_PI, len / 4, clockWise);
//midPnt3=PlotUtils.getThirdPoint(midPnt, midPnt3, Constants.HALF_PI, len / 5, clockWise);
var points = new PointLatLng[] { midPnt, midPnt1, midPnt2, pnt3 };
// 计算箭头部分
var arrowPnts = this.GetArrowHeadPoints(points, this.headHeightFactor, this.headWidthFactor, this.neckHeightFactor, this.neckWidthFactor);
var neckLeftPoint = arrowPnts[0];
var neckRightPoint = arrowPnts[4];
// 计算箭身部分
var tailWidthFactor = PlotUtil.Distance(pnt1, pnt2) / PlotUtil.GetBaseLength(points.ToList()) / 2;
var bodyPnts = this.GetArrowBodyPoints(points, neckLeftPoint, neckRightPoint, tailWidthFactor).ToArray();
var n = bodyPnts.Length;
var lPoints = bodyPnts.Take(n / 2).ToList();
var rPoints = bodyPnts.Skip(n / 2).Take(n).ToList();
lPoints.Add(neckLeftPoint);
rPoints.Add(neckRightPoint);
lPoints.Reverse();
lPoints.Add(pnt2);
rPoints.Reverse();
rPoints.Add(pnt1);
lPoints.Reverse();
return lPoints.Concat(arrowPnts).Concat(rPoints).ToArray();
}
private PointLatLng[] GetArrowBodyPoints(PointLatLng[] points, PointLatLng neckLeft, PointLatLng neckRight, double tailWidthFactor)
{
var allLen = PlotUtil.WholeDistance(points.ToList());
var len = PlotUtil.GetBaseLength(points.ToList());
var tailWidth = len * tailWidthFactor;
var neckWidth = PlotUtil.Distance(neckLeft, neckRight);
var widthDif = (tailWidth - neckWidth) / 2;
double tempLen = 0.0;
List leftBodyPnts = new List();
List rightBodyPnts = new List();
for (var i = 1; i < points.Length - 1; i++)
{
var angle = PlotUtil.GetAngleOfThreePoints(points[i - 1], points[i], points[i + 1]) / 2;
tempLen += PlotUtil.Distance(points[i - 1], points[i]);
var w = (tailWidth / 2 - tempLen / allLen * widthDif) / Math.Sin(angle);
var left = PlotUtil.GetThirdPoint(points[i - 1], points[i], Math.PI - angle, w, true);
var right = PlotUtil.GetThirdPoint(points[i - 1], points[i], angle, w, false);
leftBodyPnts.Add(left);
rightBodyPnts.Add(right);
}
return leftBodyPnts.Concat(rightBodyPnts).ToArray();
}
private PointLatLng[] GetArrowHeadPoints(PointLatLng[] points, double headHeightFactor, double headWidthFactor, double neckHeightFactor, double neckWidthFactor)
{
var len = PlotUtil.GetBaseLength(points.ToList());
var headHeight = len * headHeightFactor;
var headPnt = points[points.Length - 1];
//var tailWidth = PlotUtil.Distance(tailLeft, tailRight);
var headWidth = headHeight * headWidthFactor;
var neckWidth = headHeight * neckWidthFactor;
var neckHeight = headHeight * neckHeightFactor;
var headEndPnt = PlotUtil.GetThirdPoint(points[points.Length - 2], headPnt, 0, headHeight, true);
var neckEndPnt = PlotUtil.GetThirdPoint(points[points.Length - 2], headPnt, 0, neckHeight, true);
var headLeft = PlotUtil.GetThirdPoint(headPnt, headEndPnt, Constants.HALF_PI, headWidth, false);
var headRight = PlotUtil.GetThirdPoint(headPnt, headEndPnt, Constants.HALF_PI, headWidth, true);
var neckLeft = PlotUtil.GetThirdPoint(headPnt, neckEndPnt, Constants.HALF_PI, neckWidth, false);
var neckRight = PlotUtil.GetThirdPoint(headPnt, neckEndPnt, Constants.HALF_PI, neckWidth, true);
return new PointLatLng[] { neckLeft, headLeft, headPnt, headRight, neckRight };
}
private PointLatLng GetTempPoint4(PointLatLng linePnt1, PointLatLng linePnt2, PointLatLng point)
{
var midPnt = PlotUtil.Mid(linePnt1, linePnt2);
var len = PlotUtil.Distance(midPnt, point);
var angle = PlotUtil.GetAngleOfThreePoints(linePnt1, midPnt, point);
PointLatLng symPnt;
double distance1;
double distance2;
PointLatLng mid;
if (angle < Constants.HALF_PI)
{
distance1 = len * Math.Sin(angle);
distance2 = len * Math.Cos(angle);
mid = PlotUtil.GetThirdPoint(linePnt1, midPnt, Constants.HALF_PI, distance1, false);
symPnt = PlotUtil.GetThirdPoint(midPnt, mid, Constants.HALF_PI, distance2, true);
}
else if (angle >= Constants.HALF_PI && angle < Math.PI)
{
distance1 = len * Math.Sin(Math.PI - angle);
distance2 = len * Math.Cos(Math.PI - angle);
mid = PlotUtil.GetThirdPoint(linePnt1, midPnt, Constants.HALF_PI, distance1, false);
symPnt = PlotUtil.GetThirdPoint(midPnt, mid, Constants.HALF_PI, distance2, false);
}
else if (angle >= Math.PI && angle < Math.PI * 1.5)
{
distance1 = len * Math.Sin(angle - Math.PI);
distance2 = len * Math.Cos(angle - Math.PI);
mid = PlotUtil.GetThirdPoint(linePnt1, midPnt, Constants.HALF_PI, distance1, true);
symPnt = PlotUtil.GetThirdPoint(midPnt, mid, Constants.HALF_PI, distance2, true);
}
else
{
distance1 = len * Math.Sin(Math.PI * 2 - angle);
distance2 = len * Math.Cos(Math.PI * 2 - angle);
mid = PlotUtil.GetThirdPoint(linePnt1, midPnt, Constants.HALF_PI, distance1, true);
symPnt = PlotUtil.GetThirdPoint(midPnt, mid, Constants.HALF_PI, distance2, false);
}
return symPnt;
}
public int GetPointCount()
{
return this.points.Length;
}
public PointLatLng[] GetPoints()
{
return this.points;
}
public bool IsPlot()
{
return true;
}
public void SetPoints(PointLatLng[] value)
{
//将经纬度坐标转为投影坐标参与计算
if (value != null)
value = GeometryUtil.WGS84ToWebMercator2(value.ToList()).ToArray();
this.points = (value != null) ? value : new PointLatLng[] { };
if (this.points.Length >= 1)
this.Generate();
}
public void UpdateLastPoint(PointLatLng point)
{
this.UpdatePoint(point, this.points.Length - 1);
}
public void UpdatePoint(PointLatLng point, int index)
{
if (index >= 0 && index < this.points.Length)
{
this.points[index] = point;
this.Generate();
}
}
}
///
/// 直箭头
///
public class StraightArrow : GMapRoute,IPlot
{
protected string geo_type = string.Empty;
protected PointLatLng[] points;
private PlotTypes type;
private int fixPointCount = 0;
private double maxArrowLength = 0.0;
private int arrowLengthScale=5;
public StraightArrow(PointLatLng[] points,string name= "StraightArrow")
:base(points.ToList(), name)
{
this.points = points;
this.geo_type = "RootTest";
this.type = PlotTypes.STRAIGHT_ARROW;
this.fixPointCount = 2;
this.maxArrowLength = 3000000;
this.arrowLengthScale = 5;
this.SetPoints(points);
}
public void FinishDrawing()
{
}
public void Generate()
{
if (this.GetPointCount() < 2)
{
return;
}
var pnts = this.GetPoints();
var pnt1 = pnts[0];
var pnt2 = pnts[1];
var distance = PlotUtil.Distance(pnt1, pnt2);
var len = distance / this.arrowLengthScale;
len = len > this.maxArrowLength ? this.maxArrowLength : len;
var leftPnt = PlotUtil.GetThirdPoint(pnt1, pnt2, Math.PI / 6, len, false);
var rightPnt = PlotUtil.GetThirdPoint(pnt1, pnt2, Math.PI / 6, len, true);
List tempPoints = new PointLatLng[] { pnt1, pnt2, leftPnt, pnt2, rightPnt }.ToList();
var temps = GeometryUtil.ConvertCoordinates(tempPoints, ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temps);
}
public int GetPointCount()
{
return this.points.Length;
}
public PointLatLng[] GetPoints()
{
return this.points;
}
public bool IsPlot()
{
return true;
}
public void SetPoints(PointLatLng[] value)
{
//将经纬度坐标转为投影坐标参与计算
if (value != null)
value = GeometryUtil.WGS84ToWebMercator2(value.ToList()).ToArray();
this.points = (value != null) ? value : new PointLatLng[] { };
if (this.points.Length >= 1)
this.Generate();
}
public void UpdateLastPoint(PointLatLng point)
{
this.UpdatePoint(point, this.points.Length - 1);
}
public void UpdatePoint(PointLatLng point, int index)
{
if (index >= 0 && index < this.points.Length)
{
this.points[index] = point;
this.Generate();
}
}
}
///
/// 细直箭头
///
public class FineArrow : GMapPolygon, IPlot
{
protected string geo_type = string.Empty;
protected PointLatLng[] points;
protected PlotTypes type = PlotTypes.FINE_ARROW;
protected double tailWidthFactor = 0.15;
protected double neckWidthFactor = 0.2;
protected double headWidthFactor = 0.25;
protected double headAngle = Math.PI / 8.5;
protected double neckAngle = Math.PI / 13;
private int fixPointCount = 2;
public FineArrow(PointLatLng[] points):
base(points.ToList(), "FineArrow")
{
this.points = points;
this.geo_type = "RootTest";
this.type = PlotTypes.FINE_ARROW;
this.tailWidthFactor = 0.15;
this.neckWidthFactor = 0.2;
this.headWidthFactor = 0.25;
this.headAngle = Math.PI / 8.5;
this.neckAngle = Math.PI / 13;
this.fixPointCount = 2;
this.SetPoints(points);
}
public void FinishDrawing()
{
}
public void Generate()
{
var count = this.GetPointCount();
if (count < 2)
{
return;
}
var pnts = this.GetPoints();
var pnt1 = pnts[0];
var pnt2 = pnts[1];
var len = PlotUtil.GetBaseLength(pnts.ToList());
var tailWidth = len * this.tailWidthFactor;
var neckWidth = len * this.neckWidthFactor;
var headWidth = len * this.headWidthFactor;
var tailLeft = PlotUtil.GetThirdPoint(pnt2, pnt1, Constants.HALF_PI, tailWidth, true);
var tailRight = PlotUtil.GetThirdPoint(pnt2, pnt1, Constants.HALF_PI, tailWidth, false);
var headLeft = PlotUtil.GetThirdPoint(pnt1, pnt2, this.headAngle, headWidth, false);
var headRight = PlotUtil.GetThirdPoint(pnt1, pnt2, this.headAngle, headWidth, true);
var neckLeft = PlotUtil.GetThirdPoint(pnt1, pnt2, this.neckAngle, neckWidth, false);
var neckRight = PlotUtil.GetThirdPoint(pnt1, pnt2, this.neckAngle, neckWidth, true);
var pList = new PointLatLng[]{ tailLeft, neckLeft, headLeft, pnt2, headRight, neckRight, tailRight };
var temps = GeometryUtil.ConvertCoordinates(pList.ToList(), ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temps);
}
public int GetPointCount()
{
return this.points.Length;
}
public PointLatLng[] GetPoints()
{
return this.points;
}
public bool IsPlot()
{
return true;
}
public void SetPoints(PointLatLng[] value)
{
//将经纬度坐标转为投影坐标参与计算
if (value != null)
value = GeometryUtil.WGS84ToWebMercator2(value.ToList()).ToArray();
this.points = (value != null) ? value : new PointLatLng[] { };
if (this.points.Length >= 1)
this.Generate();
}
public void UpdateLastPoint(PointLatLng point)
{
this.UpdatePoint(point, this.points.Length - 1);
}
public void UpdatePoint(PointLatLng point, int index)
{
if (index >= 0 && index < this.points.Length)
{
this.points[index] = point;
this.Generate();
}
}
}
///
/// 突击方向
///
public class AssaultDirection:FineArrow
{
public AssaultDirection(PointLatLng[] points)
:base(points)
{
this.type = PlotTypes.ASSAULT_DIRECTION;
this.tailWidthFactor = 0.2;
this.neckWidthFactor = 0.25;
this.headWidthFactor = 0.3;
this.headAngle = Math.PI / 4;
this.neckAngle = Math.PI * 0.17741;
this.SetPoints(points);
}
}
///
/// 进攻方向
///
public class AttackArrow : GMapPolygon, IPlot
{
protected string geo_type = string.Empty;
protected PointLatLng[] points;
protected PlotTypes type = PlotTypes.ATTACK_ARROW;
protected double headHeightFactor = 0.18;
protected double headWidthFactor = 0.3;
protected double neckHeightFactor = 0.85;
protected double neckWidthFactor = 0.15;
protected double headTailFactor = 0.8;
public AttackArrow(PointLatLng[] points,string name= "AttackArrow")
:base(points.ToList(), name)
{
this.points = points;
this.geo_type = "RootTest";
this.type = PlotTypes.ATTACK_ARROW;
this.headHeightFactor = 0.18;
this.headWidthFactor = 0.3;
this.neckHeightFactor = 0.85;
this.neckWidthFactor = 0.15;
this.headTailFactor = 0.8;
this.SetPoints(points);
}
public void FinishDrawing()
{
}
public virtual void Generate()
{
if (this.GetPointCount() < 2)
{
return;
}
if (this.GetPointCount() == 2)
{
var temp = GeometryUtil.ConvertCoordinates(this.points.ToList(), ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temp);
return;
}
var pnts = this.GetPoints();
// 计算箭尾
var tailLeft = pnts[0];
var tailRight = pnts[1];
if (PlotUtil.IsClockWise(pnts[0], pnts[1], pnts[2]))
{
tailLeft = pnts[1];
tailRight = pnts[0];
}
var midTail = PlotUtil.Mid(tailLeft, tailRight);
var bonePnts = new PointLatLng[] { midTail }.Concat(pnts.Skip(2)).ToArray();
// 计算箭头
var headPnts = this.GetArrowHeadPoints(bonePnts, tailLeft, tailRight);
var neckLeft = headPnts[0];
var neckRight = headPnts[4];
var tailWidthFactor = PlotUtil.Distance(tailLeft, tailRight) / PlotUtil.GetBaseLength(bonePnts.ToList());
// 计算箭身
var bodyPnts = this.GetArrowBodyPoints(bonePnts, neckLeft, neckRight, tailWidthFactor);
// 整合
var count = bodyPnts.Length;
var leftPnts = new PointLatLng[] { tailLeft }.Concat(bodyPnts.Take(count / 2)).ToList();
leftPnts.RemoveAt(1);
leftPnts.Add(neckLeft);
var rightPnts = new PointLatLng[] { tailRight }.Concat(bodyPnts.Skip(count / 2).Take(bodyPnts.Length)).ToList();
rightPnts.RemoveAt(1);
rightPnts.Add(neckRight);
leftPnts = PlotUtil.GetQBSplinePoints(leftPnts.ToArray());
rightPnts = PlotUtil.GetQBSplinePoints(rightPnts.ToArray());
//右侧曲线节点反转
rightPnts.Reverse();
List tempPoints = leftPnts.ToArray().Concat(headPnts).Concat(rightPnts).ToList();
var temps = GeometryUtil.ConvertCoordinates(tempPoints, ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temps);
}
protected PointLatLng[] GetArrowHeadPoints(PointLatLng[] points, PointLatLng tailLeft, PointLatLng tailRight)
{
var len = PlotUtil.GetBaseLength(points.ToList());
var headHeight = len * this.headHeightFactor;
var headPnt = points[points.Length - 1];
len = PlotUtil.Distance(headPnt, points[points.Length - 2]);
var tailWidth = PlotUtil.Distance(tailLeft, tailRight);
if (headHeight > tailWidth * this.headTailFactor)
{
headHeight = tailWidth * this.headTailFactor;
}
var headWidth = headHeight * this.headWidthFactor;
var neckWidth = headHeight * this.neckWidthFactor;
headHeight = headHeight > len ? len : headHeight;
var neckHeight = headHeight * this.neckHeightFactor;
var headEndPnt = PlotUtil.GetThirdPoint(points[points.Length - 2], headPnt, 0, headHeight, true);
var neckEndPnt = PlotUtil.GetThirdPoint(points[points.Length - 2], headPnt, 0, neckHeight, true);
var headLeft = PlotUtil.GetThirdPoint(headPnt, headEndPnt, Constants.HALF_PI, headWidth, false);
var headRight = PlotUtil.GetThirdPoint(headPnt, headEndPnt, Constants.HALF_PI, headWidth, true);
var neckLeft = PlotUtil.GetThirdPoint(headPnt, neckEndPnt, Constants.HALF_PI, neckWidth, false);
var neckRight = PlotUtil.GetThirdPoint(headPnt, neckEndPnt, Constants.HALF_PI, neckWidth, true);
return new PointLatLng[] { neckLeft, headLeft, headPnt, headRight, neckRight };
}
protected PointLatLng[] GetArrowBodyPoints(PointLatLng[] bonePnts, PointLatLng neckLeft, PointLatLng neckRight, double tailWidthFactor)
{
var allLen = PlotUtil.WholeDistance(points.ToList());
var len = PlotUtil.GetBaseLength(points.ToList());
var tailWidth = len * tailWidthFactor;
var neckWidth = PlotUtil.Distance(neckLeft, neckRight);
var widthDif = (tailWidth - neckWidth) / 2;
var tempLen = 0.0;
List leftBodyPnts = new List();
List rightBodyPnts = new List();
for (int i = 1; i < points.Length - 1; i++)
{
var angle = PlotUtil.GetAngleOfThreePoints(points[i - 1], points[i], points[i + 1]) / 2;
tempLen += PlotUtil.Distance(points[i - 1], points[i]);
var w = (tailWidth / 2 - tempLen / allLen * widthDif) / Math.Sin(angle);
var left = PlotUtil.GetThirdPoint(points[i - 1], points[i], Math.PI - angle, w, true);
var right = PlotUtil.GetThirdPoint(points[i - 1], points[i], angle, w, false);
leftBodyPnts.Add(left);
rightBodyPnts.Add(right);
}
return leftBodyPnts.Concat(rightBodyPnts).ToArray();
}
public int GetPointCount()
{
return points.Length;
}
public PointLatLng[] GetPoints()
{
return this.points;
}
public bool IsPlot()
{
return true;
}
public void SetPoints(PointLatLng[] value)
{
//将经纬度坐标转为投影坐标参与计算
if (value != null)
value = GeometryUtil.WGS84ToWebMercator2(value.ToList()).ToArray();
this.points = (value != null) ? value : new PointLatLng[] { };
if (this.points.Length >= 1)
this.Generate();
}
public void UpdateLastPoint(PointLatLng point)
{
this.UpdatePoint(point, this.points.Length - 1);
}
public void UpdatePoint(PointLatLng point, int index)
{
if (index >= 0 && index < this.points.Length)
{
this.points[index] = point;
this.Generate();
}
}
}
- TailedAttackArrow:进攻方向(尾)
///
/// 进攻箭头(尾)
///
public class TailedAttackArrow:AttackArrow
{
private double tailWidthFactor = 0.1;
private double swallowTailFactor = 1;
private PointLatLng swallowTailPnt;
public TailedAttackArrow(PointLatLng[] points,string name= "TailedAttackArrow")
:base(points,name)
{
this.points = points;
this.geo_type = "RootTest";
this.type = PlotTypes.TAILED_ATTACK_ARROW;
this.headHeightFactor = 0.18;
this.headWidthFactor = 0.3;
this.neckHeightFactor = 0.85;
this.neckWidthFactor = 0.15;
this.tailWidthFactor = 0.1;
this.headTailFactor = 0.8;
this.swallowTailFactor = 1;
this.swallowTailPnt = PointLatLng.Empty; ;
this.SetPoints(points);
}
public override void Generate()
{
var count = this.GetPointCount();
if (count < 2)
{
return;
}
if (this.GetPointCount() == 2)
{
this.Points.Clear();
var temp = GeometryUtil.ConvertCoordinates(this.points.ToList(), ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.AddRange(temp);
return;
}
var pnts = this.GetPoints();
var tailLeft = pnts[0];
var tailRight = pnts[1];
if (PlotUtil.IsClockWise(pnts[0], pnts[1], pnts[2]))
{
tailLeft = pnts[1];
tailRight = pnts[0];
}
var midTail = PlotUtil.Mid(tailLeft, tailRight);
var bonePnts = new PointLatLng[] { midTail }.Concat(pnts.Skip(2).Take(pnts.Length)).ToArray();
var headPnts = this.GetArrowHeadPoints(bonePnts, tailLeft, tailRight);
var neckLeft = headPnts[0];
var neckRight = headPnts[4];
var tailWidth = PlotUtil.Distance(tailLeft, tailRight);
var allLen = PlotUtil.GetBaseLength(bonePnts.ToList());
var len = allLen * this.tailWidthFactor * this.swallowTailFactor;
this.swallowTailPnt = PlotUtil.GetThirdPoint(bonePnts[1], bonePnts[0], 0, len, true);
var factor = tailWidth / allLen;
var bodyPnts = this.GetArrowBodyPoints(bonePnts, neckLeft, neckRight, factor);
count = bodyPnts.Length;
var leftPnts = new PointLatLng[] { tailLeft }.Concat(bodyPnts.Take(count / 2)).ToList();
leftPnts.RemoveAt(1);
leftPnts.Add(neckLeft);
var rightPnts = new PointLatLng[] { tailRight }.Concat(bodyPnts.Skip(count / 2)).ToList();
rightPnts.RemoveAt(1);
rightPnts.Add(neckRight);
leftPnts = PlotUtil.GetQBSplinePoints(leftPnts.ToArray());
rightPnts = PlotUtil.GetQBSplinePoints(rightPnts.ToArray());
rightPnts.Reverse();
List tempPoints = leftPnts.Concat(headPnts).Concat(rightPnts).Concat(new PointLatLng[] { swallowTailPnt, leftPnts[0] }).ToList();
var temps = GeometryUtil.ConvertCoordinates(tempPoints, ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temps);
}
}
///
/// 分队战斗行动
///
public class SquadCombat:AttackArrow
{
private double tailWidthFactor = 0.0;
public SquadCombat(PointLatLng[] points)
:base(points)
{
this.type = PlotTypes.SQUAD_COMBAT;
this.headHeightFactor = 0.18;
this.headWidthFactor = 0.3;
this.neckHeightFactor = 0.85;
this.neckWidthFactor = 0.15;
this.tailWidthFactor = 0.1;
this.SetPoints(points);
}
public override void Generate()
{
var count = this.GetPointCount();
if (count < 2)
{
return;
}
var pnts = this.GetPoints();
var tailPnts = this.GetTailPoints(pnts);
var headPnts = this.GetArrowHeadPoints(pnts, tailPnts[0], tailPnts[1]);
var neckLeft = headPnts[0];
var neckRight = headPnts[4];
var bodyPnts = this.GetArrowBodyPoints(pnts, neckLeft, neckRight, this.tailWidthFactor);
count = bodyPnts.Length;
var leftPnts = new PointLatLng[] { tailPnts[0] }.Concat(bodyPnts.Take(count / 2)).ToList();
leftPnts.Add(neckLeft);
var rightPnts = new PointLatLng[] { tailPnts[1] }.Concat(bodyPnts.Skip(count / 2).Take(count)).ToList();
rightPnts.Add(neckRight);
leftPnts = PlotUtil.GetQBSplinePoints(leftPnts.ToArray());
rightPnts = PlotUtil.GetQBSplinePoints(rightPnts.ToArray());
rightPnts.Reverse();
List tempPoints = leftPnts.Concat(headPnts.Concat(rightPnts)).ToList();
var temps = GeometryUtil.ConvertCoordinates(tempPoints, ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temps);
}
private PointLatLng[] GetTailPoints(PointLatLng[] pnts)
{
var allLen = PlotUtil.GetBaseLength(points.ToList());
var tailWidth = allLen * this.tailWidthFactor;
var tailLeft = PlotUtil.GetThirdPoint(points[1], points[0], Constants.HALF_PI, tailWidth, false);
var tailRight = PlotUtil.GetThirdPoint(points[1], points[0], Constants.HALF_PI, tailWidth, true);
return new PointLatLng[] { tailLeft, tailRight };
}
}
- TailedSquadCombat:分队战斗行动(尾)
///
/// 分队战斗行动(尾)
///
public class TailedSquadCombat: AttackArrow
{
private double tailWidthFactor = 0.0;
private double swallowTailFactor = 1;
private PointLatLng swallowTailPnt;
public TailedSquadCombat(PointLatLng[] points,string name="TailedSquadCombat")
:base(points,name)
{
this.points = points;
this.geo_type = "RootTest";
this.type = PlotTypes.TAILED_SQUAD_COMBAT;
this.headHeightFactor = 0.18;
this.headWidthFactor = 0.3;
this.neckHeightFactor = 0.85;
this.neckWidthFactor = 0.15;
this.tailWidthFactor = 0.1;
this.swallowTailFactor = 1;
this.swallowTailPnt = PointLatLng.Empty ;
this.SetPoints(points);
}
public override void Generate()
{
var count = this.GetPointCount();
if (count < 2)
{
return;
}
var pnts = this.GetPoints();
var tailPnts = this.GetTailPoints(pnts);
var headPnts = this.GetArrowHeadPoints(pnts, tailPnts[0], tailPnts[2]);
var neckLeft = headPnts[0];
var neckRight = headPnts[4];
var bodyPnts = this.GetArrowBodyPoints(pnts, neckLeft, neckRight, this.tailWidthFactor);
count = bodyPnts.Length;
var leftPnts = new PointLatLng[] { tailPnts[0] }.Concat(bodyPnts.Take(count / 2)).ToList();
leftPnts.Add(neckLeft);
var rightPnts = new PointLatLng[] { tailPnts[2] }.Concat(bodyPnts.Skip(count / 2).Take(count)).ToList();
rightPnts.Add(neckRight);
leftPnts = PlotUtil.GetQBSplinePoints(leftPnts.ToArray());
rightPnts = PlotUtil.GetQBSplinePoints(rightPnts.ToArray());
rightPnts.Reverse();
List tempPoints = leftPnts.Concat(headPnts).Concat(rightPnts).Concat(new PointLatLng[] { tailPnts[1], leftPnts[0] }).ToList();
var temps = GeometryUtil.ConvertCoordinates(tempPoints, ProjNet.CoordinateSystems.ProjectedCoordinateSystem.WebMercator, ProjNet.CoordinateSystems.GeographicCoordinateSystem.WGS84);
this.Points.Clear();
this.Points.AddRange(temps);
}
private PointLatLng[] GetTailPoints(PointLatLng[] points)
{
var allLen = PlotUtil.GetBaseLength(points.ToList());
var tailWidth = allLen * this.tailWidthFactor;
var tailLeft = PlotUtil.GetThirdPoint(points[1], points[0], Constants.HALF_PI, tailWidth, false);
var tailRight = PlotUtil.GetThirdPoint(points[1], points[0], Constants.HALF_PI, tailWidth, true);
var len = tailWidth * this.swallowTailFactor;
var swallowTailPnt = PlotUtil.GetThirdPoint(points[1], points[0], 0, len, true);
return new PointLatLng[] { tailLeft, swallowTailPnt, tailRight };
}
}
- 坐标列表去重:基于List的Distinct方法去重
public class PointLatLngComparer : IEqualityComparer
{
public bool Equals(PointLatLng x, PointLatLng y)
{
return x.Lat == y.Lat && x.Lng == y.Lng;
}
public int GetHashCode(PointLatLng obj)
{
return string.Format("{0},{1}", obj.Lng, obj.Lat).GetHashCode();
}
}
//controlPoints 是List的变量,坐标去重
controlPoints = controlPoints.Distinct(new PointLatLngComparer()).ToList();