示例#1
0
        /// <summary>
        /// Build new polygon from ellipse. The ellipse is
        /// defined by the specified bounding rectangle. The
        /// second parameter specifies how close the
        /// polygon approximates the ellipse.
        /// Factor of 0 specifies simplest polygon, while
        /// factor 100 specifies the most complex polygon.
        /// </summary>
        /// <param name="bounds"></param>
        /// <param name="factor"></param>
        public Polygon(RectangleF bounds, int factor)
        {
            if (factor < 0)
            {
                factor = 0;
            }
            if (factor > 100)
            {
                factor = 100;
            }

            GraphicsPath path = new GraphicsPath();

            path.AddEllipse(bounds);
            path.Flatten(new Matrix(), (float)factor / 100f);
            _points = new PointList(path.PathPoints);

            path.Dispose();

            Complete();
        }
示例#2
0
		/// <summary>
		/// Creates single h-line at the specified vertical offset.
		/// </summary>
		private PointList BuildLine(float yOff)
		{
			PointF p11 = new PointF(_bounds.Left - 1, 0);
			PointF p12 = new PointF(_bounds.Right + 1, 0);
			PointF p21 = new PointF(_bounds.Left - 1, 0);
			PointF p22 = new PointF(_bounds.Right + 1, 0);

			p11.Y = p12.Y = yOff;
			yOff += _text.Height;
			if (yOff > _bounds.Bottom)
				return null;
			p21.Y = p22.Y = yOff;

			ArrayList merge = new ArrayList();
			PointList result = new PointList();
			PointList row1 = PolygonIntersect(p11, p12);
			PointList row2 = PolygonIntersect(p21, p22);

			int i;
			for (i = 0; i < row1.Count; i++)
				merge.Add(new DirPt(row1[i], i % 2 == 1 ? 2 : 0));
			for (i = 0; i < row2.Count; i++)
				merge.Add(new DirPt(row2[i], i % 2 == 1 ? 3 : 1));

			merge.Sort();

			PointF pt = PointF.Empty;
			int inter = -1; // 0 - for first line, 2 for second line, 4 - for both
			for (i = 0; i < merge.Count; i++)
			{
				DirPt temp = merge[i] as DirPt;

				if (temp.Direction == 2 || temp.Direction == 3) // out
				{
					if (inter != 4)
					{
						if (inter == 0 && temp.Direction == 2)
							inter = -1;
						else if (inter == 2 && temp.Direction == 3)
							inter = -1;
						continue;
					}

					pt.Y = yOff - _text.Height;
					temp.Point = new PointF(temp.Point.X, yOff);

					// Make points relative to the upper-left point of the polygon
					pt.X -= _bounds.Left;
					pt.Y -= _bounds.Top;
					temp.Point = new PointF(
						temp.Point.X - _bounds.Left,
						temp.Point.Y - _bounds.Top);

					result.Add(pt);
					result.Add(temp.Point);

					if (temp.Direction == 2)
						inter = 2;
					else
						inter = 0;
				}
				else
				{
					pt = temp.Point;

					if (temp.Direction == 0)
					{
						if (inter == -1)
							inter = 0;
						else if (inter == 2)
							inter = 4;
					}
					else
					{
						if (inter == -1)
							inter = 2;
						else if (inter == 0)
							inter = 4;
					}
				}
			}

			// Check if the center point of each
			// rectangle lies within the polygon
			for (i = 0; i < result.Count; )
			{
				PointF pt1 = result[i];
				PointF pt2 = result[i + 1];
				PointF ptc = PointF.Empty;
		
				ptc.X = (pt1.X + pt2.X) / 2 + _bounds.Left;
				ptc.Y = (pt1.Y + pt2.Y) / 2 + _bounds.Top;

				if (!_polygon.Contains(ptc))
				{
					result.RemoveAt(i);
					result.RemoveAt(i);
				}
				else
				{
					i += 2;
				}
			}

			return result;
		}
示例#3
0
		/// <summary>
		/// Finds a point inside the polygon.
		/// </summary>
		public PointF GetInternalPoint()
		{
			int cvi = FindConvexVertex();
			int prev = cvi > 0 ? cvi - 1 : _points.Count - 1;
			int next = (cvi + 1) % _points.Count;

			PointF v = _points[cvi];
			PointF a = _points[prev];
			PointF b = _points[next];

			PointList pl = new PointList();
			pl.Add(a); pl.Add(v); pl.Add(b);

			Polygon avb = new Polygon(pl);

			float minDist = float.MaxValue;
			PointF intPt = v;

			for (int i = 0; i < _points.Count; ++i)
			{
				if (i == cvi) continue;
				if (i == prev) continue;
				if (i == next) continue;

				PointF q = _points[i];
				if (avb.Contains(q))
				{
					float dist = (float)Math.Sqrt((q.X-v.X)*(q.X-v.X) + (q.Y-v.Y)*(q.Y-v.Y));
					if (dist < minDist)
					{
						minDist = dist;
						intPt = q;
					}
				}
			}

			if (intPt == v)
				return new PointF((a.X + b.X) / 2, (a.Y + b.Y) / 2);
			else
				return new PointF((v.X + intPt.X)/ 2, (v.Y + intPt.Y) / 2);
		}
示例#4
0
		/// <summary>
		/// Calculates the intersections between the 
		/// polygon and the line defined by the given points.
		/// The result is a list containing all points of intersection.
		/// </summary>
		public PointList IntersectLine(PointF a, PointF b)
		{
			PointList result = new PointList();
			PointF point;

			for (int i = 0; i < _points.Count - 1; i++)
			{
				point = new Line(_points[i], _points[i + 1]).
					IntersectLine(a, b);

				if (!float.IsPositiveInfinity(point.X))
					result.Add(point);
			}

			return result;
		}
示例#5
0
		/// <summary>
		/// Build new polygon from ellipse. The ellipse is
		/// defined by the specified bounding rectangle. The
		/// second parameter specifies how close the
		/// polygon approximates the ellipse.
		/// Factor of 0 specifies simplest polygon, while
		/// factor 100 specifies the most complex polygon.
		/// </summary>
		/// <param name="bounds"></param>
		/// <param name="factor"></param>
		public Polygon(RectangleF bounds, int factor)
		{
			if (factor < 0)
				factor = 0;
			if (factor > 100)
				factor = 100;

			GraphicsPath path = new GraphicsPath();

			path.AddEllipse(bounds);
			path.Flatten(new Matrix(), (float)factor / 100f);
			_points = new PointList(path.PathPoints);

			path.Dispose();

			Complete();
		}
示例#6
0
		/// <summary>
		/// Builds new polygon object from the specified rectangle.
		/// </summary>
		/// <param name="rect"></param>
		public Polygon(RectangleF rect)
		{
			float l = Math.Min(rect.Left, rect.Right);
			float r = Math.Max(rect.Left, rect.Right);
			float t = Math.Min(rect.Top, rect.Bottom);
			float b = Math.Max(rect.Top, rect.Bottom);

			_points = new PointList(
				new PointF[]
				{
					new PointF(l, t),
					new PointF(r, t),
					new PointF(r, b),
					new PointF(l, b)
				});

			Complete();
		}
示例#7
0
		/// <summary>
		/// Builds new polygon object from a given points list.
		/// </summary>
		public Polygon(PointList points)
		{
			if (points.Count < 3)
				throw new Exception("Polygons need at least 3 points.");

			_points = new PointList(points);

			Complete();
		}