private static void DrawLinestring(Geometry.Linestring linestring, Geometry.Box box, Graphics graphics, Settings settings, Geometry.Traits traits) { LocalCS cs = new LocalCS(box, graphics); Drawer drawer = new Drawer(graphics, settings.color); if (traits.Unit == Geometry.Unit.None) { for (int i = 1; i < linestring.Count; ++i) { PointF p0 = cs.Convert(linestring[i - 1]); PointF p1 = cs.Convert(linestring[i]); drawer.DrawLine(p0, p1); if (settings.showDir) { drawer.DrawDir(p0, p1); } } } else // Radian, Degree { Drawer.PeriodicDrawableRange pd = new Drawer.PeriodicDrawableRange(cs, linestring, false, traits.Unit, settings.densify); Geometry.Interval interval = RelativeEnvelopeLon(linestring, false, traits.Unit); drawer.DrawPeriodic(cs, box, interval, traits.Unit, pd, false, settings.showDir, settings.showDots); } }
public void DrawPeriodicPoint(LocalCS cs, Geometry.Point point, Geometry.Box box, Geometry.Unit unit, bool drawDots) { PointF p = cs.Convert(point); DrawPoint(p); double pi2 = 2 * Geometry.HalfAngle(unit); Pen pen = drawDots ? this.penDot : this.pen; // draw points on the west double x_tmp = point[0] - pi2; while (x_tmp >= box.Min[0]) { p.X = cs.ConvertX(x_tmp); DrawPoint(p, pen); x_tmp -= pi2; } // draw points on the east x_tmp = point[0] + pi2; while (x_tmp <= box.Max[0]) { p.X = cs.ConvertX(x_tmp); DrawPoint(p, pen); x_tmp += pi2; } }
public System.Drawing.Point GetDrawingPoint(Geometry.Box box, Graphics graphics) { LocalCS cs = new LocalCS(box, graphics); PointF pf = cs.Convert(point); return(new System.Drawing.Point((int)Math.Round(pf.X), (int)Math.Round(pf.Y))); }
public PeriodicDrawableBox(LocalCS cs, Geometry.IRandomAccessRange <Geometry.Point> points, Geometry.Unit unit) : base(true) { int count = points.Count + 1; xs_orig = new float[count]; points_rel = new PointF[count]; xs_orig[0] = cs.ConvertX(points[0][0]); points_rel[0] = cs.Convert(points[0]); for (int i = 1; i < points.Count; ++i) { xs_orig[i] = cs.ConvertX(points[i][0]); // always relative to p0 double distNorm = Geometry.NormalizedAngleUnsigned(points[i][0] - points[0][0], unit); // [0, 2pi] - min is always lesser than max double x_curr = points[0][0] + distNorm; // always relative to p0 points_rel[i] = new PointF(cs.ConvertX(x_curr), cs.ConvertY(points[i][1])); } // close xs_orig[points.Count] = xs_orig[0]; points_rel[points.Count] = points_rel[0]; }
public void Draw(Geometry.Box box, Graphics graphics, Settings settings, Geometry.Traits traits) { LocalCS cs = new LocalCS(box, graphics); Drawer drawer = new Drawer(graphics, settings.color); if (traits.Unit == Geometry.Unit.None) { PointF[] dst_points = cs.Convert(this); if (dst_points != null) { drawer.FillPolygon(dst_points); drawer.DrawPolygon(dst_points); if (settings.showDir) { drawer.DrawDirs(dst_points, true); drawer.DrawPoint(dst_points[0].X, dst_points[0].Y); } } } else { Drawer.PeriodicDrawableRange pd = new Drawer.PeriodicDrawableRange(cs, this, true, traits.Unit, settings.densify); Geometry.Interval interval = RelativeEnvelopeLon(this, true, traits.Unit); drawer.DrawPeriodic(cs, box, interval, traits.Unit, pd, true, settings.showDir, settings.showDots); if (settings.showDir && this.Count > 0) { drawer.DrawPeriodicPoint(cs, this[0], box, traits.Unit, settings.showDots); } } }
public void DrawPeriodicPoint(LocalCS cs, Geometry.Point point, Geometry.Box box, Geometry.Unit unit) { PointF p = cs.Convert(point); DrawPoint(p); Pen penDot = (Pen)pen.Clone(); penDot.DashStyle = DashStyle.Dot; double pi2 = 2 * Geometry.HalfAngle(unit); // draw points on the west double x_tmp = point[0] - pi2; while (x_tmp >= box.Min[0]) { p.X = cs.ConvertX(x_tmp); DrawPoint(p, penDot); x_tmp -= pi2; } // draw points on the east x_tmp = point[0] + pi2; while (x_tmp <= box.Max[0]) { p.X = cs.ConvertX(x_tmp); DrawPoint(p, penDot); x_tmp += pi2; } }
public PeriodicDrawableRange(LocalCS cs, Geometry.IRandomAccessRange <Geometry.Point> points, Geometry.Box box, Geometry.Unit unit) { if (points.Count < 2) { return; } double pi = Geometry.HalfAngle(unit); periodf = cs.ConvertDimension(2 * pi); xs_orig = new float[points.Count]; points_rel = new PointF[points.Count]; xs_orig[0] = cs.ConvertX(points[0][0]); points_rel[0] = cs.Convert(points[0]); minf = points_rel[0].X; maxf = points_rel[0].X; double x0 = Geometry.NormalizedAngle(points[0][0], unit); double x0_prev = points[0][0]; for (int i = 1; i < points.Count; ++i) { xs_orig[i] = cs.ConvertX(points[i][0]); double x1 = Geometry.NormalizedAngle(points[i][0], unit); double dist = x1 - x0; // [-2pi, 2pi] double distNorm = Geometry.NormalizedAngle(dist, unit); // [-pi, pi] double x0_curr = x0_prev + distNorm; points_rel[i] = new PointF(cs.ConvertX(x0_curr), cs.ConvertY(points[i][1])); // expand relative box X if (points_rel[i].X < minf) { minf = points_rel[i].X; } if (points_rel[i].X > maxf) { maxf = points_rel[i].X; } x0_prev = x0_curr; x0 = x1; } box_minf = cs.ConvertX(box.Min[0]); box_maxf = cs.ConvertX(box.Max[0]); }
public void Draw(Geometry.Box box, Graphics graphics, Settings settings, Geometry.Traits traits) { LocalCS cs = new LocalCS(box, graphics); Drawer drawer = new Drawer(graphics, settings.color); if (traits.Unit == Geometry.Unit.None) { PointF p0 = cs.Convert(this[0]); PointF p1 = cs.Convert(this[1]); drawer.DrawLine(p0, p1); if (settings.showDir) { drawer.DrawDir(p0, p1); } } else // Radian, Degree { Drawer.PeriodicDrawableRange pd = new Drawer.PeriodicDrawableRange(cs, this, false, traits.Unit, settings.densify); Geometry.Interval interval = RelativeEnvelopeLon(this, false, traits.Unit); drawer.DrawPeriodic(cs, box, interval, traits.Unit, pd, false, settings.showDir, settings.showDots); } }
private static void DrawPoint(Geometry.Point point, Geometry.Box box, Graphics graphics, Settings settings, Geometry.Traits traits) { LocalCS cs = new LocalCS(box, graphics); Drawer drawer = new Drawer(graphics, settings.color); if (traits.Unit == Geometry.Unit.None) { PointF p = cs.Convert(point); drawer.DrawPoint(p); } else // Radian, Degree { drawer.DrawPeriodicPoint(cs, point, box, traits.Unit, settings.showDots); } }
public PeriodicDrawableNSphere(LocalCS cs, Geometry.NSphere nsphere, Geometry.Box box, Geometry.Unit unit) { double pi = Geometry.HalfAngle(unit); periodf = cs.ConvertDimension(2 * pi); c_rel = cs.Convert(nsphere.Center); r = cs.ConvertDimension(nsphere.Radius); minf = c_rel.X - r; maxf = c_rel.X + r; box_minf = cs.ConvertX(box.Min[0]); box_maxf = cs.ConvertX(box.Max[0]); }
public PeriodicDrawableBox(LocalCS cs, Geometry.IRandomAccessRange <Geometry.Point> points, Geometry.Box box, Geometry.Unit unit) { double pi = Geometry.HalfAngle(unit); periodf = cs.ConvertDimension(2 * pi); xs_orig = new float[points.Count]; points_rel = new PointF[points.Count]; xs_orig[0] = cs.ConvertX(points[0][0]); points_rel[0] = cs.Convert(points[0]); minf = points_rel[0].X; maxf = points_rel[0].X; double x0 = Geometry.NormalizedAngle(points[0][0], unit); for (int i = 1; i < points.Count; ++i) { xs_orig[i] = cs.ConvertX(points[i][0]); double x1 = Geometry.NormalizedAngle(points[i][0], unit); double dist = x1 - x0; // [-2pi, 2pi] double distNorm = Geometry.NormalizedAngle(dist, unit); // [-pi, pi] while (distNorm < 0) { distNorm += 2 * Geometry.HalfAngle(unit); // [0, 2pi] - min is always lesser than max } double x0_curr = points[0][0] + distNorm; // always relative to p0 points_rel[i] = new PointF(cs.ConvertX(x0_curr), cs.ConvertY(points[i][1])); // expand relative box X if (points_rel[i].X < minf) { minf = points_rel[i].X; } if (points_rel[i].X > maxf) { maxf = points_rel[i].X; } } box_minf = cs.ConvertX(box.Min[0]); box_maxf = cs.ConvertX(box.Max[0]); }
public void Draw(Geometry.Box box, Graphics graphics, Settings settings, Geometry.Traits traits) { LocalCS cs = new LocalCS(box, graphics); Drawer drawer = new Drawer(graphics, settings.color); float rx = cs.ConvertDimensionX(Radius); float ry = cs.ConvertDimensionY(Radius); if (rx < 0 || ry < 0) { return; } if (traits.Unit == Geometry.Unit.None) { PointF c = cs.Convert(Center); if (rx == 0 || ry == 0) { drawer.DrawPoint(c.X, c.Y); } else { float x = c.X - rx; float y = c.Y - ry; float w = rx * 2; float h = ry * 2; drawer.DrawEllipse(x, y, w, h); drawer.FillEllipse(x, y, w, h); } } else // Radian, Degree { if (rx == 0 || ry == 0) { drawer.DrawPeriodicPoint(cs, Center, box, traits.Unit, settings.showDots); } else { Drawer.PeriodicDrawableNSphere pd = new Drawer.PeriodicDrawableNSphere(cs, this, traits.Unit); Geometry.Interval interval = RelativeEnvelopeLon(this, traits.Unit); drawer.DrawPeriodic(cs, box, interval, traits.Unit, pd, true, false, settings.showDots); } } }
private static PointF[] DensifyAndConvert(LocalCS cs, Geometry.Point p0, Geometry.Point p1, double length, Geometry.Unit unit) { double distNorm = Geometry.NormalizedAngleSigned(p1[0] - p0[0], unit); bool intersPole = IsAntipodal(distNorm, unit); double halfPi = Geometry.HalfAngle(unit) / 2; double poleLat = p1[1] - p0[1] >= 0 ? halfPi : -halfPi; int intersPoleIndex = -1; Geometry.Point[] densPoints = Geometry.SphericalDensify(p0, p1, length, unit); PointF[] result = new PointF[densPoints.Length + (intersPole ? 2 : 0)]; int k = 0; for (int j = 0; j < densPoints.Length; ++j, ++k) { double densDistNorm = Geometry.NormalizedAngleSigned(densPoints[j][0] - p0[0], unit); densPoints[j][0] = p0[0] + densDistNorm; if (intersPole && intersPoleIndex == -1 && Math.Abs(densDistNorm) > halfPi) { intersPoleIndex = j; Geometry.Point p = j == 0 ? p0 : densPoints[j - 1]; float poleF = cs.ConvertY(poleLat); result[k++] = new PointF(cs.ConvertX(p[0]), poleF); result[k++] = new PointF(cs.ConvertX(densPoints[j][0]), poleF); } result[k] = cs.Convert(densPoints[j]); } // last segment if (intersPole && intersPoleIndex == -1) { int j = densPoints.Length; intersPoleIndex = j; float poleF = cs.ConvertY(poleLat); result[j] = new PointF(cs.ConvertX(densPoints[j - 1][0]), poleF); result[j + 1] = new PointF(cs.ConvertX(p1[0]), poleF); } return(result); }
public void DrawPeriodicPoint(LocalCS cs, Geometry.Point point, Geometry.Box box, Geometry.Unit unit, bool drawDots) { PointF p = cs.Convert(point); DrawPoint(p); double twoPi = Geometry.FullAngle(unit); Pen pen = drawDots ? this.penDot : this.pen; // NOTE: Use AssignChanged becasue for big coordinates subtracting/adding // twoPi doesn't change the value of x_tmp which causes infinite loop float x = Math.Min(Math.Max(p.X, 0.0f), cs.Width); double nPeriodsWest = (point[0] - box.Min[0]) / twoPi; float pixelsWest = x; double nPeriodsEast = (box.Max[0] - point[0]) / twoPi; float pixelsEast = cs.Width - x; if (nPeriodsWest <= pixelsWest / 5) { // draw points on the west double x_tmp = point[0]; while (Util.Assign(ref x_tmp, x_tmp - twoPi) && x_tmp >= box.Min[0]) { p.X = cs.ConvertX(x_tmp); DrawPoint(p, pen); } } if (nPeriodsEast <= pixelsEast / 5) { // draw points on the east double x_tmp = point[0]; while (Util.Assign(ref x_tmp, x_tmp + twoPi) && x_tmp <= box.Max[0]) { p.X = cs.ConvertX(x_tmp); DrawPoint(p, pen); } } }
private static void DrawPolygon(Geometry.Polygon polygon, Geometry.Box box, Graphics graphics, Settings settings, Geometry.Traits traits) { LocalCS cs = new LocalCS(box, graphics); Drawer drawer = new Drawer(graphics, settings.color); if (traits.Unit == Geometry.Unit.None) { PointF[] dst_outer_points = cs.Convert(polygon.Outer); if (dst_outer_points != null) { GraphicsPath gp = new GraphicsPath(); gp.AddPolygon(dst_outer_points); if (settings.showDir) { drawer.DrawDirs(dst_outer_points, true); drawer.DrawPoint(dst_outer_points[0]); } foreach (Ring inner in polygon.Inners) { PointF[] dst_inner_points = cs.Convert(inner); if (dst_inner_points != null) { gp.AddPolygon(dst_inner_points); if (settings.showDir) { drawer.DrawDirs(dst_inner_points, true); drawer.DrawPoint(dst_inner_points[0]); } } } drawer.FillPath(gp); drawer.DrawPath(gp); } } else { Drawer.PeriodicDrawablePolygon pd = new Drawer.PeriodicDrawablePolygon(cs, polygon.Outer, polygon.Inners, traits.Unit, settings.densify); Geometry.Interval interval = RelativeEnvelopeLon(polygon.Outer, polygon.Inners, traits.Unit); drawer.DrawPeriodic(cs, box, interval, traits.Unit, pd, true, settings.showDir, settings.showDots); if (settings.showDir) { if (settings.showDir && polygon.Outer.Count > 0) { drawer.DrawPeriodicPoint(cs, polygon.Outer[0], box, traits.Unit, settings.showDots); } foreach (Ring inner in polygon.Inners) { if (inner.Count > 0) { drawer.DrawPeriodicPoint(cs, inner[0], box, traits.Unit, settings.showDots); } } } } }
public PeriodicDrawableNSphere(LocalCS cs, Geometry.NSphere nsphere, Geometry.Unit unit) { // NOTE: The radius is always in the units of the CS which is technically wrong c_rel = cs.Convert(nsphere.Center); r = cs.ConvertDimensionX(nsphere.Radius); }
public PeriodicDrawableRange(LocalCS cs, Geometry.IRandomAccessRange <Geometry.Point> points, bool closed, Geometry.Unit unit, bool densify) { this.closed = closed; this.containsPole = ContainsPole.No; if (points.Count < 2) { return; } // approx. length of densified segments /*double densLength = Math.Min(cs.InverseConvertDimensionX(20), * cs.InverseConvertDimensionY(20));*/ double densLength = Geometry.FromDegree(5, unit); int count = points.Count + (closed ? 1 : 0); xs_orig = new float[count]; points_rel = new PointF[count]; if (densify) { dens_points_rel = new PointF[points.Count][]; } xs_orig[0] = cs.ConvertX(points[0][0]); points_rel[0] = cs.Convert(points[0]); Geometry.Point p0 = points[0].Clone(); for (int i = 1; i < count; ++i) { Geometry.Point p1 = points[i % points.Count].Clone(); xs_orig[i] = cs.ConvertX(p1[0]); double distNorm = Geometry.NormalizedAngleSigned(p1[0] - p0[0], unit); // [-pi, pi] p1[0] = p0[0] + distNorm; points_rel[i] = cs.Convert(p1); if (dens_points_rel != null) { dens_points_rel[i - 1] = DensifyAndConvert(cs, p0, p1, densLength, unit); } p0 = p1; } if (closed && Math.Abs(points_rel[0].X - points_rel[points.Count].X) > 0.1) { // Check which pole double area = 0; p0 = points[0].Clone(); for (int i = 1; i < count; ++i) { Geometry.Point p1 = points[i % points.Count].Clone(); double distNorm = Geometry.NormalizedAngleSigned(p1[0] - p0[0], unit); // [-pi, pi] p1[0] = p0[0] + distNorm; area += Geometry.SphericalTrapezoidArea(p0, p1, unit); p0 = p1; } int areaSign = Math.Sign(area); int dirSign = Math.Sign(points_rel[points.Count].X - points_rel[0].X); this.containsPole = (areaSign * dirSign >= 0) ? ContainsPole.North : ContainsPole.South; } }