OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2012 Google Inc. | 2 * Copyright 2012 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 #ifndef SkIntersections_DEFINE | 7 #ifndef SkIntersections_DEFINE |
8 #define SkIntersections_DEFINE | 8 #define SkIntersections_DEFINE |
9 | 9 |
10 #include "SkPathOpsCubic.h" | 10 #include "SkPathOpsCubic.h" |
11 #include "SkPathOpsLine.h" | 11 #include "SkPathOpsLine.h" |
12 #include "SkPathOpsPoint.h" | 12 #include "SkPathOpsPoint.h" |
13 #include "SkPathOpsQuad.h" | 13 #include "SkPathOpsQuad.h" |
14 | 14 |
15 class SkIntersections { | 15 class SkIntersections { |
16 public: | 16 public: |
17 SkIntersections() | 17 SkIntersections() |
18 : fSwap(0) | 18 : fSwap(0) |
19 #ifdef SK_DEBUG | 19 #ifdef SK_DEBUG |
20 , fDepth(0) | 20 , fDepth(0) |
21 #endif | 21 #endif |
22 { | 22 { |
23 sk_bzero(fPt, sizeof(fPt)); | 23 sk_bzero(fPt, sizeof(fPt)); |
| 24 sk_bzero(fPt2, sizeof(fPt2)); |
24 sk_bzero(fT, sizeof(fT)); | 25 sk_bzero(fT, sizeof(fT)); |
25 sk_bzero(fIsCoincident, sizeof(fIsCoincident)); | 26 sk_bzero(fIsCoincident, sizeof(fIsCoincident)); |
| 27 sk_bzero(fNearlySame, sizeof(fNearlySame)); |
26 reset(); | 28 reset(); |
27 fMax = 0; // require that the caller set the max | 29 fMax = 0; // require that the caller set the max |
28 } | 30 } |
29 | 31 |
30 class TArray { | 32 class TArray { |
31 public: | 33 public: |
32 explicit TArray(const double ts[9]) : fTArray(ts) {} | 34 explicit TArray(const double ts[9]) : fTArray(ts) {} |
33 double operator[](int n) const { | 35 double operator[](int n) const { |
34 return fTArray[n]; | 36 return fTArray[n]; |
35 } | 37 } |
36 const double* fTArray; | 38 const double* fTArray; |
37 }; | 39 }; |
38 TArray operator[](int n) const { return TArray(fT[n]); } | 40 TArray operator[](int n) const { return TArray(fT[n]); } |
39 | 41 |
40 void set(const SkIntersections& i) { | |
41 memcpy(fPt, i.fPt, sizeof(fPt)); | |
42 memcpy(fT, i.fT, sizeof(fT)); | |
43 memcpy(fIsCoincident, i.fIsCoincident, sizeof(fIsCoincident)); | |
44 fUsed = i.fUsed; | |
45 fMax = i.fMax; | |
46 fSwap = i.fSwap; | |
47 SkDEBUGCODE(fDepth = i.fDepth); | |
48 } | |
49 | |
50 void allowNear(bool nearAllowed) { | 42 void allowNear(bool nearAllowed) { |
51 fAllowNear = nearAllowed; | 43 fAllowNear = nearAllowed; |
52 } | 44 } |
53 | 45 |
54 int cubic(const SkPoint a[4]) { | 46 int cubic(const SkPoint a[4]) { |
55 SkDCubic cubic; | 47 SkDCubic cubic; |
56 cubic.set(a); | 48 cubic.set(a); |
57 fMax = 1; // self intersect | 49 fMax = 1; // self intersect |
58 return intersect(cubic); | 50 return intersect(cubic); |
59 } | 51 } |
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
133 } | 125 } |
134 | 126 |
135 int lineLine(const SkPoint a[2], const SkPoint b[2]) { | 127 int lineLine(const SkPoint a[2], const SkPoint b[2]) { |
136 SkDLine aLine, bLine; | 128 SkDLine aLine, bLine; |
137 aLine.set(a); | 129 aLine.set(a); |
138 bLine.set(b); | 130 bLine.set(b); |
139 fMax = 2; | 131 fMax = 2; |
140 return intersect(aLine, bLine); | 132 return intersect(aLine, bLine); |
141 } | 133 } |
142 | 134 |
| 135 bool nearlySame(int index) const { |
| 136 SkASSERT(index == 0 || index == 1); |
| 137 return fNearlySame[index]; |
| 138 } |
| 139 |
143 const SkDPoint& pt(int index) const { | 140 const SkDPoint& pt(int index) const { |
144 return fPt[index]; | 141 return fPt[index]; |
145 } | 142 } |
146 | 143 |
| 144 const SkDPoint& pt2(int index) const { |
| 145 return fPt2[index]; |
| 146 } |
| 147 |
147 int quadHorizontal(const SkPoint a[3], SkScalar left, SkScalar right, SkScal
ar y, | 148 int quadHorizontal(const SkPoint a[3], SkScalar left, SkScalar right, SkScal
ar y, |
148 bool flipped) { | 149 bool flipped) { |
149 SkDQuad quad; | 150 SkDQuad quad; |
150 quad.set(a); | 151 quad.set(a); |
151 fMax = 2; | 152 fMax = 2; |
152 return horizontal(quad, left, right, y, flipped); | 153 return horizontal(quad, left, right, y, flipped); |
153 } | 154 } |
154 | 155 |
155 int quadVertical(const SkPoint a[3], SkScalar top, SkScalar bottom, SkScalar
x, bool flipped) { | 156 int quadVertical(const SkPoint a[3], SkScalar top, SkScalar bottom, SkScalar
x, bool flipped) { |
156 SkDQuad quad; | 157 SkDQuad quad; |
(...skipping 13 matching lines...) Expand all Loading... |
170 | 171 |
171 int quadQuad(const SkPoint a[3], const SkPoint b[3]) { | 172 int quadQuad(const SkPoint a[3], const SkPoint b[3]) { |
172 SkDQuad aQuad; | 173 SkDQuad aQuad; |
173 aQuad.set(a); | 174 aQuad.set(a); |
174 SkDQuad bQuad; | 175 SkDQuad bQuad; |
175 bQuad.set(b); | 176 bQuad.set(b); |
176 fMax = 4; | 177 fMax = 4; |
177 return intersect(aQuad, bQuad); | 178 return intersect(aQuad, bQuad); |
178 } | 179 } |
179 | 180 |
180 // leaves flip, swap, max alone | 181 // leaves swap, max alone |
181 void reset() { | 182 void reset() { |
182 fAllowNear = true; | 183 fAllowNear = true; |
183 fUsed = 0; | 184 fUsed = 0; |
184 } | 185 } |
185 | 186 |
| 187 void set(bool swap, int tIndex, double t) { |
| 188 fT[(int) swap][tIndex] = t; |
| 189 } |
| 190 |
186 void setMax(int max) { | 191 void setMax(int max) { |
187 fMax = max; | 192 fMax = max; |
188 } | 193 } |
189 | 194 |
190 void swap() { | 195 void swap() { |
191 fSwap ^= true; | 196 fSwap ^= true; |
192 } | 197 } |
193 | 198 |
194 void swapPts(); | 199 void swapPts(); |
195 | 200 |
196 bool swapped() const { | 201 bool swapped() const { |
197 return fSwap; | 202 return fSwap; |
198 } | 203 } |
199 | 204 |
200 int used() const { | 205 int used() const { |
201 return fUsed; | 206 return fUsed; |
202 } | 207 } |
203 | 208 |
204 void downDepth() { | 209 void downDepth() { |
205 SkASSERT(--fDepth >= 0); | 210 SkASSERT(--fDepth >= 0); |
206 } | 211 } |
207 | 212 |
208 void upDepth() { | 213 void upDepth() { |
209 SkASSERT(++fDepth < 16); | 214 SkASSERT(++fDepth < 16); |
210 } | 215 } |
211 | 216 |
212 void append(const SkIntersections& ); | 217 void append(const SkIntersections& ); |
213 void cleanUpCoincidence(); | 218 void cleanUpCoincidence(); |
214 int coincidentUsed() const; | 219 int coincidentUsed() const; |
| 220 void cubicInsert(double one, double two, const SkDPoint& pt, const SkDCubic&
c1, |
| 221 const SkDCubic& c2); |
215 int cubicRay(const SkPoint pts[4], const SkDLine& line); | 222 int cubicRay(const SkPoint pts[4], const SkDLine& line); |
216 void flip(); | 223 void flip(); |
217 int horizontal(const SkDLine&, double y); | 224 int horizontal(const SkDLine&, double y); |
218 int horizontal(const SkDLine&, double left, double right, double y, bool fli
pped); | 225 int horizontal(const SkDLine&, double left, double right, double y, bool fli
pped); |
219 int horizontal(const SkDQuad&, double left, double right, double y, bool fli
pped); | 226 int horizontal(const SkDQuad&, double left, double right, double y, bool fli
pped); |
220 int horizontal(const SkDQuad&, double left, double right, double y, double t
Range[2]); | 227 int horizontal(const SkDQuad&, double left, double right, double y, double t
Range[2]); |
221 int horizontal(const SkDCubic&, double y, double tRange[3]); | 228 int horizontal(const SkDCubic&, double y, double tRange[3]); |
222 int horizontal(const SkDCubic&, double left, double right, double y, bool fl
ipped); | 229 int horizontal(const SkDCubic&, double left, double right, double y, bool fl
ipped); |
223 int horizontal(const SkDCubic&, double left, double right, double y, double
tRange[3]); | 230 int horizontal(const SkDCubic&, double left, double right, double y, double
tRange[3]); |
224 // FIXME : does not respect swap | 231 // FIXME : does not respect swap |
225 int insert(double one, double two, const SkDPoint& pt); | 232 int insert(double one, double two, const SkDPoint& pt); |
226 void insertNear(double one, double two, const SkDPoint& pt); | 233 void insertNear(double one, double two, const SkDPoint& pt1, const SkDPoint&
pt2); |
227 // start if index == 0 : end if index == 1 | 234 // start if index == 0 : end if index == 1 |
228 void insertCoincident(double one, double two, const SkDPoint& pt); | 235 void insertCoincident(double one, double two, const SkDPoint& pt); |
229 int intersect(const SkDLine&, const SkDLine&); | 236 int intersect(const SkDLine&, const SkDLine&); |
230 int intersect(const SkDQuad&, const SkDLine&); | 237 int intersect(const SkDQuad&, const SkDLine&); |
231 int intersect(const SkDQuad&, const SkDQuad&); | 238 int intersect(const SkDQuad&, const SkDQuad&); |
232 int intersect(const SkDCubic&); // return true if cubic self-intersects | 239 int intersect(const SkDCubic&); // return true if cubic self-intersects |
233 int intersect(const SkDCubic&, const SkDLine&); | 240 int intersect(const SkDCubic&, const SkDLine&); |
234 int intersect(const SkDCubic&, const SkDQuad&); | 241 int intersect(const SkDCubic&, const SkDQuad&); |
235 int intersect(const SkDCubic&, const SkDCubic&); | 242 int intersect(const SkDCubic&, const SkDCubic&); |
236 int intersectRay(const SkDLine&, const SkDLine&); | 243 int intersectRay(const SkDLine&, const SkDLine&); |
(...skipping 23 matching lines...) Expand all Loading... |
260 } | 267 } |
261 | 268 |
262 private: | 269 private: |
263 bool cubicCheckCoincidence(const SkDCubic& c1, const SkDCubic& c2); | 270 bool cubicCheckCoincidence(const SkDCubic& c1, const SkDCubic& c2); |
264 bool cubicExactEnd(const SkDCubic& cubic1, bool start, const SkDCubic& cubic
2); | 271 bool cubicExactEnd(const SkDCubic& cubic1, bool start, const SkDCubic& cubic
2); |
265 void cubicNearEnd(const SkDCubic& cubic1, bool start, const SkDCubic& cubic2
, const SkDRect& ); | 272 void cubicNearEnd(const SkDCubic& cubic1, bool start, const SkDCubic& cubic2
, const SkDRect& ); |
266 void cleanUpParallelLines(bool parallel); | 273 void cleanUpParallelLines(bool parallel); |
267 void computePoints(const SkDLine& line, int used); | 274 void computePoints(const SkDLine& line, int used); |
268 | 275 |
269 SkDPoint fPt[9]; // FIXME: since scans store points as SkPoint, this should
also | 276 SkDPoint fPt[9]; // FIXME: since scans store points as SkPoint, this should
also |
| 277 SkDPoint fPt2[9]; // used by nearly same to store alternate intersection po
int |
270 double fT[2][9]; | 278 double fT[2][9]; |
271 uint16_t fIsCoincident[2]; // bit set for each curve's coincident T | 279 uint16_t fIsCoincident[2]; // bit set for each curve's coincident T |
| 280 bool fNearlySame[2]; // true if end points nearly match |
272 unsigned char fUsed; | 281 unsigned char fUsed; |
273 unsigned char fMax; | 282 unsigned char fMax; |
274 bool fAllowNear; | 283 bool fAllowNear; |
275 bool fSwap; | 284 bool fSwap; |
276 #ifdef SK_DEBUG | 285 #ifdef SK_DEBUG |
277 int fDepth; | 286 int fDepth; |
278 #endif | 287 #endif |
279 }; | 288 }; |
280 | 289 |
281 extern int (SkIntersections::*CurveRay[])(const SkPoint[], const SkDLine& ); | 290 extern int (SkIntersections::*CurveRay[])(const SkPoint[], const SkDLine& ); |
282 extern int (SkIntersections::*CurveVertical[])(const SkPoint[], SkScalar top, Sk
Scalar bottom, | 291 extern int (SkIntersections::*CurveVertical[])(const SkPoint[], SkScalar top, Sk
Scalar bottom, |
283 SkScalar x, bool flipped); | 292 SkScalar x, bool flipped); |
284 | 293 |
285 #endif | 294 #endif |
OLD | NEW |