Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(446)

Side by Side Diff: src/core/SkStrokerPriv.cpp

Issue 910213002: Use conics for round joins and caps (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: remove dup cubic code Created 5 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/core/SkGeometry.cpp ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 1
2 /* 2 /*
3 * Copyright 2006 The Android Open Source Project 3 * Copyright 2006 The Android Open Source Project
4 * 4 *
5 * Use of this source code is governed by a BSD-style license that can be 5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file. 6 * found in the LICENSE file.
7 */ 7 */
8 8
9 9
10 #include "SkStrokerPriv.h" 10 #include "SkStrokerPriv.h"
11 #include "SkGeometry.h" 11 #include "SkGeometry.h"
12 #include "SkPath.h" 12 #include "SkPath.h"
13 13
14 static void ButtCapper(SkPath* path, const SkPoint& pivot, 14 static void ButtCapper(SkPath* path, const SkPoint& pivot,
15 const SkVector& normal, const SkPoint& stop, 15 const SkVector& normal, const SkPoint& stop,
16 SkPath*) 16 SkPath*)
17 { 17 {
18 path->lineTo(stop.fX, stop.fY); 18 path->lineTo(stop.fX, stop.fY);
19 } 19 }
20 20
21 static void RoundCapper(SkPath* path, const SkPoint& pivot, 21 static void RoundCapper(SkPath* path, const SkPoint& pivot,
22 const SkVector& normal, const SkPoint& stop, 22 const SkVector& normal, const SkPoint& stop,
23 SkPath*) 23 SkPath*)
24 { 24 {
25 #ifdef SK_SUPPORT_LEGACY_ARCTO_QUADS
25 SkScalar px = pivot.fX; 26 SkScalar px = pivot.fX;
26 SkScalar py = pivot.fY; 27 SkScalar py = pivot.fY;
27 SkScalar nx = normal.fX; 28 SkScalar nx = normal.fX;
28 SkScalar ny = normal.fY; 29 SkScalar ny = normal.fY;
29 SkScalar sx = SkScalarMul(nx, CUBIC_ARC_FACTOR); 30 SkScalar sx = SkScalarMul(nx, CUBIC_ARC_FACTOR);
30 SkScalar sy = SkScalarMul(ny, CUBIC_ARC_FACTOR); 31 SkScalar sy = SkScalarMul(ny, CUBIC_ARC_FACTOR);
31 32
32 path->cubicTo(px + nx + CWX(sx, sy), py + ny + CWY(sx, sy), 33 path->cubicTo(px + nx + CWX(sx, sy), py + ny + CWY(sx, sy),
33 px + CWX(nx, ny) + sx, py + CWY(nx, ny) + sy, 34 px + CWX(nx, ny) + sx, py + CWY(nx, ny) + sy,
34 px + CWX(nx, ny), py + CWY(nx, ny)); 35 px + CWX(nx, ny), py + CWY(nx, ny));
35 path->cubicTo(px + CWX(nx, ny) - sx, py + CWY(nx, ny) - sy, 36 path->cubicTo(px + CWX(nx, ny) - sx, py + CWY(nx, ny) - sy,
36 px - nx + CWX(sx, sy), py - ny + CWY(sx, sy), 37 px - nx + CWX(sx, sy), py - ny + CWY(sx, sy),
37 stop.fX, stop.fY); 38 stop.fX, stop.fY);
39 #else
40 SkVector parallel;
41 normal.rotateCW(&parallel);
42
43 SkPoint projectedCenter = pivot + parallel;
44
45 path->conicTo(projectedCenter + normal, projectedCenter, SK_ScalarRoot2Over2 );
46 path->conicTo(projectedCenter - normal, stop, SK_ScalarRoot2Over2);
47 #endif
38 } 48 }
39 49
40 static void SquareCapper(SkPath* path, const SkPoint& pivot, 50 static void SquareCapper(SkPath* path, const SkPoint& pivot,
41 const SkVector& normal, const SkPoint& stop, 51 const SkVector& normal, const SkPoint& stop,
42 SkPath* otherPath) 52 SkPath* otherPath)
43 { 53 {
44 SkVector parallel; 54 SkVector parallel;
45 normal.rotateCW(&parallel); 55 normal.rotateCW(&parallel);
46 56
47 if (otherPath) 57 if (otherPath)
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after
129 SkRotationDirection dir = kCW_SkRotationDirection; 139 SkRotationDirection dir = kCW_SkRotationDirection;
130 140
131 if (!is_clockwise(before, after)) 141 if (!is_clockwise(before, after))
132 { 142 {
133 SkTSwap<SkPath*>(outer, inner); 143 SkTSwap<SkPath*>(outer, inner);
134 before.negate(); 144 before.negate();
135 after.negate(); 145 after.negate();
136 dir = kCCW_SkRotationDirection; 146 dir = kCCW_SkRotationDirection;
137 } 147 }
138 148
139 SkPoint pts[kSkBuildQuadArcStorage];
140 SkMatrix matrix; 149 SkMatrix matrix;
141 matrix.setScale(radius, radius); 150 matrix.setScale(radius, radius);
142 matrix.postTranslate(pivot.fX, pivot.fY); 151 matrix.postTranslate(pivot.fX, pivot.fY);
152 #ifdef SK_SUPPORT_LEGACY_ARCTO_QUADS
153 SkPoint pts[kSkBuildQuadArcStorage];
143 int count = SkBuildQuadArc(before, after, dir, &matrix, pts); 154 int count = SkBuildQuadArc(before, after, dir, &matrix, pts);
144 SkASSERT((count & 1) == 1); 155 SkASSERT((count & 1) == 1);
145 156 if (count > 1) {
146 if (count > 1) 157 for (int i = 1; i < count; i += 2) {
147 {
148 for (int i = 1; i < count; i += 2)
149 outer->quadTo(pts[i].fX, pts[i].fY, pts[i+1].fX, pts[i+1].fY); 158 outer->quadTo(pts[i].fX, pts[i].fY, pts[i+1].fX, pts[i+1].fY);
150 159 }
151 after.scale(radius); 160 after.scale(radius);
152 HandleInnerJoin(inner, pivot, after); 161 HandleInnerJoin(inner, pivot, after);
153 } 162 }
163 #else
164 SkConic conics[SkConic::kMaxConicsForArc];
165 int count = SkConic::BuildUnitArc(before, after, dir, &matrix, conics);
166 if (count > 0) {
167 for (int i = 0; i < count; ++i) {
168 outer->conicTo(conics[i].fPts[1], conics[i].fPts[2], conics[i].fW);
169 }
170 after.scale(radius);
171 HandleInnerJoin(inner, pivot, after);
172 }
173 #endif
154 } 174 }
155 175
156 #define kOneOverSqrt2 (0.707106781f) 176 #define kOneOverSqrt2 (0.707106781f)
157 177
158 static void MiterJoiner(SkPath* outer, SkPath* inner, const SkVector& beforeUnit Normal, 178 static void MiterJoiner(SkPath* outer, SkPath* inner, const SkVector& beforeUnit Normal,
159 const SkPoint& pivot, const SkVector& afterUnitNormal, 179 const SkPoint& pivot, const SkVector& afterUnitNormal,
160 SkScalar radius, SkScalar invMiterLimit, 180 SkScalar radius, SkScalar invMiterLimit,
161 bool prevIsLine, bool currIsLine) 181 bool prevIsLine, bool currIsLine)
162 { 182 {
163 // negate the dot since we're using normals instead of tangents 183 // negate the dot since we're using normals instead of tangents
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after
251 271
252 SkStrokerPriv::JoinProc SkStrokerPriv::JoinFactory(SkPaint::Join join) 272 SkStrokerPriv::JoinProc SkStrokerPriv::JoinFactory(SkPaint::Join join)
253 { 273 {
254 static const SkStrokerPriv::JoinProc gJoiners[] = { 274 static const SkStrokerPriv::JoinProc gJoiners[] = {
255 MiterJoiner, RoundJoiner, BluntJoiner 275 MiterJoiner, RoundJoiner, BluntJoiner
256 }; 276 };
257 277
258 SkASSERT((unsigned)join < SkPaint::kJoinCount); 278 SkASSERT((unsigned)join < SkPaint::kJoinCount);
259 return gJoiners[join]; 279 return gJoiners[join];
260 } 280 }
OLDNEW
« no previous file with comments | « src/core/SkGeometry.cpp ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698