• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2020 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/utils/SkRandom.h"
9 #include "src/core/SkPathPriv.h"
10 #include "tests/Test.h"
11 
next_point(SkRandom & rand)12 SkPoint next_point(SkRandom& rand) { return {rand.nextF(), rand.nextF()}; }
13 
DEF_TEST(SkPath_RangeIter,r)14 DEF_TEST(SkPath_RangeIter, r) {
15     enum class Verb {
16         kMove = (int)SkPathVerb::kMove,
17         kLine = (int)SkPathVerb::kLine,
18         kQuad = (int)SkPathVerb::kQuad,
19         kConic = (int)SkPathVerb::kConic,
20         kCubic = (int)SkPathVerb::kCubic,
21         kClose = (int)SkPathVerb::kClose,
22         kImplicitMove
23     };
24 
25     Verb verbs[] = {
26         Verb::kImplicitMove,
27         Verb::kLine,
28         Verb::kConic,
29         Verb::kClose,
30         Verb::kImplicitMove,
31         Verb::kCubic,
32         Verb::kMove,
33         Verb::kConic,
34         Verb::kLine,
35         Verb::kClose,
36         Verb::kMove,
37         Verb::kMove
38     };
39 
40     class : SkRandom {
41     public:
42         SkPoint p() { return {this->SkRandom::nextF(), this->SkRandom::nextF()}; }
43         float w() { return this->SkRandom::nextF(); }
44     } genData, testData;
45 
46     for (int i = 0; i < 10; ++i) {
47         if (genData.p() != testData.p() || genData.w() != testData.w()) {
48             ERRORF(r, "genData and testData not in sync.");
49             return;
50         }
51     }
52 
53     // Build the path.
54     SkPath path;
55     for (Verb verb : verbs) {
56         switch (verb) {
57             case Verb::kImplicitMove:
58                 break;
59             case Verb::kMove:
60                 path.moveTo(genData.p());
61                 break;
62             case Verb::kLine:
63                 path.lineTo(genData.p());
64                 break;
65             case Verb::kQuad: {
66                 auto a = genData.p();
67                 auto b = genData.p();
68                 path.quadTo(a, b);
69                 break;
70             }
71             case Verb::kCubic: {
72                 auto a = genData.p();
73                 auto b = genData.p();
74                 auto c = genData.p();
75                 path.cubicTo(a, b, c);
76                 break;
77             }
78             case Verb::kConic: {
79                 auto a = genData.p();
80                 auto b = genData.p();
81                 path.conicTo(a, b, genData.w());
82                 break;
83             }
84             case Verb::kClose:
85                 path.close();
86                 break;
87         }
88     }
89 
90     // Verify sure the RangeIter works as expected.
91     SkPathPriv::Iterate iterate(path);
92     auto iter = iterate.begin();
93     SkPoint startPt = {0,0};
94     SkPoint lastPt = {0,0};
95     for (Verb verb : verbs) {
96         auto [pathVerb, pathPts, pathWt] = *iter++;
97         switch (verb) {
98             case Verb::kImplicitMove:
99                 REPORTER_ASSERT(r, pathPts[0] == startPt);
100                 lastPt = pathPts[0];
101                 break;
102             case Verb::kMove:
103                 REPORTER_ASSERT(r, pathPts[0] == testData.p());
104                 startPt = lastPt = pathPts[0];
105                 break;
106             case Verb::kLine:
107                 REPORTER_ASSERT(r, pathPts[0] == lastPt);
108                 REPORTER_ASSERT(r, pathPts[1] == testData.p());
109                 lastPt = pathPts[1];
110                 break;
111             case Verb::kQuad:
112                 REPORTER_ASSERT(r, pathPts[0] == lastPt);
113                 REPORTER_ASSERT(r, pathPts[1] == testData.p());
114                 REPORTER_ASSERT(r, pathPts[2] == testData.p());
115                 lastPt = pathPts[2];
116                 break;
117             case Verb::kCubic:
118                 REPORTER_ASSERT(r, pathPts[0] == lastPt);
119                 REPORTER_ASSERT(r, pathPts[1] == testData.p());
120                 REPORTER_ASSERT(r, pathPts[2] == testData.p());
121                 REPORTER_ASSERT(r, pathPts[3] == testData.p());
122                 lastPt = pathPts[3];
123                 break;
124             case Verb::kConic:
125                 REPORTER_ASSERT(r, pathPts[0] == lastPt);
126                 REPORTER_ASSERT(r, pathPts[1] == testData.p());
127                 REPORTER_ASSERT(r, pathPts[2] == testData.p());
128                 REPORTER_ASSERT(r, *pathWt == testData.w());
129                 lastPt = pathPts[2];
130                 break;
131             case Verb::kClose:
132                 REPORTER_ASSERT(r, pathPts[0] == lastPt);
133                 break;
134         }
135     }
136     REPORTER_ASSERT(r, iter == iterate.end());
137 }
138