1 /*
2 * Copyright 2014 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8 #include "include/core/SkString.h"
9 #include "include/private/SkMutex.h"
10 #include "src/pathops/SkIntersectionHelper.h"
11 #include "src/pathops/SkOpCoincidence.h"
12 #include "src/pathops/SkOpContour.h"
13 #include "src/pathops/SkOpSegment.h"
14 #include "tests/PathOpsDebug.h"
15 #include "tests/PathOpsTSectDebug.h"
16
17 bool PathOpsDebug::gJson;
18 bool PathOpsDebug::gMarkJsonFlaky;
19 bool PathOpsDebug::gOutFirst;
20 bool PathOpsDebug::gCheckForDuplicateNames;
21 bool PathOpsDebug::gOutputSVG;
22 FILE* PathOpsDebug::gOut;
23
DebugDumpDouble(double x)24 inline void DebugDumpDouble(double x) {
25 if (x == floor(x)) {
26 SkDebugf("%.0f", x);
27 } else {
28 SkDebugf("%1.19g", x);
29 }
30 }
31
DebugDumpFloat(float x)32 inline void DebugDumpFloat(float x) {
33 if (x == floorf(x)) {
34 SkDebugf("%.0f", x);
35 } else {
36 SkDebugf("%1.9gf", x);
37 }
38 }
39
DebugDumpHexFloat(float x)40 inline void DebugDumpHexFloat(float x) {
41 SkDebugf("SkBits2Float(0x%08x)", SkFloat2Bits(x));
42 }
43
44 // if not defined by PathOpsDebug.cpp ...
45 #if !defined SK_DEBUG && FORCE_RELEASE
ValidWind(int wind)46 bool SkPathOpsDebug::ValidWind(int wind) {
47 return wind > SK_MinS32 + 0xFFFF && wind < SK_MaxS32 - 0xFFFF;
48 }
49
WindingPrintf(int wind)50 void SkPathOpsDebug::WindingPrintf(int wind) {
51 if (wind == SK_MinS32) {
52 SkDebugf("?");
53 } else {
54 SkDebugf("%d", wind);
55 }
56 }
57 #endif
58
DumpID(int id)59 static void DumpID(int id) {
60 SkDebugf("} ");
61 if (id >= 0) {
62 SkDebugf("id=%d", id);
63 }
64 SkDebugf("\n");
65 }
66
dump() const67 void SkDConic::dump() const {
68 dumpInner();
69 SkDebugf("},\n");
70 }
71
dumpID(int id) const72 void SkDConic::dumpID(int id) const {
73 dumpInner();
74 DumpID(id);
75 }
76
dumpInner() const77 void SkDConic::dumpInner() const {
78 SkDebugf("{");
79 fPts.dumpInner();
80 SkDebugf("}}, %1.9gf", fWeight);
81 }
82
dump() const83 void SkDCubic::dump() const {
84 this->dumpInner();
85 SkDebugf("}},\n");
86 }
87
dumpID(int id) const88 void SkDCubic::dumpID(int id) const {
89 this->dumpInner();
90 SkDebugf("}");
91 DumpID(id);
92 }
93
double_is_NaN(double x)94 static inline bool double_is_NaN(double x) { return x != x; }
95
dumpInner() const96 void SkDCubic::dumpInner() const {
97 SkDebugf("{{");
98 int index = 0;
99 do {
100 if (index != 0) {
101 if (double_is_NaN(fPts[index].fX) && double_is_NaN(fPts[index].fY)) {
102 return;
103 }
104 SkDebugf(", ");
105 }
106 fPts[index].dump();
107 } while (++index < 3);
108 if (double_is_NaN(fPts[index].fX) && double_is_NaN(fPts[index].fY)) {
109 return;
110 }
111 SkDebugf(", ");
112 fPts[index].dump();
113 }
114
dump() const115 void SkDCurve::dump() const {
116 dumpID(-1);
117 }
118
dumpID(int id) const119 void SkDCurve::dumpID(int id) const {
120 #ifndef SK_RELEASE
121 switch(fVerb) {
122 case SkPath::kLine_Verb:
123 fLine.dumpID(id);
124 break;
125 case SkPath::kQuad_Verb:
126 fQuad.dumpID(id);
127 break;
128 case SkPath::kConic_Verb:
129 fConic.dumpID(id);
130 break;
131 case SkPath::kCubic_Verb:
132 fCubic.dumpID(id);
133 break;
134 default:
135 SkASSERT(0);
136 }
137 #else
138 fCubic.dumpID(id);
139 #endif
140 }
141
dump() const142 void SkDLine::dump() const {
143 this->dumpInner();
144 SkDebugf("}},\n");
145 }
146
dumpID(int id) const147 void SkDLine::dumpID(int id) const {
148 this->dumpInner();
149 SkDebugf("}");
150 DumpID(id);
151 }
152
dumpInner() const153 void SkDLine::dumpInner() const {
154 SkDebugf("{{");
155 fPts[0].dump();
156 SkDebugf(", ");
157 fPts[1].dump();
158 }
159
dump() const160 void SkDPoint::dump() const {
161 SkDebugf("{");
162 DebugDumpDouble(fX);
163 SkDebugf(", ");
164 DebugDumpDouble(fY);
165 SkDebugf("}");
166 }
167
Dump(const SkPoint & pt)168 void SkDPoint::Dump(const SkPoint& pt) {
169 SkDebugf("{");
170 DebugDumpFloat(pt.fX);
171 SkDebugf(", ");
172 DebugDumpFloat(pt.fY);
173 SkDebugf("}");
174 }
175
DumpHex(const SkPoint & pt)176 void SkDPoint::DumpHex(const SkPoint& pt) {
177 SkDebugf("{");
178 DebugDumpHexFloat(pt.fX);
179 SkDebugf(", ");
180 DebugDumpHexFloat(pt.fY);
181 SkDebugf("}");
182 }
183
dump() const184 void SkDQuad::dump() const {
185 dumpInner();
186 SkDebugf("}},\n");
187 }
188
dumpID(int id) const189 void SkDQuad::dumpID(int id) const {
190 dumpInner();
191 SkDebugf("}");
192 DumpID(id);
193 }
194
dumpInner() const195 void SkDQuad::dumpInner() const {
196 SkDebugf("{{");
197 int index = 0;
198 do {
199 fPts[index].dump();
200 SkDebugf(", ");
201 } while (++index < 2);
202 fPts[index].dump();
203 }
204
dump() const205 void SkIntersections::dump() const {
206 SkDebugf("used=%d of %d", fUsed, fMax);
207 for (int index = 0; index < fUsed; ++index) {
208 SkDebugf(" t=(%s%1.9g,%s%1.9g) pt=(%1.9g,%1.9g)",
209 fIsCoincident[0] & (1 << index) ? "*" : "", fT[0][index],
210 fIsCoincident[1] & (1 << index) ? "*" : "", fT[1][index],
211 fPt[index].fX, fPt[index].fY);
212 if (index < 2 && fNearlySame[index]) {
213 SkDebugf(" pt2=(%1.9g,%1.9g)",fPt2[index].fX, fPt2[index].fY);
214 }
215 }
216 SkDebugf("\n");
217 }
218
AngleAngle(const SkOpAngle * angle,int id)219 const SkOpAngle* AngleAngle(const SkOpAngle* angle, int id) {
220 return angle->debugAngle(id);
221 }
222
AngleContour(SkOpAngle * angle,int id)223 SkOpContour* AngleContour(SkOpAngle* angle, int id) {
224 return angle->debugContour(id);
225 }
226
AnglePtT(const SkOpAngle * angle,int id)227 const SkOpPtT* AnglePtT(const SkOpAngle* angle, int id) {
228 return angle->debugPtT(id);
229 }
230
AngleSegment(const SkOpAngle * angle,int id)231 const SkOpSegment* AngleSegment(const SkOpAngle* angle, int id) {
232 return angle->debugSegment(id);
233 }
234
AngleSpan(const SkOpAngle * angle,int id)235 const SkOpSpanBase* AngleSpan(const SkOpAngle* angle, int id) {
236 return angle->debugSpan(id);
237 }
238
ContourAngle(SkOpContour * contour,int id)239 const SkOpAngle* ContourAngle(SkOpContour* contour, int id) {
240 return contour->debugAngle(id);
241 }
242
ContourContour(SkOpContour * contour,int id)243 SkOpContour* ContourContour(SkOpContour* contour, int id) {
244 return contour->debugContour(id);
245 }
246
ContourPtT(SkOpContour * contour,int id)247 const SkOpPtT* ContourPtT(SkOpContour* contour, int id) {
248 return contour->debugPtT(id);
249 }
250
ContourSegment(SkOpContour * contour,int id)251 const SkOpSegment* ContourSegment(SkOpContour* contour, int id) {
252 return contour->debugSegment(id);
253 }
254
ContourSpan(SkOpContour * contour,int id)255 const SkOpSpanBase* ContourSpan(SkOpContour* contour, int id) {
256 return contour->debugSpan(id);
257 }
258
CoincidenceAngle(SkOpCoincidence * coin,int id)259 const SkOpAngle* CoincidenceAngle(SkOpCoincidence* coin, int id) {
260 return coin->debugAngle(id);
261 }
262
CoincidenceContour(SkOpCoincidence * coin,int id)263 SkOpContour* CoincidenceContour(SkOpCoincidence* coin, int id) {
264 return coin->debugContour(id);
265 }
266
CoincidencePtT(SkOpCoincidence * coin,int id)267 const SkOpPtT* CoincidencePtT(SkOpCoincidence* coin, int id) {
268 return coin->debugPtT(id);
269 }
270
CoincidenceSegment(SkOpCoincidence * coin,int id)271 const SkOpSegment* CoincidenceSegment(SkOpCoincidence* coin, int id) {
272 return coin->debugSegment(id);
273 }
274
CoincidenceSpan(SkOpCoincidence * coin,int id)275 const SkOpSpanBase* CoincidenceSpan(SkOpCoincidence* coin, int id) {
276 return coin->debugSpan(id);
277 }
278
PtTAngle(const SkOpPtT * ptT,int id)279 const SkOpAngle* PtTAngle(const SkOpPtT* ptT, int id) {
280 return ptT->debugAngle(id);
281 }
282
PtTContour(SkOpPtT * ptT,int id)283 SkOpContour* PtTContour(SkOpPtT* ptT, int id) {
284 return ptT->debugContour(id);
285 }
286
PtTPtT(const SkOpPtT * ptT,int id)287 const SkOpPtT* PtTPtT(const SkOpPtT* ptT, int id) {
288 return ptT->debugPtT(id);
289 }
290
PtTSegment(const SkOpPtT * ptT,int id)291 const SkOpSegment* PtTSegment(const SkOpPtT* ptT, int id) {
292 return ptT->debugSegment(id);
293 }
294
PtTSpan(const SkOpPtT * ptT,int id)295 const SkOpSpanBase* PtTSpan(const SkOpPtT* ptT, int id) {
296 return ptT->debugSpan(id);
297 }
298
SegmentAngle(const SkOpSegment * span,int id)299 const SkOpAngle* SegmentAngle(const SkOpSegment* span, int id) {
300 return span->debugAngle(id);
301 }
302
SegmentContour(SkOpSegment * span,int id)303 SkOpContour* SegmentContour(SkOpSegment* span, int id) {
304 return span->debugContour(id);
305 }
306
SegmentPtT(const SkOpSegment * span,int id)307 const SkOpPtT* SegmentPtT(const SkOpSegment* span, int id) {
308 return span->debugPtT(id);
309 }
310
SegmentSegment(const SkOpSegment * span,int id)311 const SkOpSegment* SegmentSegment(const SkOpSegment* span, int id) {
312 return span->debugSegment(id);
313 }
314
SegmentSpan(const SkOpSegment * span,int id)315 const SkOpSpanBase* SegmentSpan(const SkOpSegment* span, int id) {
316 return span->debugSpan(id);
317 }
318
SpanAngle(const SkOpSpanBase * span,int id)319 const SkOpAngle* SpanAngle(const SkOpSpanBase* span, int id) {
320 return span->debugAngle(id);
321 }
322
SpanContour(SkOpSpanBase * span,int id)323 SkOpContour* SpanContour(SkOpSpanBase* span, int id) {
324 return span->debugContour(id);
325 }
326
SpanPtT(const SkOpSpanBase * span,int id)327 const SkOpPtT* SpanPtT(const SkOpSpanBase* span, int id) {
328 return span->debugPtT(id);
329 }
330
SpanSegment(const SkOpSpanBase * span,int id)331 const SkOpSegment* SpanSegment(const SkOpSpanBase* span, int id) {
332 return span->debugSegment(id);
333 }
334
SpanSpan(const SkOpSpanBase * span,int id)335 const SkOpSpanBase* SpanSpan(const SkOpSpanBase* span, int id) {
336 return span->debugSpan(id);
337 }
338
339 #if DEBUG_COIN
DumpCoinDict()340 void SkPathOpsDebug::DumpCoinDict() {
341 SkPathOpsDebug::gCoinSumChangedDict.dump("unused coin algorithm", false);
342 SkPathOpsDebug::gCoinSumVisitedDict.dump("visited coin function", true);
343 }
344
dump(const char * str,bool visitCheck) const345 void SkPathOpsDebug::CoinDict::dump(const char* str, bool visitCheck) const {
346 int count = fDict.count();
347 for (int index = 0; index < count; ++index) {
348 const auto& entry = fDict[index];
349 if (visitCheck || entry.fGlitchType == kUninitialized_Glitch) {
350 SkDebugf("%s %s : line %d iteration %d", str, entry.fFunctionName,
351 entry.fLineNumber, entry.fIteration);
352 DumpGlitchType(entry.fGlitchType);
353 SkDebugf("\n");
354 }
355 }
356 }
357 #endif
358
dumpContours() const359 void SkOpContour::dumpContours() const {
360 SkOpContour* contour = this->globalState()->contourHead();
361 do {
362 contour->dump();
363 } while ((contour = contour->next()));
364 }
365
dumpContoursAll() const366 void SkOpContour::dumpContoursAll() const {
367 SkOpContour* contour = this->globalState()->contourHead();
368 do {
369 contour->dumpAll();
370 } while ((contour = contour->next()));
371 }
372
dumpContoursAngles() const373 void SkOpContour::dumpContoursAngles() const {
374 SkOpContour* contour = this->globalState()->contourHead();
375 do {
376 contour->dumpAngles();
377 } while ((contour = contour->next()));
378 }
379
dumpContoursPts() const380 void SkOpContour::dumpContoursPts() const {
381 SkOpContour* contour = this->globalState()->contourHead();
382 do {
383 contour->dumpPts();
384 } while ((contour = contour->next()));
385 }
386
dumpContoursPt(int segmentID) const387 void SkOpContour::dumpContoursPt(int segmentID) const {
388 SkOpContour* contour = this->globalState()->contourHead();
389 do {
390 contour->dumpPt(segmentID);
391 } while ((contour = contour->next()));
392 }
393
dumpContoursSegment(int segmentID) const394 void SkOpContour::dumpContoursSegment(int segmentID) const {
395 SkOpContour* contour = this->globalState()->contourHead();
396 do {
397 contour->dumpSegment(segmentID);
398 } while ((contour = contour->next()));
399 }
400
dumpContoursSpan(int spanID) const401 void SkOpContour::dumpContoursSpan(int spanID) const {
402 SkOpContour* contour = this->globalState()->contourHead();
403 do {
404 contour->dumpSpan(spanID);
405 } while ((contour = contour->next()));
406 }
407
dumpContoursSpans() const408 void SkOpContour::dumpContoursSpans() const {
409 SkOpContour* contour = this->globalState()->contourHead();
410 do {
411 contour->dumpSpans();
412 } while ((contour = contour->next()));
413 }
414
415 #ifdef SK_DEBUG
DebugSpan(const SkTSect * sect,int id)416 const SkTSpan* DebugSpan(const SkTSect* sect, int id) {
417 return sect->debugSpan(id);
418 }
419
DebugT(const SkTSect * sect,double t)420 const SkTSpan* DebugT(const SkTSect* sect, double t) {
421 return sect->debugT(t);
422 }
423 #endif
424
Dump(const SkTSect * sect)425 void Dump(const SkTSect* sect) {
426 sect->dump();
427 }
428
DumpBoth(SkTSect * sect1,SkTSect * sect2)429 void DumpBoth(SkTSect* sect1, SkTSect* sect2) {
430 sect1->dumpBoth(sect2);
431 }
432
DumpBounded(SkTSect * sect1,int id)433 void DumpBounded(SkTSect* sect1, int id) {
434 sect1->dumpBounded(id);
435 }
436
DumpBounds(SkTSect * sect1)437 void DumpBounds(SkTSect* sect1) {
438 sect1->dumpBounds();
439 }
440
DumpCoin(SkTSect * sect1)441 void DumpCoin(SkTSect* sect1) {
442 sect1->dumpCoin();
443 }
444
DumpCoinCurves(SkTSect * sect1)445 void DumpCoinCurves(SkTSect* sect1) {
446 sect1->dumpCoinCurves();
447 }
448
DumpCurves(const SkTSect * sect)449 void DumpCurves(const SkTSect* sect) {
450 sect->dumpCurves();
451 }
452
Dump(const SkTSpan * span)453 void Dump(const SkTSpan* span) {
454 span->dump();
455 }
456
DumpAll(const SkTSpan * span)457 void DumpAll(const SkTSpan* span) {
458 span->dumpAll();
459 }
460
DumpBounded(const SkTSpan * span)461 void DumpBounded(const SkTSpan* span) {
462 span->dumpBounded(0);
463 }
464
DumpCoin(const SkTSpan * span)465 void DumpCoin(const SkTSpan* span) {
466 span->dumpCoin();
467 }
468
dumpTestCase(const SkDQuad & quad1,const SkDQuad & quad2,int testNo)469 static void dumpTestCase(const SkDQuad& quad1, const SkDQuad& quad2, int testNo) {
470 SkDebugf("\n<div id=\"quad%d\">\n", testNo);
471 quad1.dumpInner();
472 SkDebugf("}}, ");
473 quad2.dump();
474 SkDebugf("</div>\n\n");
475 }
476
dumpTestTrailer()477 static void dumpTestTrailer() {
478 SkDebugf("</div>\n\n<script type=\"text/javascript\">\n\n");
479 SkDebugf(" var testDivs = [\n");
480 }
481
dumpTestList(int testNo,double min)482 static void dumpTestList(int testNo, double min) {
483 SkDebugf(" quad%d,", testNo);
484 if (min > 0) {
485 SkDebugf(" // %1.9g", min);
486 }
487 SkDebugf("\n");
488 }
489
DumpQ(const SkDQuad & quad1,const SkDQuad & quad2,int testNo)490 void DumpQ(const SkDQuad& quad1, const SkDQuad& quad2, int testNo) {
491 SkDebugf("\n");
492 dumpTestCase(quad1, quad2, testNo);
493 dumpTestTrailer();
494 dumpTestList(testNo, 0);
495 SkDebugf("\n");
496 }
497
DumpT(const SkDQuad & quad,double t)498 void DumpT(const SkDQuad& quad, double t) {
499 SkDLine line = {{quad.ptAtT(t), quad[0]}};
500 line.dump();
501 }
502
debugAngle(int id) const503 const SkOpAngle* SkOpAngle::debugAngle(int id) const {
504 return this->segment()->debugAngle(id);
505 }
506
debugCoincidence() const507 const SkOpCoincidence* SkOpAngle::debugCoincidence() const {
508 return this->segment()->debugCoincidence();
509 }
510
debugContour(int id) const511 SkOpContour* SkOpAngle::debugContour(int id) const {
512 return this->segment()->debugContour(id);
513 }
514
debugPtT(int id) const515 const SkOpPtT* SkOpAngle::debugPtT(int id) const {
516 return this->segment()->debugPtT(id);
517 }
518
debugSegment(int id) const519 const SkOpSegment* SkOpAngle::debugSegment(int id) const {
520 return this->segment()->debugSegment(id);
521 }
522
debugSign() const523 int SkOpAngle::debugSign() const {
524 SkASSERT(fStart->t() != fEnd->t());
525 return fStart->t() < fEnd->t() ? -1 : 1;
526 }
527
debugSpan(int id) const528 const SkOpSpanBase* SkOpAngle::debugSpan(int id) const {
529 return this->segment()->debugSpan(id);
530 }
531
dump() const532 void SkOpAngle::dump() const {
533 dumpOne(true);
534 SkDebugf("\n");
535 }
536
dumpOne(bool functionHeader) const537 void SkOpAngle::dumpOne(bool functionHeader) const {
538 // fSegment->debugValidate();
539 const SkOpSegment* segment = this->segment();
540 const SkOpSpan& mSpan = *fStart->starter(fEnd);
541 if (functionHeader) {
542 SkDebugf("%s ", __FUNCTION__);
543 }
544 SkDebugf("[%d", segment->debugID());
545 SkDebugf("/%d", debugID());
546 SkDebugf("] next=");
547 if (fNext) {
548 SkDebugf("%d", fNext->fStart->segment()->debugID());
549 SkDebugf("/%d", fNext->debugID());
550 } else {
551 SkDebugf("?");
552 }
553 SkDebugf(" sect=%d/%d ", fSectorStart, fSectorEnd);
554 SkDebugf(" s=%1.9g [%d] e=%1.9g [%d]", fStart->t(), fStart->debugID(),
555 fEnd->t(), fEnd->debugID());
556 SkDebugf(" sgn=%d windVal=%d", this->debugSign(), mSpan.windValue());
557
558 SkDebugf(" windSum=");
559 SkPathOpsDebug::WindingPrintf(mSpan.windSum());
560 if (mSpan.oppValue() != 0 || mSpan.oppSum() != SK_MinS32) {
561 SkDebugf(" oppVal=%d", mSpan.oppValue());
562 SkDebugf(" oppSum=");
563 SkPathOpsDebug::WindingPrintf(mSpan.oppSum());
564 }
565 if (mSpan.done()) {
566 SkDebugf(" done");
567 }
568 if (unorderable()) {
569 SkDebugf(" unorderable");
570 }
571 if (segment->operand()) {
572 SkDebugf(" operand");
573 }
574 }
575
dumpTo(const SkOpSegment * segment,const SkOpAngle * to) const576 void SkOpAngle::dumpTo(const SkOpSegment* segment, const SkOpAngle* to) const {
577 const SkOpAngle* first = this;
578 const SkOpAngle* next = this;
579 const char* indent = "";
580 do {
581 SkDebugf("%s", indent);
582 next->dumpOne(false);
583 if (segment == next->fStart->segment()) {
584 if (this == fNext) {
585 SkDebugf(" << from");
586 }
587 if (to == fNext) {
588 SkDebugf(" << to");
589 }
590 }
591 SkDebugf("\n");
592 indent = " ";
593 next = next->fNext;
594 } while (next && next != first);
595 }
596
dumpCurves() const597 void SkOpAngle::dumpCurves() const {
598 const SkOpAngle* first = this;
599 const SkOpAngle* next = this;
600 do {
601 next->fPart.fCurve.dumpID(next->segment()->debugID());
602 next = next->fNext;
603 } while (next && next != first);
604 }
605
dumpLoop() const606 void SkOpAngle::dumpLoop() const {
607 const SkOpAngle* first = this;
608 const SkOpAngle* next = this;
609 do {
610 next->dumpOne(false);
611 SkDebugf("\n");
612 next = next->fNext;
613 } while (next && next != first);
614 }
615
dumpTest() const616 void SkOpAngle::dumpTest() const {
617 const SkOpAngle* first = this;
618 const SkOpAngle* next = this;
619 do {
620 SkDebugf("{ ");
621 SkOpSegment* segment = next->segment();
622 segment->dumpPts();
623 SkDebugf(", %d, %1.9g, %1.9g, {} },\n", SkPathOpsVerbToPoints(segment->verb()) + 1,
624 next->start()->t(), next->end()->t());
625 next = next->fNext;
626 } while (next && next != first);
627 }
628
debugMatchID(int id) const629 bool SkOpPtT::debugMatchID(int id) const {
630 int limit = this->debugLoopLimit(false);
631 int loop = 0;
632 const SkOpPtT* ptT = this;
633 do {
634 if (ptT->debugID() == id) {
635 return true;
636 }
637 } while ((!limit || ++loop <= limit) && (ptT = ptT->next()) && ptT != this);
638 return false;
639 }
640
debugAngle(int id) const641 const SkOpAngle* SkOpPtT::debugAngle(int id) const {
642 return this->span()->debugAngle(id);
643 }
644
debugContour(int id) const645 SkOpContour* SkOpPtT::debugContour(int id) const {
646 return this->span()->debugContour(id);
647 }
648
debugCoincidence() const649 const SkOpCoincidence* SkOpPtT::debugCoincidence() const {
650 return this->span()->debugCoincidence();
651 }
652
debugPtT(int id) const653 const SkOpPtT* SkOpPtT::debugPtT(int id) const {
654 return this->span()->debugPtT(id);
655 }
656
debugSegment(int id) const657 const SkOpSegment* SkOpPtT::debugSegment(int id) const {
658 return this->span()->debugSegment(id);
659 }
660
debugSpan(int id) const661 const SkOpSpanBase* SkOpPtT::debugSpan(int id) const {
662 return this->span()->debugSpan(id);
663 }
664
dump() const665 void SkOpPtT::dump() const {
666 SkDebugf("seg=%d span=%d ptT=%d",
667 this->segment()->debugID(), this->span()->debugID(), this->debugID());
668 this->dumpBase();
669 SkDebugf("\n");
670 }
671
dumpAll() const672 void SkOpPtT::dumpAll() const {
673 contour()->indentDump();
674 const SkOpPtT* next = this;
675 int limit = debugLoopLimit(true);
676 int loop = 0;
677 do {
678 SkDebugf("%.*s", contour()->debugIndent(), " ");
679 SkDebugf("seg=%d span=%d ptT=%d",
680 next->segment()->debugID(), next->span()->debugID(), next->debugID());
681 next->dumpBase();
682 SkDebugf("\n");
683 if (limit && ++loop >= limit) {
684 SkDebugf("*** abort loop ***\n");
685 break;
686 }
687 } while ((next = next->fNext) && next != this);
688 contour()->outdentDump();
689 }
690
dumpBase() const691 void SkOpPtT::dumpBase() const {
692 SkDebugf(" t=%1.9g pt=(%1.9g,%1.9g)%s%s%s", this->fT, this->fPt.fX, this->fPt.fY,
693 this->fCoincident ? " coin" : "",
694 this->fDuplicatePt ? " dup" : "", this->fDeleted ? " deleted" : "");
695 }
696
debugAngle(int id) const697 const SkOpAngle* SkOpSpanBase::debugAngle(int id) const {
698 return this->segment()->debugAngle(id);
699 }
700
debugCoincidence() const701 const SkOpCoincidence* SkOpSpanBase::debugCoincidence() const {
702 return this->segment()->debugCoincidence();
703 }
704
debugContour(int id) const705 SkOpContour* SkOpSpanBase::debugContour(int id) const {
706 return this->segment()->debugContour(id);
707 }
708
debugPtT(int id) const709 const SkOpPtT* SkOpSpanBase::debugPtT(int id) const {
710 return this->segment()->debugPtT(id);
711 }
712
debugSegment(int id) const713 const SkOpSegment* SkOpSpanBase::debugSegment(int id) const {
714 return this->segment()->debugSegment(id);
715 }
716
debugSpan(int id) const717 const SkOpSpanBase* SkOpSpanBase::debugSpan(int id) const {
718 return this->segment()->debugSpan(id);
719 }
720
dump() const721 void SkOpSpanBase::dump() const {
722 this->dumpHead();
723 this->fPtT.dump();
724 }
725
dumpHead() const726 void SkOpSpanBase::dumpHead() const {
727 SkDebugf("%.*s", contour()->debugIndent(), " ");
728 SkDebugf("seg=%d span=%d", this->segment()->debugID(), this->debugID());
729 this->dumpBase();
730 SkDebugf("\n");
731 }
732
dumpAll() const733 void SkOpSpanBase::dumpAll() const {
734 this->dumpHead();
735 this->fPtT.dumpAll();
736 }
737
dumpBase() const738 void SkOpSpanBase::dumpBase() const {
739 if (this->fAligned) {
740 SkDebugf(" aligned");
741 }
742 if (this->fChased) {
743 SkDebugf(" chased");
744 }
745 #ifdef SK_DEBUG
746 if (this->fDebugDeleted) {
747 SkDebugf(" deleted");
748 }
749 #endif
750 if (!this->final()) {
751 this->upCast()->dumpSpan();
752 }
753 const SkOpSpanBase* coin = this->coinEnd();
754 if (this != coin) {
755 SkDebugf(" coinEnd seg/span=%d/%d", coin->segment()->debugID(), coin->debugID());
756 } else if (this->final() || !this->upCast()->isCoincident()) {
757 const SkOpPtT* oPt = this->ptT()->next();
758 SkDebugf(" seg/span=%d/%d", oPt->segment()->debugID(), oPt->span()->debugID());
759 }
760 SkDebugf(" adds=%d", fSpanAdds);
761 }
762
dumpCoin() const763 void SkOpSpanBase::dumpCoin() const {
764 const SkOpSpan* span = this->upCastable();
765 if (!span) {
766 return;
767 }
768 if (!span->isCoincident()) {
769 return;
770 }
771 span->dumpCoin();
772 }
773
dumpCoin() const774 void SkOpSpan::dumpCoin() const {
775 const SkOpSpan* coincident = fCoincident;
776 bool ok = debugCoinLoopCheck();
777 this->dump();
778 int loop = 0;
779 do {
780 coincident->dump();
781 if (!ok && ++loop > 10) {
782 SkDebugf("*** abort loop ***\n");
783 break;
784 }
785 } while ((coincident = coincident->fCoincident) != this);
786 }
787
dumpSpan() const788 bool SkOpSpan::dumpSpan() const {
789 SkOpSpan* coin = fCoincident;
790 if (this != coin) {
791 SkDebugf(" coinStart seg/span=%d/%d", coin->segment()->debugID(), coin->debugID());
792 }
793 SkDebugf(" windVal=%d", this->windValue());
794 SkDebugf(" windSum=");
795 SkPathOpsDebug::WindingPrintf(this->windSum());
796 if (this->oppValue() != 0 || this->oppSum() != SK_MinS32) {
797 SkDebugf(" oppVal=%d", this->oppValue());
798 SkDebugf(" oppSum=");
799 SkPathOpsDebug::WindingPrintf(this->oppSum());
800 }
801 if (this->done()) {
802 SkDebugf(" done");
803 }
804 return this != coin;
805 }
806
debugAngle(int id) const807 const SkOpAngle* SkOpSegment::debugAngle(int id) const {
808 return this->contour()->debugAngle(id);
809 }
810
debugCoincidence() const811 const SkOpCoincidence* SkOpSegment::debugCoincidence() const {
812 return this->contour()->debugCoincidence();
813 }
814
debugContour(int id) const815 SkOpContour* SkOpSegment::debugContour(int id) const {
816 return this->contour()->debugContour(id);
817 }
818
debugPtT(int id) const819 const SkOpPtT* SkOpSegment::debugPtT(int id) const {
820 return this->contour()->debugPtT(id);
821 }
822
debugSegment(int id) const823 const SkOpSegment* SkOpSegment::debugSegment(int id) const {
824 return this->contour()->debugSegment(id);
825 }
826
debugSpan(int id) const827 const SkOpSpanBase* SkOpSegment::debugSpan(int id) const {
828 return this->contour()->debugSpan(id);
829 }
830
dump() const831 void SkOpSegment::dump() const {
832 SkDebugf("%.*s", contour()->debugIndent(), " ");
833 this->dumpPts();
834 const SkOpSpanBase* span = &fHead;
835 contour()->indentDump();
836 do {
837 SkDebugf("%.*s span=%d ", contour()->debugIndent(), " ", span->debugID());
838 span->ptT()->dumpBase();
839 span->dumpBase();
840 SkDebugf("\n");
841 } while (!span->final() && (span = span->upCast()->next()));
842 contour()->outdentDump();
843 }
844
dumpAll() const845 void SkOpSegment::dumpAll() const {
846 SkDebugf("%.*s", contour()->debugIndent(), " ");
847 this->dumpPts();
848 const SkOpSpanBase* span = &fHead;
849 contour()->indentDump();
850 do {
851 span->dumpAll();
852 } while (!span->final() && (span = span->upCast()->next()));
853 contour()->outdentDump();
854 }
855
dumpAngles() const856 void SkOpSegment::dumpAngles() const {
857 SkDebugf("seg=%d\n", debugID());
858 const SkOpSpanBase* span = &fHead;
859 do {
860 const SkOpAngle* fAngle = span->fromAngle();
861 const SkOpAngle* tAngle = span->final() ? nullptr : span->upCast()->toAngle();
862 if (fAngle) {
863 SkDebugf(" span=%d from=%d ", span->debugID(), fAngle->debugID());
864 fAngle->dumpTo(this, tAngle);
865 }
866 if (tAngle) {
867 SkDebugf(" span=%d to=%d ", span->debugID(), tAngle->debugID());
868 tAngle->dumpTo(this, fAngle);
869 }
870 } while (!span->final() && (span = span->upCast()->next()));
871 }
872
dumpCoin() const873 void SkOpSegment::dumpCoin() const {
874 const SkOpSpan* span = &fHead;
875 do {
876 span->dumpCoin();
877 } while ((span = span->next()->upCastable()));
878 }
879
dumpPtsInner(const char * prefix) const880 void SkOpSegment::dumpPtsInner(const char* prefix) const {
881 int last = SkPathOpsVerbToPoints(fVerb);
882 SkDebugf("%s=%d {{", prefix, this->debugID());
883 if (fVerb == SkPath::kConic_Verb) {
884 SkDebugf("{");
885 }
886 int index = 0;
887 do {
888 SkDPoint::Dump(fPts[index]);
889 SkDebugf(", ");
890 } while (++index < last);
891 SkDPoint::Dump(fPts[index]);
892 SkDebugf("}}");
893 if (fVerb == SkPath::kConic_Verb) {
894 SkDebugf(", %1.9gf}", fWeight);
895 }
896 }
897
dumpPts(const char * prefix) const898 void SkOpSegment::dumpPts(const char* prefix) const {
899 dumpPtsInner(prefix);
900 SkDebugf("\n");
901 }
902
dump() const903 void SkCoincidentSpans::dump() const {
904 SkDebugf("- seg=%d span=%d ptT=%d ", fCoinPtTStart->segment()->debugID(),
905 fCoinPtTStart->span()->debugID(), fCoinPtTStart->debugID());
906 fCoinPtTStart->dumpBase();
907 SkDebugf(" span=%d ptT=%d ", fCoinPtTEnd->span()->debugID(), fCoinPtTEnd->debugID());
908 fCoinPtTEnd->dumpBase();
909 if (fCoinPtTStart->segment()->operand()) {
910 SkDebugf(" operand");
911 }
912 if (fCoinPtTStart->segment()->isXor()) {
913 SkDebugf(" xor");
914 }
915 SkDebugf("\n");
916 SkDebugf("+ seg=%d span=%d ptT=%d ", fOppPtTStart->segment()->debugID(),
917 fOppPtTStart->span()->debugID(), fOppPtTStart->debugID());
918 fOppPtTStart->dumpBase();
919 SkDebugf(" span=%d ptT=%d ", fOppPtTEnd->span()->debugID(), fOppPtTEnd->debugID());
920 fOppPtTEnd->dumpBase();
921 if (fOppPtTStart->segment()->operand()) {
922 SkDebugf(" operand");
923 }
924 if (fOppPtTStart->segment()->isXor()) {
925 SkDebugf(" xor");
926 }
927 SkDebugf("\n");
928 }
929
dump() const930 void SkOpCoincidence::dump() const {
931 SkCoincidentSpans* span = fHead;
932 while (span) {
933 span->dump();
934 span = span->next();
935 }
936 if (!fTop || fHead == fTop) {
937 return;
938 }
939 SkDebugf("top:\n");
940 span = fTop;
941 int count = 0;
942 while (span) {
943 span->dump();
944 span = span->next();
945 SkCoincidentSpans* check = fTop;
946 ++count;
947 for (int index = 0; index < count; ++index) {
948 if (span == check) {
949 SkDebugf("(loops to #%d)\n", index);
950 return;
951 }
952 check = check->next();
953 }
954 }
955 }
956
dump() const957 void SkOpContour::dump() const {
958 SkDebugf("contour=%d count=%d op=%d xor=%d\n", this->debugID(), fCount, fOperand, fXor);
959 if (!fCount) {
960 return;
961 }
962 const SkOpSegment* segment = &fHead;
963 SkDEBUGCODE(fDebugIndent = 0);
964 this->indentDump();
965 do {
966 segment->dump();
967 } while ((segment = segment->next()));
968 this->outdentDump();
969 }
970
dumpAll() const971 void SkOpContour::dumpAll() const {
972 SkDebugf("contour=%d count=%d op=%d xor=%d\n", this->debugID(), fCount, fOperand, fXor);
973 if (!fCount) {
974 return;
975 }
976 const SkOpSegment* segment = &fHead;
977 SkDEBUGCODE(fDebugIndent = 0);
978 this->indentDump();
979 do {
980 segment->dumpAll();
981 } while ((segment = segment->next()));
982 this->outdentDump();
983 }
984
985
dumpAngles() const986 void SkOpContour::dumpAngles() const {
987 SkDebugf("contour=%d\n", this->debugID());
988 const SkOpSegment* segment = &fHead;
989 do {
990 SkDebugf(" seg=%d ", segment->debugID());
991 segment->dumpAngles();
992 } while ((segment = segment->next()));
993 }
994
dumpPt(int index) const995 void SkOpContour::dumpPt(int index) const {
996 const SkOpSegment* segment = &fHead;
997 do {
998 if (segment->debugID() == index) {
999 segment->dumpPts();
1000 }
1001 } while ((segment = segment->next()));
1002 }
1003
dumpPts(const char * prefix) const1004 void SkOpContour::dumpPts(const char* prefix) const {
1005 SkDebugf("contour=%d\n", this->debugID());
1006 const SkOpSegment* segment = &fHead;
1007 do {
1008 SkDebugf(" %s=%d ", prefix, segment->debugID());
1009 segment->dumpPts(prefix);
1010 } while ((segment = segment->next()));
1011 }
1012
dumpPtsX(const char * prefix) const1013 void SkOpContour::dumpPtsX(const char* prefix) const {
1014 if (!this->fCount) {
1015 SkDebugf("<empty>\n");
1016 return;
1017 }
1018 const SkOpSegment* segment = &fHead;
1019 do {
1020 segment->dumpPts(prefix);
1021 } while ((segment = segment->next()));
1022 }
1023
dumpSegment(int index) const1024 void SkOpContour::dumpSegment(int index) const {
1025 debugSegment(index)->dump();
1026 }
1027
dumpSegments(const char * prefix,SkPathOp op) const1028 void SkOpContour::dumpSegments(const char* prefix, SkPathOp op) const {
1029 bool firstOp = false;
1030 const SkOpContour* c = this;
1031 do {
1032 if (!firstOp && c->operand()) {
1033 #if DEBUG_ACTIVE_OP
1034 SkDebugf("op %s\n", SkPathOpsDebug::kPathOpStr[op]);
1035 #endif
1036 firstOp = true;
1037 }
1038 c->dumpPtsX(prefix);
1039 } while ((c = c->next()));
1040 }
1041
dumpSpan(int index) const1042 void SkOpContour::dumpSpan(int index) const {
1043 debugSpan(index)->dump();
1044 }
1045
dumpSpans() const1046 void SkOpContour::dumpSpans() const {
1047 SkDebugf("contour=%d\n", this->debugID());
1048 const SkOpSegment* segment = &fHead;
1049 do {
1050 SkDebugf(" seg=%d ", segment->debugID());
1051 segment->dump();
1052 } while ((segment = segment->next()));
1053 }
1054
dump() const1055 void SkOpCurve::dump() const {
1056 int count = SkPathOpsVerbToPoints(SkDEBUGRELEASE(fVerb, SkPath::kCubic_Verb));
1057 SkDebugf("{{");
1058 int index;
1059 for (index = 0; index <= count - 1; ++index) {
1060 SkDebugf("{%1.9gf,%1.9gf}, ", fPts[index].fX, fPts[index].fY);
1061 }
1062 SkDebugf("{%1.9gf,%1.9gf}}}\n", fPts[index].fX, fPts[index].fY);
1063 }
1064
1065 #ifdef SK_DEBUG
debugAngle(int id) const1066 const SkOpAngle* SkOpGlobalState::debugAngle(int id) const {
1067 const SkOpContour* contour = fContourHead;
1068 do {
1069 const SkOpSegment* segment = contour->first();
1070 while (segment) {
1071 const SkOpSpan* span = segment->head();
1072 do {
1073 SkOpAngle* angle = span->fromAngle();
1074 if (angle && angle->debugID() == id) {
1075 return angle;
1076 }
1077 angle = span->toAngle();
1078 if (angle && angle->debugID() == id) {
1079 return angle;
1080 }
1081 } while ((span = span->next()->upCastable()));
1082 const SkOpSpanBase* tail = segment->tail();
1083 SkOpAngle* angle = tail->fromAngle();
1084 if (angle && angle->debugID() == id) {
1085 return angle;
1086 }
1087 segment = segment->next();
1088 }
1089 } while ((contour = contour->next()));
1090 return nullptr;
1091 }
1092
debugContour(int id) const1093 SkOpContour* SkOpGlobalState::debugContour(int id) const {
1094 SkOpContour* contour = fContourHead;
1095 do {
1096 if (contour->debugID() == id) {
1097 return contour;
1098 }
1099 } while ((contour = contour->next()));
1100 return nullptr;
1101 }
1102
debugPtT(int id) const1103 const SkOpPtT* SkOpGlobalState::debugPtT(int id) const {
1104 const SkOpContour* contour = fContourHead;
1105 do {
1106 const SkOpSegment* segment = contour->first();
1107 while (segment) {
1108 const SkOpSpan* span = segment->head();
1109 do {
1110 const SkOpPtT* ptT = span->ptT();
1111 if (ptT->debugMatchID(id)) {
1112 return ptT;
1113 }
1114 } while ((span = span->next()->upCastable()));
1115 const SkOpSpanBase* tail = segment->tail();
1116 const SkOpPtT* ptT = tail->ptT();
1117 if (ptT->debugMatchID(id)) {
1118 return ptT;
1119 }
1120 segment = segment->next();
1121 }
1122 } while ((contour = contour->next()));
1123 return nullptr;
1124 }
1125
debugSegment(int id) const1126 const SkOpSegment* SkOpGlobalState::debugSegment(int id) const {
1127 const SkOpContour* contour = fContourHead;
1128 do {
1129 const SkOpSegment* segment = contour->first();
1130 while (segment) {
1131 if (segment->debugID() == id) {
1132 return segment;
1133 }
1134 segment = segment->next();
1135 }
1136 } while ((contour = contour->next()));
1137 return nullptr;
1138 }
1139
debugSpan(int id) const1140 const SkOpSpanBase* SkOpGlobalState::debugSpan(int id) const {
1141 const SkOpContour* contour = fContourHead;
1142 do {
1143 const SkOpSegment* segment = contour->first();
1144 while (segment) {
1145 const SkOpSpan* span = segment->head();
1146 do {
1147 if (span->debugID() == id) {
1148 return span;
1149 }
1150 } while ((span = span->next()->upCastable()));
1151 const SkOpSpanBase* tail = segment->tail();
1152 if (tail->debugID() == id) {
1153 return tail;
1154 }
1155 segment = segment->next();
1156 }
1157 } while ((contour = contour->next()));
1158 return nullptr;
1159 }
1160 #endif
1161
dumpIsCoincidentStr() const1162 char SkTCoincident::dumpIsCoincidentStr() const {
1163 if (!!fMatch != fMatch) {
1164 return '?';
1165 }
1166 return fMatch ? '*' : 0;
1167 }
1168
dump() const1169 void SkTCoincident::dump() const {
1170 SkDebugf("t=%1.9g pt=(%1.9g,%1.9g)%s\n", fPerpT, fPerpPt.fX, fPerpPt.fY,
1171 fMatch ? " match" : "");
1172 }
1173
1174 #ifdef SK_DEBUG
1175
debugSpan(int id) const1176 const SkTSpan* SkTSect::debugSpan(int id) const {
1177 const SkTSpan* test = fHead;
1178 do {
1179 if (test->debugID() == id) {
1180 return test;
1181 }
1182 } while ((test = test->next()));
1183 return nullptr;
1184 }
1185
debugT(double t) const1186 const SkTSpan* SkTSect::debugT(double t) const {
1187 const SkTSpan* test = fHead;
1188 const SkTSpan* closest = nullptr;
1189 double bestDist = DBL_MAX;
1190 do {
1191 if (between(test->fStartT, t, test->fEndT)) {
1192 return test;
1193 }
1194 double testDist = std::min(fabs(test->fStartT - t), fabs(test->fEndT - t));
1195 if (bestDist > testDist) {
1196 bestDist = testDist;
1197 closest = test;
1198 }
1199 } while ((test = test->next()));
1200 SkASSERT(closest);
1201 return closest;
1202 }
1203
1204 #endif
1205
dump() const1206 void SkTSect::dump() const {
1207 dumpCommon(fHead);
1208 }
1209
1210 extern int gDumpTSectNum;
1211
dumpBoth(SkTSect * opp) const1212 void SkTSect::dumpBoth(SkTSect* opp) const {
1213 #if DEBUG_T_SECT_DUMP <= 2
1214 #if DEBUG_T_SECT_DUMP == 2
1215 SkDebugf("%d ", ++gDumpTSectNum);
1216 #endif
1217 this->dump();
1218 SkDebugf("\n");
1219 opp->dump();
1220 SkDebugf("\n");
1221 #elif DEBUG_T_SECT_DUMP == 3
1222 SkDebugf("<div id=\"sect%d\">\n", ++gDumpTSectNum);
1223 if (this->fHead) {
1224 this->dumpCurves();
1225 }
1226 if (opp->fHead) {
1227 opp->dumpCurves();
1228 }
1229 SkDebugf("</div>\n\n");
1230 #endif
1231 }
1232
dumpBounded(int id) const1233 void SkTSect::dumpBounded(int id) const {
1234 #ifdef SK_DEBUG
1235 const SkTSpan* bounded = debugSpan(id);
1236 if (!bounded) {
1237 SkDebugf("no span matches %d\n", id);
1238 return;
1239 }
1240 const SkTSpan* test = bounded->debugOpp()->fHead;
1241 do {
1242 if (test->findOppSpan(bounded)) {
1243 test->dump();
1244 SkDebugf(" ");
1245 }
1246 } while ((test = test->next()));
1247 SkDebugf("\n");
1248 #endif
1249 }
1250
dumpBounds() const1251 void SkTSect::dumpBounds() const {
1252 const SkTSpan* test = fHead;
1253 do {
1254 test->dumpBounds();
1255 } while ((test = test->next()));
1256 }
1257
dumpCoin() const1258 void SkTSect::dumpCoin() const {
1259 dumpCommon(fCoincident);
1260 }
1261
dumpCoinCurves() const1262 void SkTSect::dumpCoinCurves() const {
1263 dumpCommonCurves(fCoincident);
1264 }
1265
dumpCommon(const SkTSpan * test) const1266 void SkTSect::dumpCommon(const SkTSpan* test) const {
1267 SkDebugf("id=%d", debugID());
1268 if (!test) {
1269 SkDebugf(" (empty)");
1270 return;
1271 }
1272 do {
1273 SkDebugf(" ");
1274 test->dump();
1275 } while ((test = test->next()));
1276 }
1277
dumpCommonCurves(const SkTSpan * test) const1278 void SkTSect::dumpCommonCurves(const SkTSpan* test) const {
1279 #if DEBUG_T_SECT
1280 do {
1281 test->fPart->dumpID(test->debugID());
1282 } while ((test = test->next()));
1283 #endif
1284 }
1285
dumpCurves() const1286 void SkTSect::dumpCurves() const {
1287 dumpCommonCurves(fHead);
1288 }
1289
1290 #ifdef SK_DEBUG
1291
debugSpan(int id) const1292 const SkTSpan* SkTSpan::debugSpan(int id) const {
1293 return fDebugSect->debugSpan(id);
1294 }
1295
debugT(double t) const1296 const SkTSpan* SkTSpan::debugT(double t) const {
1297 return fDebugSect->debugT(t);
1298 }
1299
1300 #endif
1301
dumpAll() const1302 void SkTSpan::dumpAll() const {
1303 dumpID();
1304 SkDebugf("=(%g,%g) [", fStartT, fEndT);
1305 const SkTSpanBounded* testBounded = fBounded;
1306 while (testBounded) {
1307 const SkTSpan* span = testBounded->fBounded;
1308 const SkTSpanBounded* next = testBounded->fNext;
1309 span->dumpID();
1310 SkDebugf("=(%g,%g)", span->fStartT, span->fEndT);
1311 if (next) {
1312 SkDebugf(" ");
1313 }
1314 testBounded = next;
1315 }
1316 SkDebugf("]\n");
1317 }
1318
dump() const1319 void SkTSpan::dump() const {
1320 dumpID();
1321 SkDebugf("=(%g,%g) [", fStartT, fEndT);
1322 const SkTSpanBounded* testBounded = fBounded;
1323 while (testBounded) {
1324 const SkTSpan* span = testBounded->fBounded;
1325 const SkTSpanBounded* next = testBounded->fNext;
1326 span->dumpID();
1327 if (next) {
1328 SkDebugf(",");
1329 }
1330 testBounded = next;
1331 }
1332 SkDebugf("]");
1333 }
1334
dumpBounded(int id) const1335 void SkTSpan::dumpBounded(int id) const {
1336 SkDEBUGCODE(fDebugSect->dumpBounded(id));
1337 }
1338
dumpBounds() const1339 void SkTSpan::dumpBounds() const {
1340 dumpID();
1341 SkDebugf(" bounds=(%1.9g,%1.9g, %1.9g,%1.9g) boundsMax=%1.9g%s\n",
1342 fBounds.fLeft, fBounds.fTop, fBounds.fRight, fBounds.fBottom, fBoundsMax,
1343 fCollapsed ? " collapsed" : "");
1344 }
1345
dumpCoin() const1346 void SkTSpan::dumpCoin() const {
1347 dumpID();
1348 SkDebugf(" coinStart ");
1349 fCoinStart.dump();
1350 SkDebugf(" coinEnd ");
1351 fCoinEnd.dump();
1352 }
1353
dumpID() const1354 void SkTSpan::dumpID() const {
1355 char cS = fCoinStart.dumpIsCoincidentStr();
1356 if (cS) {
1357 SkDebugf("%c", cS);
1358 }
1359 SkDebugf("%d", debugID());
1360 char cE = fCoinEnd.dumpIsCoincidentStr();
1361 if (cE) {
1362 SkDebugf("%c", cE);
1363 }
1364 }
1365
1366 #if DEBUG_T_SECT_DUMP > 1
1367 int gDumpTSectNum;
1368 #endif
1369
1370 // global path dumps for msvs Visual Studio 17 to use from Immediate Window
Dump(const SkOpContour & contour)1371 void Dump(const SkOpContour& contour) {
1372 contour.dump();
1373 }
1374
DumpAll(const SkOpContour & contour)1375 void DumpAll(const SkOpContour& contour) {
1376 contour.dumpAll();
1377 }
1378
DumpAngles(const SkOpContour & contour)1379 void DumpAngles(const SkOpContour& contour) {
1380 contour.dumpAngles();
1381 }
1382
DumpContours(const SkOpContour & contour)1383 void DumpContours(const SkOpContour& contour) {
1384 contour.dumpContours();
1385 }
1386
DumpContoursAll(const SkOpContour & contour)1387 void DumpContoursAll(const SkOpContour& contour) {
1388 contour.dumpContoursAll();
1389 }
1390
DumpContoursAngles(const SkOpContour & contour)1391 void DumpContoursAngles(const SkOpContour& contour) {
1392 contour.dumpContoursAngles();
1393 }
1394
DumpContoursPts(const SkOpContour & contour)1395 void DumpContoursPts(const SkOpContour& contour) {
1396 contour.dumpContoursPts();
1397 }
1398
DumpContoursPt(const SkOpContour & contour,int segmentID)1399 void DumpContoursPt(const SkOpContour& contour, int segmentID) {
1400 contour.dumpContoursPt(segmentID);
1401 }
1402
DumpContoursSegment(const SkOpContour & contour,int segmentID)1403 void DumpContoursSegment(const SkOpContour& contour, int segmentID) {
1404 contour.dumpContoursSegment(segmentID);
1405 }
1406
DumpContoursSpan(const SkOpContour & contour,int segmentID)1407 void DumpContoursSpan(const SkOpContour& contour, int segmentID) {
1408 contour.dumpContoursSpan(segmentID);
1409 }
1410
DumpContoursSpans(const SkOpContour & contour)1411 void DumpContoursSpans(const SkOpContour& contour) {
1412 contour.dumpContoursSpans();
1413 }
1414
DumpPt(const SkOpContour & contour,int pt)1415 void DumpPt(const SkOpContour& contour, int pt) {
1416 contour.dumpPt(pt);
1417 }
1418
DumpPts(const SkOpContour & contour,const char * prefix)1419 void DumpPts(const SkOpContour& contour, const char* prefix) {
1420 contour.dumpPts(prefix);
1421 }
1422
DumpSegment(const SkOpContour & contour,int seg)1423 void DumpSegment(const SkOpContour& contour, int seg) {
1424 contour.dumpSegment(seg);
1425 }
1426
DumpSegments(const SkOpContour & contour,const char * prefix,SkPathOp op)1427 void DumpSegments(const SkOpContour& contour, const char* prefix, SkPathOp op) {
1428 contour.dumpSegments(prefix, op);
1429 }
1430
DumpSpan(const SkOpContour & contour,int span)1431 void DumpSpan(const SkOpContour& contour, int span) {
1432 contour.dumpSpan(span);
1433 }
1434
DumpSpans(const SkOpContour & contour)1435 void DumpSpans(const SkOpContour& contour ) {
1436 contour.dumpSpans();
1437 }
1438
Dump(const SkOpSegment & segment)1439 void Dump(const SkOpSegment& segment) {
1440 segment.dump();
1441 }
1442
DumpAll(const SkOpSegment & segment)1443 void DumpAll(const SkOpSegment& segment) {
1444 segment.dumpAll();
1445 }
1446
DumpAngles(const SkOpSegment & segment)1447 void DumpAngles(const SkOpSegment& segment) {
1448 segment.dumpAngles();
1449 }
1450
DumpCoin(const SkOpSegment & segment)1451 void DumpCoin(const SkOpSegment& segment) {
1452 segment.dumpCoin();
1453 }
1454
DumpPts(const SkOpSegment & segment,const char * prefix)1455 void DumpPts(const SkOpSegment& segment, const char* prefix) {
1456 segment.dumpPts(prefix);
1457 }
1458
Dump(const SkOpPtT & ptT)1459 void Dump(const SkOpPtT& ptT) {
1460 ptT.dump();
1461 }
1462
DumpAll(const SkOpPtT & ptT)1463 void DumpAll(const SkOpPtT& ptT) {
1464 ptT.dumpAll();
1465 }
1466
Dump(const SkOpSpanBase & spanBase)1467 void Dump(const SkOpSpanBase& spanBase) {
1468 spanBase.dump();
1469 }
1470
DumpCoin(const SkOpSpanBase & spanBase)1471 void DumpCoin(const SkOpSpanBase& spanBase) {
1472 spanBase.dumpCoin();
1473 }
1474
DumpAll(const SkOpSpanBase & spanBase)1475 void DumpAll(const SkOpSpanBase& spanBase) {
1476 spanBase.dumpAll();
1477 }
1478
DumpCoin(const SkOpSpan & span)1479 void DumpCoin(const SkOpSpan& span) {
1480 span.dumpCoin();
1481 }
1482
DumpSpan(const SkOpSpan & span)1483 bool DumpSpan(const SkOpSpan& span) {
1484 return span.dumpSpan();
1485 }
1486
Dump(const SkDConic & conic)1487 void Dump(const SkDConic& conic) {
1488 conic.dump();
1489 }
1490
DumpID(const SkDConic & conic,int id)1491 void DumpID(const SkDConic& conic, int id) {
1492 conic.dumpID(id);
1493 }
1494
Dump(const SkDCubic & cubic)1495 void Dump(const SkDCubic& cubic) {
1496 cubic.dump();
1497 }
1498
DumpID(const SkDCubic & cubic,int id)1499 void DumpID(const SkDCubic& cubic, int id) {
1500 cubic.dumpID(id);
1501 }
1502
Dump(const SkDLine & line)1503 void Dump(const SkDLine& line) {
1504 line.dump();
1505 }
1506
DumpID(const SkDLine & line,int id)1507 void DumpID(const SkDLine& line, int id) {
1508 line.dumpID(id);
1509 }
1510
Dump(const SkDQuad & quad)1511 void Dump(const SkDQuad& quad) {
1512 quad.dump();
1513 }
1514
DumpID(const SkDQuad & quad,int id)1515 void DumpID(const SkDQuad& quad, int id) {
1516 quad.dumpID(id);
1517 }
1518
Dump(const SkDPoint & point)1519 void Dump(const SkDPoint& point) {
1520 point.dump();
1521 }
1522
Dump(const SkOpAngle & angle)1523 void Dump(const SkOpAngle& angle) {
1524 angle.dump();
1525 }
1526