SvgLinearGradientServer.cs 3.46 KB
Newer Older
davescriven's avatar
davescriven committed
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing.Drawing2D;
using System.Drawing;
using System.ComponentModel;

namespace Svg
{
    public sealed class SvgLinearGradientServer : SvgGradientServer
    {
        private SvgUnit _x1;
        private SvgUnit _y1;
        private SvgUnit _x2;
        private SvgUnit _y2;

        [DefaultValue(typeof(SvgUnit), "0"), SvgAttribute("x1")]
        public SvgUnit X1
        {
            get { return this._x1; }
            set
            {
                this._x1 = value;
            }
        }

        [DefaultValue(typeof(SvgUnit), "0"), SvgAttribute("y1")]
        public SvgUnit Y1
        {
            get { return this._y1; }
            set
            {
                this._y1 = value;
            }
        }

        [DefaultValue(typeof(SvgUnit), "0"), SvgAttribute("x2")]
        public SvgUnit X2
        {
            get { return this._x2; }
            set
            {
                this._x2 = value;
            }
        }

        [DefaultValue(typeof(SvgUnit), "0"), SvgAttribute("y2")]
        public SvgUnit Y2
        {
            get { return this._y2; }
            set
            {
                this._y2 = value;
            }
        }

        public SvgLinearGradientServer()
        {
            this._x1 = new SvgUnit(0.0f);
            this._y1 = new SvgUnit(0.0f);
            this._x2 = new SvgUnit(0.0f);
            this._y2 = new SvgUnit(0.0f);
        }

        public SvgPoint Start
        {
            get { return new SvgPoint(this.X1, this.Y1); }
        }

        public SvgPoint End
        {
            get { return new SvgPoint(this.X2, this.Y2); }
        }

        public override Brush GetBrush(SvgGraphicsElement owner, float opacity)
        {
            // Need at least 2 colours to do the gradient fill
            if (this.Stops.Count < 2)
79
            {
davescriven's avatar
davescriven committed
80
                return null;
81
            }
davescriven's avatar
davescriven committed
82
83
84

            PointF start;
            PointF end;
85
            RectangleF bounds = (this.GradientUnits == SvgCoordinateUnits.ObjectBoundingBox) ? owner.Bounds : owner.OwnerDocument.GetDimensions();
davescriven's avatar
davescriven committed
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100

            // Have start/end points been set? If not the gradient is horizontal
            if (!this.End.IsEmpty())
            {
                // Get the points to work out an angle
                if (this.Start.IsEmpty())
                {
                    start = bounds.Location;
                }
                else
                {
                    start = new PointF(this.Start.X.ToDeviceValue(owner), this.Start.Y.ToDeviceValue(owner, true));
                }

                float x = (this.End.X.IsEmpty) ? start.X : this.End.X.ToDeviceValue(owner);
davescriven's avatar
davescriven committed
101
                end = new PointF(x, this.End.Y.ToDeviceValue(owner, true));
davescriven's avatar
davescriven committed
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
            }
            else
            {
                // Default: horizontal
                start = bounds.Location;
                end = new PointF(bounds.Right, bounds.Top);
            }

            LinearGradientBrush gradient = new LinearGradientBrush(start, end, Color.Transparent, Color.Transparent);
            gradient.InterpolationColors = base.GetColourBlend(owner, opacity);

            // Needed to fix an issue where the gradient was being wrapped when though it had the correct bounds
            gradient.WrapMode = WrapMode.TileFlipX;
            return gradient;
        }
    }
}