Inkscape
Vector Graphics Editor
Loading...
Searching...
No Matches
elliptical-arc.h
Go to the documentation of this file.
1/*
6 * Authors:
7 * MenTaLguY <mental@rydia.net>
8 * Marco Cecchetti <mrcekets at gmail.com>
9 * Krzysztof KosiƄski <tweenk.pl@gmail.com>
10 *
11 * Copyright 2007-2009 Authors
12 *
13 * This library is free software; you can redistribute it and/or
14 * modify it either under the terms of the GNU Lesser General Public
15 * License version 2.1 as published by the Free Software Foundation
16 * (the "LGPL") or, at your option, under the terms of the Mozilla
17 * Public License Version 1.1 (the "MPL"). If you do not alter this
18 * notice, a recipient may use your version of this file under either
19 * the MPL or the LGPL.
20 *
21 * You should have received a copy of the LGPL along with this library
22 * in the file COPYING-LGPL-2.1; if not, write to the Free Software
23 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 * You should have received a copy of the MPL along with this library
25 * in the file COPYING-MPL-1.1
26 *
27 * The contents of this file are subject to the Mozilla Public License
28 * Version 1.1 (the "License"); you may not use this file except in
29 * compliance with the License. You may obtain a copy of the License at
30 * http://www.mozilla.org/MPL/
31 *
32 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY
33 * OF ANY KIND, either express or implied. See the LGPL or the MPL for
34 * the specific language governing rights and limitations.
35 */
36
37#ifndef LIB2GEOM_SEEN_ELLIPTICAL_ARC_H
38#define LIB2GEOM_SEEN_ELLIPTICAL_ARC_H
39
40#include <algorithm>
41#include <2geom/affine.h>
42#include <2geom/angle.h>
43#include <2geom/bezier-curve.h>
44#include <2geom/curve.h>
45#include <2geom/ellipse.h>
46#include <2geom/sbasis-curve.h> // for non-native methods
47#include <2geom/utils.h>
48
49namespace Geom
50{
51
52class EllipticalArc : public Curve
53{
54public:
57 : _initial_point(0,0)
58 , _final_point(0,0)
59 , _large_arc(false)
60 {}
70 EllipticalArc( Point const &ip, Point const &r,
71 Coord rot_angle, bool large_arc, bool sweep,
72 Point const &fp
73 )
74 : _initial_point(ip)
75 , _final_point(fp)
76 , _ellipse(0, 0, r[X], r[Y], rot_angle)
77 , _angles(0, 0, sweep)
78 , _large_arc(large_arc)
79 {
81 }
82
84 EllipticalArc( Point const &ip, Coord rx, Coord ry,
85 Coord rot_angle, bool large_arc, bool sweep,
86 Point const &fp
87 )
88 : _initial_point(ip)
89 , _final_point(fp)
90 , _ellipse(0, 0, rx, ry, rot_angle)
91 , _angles(0, 0, sweep)
92 , _large_arc(large_arc)
93 {
95 }
96
99
103 Coord center(Dim2 d) const { return _ellipse.center(d); }
104
107 Point center() const { return _ellipse.center(); }
108
112 Coord ray(Dim2 d) const { return _ellipse.ray(d); }
113
116 Point rays() const { return _ellipse.rays(); }
117
121 return _ellipse.rotationAngle();
122 }
123
126 bool largeArc() const { return _large_arc; }
127
131 bool sweep() const { return _angles.sweep(); }
132
134 Angle finalAngle() const { return _angles.finalAngle(); }
136
139
141 void set( Point const &ip, double rx, double ry,
142 double rot_angle, bool large_arc, bool sweep,
143 Point const &fp
144 )
145 {
146 _initial_point = ip;
147 _final_point = fp;
148 _ellipse.setRays(rx, ry);
149 _ellipse.setRotationAngle(rot_angle);
151 _large_arc = large_arc;
153 }
154
156 void set( Point const &ip, Point const &r,
157 Angle rot_angle, bool large_arc, bool sweep,
158 Point const &fp
159 )
160 {
161 _initial_point = ip;
162 _final_point = fp;
163 _ellipse.setRays(r);
164 _ellipse.setRotationAngle(rot_angle);
166 _large_arc = large_arc;
168 }
169
175 void setEndpoints(Point const &ip, Point const &fp) {
176 _initial_point = ip;
177 _final_point = fp;
179 }
181
184
187 bool containsAngle(Angle angle) const { return _angles.contains(angle); }
188
192 Point pointAtAngle(Coord t) const;
193
198 Coord valueAtAngle(Coord t, Dim2 d) const;
199
201 Coord timeAtAngle(Angle a) const { return _angles.timeAtAngle(a); }
202
204 Angle angleAt(Coord t) const { return _angles.angleAt(t); }
205
209 Coord sweepAngle() const { return _angles.sweepAngle(); }
210
213 Coord angularExtent() const { return _angles.extent(); }
214
217
219 Point pointAt(Coord t) const override;
220
222 Coord valueAt(Coord t, Dim2 d) const override;
223
232
239
242
244 bool isChord() const {
245 return ray(X) == 0 || ray(Y) == 0;
246 }
247
252
253 // implementation of overloads goes here
254 Point initialPoint() const override { return _initial_point; }
255 Point finalPoint() const override { return _final_point; }
256 Curve* duplicate() const override { return new EllipticalArc(*this); }
257 void setInitial(Point const &p) override {
258 _initial_point = p;
260 }
261 void setFinal(Point const &p) override {
262 _final_point = p;
264 }
265 bool isDegenerate() const override {
267 }
268 bool isLineSegment() const override { return isChord(); }
269 Rect boundsFast() const override {
270 return boundsExact();
271 }
272 Rect boundsExact() const override;
273 void expandToTransformed(Rect &bbox, Affine const &transform) const override;
274 // TODO: native implementation of the following methods
275 OptRect boundsLocal(OptInterval const &i, unsigned int deg) const override {
276 return SBasisCurve(toSBasis()).boundsLocal(i, deg);
277 }
278 std::vector<double> roots(double v, Dim2 d) const override;
279#ifdef HAVE_GSL
280 std::vector<double> allNearestTimes( Point const& p, double from = 0, double to = 1 ) const override;
281 double nearestTime( Point const& p, double from = 0, double to = 1 ) const override {
282 if ( are_near(ray(X), ray(Y)) && are_near(center(), p) ) {
283 return from;
284 }
285 return allNearestTimes(p, from, to).front();
286 }
287#endif
288 std::vector<CurveIntersection> intersect(Curve const &other, Coord eps=EPSILON) const override;
289 int degreesOfFreedom() const override { return 7; }
290 Curve *derivative() const override;
291
292 using Curve::operator*=;
293 void operator*=(Translate const &tr) override;
294 void operator*=(Scale const &s) override;
295 void operator*=(Rotate const &r) override;
296 void operator*=(Zoom const &z) override;
297 void operator*=(Affine const &m) override;
298
299 std::vector<Point> pointAndDerivatives(Coord t, unsigned int n) const override;
300 D2<SBasis> toSBasis() const override;
301 Curve *portion(double f, double t) const override;
302 Curve *reverse() const override;
303 bool isNear(Curve const &other, Coord precision) const override;
304 void feed(PathSink &sink, bool moveto_initial) const override;
305 int winding(Point const &p) const override;
306
307protected:
308 bool _equalTo(Curve const &c) const override;
309
310private:
312 std::vector<ShapeIntersection> _filterIntersections(std::vector<ShapeIntersection> &&xs, bool is_first) const;
313 bool _validateIntersection(ShapeIntersection &xing, bool is_first) const;
314 std::vector<ShapeIntersection> _intersectSameEllipse(EllipticalArc const *other) const;
315
320}; // end class EllipticalArc
321
322
323// implemented in elliptical-arc-from-sbasis.cpp
326bool arc_from_sbasis(EllipticalArc &ea, D2<SBasis> const &in,
327 double tolerance = EPSILON, unsigned num_samples = 20);
328
331std::ostream &operator<<(std::ostream &out, EllipticalArc const &ea);
332
333} // end namespace Geom
334
335#endif // LIB2GEOM_SEEN_ELLIPTICAL_ARC_H
336
337/*
338 Local Variables:
339 mode:c++
340 c-file-style:"stroustrup"
341 c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
342 indent-tabs-mode:nil
343 fill-column:99
344 End:
345*/
346// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:fileencoding=utf-8:textwidth=99 :
Abstract curve type.
Various utility functions.
3x3 affine transformation matrix.
Various trigoniometric helper functions.
Bezier curve.
3x3 matrix representing an affine transformation.
Definition affine.h:70
Directed angular interval.
Definition angle.h:188
void setSweep(bool s)
Set whether the interval goes in the direction of increasing angles.
Definition angle.h:272
Angle finalAngle() const
Get the end angle.
Definition angle.h:231
bool sweep() const
Check whether the interval goes in the direction of increasing angles.
Definition angle.h:233
Coord sweepAngle() const
Get the sweep angle of the interval.
Definition angle.h:352
Angle angleAt(Coord t) const
Get an angle corresponding to the specified time value.
Definition angle.h:288
Coord timeAtAngle(Angle a) const
Compute a time value that would evaluate to the given angle.
Definition angle.h:299
Coord extent() const
Extent of the angle interval.
Definition angle.h:342
Angle initialAngle() const
Get the start angle.
Definition angle.h:229
bool contains(Angle a) const
Check whether the interval includes the given angle.
Definition angle.h:326
Wrapper for angular values.
Definition angle.h:73
Abstract continuous curve on a plane defined on [0,1].
Definition curve.h:78
void transform(Affine const &m)
Transform this curve by an affine transformation.
Definition curve.h:193
Adaptor that creates 2D functions from 1D ones.
Definition d2.h:55
Set of points with a constant sum of distances from two foci.
Definition ellipse.h:68
void setRays(Point const &p)
Set both rays of the ellipse.
Definition ellipse.h:111
void setRotationAngle(Angle a)
Set the angle the X ray makes with the +X axis.
Definition ellipse.h:117
Angle rotationAngle() const
Get the angle the X ray makes with the +X axis.
Definition ellipse.h:126
Affine unitCircleTransform() const
Compute the transform that maps the unit circle to this ellipse.
Definition ellipse.cpp:110
Affine inverseUnitCircleTransform() const
Compute the transform that maps this ellipse to the unit circle.
Definition ellipse.cpp:117
Coord ray(Dim2 d) const
Get one ray of the ellipse.
Definition ellipse.h:124
Point rays() const
Get both rays as a point.
Definition ellipse.h:122
Point center() const
Definition ellipse.h:119
Elliptical arc curve.
Coord timeAtAngle(Angle a) const
Compute the curve time value corresponding to the given angular value.
int degreesOfFreedom() const override
Return the number of independent parameters required to represent all variations of this curve.
bool isDegenerate() const override
Check whether the curve has exactly zero length.
Rect boundsFast() const override
Quickly compute the curve's approximate bounding box.
bool containsAngle(Angle angle) const
Check whether the arc contains the given angle.
Angle initialAngle() const
std::vector< double > roots(double v, Dim2 d) const override
Computes time values at which the curve intersects an axis-aligned line.
D2< SBasis > toSBasis() const override
Convert the curve to a symmetric power basis polynomial.
bool isLineSegment() const override
Check whether the curve is a line segment.
Point pointAt(Coord t) const override
Evaluate the arc in the curve domain, i.e. .
void set(Point const &ip, double rx, double ry, double rot_angle, bool large_arc, bool sweep, Point const &fp)
Change all of the arc's parameters.
AngleInterval _angles
AngleInterval angularInterval() const
Get the angular interval of the arc.
Point finalPoint() const override
Retrieve the end of the curve.
Coord valueAt(Coord t, Dim2 d) const override
Evaluate a single coordinate on the arc in the curve domain.
double nearestTime(Point const &p, double from=0, double to=1) const override
Compute a time value at which the curve comes closest to a specified point.
Curve * reverse() const override
Create a reversed version of this curve.
std::vector< Point > pointAndDerivatives(Coord t, unsigned int n) const override
int winding(Point const &p) const override
Compute the partial winding number of this curve.
Rect boundsExact() const override
Compute bounds of an elliptical arc.
Curve * duplicate() const override
Create an exact copy of this curve.
EllipticalArc(Point const &ip, Coord rx, Coord ry, Coord rot_angle, bool large_arc, bool sweep, Point const &fp)
Create a new elliptical arc, giving the ellipse's rays as separate coordinates.
Affine inverseUnitCircleTransform() const
Compute a transform that maps the arc's ellipse to the unit circle.
void feed(PathSink &sink, bool moveto_initial) const override
Feed the curve to a PathSink.
bool largeArc() const
Whether the arc is larger than half an ellipse.
Point initialPoint() const override
Retrieve the start of the curve.
void setFinal(Point const &p) override
Change the ending point of the curve.
void setEndpoints(Point const &ip, Point const &fp)
Change the initial and final point in one operation.
OptRect boundsLocal(OptInterval const &i, unsigned int deg) const override
Coord angularExtent() const
Get the elliptical angle spanned by the arc.
LineSegment chord() const
Get the line segment connecting the arc's endpoints.
Angle rotationAngle() const
Get the defining ellipse's rotation.
bool _validateIntersection(ShapeIntersection &xing, bool is_first) const
Convert the passed intersection to curve time and check whether the intersection is numerically sane.
std::vector< ShapeIntersection > _intersectSameEllipse(EllipticalArc const *other) const
Check if two arcs on the same ellipse intersect/overlap.
bool isChord() const
Check whether both rays are nonzero.
void expandToTransformed(Rect &bbox, Affine const &transform) const override
Expand the given rectangle to include the transformed curve, assuming it already contains its initial...
void set(Point const &ip, Point const &r, Angle rot_angle, bool large_arc, bool sweep, Point const &fp)
Change all of the arc's parameters.
Point rays() const
Get both rays as a point.
Affine unitCircleTransform() const
Compute a transform that maps the unit circle to the arc's ellipse.
std::vector< CurveIntersection > intersect(Curve const &other, Coord eps=EPSILON) const override
Compute intersections with another curve.
Curve * derivative() const override
Create a derivative of this curve.
Angle angleAt(Coord t) const
Compute the angular domain value corresponding to the given time value.
void operator*=(Translate const &tr) override
Point pointAtAngle(Coord t) const
Evaluate the arc at the specified angular coordinate.
EllipticalArc()
Creates an arc with all variables set to zero.
void setInitial(Point const &p) override
Change the starting point of the curve.
Coord center(Dim2 d) const
Get a coordinate of the elliptical arc's center.
Coord ray(Dim2 d) const
Get one of the ellipse's rays.
Coord sweepAngle() const
Compute the amount by which the angle parameter changes going from start to end.
bool _equalTo(Curve const &c) const override
bool sweep() const
Whether the arc turns clockwise.
Point center() const
Get the arc's center.
Coord valueAtAngle(Coord t, Dim2 d) const
Evaluate one of the arc's coordinates at the specified angle.
Angle finalAngle() const
std::vector< ShapeIntersection > _filterIntersections(std::vector< ShapeIntersection > &&xs, bool is_first) const
Convert the passed intersections to curve time parametrization and filter out any invalid intersectio...
Curve * portion(double f, double t) const override
Create a curve that corresponds to a part of this curve.
std::vector< double > allNearestTimes(Point const &p, double from=0, double to=1) const override
Compute time values at which the curve comes closest to a specified point.
bool isNear(Curve const &other, Coord precision) const override
Test whether two curves are approximately the same.
EllipticalArc(Point const &ip, Point const &r, Coord rot_angle, bool large_arc, bool sweep, Point const &fp)
Create a new elliptical arc.
Intersection between two shapes.
Range of real numbers that can be empty.
Definition interval.h:199
Axis-aligned rectangle that can be empty.
Definition rect.h:203
Callback interface for processing path data.
Definition path-sink.h:56
Two-dimensional point that doubles as a vector.
Definition point.h:66
Axis aligned, non-empty rectangle.
Definition rect.h:92
Rotation around the origin.
Definition transforms.h:187
Symmetric power basis curve.
OptRect boundsLocal(OptInterval const &i, unsigned deg) const override
Scaling from the origin.
Definition transforms.h:150
Translation by a vector.
Definition transforms.h:115
Combination of a translation and uniform scale.
Definition transforms.h:292
Css & result
double c[8][4]
Ellipse shape.
BezierCurveN< 1 > LineSegment
Line segment.
Dim2
2D axis enumeration (X or Y).
Definition coord.h:48
double Coord
Floating point type used to store coordinates.
Definition coord.h:76
constexpr Coord EPSILON
Default "acceptably small" value.
Definition coord.h:84
@ Y
Definition coord.h:48
@ X
Definition coord.h:48
Various utility functions.
Definition affine.h:22
std::ostream & operator<<(std::ostream &os, const Bezier &b)
Definition bezier.h:372
bool arc_from_sbasis(EllipticalArc &ea, D2< SBasis > const &in, double tolerance, unsigned num_samples)
bool are_near(Affine const &a1, Affine const &a2, Coord eps=EPSILON)
Symmetric power basis curve.