SvgPath.cs 3.37 KB
Newer Older
davescriven's avatar
davescriven committed
1
2
3
4
5
using System.Drawing.Drawing2D;
using Svg.Pathing;

namespace Svg
{
6
7
8
    /// <summary>
    /// Represents an SVG path element.
    /// </summary>
9
    [SvgElement("path")]
10
    public class SvgPath : SvgMarkerElement
davescriven's avatar
davescriven committed
11
12
13
    {
        private GraphicsPath _path;

14
15
16
        /// <summary>
        /// Gets or sets a <see cref="SvgPathSegmentList"/> of path data.
        /// </summary>
Eric Domke's avatar
Eric Domke committed
17
        [SvgAttribute("d", true)]
davescriven's avatar
davescriven committed
18
19
        public SvgPathSegmentList PathData
        {
20
        	get { return this.Attributes.GetAttribute<SvgPathSegmentList>("d"); }
21
22
23
24
25
26
            set
            {
            	this.Attributes["d"] = value;
            	value._owner = this;
                this.IsPathDirty = true;
            }
davescriven's avatar
davescriven committed
27
28
        }

29
30
31
        /// <summary>
        /// Gets or sets the length of the path.
        /// </summary>
Eric Domke's avatar
Eric Domke committed
32
        [SvgAttribute("pathLength", true)]
Eric Domke's avatar
Eric Domke committed
33
        public float PathLength
davescriven's avatar
davescriven committed
34
        {
Eric Domke's avatar
Eric Domke committed
35
            get { return this.Attributes.GetAttribute<float>("pathLength"); }
36
            set { this.Attributes["pathLength"] = value; }
davescriven's avatar
davescriven committed
37
38
        }

39
	
40

davescriven's avatar
davescriven committed
41
42
43
        /// <summary>
        /// Gets the <see cref="GraphicsPath"/> for this element.
        /// </summary>
Eric Domke's avatar
Eric Domke committed
44
        public override GraphicsPath Path(ISvgRenderer renderer)
davescriven's avatar
davescriven committed
45
        {
46
            if (this._path == null || this.IsPathDirty)
davescriven's avatar
davescriven committed
47
            {
48
                this._path = new GraphicsPath();
davescriven's avatar
davescriven committed
49

50
51
52
                foreach (SvgPathSegment segment in this.PathData)
                {
                    segment.AddToPath(_path);
davescriven's avatar
davescriven committed
53
                }
54

55
56
57
58
59
60
61
62
63
64
65
66
67
68
                if (_path.PointCount == 0)
                {
                    if (this.PathData.Count > 0)
                    {
                        // special case with one move command only, see #223
                        var segment = this.PathData.Last;
                        _path.AddLine(segment.End, segment.End);
                        this.Fill = SvgPaintServer.None;
                    }
                    else
                    {
                        _path = null;
                    }
                }
69
                this.IsPathDirty = false;
70
            }
71
            return _path;
davescriven's avatar
davescriven committed
72
73
74
75
76
        }

        internal void OnPathUpdated()
        {
            this.IsPathDirty = true;
77
            OnAttributeChanged(new AttributeEventArgs{ Attribute = "d", Value = this.Attributes.GetAttribute<SvgPathSegmentList>("d") });
davescriven's avatar
davescriven committed
78
79
        }

80
81
82
        /// <summary>
        /// Gets the bounds of the element.
        /// </summary>
Tebjan Halm's avatar
Tebjan Halm committed
83
84
        /// <value>The bounds.</value>
        public override System.Drawing.RectangleF Bounds
davescriven's avatar
davescriven committed
85
        {
Tebjan Halm's avatar
Tebjan Halm committed
86
            get { return this.Path(null).GetBounds(); }
davescriven's avatar
davescriven committed
87
88
        }

89
90
91
        /// <summary>
        /// Initializes a new instance of the <see cref="SvgPath"/> class.
        /// </summary>
davescriven's avatar
davescriven committed
92
93
        public SvgPath()
        {
94
95
96
            var pathData = new SvgPathSegmentList();
            this.Attributes["d"] = pathData;
            pathData._owner = this;
davescriven's avatar
davescriven committed
97
        }
98

99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
		public override SvgElement DeepCopy()
		{
			return DeepCopy<SvgPath>();
		}

		public override SvgElement DeepCopy<T>()
		{
			var newObj = base.DeepCopy<T>() as SvgPath;
			foreach (var pathData in this.PathData)
				newObj.PathData.Add(pathData.Clone());
			newObj.PathLength = this.PathLength;
			newObj.MarkerStart = this.MarkerStart;
			newObj.MarkerEnd = this.MarkerEnd;
			return newObj;

		}
davescriven's avatar
davescriven committed
115
116
    }
}