1/*
2 *  Copyright (C) 2007-2009 Torch Mobile, Inc.
3 *
4 *  This library is free software; you can redistribute it and/or
5 *  modify it under the terms of the GNU Library General Public
6 *  License as published by the Free Software Foundation; either
7 *  version 2 of the License, or (at your option) any later version.
8 *
9 *  This library is distributed in the hope that it will be useful,
10 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
11 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12 *  Library General Public License for more details.
13 *
14 *  You should have received a copy of the GNU Library General Public License
15 *  along with this library; see the file COPYING.LIB.  If not, write to
16 *  the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 *  Boston, MA 02110-1301, USA.
18 */
19
20#ifndef PlatformPathWinCE_h
21#define PlatformPathWinCE_h
22
23#include "FloatPoint.h"
24#include "FloatRect.h"
25#include "Path.h"
26#include <windows.h>
27#include <wtf/Vector.h>
28
29namespace WebCore {
30
31    class GraphicsContext;
32
33    struct PathPoint {
34        float m_x;
35        float m_y;
36        const float& x() const { return m_x; }
37        const float& y() const { return m_y; }
38        void set(float x, float y)
39        {
40            m_x = x;
41            m_y = y;
42        };
43        operator FloatPoint() const { return FloatPoint(m_x, m_y); }
44        void move(const FloatSize& offset)
45        {
46            m_x += offset.width();
47            m_y += offset.height();
48        }
49        PathPoint& operator=(const FloatPoint& p)
50        {
51            m_x = p.x();
52            m_y = p.y();
53            return *this;
54        }
55        void clear() { m_x = m_y = 0; }
56    };
57
58    struct PathPolygon: public Vector<PathPoint> {
59        void move(const FloatSize& offset);
60        void transform(const AffineTransform& t);
61        bool contains(const FloatPoint& point) const;
62    };
63
64    class PlatformPathElement {
65    public:
66        enum PlaformPathElementType {
67            PathMoveTo,
68            PathLineTo,
69            PathArcTo,
70            PathQuadCurveTo,
71            PathBezierCurveTo,
72            PathCloseSubpath,
73        };
74
75        struct MoveTo {
76            PathPoint m_end;
77        };
78
79        struct LineTo {
80            PathPoint m_end;
81        };
82
83        struct ArcTo {
84            PathPoint m_end;
85            PathPoint m_center;
86            PathPoint m_radius;
87            bool m_clockwise;
88        };
89
90        struct QuadCurveTo {
91            PathPoint m_point0;
92            PathPoint m_point1;
93        };
94
95        struct BezierCurveTo {
96            PathPoint m_point0;
97            PathPoint m_point1;
98            PathPoint m_point2;
99        };
100
101        PlatformPathElement(): m_type(PathCloseSubpath) { m_data.m_points[0].set(0, 0);    }
102        PlatformPathElement(const MoveTo& data): m_type(PathMoveTo) { m_data.m_moveToData = data; }
103        PlatformPathElement(const LineTo& data): m_type(PathLineTo) { m_data.m_lineToData = data; }
104        PlatformPathElement(const ArcTo& data): m_type(PathArcTo) { m_data.m_arcToData = data; }
105        PlatformPathElement(const QuadCurveTo& data): m_type(PathQuadCurveTo) { m_data.m_quadCurveToData = data; }
106        PlatformPathElement(const BezierCurveTo& data): m_type(PathBezierCurveTo) { m_data.m_bezierCurveToData = data; }
107
108        const MoveTo& moveTo() const { return m_data.m_moveToData; }
109        const LineTo& lineTo() const { return m_data.m_lineToData; }
110        const ArcTo& arcTo() const { return m_data.m_arcToData; }
111        const QuadCurveTo& quadCurveTo() const { return m_data.m_quadCurveToData; }
112        const BezierCurveTo& bezierCurveTo() const { return m_data.m_bezierCurveToData; }
113        const PathPoint& lastPoint() const
114        {
115            int n = numPoints();
116            return n > 1 ? m_data.m_points[n - 1] : m_data.m_points[0];
117        }
118        const PathPoint& pointAt(int index) const { return m_data.m_points[index]; }
119        int numPoints() const;
120        int numControlPoints() const;
121        void move(const FloatSize& offset);
122        void transform(const AffineTransform& t);
123        PathElementType type() const;
124        PlaformPathElementType platformType() const { return m_type; }
125        void inflateRectToContainMe(FloatRect& r, const FloatPoint& lastPoint) const;
126
127    private:
128        PlaformPathElementType m_type;
129        union {
130            MoveTo m_moveToData;
131            LineTo m_lineToData;
132            ArcTo m_arcToData;
133            QuadCurveTo m_quadCurveToData;
134            BezierCurveTo m_bezierCurveToData;
135            PathPoint m_points[4];
136        } m_data;
137    };
138
139    typedef Vector<PlatformPathElement> PlatformPathElements;
140
141    class PlatformPath {
142    public:
143        PlatformPath();
144        const PlatformPathElements& elements() const { return m_elements; }
145        void append(const PlatformPathElement& e);
146        void append(const PlatformPath& p);
147        void clear();
148        bool isEmpty() const { return m_elements.isEmpty(); }
149
150        void strokePath(HDC, const AffineTransform* tr) const;
151        void fillPath(HDC, const AffineTransform* tr) const;
152        FloatPoint lastPoint() const { return m_elements.isEmpty() ? FloatPoint(0, 0) : m_elements.last().lastPoint(); }
153
154        const FloatRect& boundingRect() const { return m_boundingRect; }
155        bool contains(const FloatPoint& point, WindRule rule) const;
156        void translate(const FloatSize& size);
157        void transform(const AffineTransform& t);
158
159        void moveTo(const FloatPoint&);
160        void addLineTo(const FloatPoint&);
161        void addQuadCurveTo(const FloatPoint& controlPoint, const FloatPoint& point);
162        void addBezierCurveTo(const FloatPoint& controlPoint1, const FloatPoint& controlPoint2, const FloatPoint&);
163        void addArcTo(const FloatPoint&, const FloatPoint&, float radius);
164        void closeSubpath();
165        void addEllipse(const FloatPoint& p, float a, float b, float sar, float ear, bool anticlockwise);
166        void addRect(const FloatRect& r);
167        void addEllipse(const FloatRect& r);
168        void apply(void* info, PathApplierFunction function) const;
169
170    private:
171        void ensureSubpath();
172        void addToSubpath(const PlatformPathElement& e);
173
174        PlatformPathElements m_elements;
175        FloatRect m_boundingRect;
176        Vector<PathPolygon> m_subpaths;
177        PathPoint m_currentPoint;
178        bool m_penLifted;
179    };
180
181}
182
183#endif // PlatformPathWinCE_h
184