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

Side by Side Diff: src/core/SkLinearBitmapPipeline_core.h

Issue 1757193002: Add test cases for Clamp and Repeat tiles. (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: Simplify span breakAt usage, by making breakAt consistant for +/- dx. Created 4 years, 9 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/SkLinearBitmapPipeline.cpp ('k') | src/core/SkLinearBitmapPipeline_tile.h » ('j') | 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 * Copyright 2016 Google Inc. 2 * Copyright 2016 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 7
8 #ifndef SkLinearBitmapPipeline_core_DEFINED 8 #ifndef SkLinearBitmapPipeline_core_DEFINED
9 #define SkLinearBitmapPipeline_core_DEFINED 9 #define SkLinearBitmapPipeline_core_DEFINED
10 10
11 #include <cmath>
12
11 // Tweak ABI of functions that pass Sk4f by value to pass them via registers. 13 // Tweak ABI of functions that pass Sk4f by value to pass them via registers.
12 #if defined(_MSC_VER) && SK_CPU_SSE_LEVEL >= SK_CPU_SSE_LEVEL_SSE2 14 #if defined(_MSC_VER) && SK_CPU_SSE_LEVEL >= SK_CPU_SSE_LEVEL_SSE2
13 #define VECTORCALL __vectorcall 15 #define VECTORCALL __vectorcall
14 #elif defined(SK_CPU_ARM32) && defined(SK_ARM_HAS_NEON) 16 #elif defined(SK_CPU_ARM32) && defined(SK_ARM_HAS_NEON)
15 #define VECTORCALL __attribute__((pcs("aapcs-vfp"))) 17 #define VECTORCALL __attribute__((pcs("aapcs-vfp")))
16 #else 18 #else
17 #define VECTORCALL 19 #define VECTORCALL
18 #endif 20 #endif
19 21
20 namespace { 22 namespace {
21 struct X { 23 struct X {
22 explicit X(SkScalar val) : fVal{val} { } 24 explicit X(SkScalar val) : fVal{val} { }
23 explicit X(SkPoint pt) : fVal{pt.fX} { } 25 explicit X(SkPoint pt) : fVal{pt.fX} { }
24 explicit X(SkSize s) : fVal{s.fWidth} { } 26 explicit X(SkSize s) : fVal{s.fWidth} { }
25 explicit X(SkISize s) : fVal(s.fWidth) { } 27 explicit X(SkISize s) : fVal((SkScalar)s.fWidth) { }
26 operator SkScalar () const {return fVal;} 28 operator SkScalar () const {return fVal;}
27 private: 29 private:
28 SkScalar fVal; 30 SkScalar fVal;
29 }; 31 };
30 32
31 struct Y { 33 struct Y {
32 explicit Y(SkScalar val) : fVal{val} { } 34 explicit Y(SkScalar val) : fVal{val} { }
33 explicit Y(SkPoint pt) : fVal{pt.fY} { } 35 explicit Y(SkPoint pt) : fVal{pt.fY} { }
34 explicit Y(SkSize s) : fVal{s.fHeight} { } 36 explicit Y(SkSize s) : fVal{s.fHeight} { }
35 explicit Y(SkISize s) : fVal(s.fHeight) { } 37 explicit Y(SkISize s) : fVal((SkScalar)s.fHeight) { }
36 operator SkScalar () const {return fVal;} 38 operator SkScalar () const {return fVal;}
37 private: 39 private:
38 SkScalar fVal; 40 SkScalar fVal;
39 }; 41 };
40 42
41 // The Span class enables efficient processing horizontal spans of pixels. 43 // The Span class enables efficient processing horizontal spans of pixels.
42 // * start - the point where to start the span. 44 // * start - the point where to start the span.
43 // * length - the number of pixels to traverse in source space. 45 // * length - the number of pixels to traverse in source space.
44 // * count - the number of pixels to produce in destination space. 46 // * count - the number of pixels to produce in destination space.
45 // Both start and length are mapped through the inversion matrix to produce valu es in source 47 // Both start and length are mapped through the inversion matrix to produce valu es in source
(...skipping 20 matching lines...) Expand all
66 SkScalar length() const { return fLength; } 68 SkScalar length() const { return fLength; }
67 SkScalar startX() const { return X(fStart); } 69 SkScalar startX() const { return X(fStart); }
68 SkScalar endX() const { return startX() + length(); } 70 SkScalar endX() const { return startX() + length(); }
69 void clear() { 71 void clear() {
70 fCount = 0; 72 fCount = 0;
71 } 73 }
72 74
73 bool completelyWithin(SkScalar xMin, SkScalar xMax) const { 75 bool completelyWithin(SkScalar xMin, SkScalar xMax) const {
74 SkScalar sMin, sMax; 76 SkScalar sMin, sMax;
75 std::tie(sMin, sMax) = std::minmax(startX(), endX()); 77 std::tie(sMin, sMax) = std::minmax(startX(), endX());
76 return xMin <= sMin && sMax <= xMax; 78 return xMin <= sMin && sMax < xMax;
77 } 79 }
78 80
79 void offset(SkScalar offsetX) { 81 void offset(SkScalar offsetX) {
80 fStart.offset(offsetX, 0.0f); 82 fStart.offset(offsetX, 0.0f);
81 } 83 }
82 84
83 Span breakAt(SkScalar breakX, SkScalar dx) { 85 Span breakAt(SkScalar breakX, SkScalar dx) {
84 SkASSERT(std::isfinite(breakX)); 86 SkASSERT(std::isfinite(breakX));
85 SkASSERT(std::isfinite(dx)); 87 SkASSERT(std::isfinite(dx));
86 SkASSERT(dx != 0.0f); 88 SkASSERT(dx != 0.0f);
87 89
88 if (this->isEmpty()) { 90 if (this->isEmpty()) {
89 return Span{{0.0, 0.0}, 0.0f, 0}; 91 return Span{{0.0, 0.0}, 0.0f, 0};
90 } 92 }
91 93
92 int dxSteps = SkScalarFloorToInt((breakX - this->startX()) / dx); 94 int dxSteps = SkScalarFloorToInt((breakX - this->startX()) / dx);
95
96 // Calculate the values for the span to cleave off.
97 SkScalar newLength = dxSteps * dx;
98
93 if (dxSteps < 0) { 99 if (dxSteps < 0) {
94 // The span is wholly after breakX. 100 // The span is wholly after breakX.
95 return Span{{0.0, 0.0}, 0.0f, 0}; 101 return Span{{0.0, 0.0}, 0.0f, 0};
96 } else if (dxSteps > fCount) { 102 } else if (dxSteps >= fCount) {
97 // The span is wholly before breakX. 103 // The span is wholly before breakX.
98 Span answer = *this; 104 Span answer = *this;
99 this->clear(); 105 this->clear();
100 return answer; 106 return answer;
101 } 107 }
102 108
103 // Calculate the values for the span to cleave off. 109 // If the last (or first if count = 1) sample lands directly on the boun dary. Include it
110 // when dx < 0 and exclude it when dx > 0.
111 // Reasoning:
112 // dx > 0: The sample point on the boundary is part of the next span be cause the entire
113 // pixel is after the boundary.
114 // dx < 0: The sample point on the boundary is part of the current span because the
115 // entire pixel is before the boundary.
116 if (startX() + newLength == breakX && dx > 0) {
117 if (dxSteps != 0) {
118 dxSteps -= 1;
119 newLength -= dx;
120 } else {
121 return Span{{0.0, 0.0}, 0.0f, 0};
122 }
123 }
124
104 SkPoint newStart = fStart; 125 SkPoint newStart = fStart;
105 SkScalar newLength = dxSteps * dx;
106 int newCount = dxSteps + 1; 126 int newCount = dxSteps + 1;
107 SkASSERT(newCount > 0); 127 SkASSERT(newCount > 0);
108 128
109 // Update this span to reflect the break. 129 // Update this span to reflect the break.
110 SkScalar lengthToStart = newLength + dx; 130 SkScalar lengthToStart = newLength + dx;
111 fLength -= lengthToStart; 131 fLength -= lengthToStart;
112 fCount -= newCount; 132 fCount -= newCount;
113 fStart = {this->startX() + lengthToStart, Y(fStart)}; 133 fStart = {this->startX() + lengthToStart, Y(fStart)};
114 134
115 return Span{newStart, newLength, newCount}; 135 return Span{newStart, newLength, newCount};
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after
202 // never used. 222 // never used.
203 while (count > 0) { 223 while (count > 0) {
204 next->bilerpList(xs, ys); 224 next->bilerpList(xs, ys);
205 xs = xs + dx; 225 xs = xs + dx;
206 count -= 1; 226 count -= 1;
207 } 227 }
208 } 228 }
209 } // namespace 229 } // namespace
210 230
211 #endif // SkLinearBitmapPipeline_core_DEFINED 231 #endif // SkLinearBitmapPipeline_core_DEFINED
OLDNEW
« no previous file with comments | « src/core/SkLinearBitmapPipeline.cpp ('k') | src/core/SkLinearBitmapPipeline_tile.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698