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

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

Issue 1934313002: move colorshader into its own .cpp, add color4f variant (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: register for serialization, amend GM view for future picture expansion Created 4 years, 7 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/SkColorShader.h ('k') | src/core/SkGlobalInitialization_core.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 /*
2 * Copyright 2016 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 "SkColorShader.h"
9 #include "SkColorSpace.h"
10 #include "SkReadBuffer.h"
11 #include "SkUtils.h"
12
13 SkColorShader::SkColorShader(SkColor c) : fColor(c) {}
14
15 bool SkColorShader::isOpaque() const {
16 return SkColorGetA(fColor) == 255;
17 }
18
19 sk_sp<SkFlattenable> SkColorShader::CreateProc(SkReadBuffer& buffer) {
20 return sk_make_sp<SkColorShader>(buffer.readColor());
21 }
22
23 void SkColorShader::flatten(SkWriteBuffer& buffer) const {
24 buffer.writeColor(fColor);
25 }
26
27 uint32_t SkColorShader::ColorShaderContext::getFlags() const {
28 return fFlags;
29 }
30
31 SkShader::Context* SkColorShader::onCreateContext(const ContextRec& rec, void* s torage) const {
32 return new (storage) ColorShaderContext(*this, rec);
33 }
34
35 SkColorShader::ColorShaderContext::ColorShaderContext(const SkColorShader& shade r,
36 const ContextRec& rec)
37 : INHERITED(shader, rec)
38 {
39 SkColor color = shader.fColor;
40 unsigned a = SkAlphaMul(SkColorGetA(color), SkAlpha255To256(rec.fPaint->getA lpha()));
41
42 unsigned r = SkColorGetR(color);
43 unsigned g = SkColorGetG(color);
44 unsigned b = SkColorGetB(color);
45
46 if (a != 255) {
47 r = SkMulDiv255Round(r, a);
48 g = SkMulDiv255Round(g, a);
49 b = SkMulDiv255Round(b, a);
50 }
51 fPMColor = SkPackARGB32(a, r, g, b);
52
53 SkColor4f c4 = SkColor4f::FromColor(shader.fColor);
54 c4.fA *= rec.fPaint->getAlpha() / 255.0f;
55 fPM4f = c4.premul();
56
57 fFlags = kConstInY32_Flag;
58 if (255 == a) {
59 fFlags |= kOpaqueAlpha_Flag;
60 }
61 }
62
63 void SkColorShader::ColorShaderContext::shadeSpan(int x, int y, SkPMColor span[] , int count) {
64 sk_memset32(span, fPMColor, count);
65 }
66
67 void SkColorShader::ColorShaderContext::shadeSpanAlpha(int x, int y, uint8_t alp ha[], int count) {
68 memset(alpha, SkGetPackedA32(fPMColor), count);
69 }
70
71 void SkColorShader::ColorShaderContext::shadeSpan4f(int x, int y, SkPM4f span[], int count) {
72 for (int i = 0; i < count; ++i) {
73 span[i] = fPM4f;
74 }
75 }
76
77 SkShader::GradientType SkColorShader::asAGradient(GradientInfo* info) const {
78 if (info) {
79 if (info->fColors && info->fColorCount >= 1) {
80 info->fColors[0] = fColor;
81 }
82 info->fColorCount = 1;
83 info->fTileMode = SkShader::kRepeat_TileMode;
84 }
85 return kColor_GradientType;
86 }
87
88 #if SK_SUPPORT_GPU
89
90 #include "SkGr.h"
91 #include "effects/GrConstColorProcessor.h"
92 const GrFragmentProcessor* SkColorShader::asFragmentProcessor(GrContext*, const SkMatrix&,
93 const SkMatrix*,
94 SkFilterQuality) c onst {
95 GrColor color = SkColorToPremulGrColor(fColor);
96 return GrConstColorProcessor::Create(color, GrConstColorProcessor::kModulate A_InputMode);
97 }
98
99 #endif
100
101 #ifndef SK_IGNORE_TO_STRING
102 void SkColorShader::toString(SkString* str) const {
103 str->append("SkColorShader: (");
104
105 str->append("Color: ");
106 str->appendHex(fColor);
107
108 this->INHERITED::toString(str);
109
110 str->append(")");
111 }
112 #endif
113
114 //////////////////////////////////////////////////////////////////////////////// ///////////////////
115 //////////////////////////////////////////////////////////////////////////////// ///////////////////
116
117 static unsigned unit_to_byte(float unit) {
118 SkASSERT(unit >= 0 && unit <= 1);
119 return (unsigned)(unit * 255 + 0.5);
120 }
121
122 static SkColor unit_to_skcolor(const SkColor4f& unit, SkColorSpace* cs) {
123 return SkColorSetARGB(unit_to_byte(unit.fA), unit_to_byte(unit.fR),
124 unit_to_byte(unit.fG), unit_to_byte(unit.fB));
125 }
126
127 SkColor4Shader::SkColor4Shader(const SkColor4f& color, sk_sp<SkColorSpace> space )
128 : fColorSpace(std::move(space))
129 , fColor4(color)
130 , fCachedByteColor(unit_to_skcolor(color.pin(), space.get()))
131 {}
132
133 sk_sp<SkFlattenable> SkColor4Shader::CreateProc(SkReadBuffer& buffer) {
134 SkColor4f color;
135 color.fA = buffer.readScalar(); // readFloat()
136 color.fR = buffer.readScalar();
137 color.fG = buffer.readScalar();
138 color.fB = buffer.readScalar();
139 if (buffer.readBool()) {
140 // TODO how do we unflatten colorspaces
141 }
142 return SkShader::MakeColorShader(color, nullptr);
143 }
144
145 void SkColor4Shader::flatten(SkWriteBuffer& buffer) const {
146 buffer.writeScalar(fColor4.fA); // writeFloat()
147 buffer.writeScalar(fColor4.fR);
148 buffer.writeScalar(fColor4.fG);
149 buffer.writeScalar(fColor4.fB);
150 buffer.writeBool(false); // TODO how do we flatten colorspaces?
151 }
152
153 uint32_t SkColor4Shader::Color4Context::getFlags() const {
154 return fFlags;
155 }
156
157 SkShader::Context* SkColor4Shader::onCreateContext(const ContextRec& rec, void* storage) const {
158 return new (storage) Color4Context(*this, rec);
159 }
160
161 SkColor4Shader::Color4Context::Color4Context(const SkColor4Shader& shader,
162 const ContextRec& rec)
163 : INHERITED(shader, rec)
164 {
165 SkColor color = shader.fCachedByteColor;
166 unsigned a = SkAlphaMul(SkColorGetA(color), SkAlpha255To256(rec.fPaint->getA lpha()));
167
168 unsigned r = SkColorGetR(color);
169 unsigned g = SkColorGetG(color);
170 unsigned b = SkColorGetB(color);
171
172 if (a != 255) {
173 r = SkMulDiv255Round(r, a);
174 g = SkMulDiv255Round(g, a);
175 b = SkMulDiv255Round(b, a);
176 }
177 fPMColor = SkPackARGB32(a, r, g, b);
178
179 SkColor4f c4 = shader.fColor4;
180 c4.fA *= rec.fPaint->getAlpha() * (1 / 255.0f);
181 fPM4f = c4.premul();
182
183 fFlags = kConstInY32_Flag;
184 if (255 == a) {
185 fFlags |= kOpaqueAlpha_Flag;
186 }
187 }
188
189 void SkColor4Shader::Color4Context::shadeSpan(int x, int y, SkPMColor span[], in t count) {
190 sk_memset32(span, fPMColor, count);
191 }
192
193 void SkColor4Shader::Color4Context::shadeSpanAlpha(int x, int y, uint8_t alpha[] , int count) {
194 memset(alpha, SkGetPackedA32(fPMColor), count);
195 }
196
197 void SkColor4Shader::Color4Context::shadeSpan4f(int x, int y, SkPM4f span[], int count) {
198 for (int i = 0; i < count; ++i) {
199 span[i] = fPM4f;
200 }
201 }
202
203 // TODO: do we need an updated version of this method for color4+colorspace?
204 SkShader::GradientType SkColor4Shader::asAGradient(GradientInfo* info) const {
205 if (info) {
206 if (info->fColors && info->fColorCount >= 1) {
207 info->fColors[0] = fCachedByteColor;
208 }
209 info->fColorCount = 1;
210 info->fTileMode = SkShader::kRepeat_TileMode;
211 }
212 return kColor_GradientType;
213 }
214
215 #if SK_SUPPORT_GPU
216
217 #include "SkGr.h"
218 #include "effects/GrConstColorProcessor.h"
219 const GrFragmentProcessor* SkColor4Shader::asFragmentProcessor(GrContext*, const SkMatrix&,
220 const SkMatrix*,
221 SkFilterQuality) const {
222 // TODO: how to communicate color4f to Gr
223 GrColor color = SkColorToPremulGrColor(fCachedByteColor);
224 return GrConstColorProcessor::Create(color, GrConstColorProcessor::kModulate A_InputMode);
225 }
226
227 #endif
228
229 #ifndef SK_IGNORE_TO_STRING
230 void SkColor4Shader::toString(SkString* str) const {
231 str->append("SkColor4Shader: (");
232
233 str->append("ARGB:");
234 for (int i = 0; i < 4; ++i) {
235 str->appendf(" %g", fColor4.vec()[i]);
236 }
237 str->append(" )");
238 }
239 #endif
240
241 sk_sp<SkShader> SkShader::MakeColorShader(const SkColor4f& color, sk_sp<SkColorS pace> space) {
242 if (!SkScalarsAreFinite(color.vec(), 4)) {
243 return nullptr;
244 }
245 return sk_make_sp<SkColor4Shader>(color, std::move(space));
246 }
247
248 //////////////////////////////////////////////////////////////////////////////// ///////////////////
249 //////////////////////////////////////////////////////////////////////////////// ///////////////////
250
251 static void D32_BlitBW(SkShader::Context::BlitState* state, int x, int y, const SkPixmap& dst,
252 int count) {
253 SkXfermode::D32Proc proc = (SkXfermode::D32Proc)state->fStorage[0];
254 const SkPM4f* src = (const SkPM4f*)state->fStorage[1];
255 proc(state->fXfer, dst.writable_addr32(x, y), src, count, nullptr);
256 }
257
258 static void D32_BlitAA(SkShader::Context::BlitState* state, int x, int y, const SkPixmap& dst,
259 int count, const SkAlpha aa[]) {
260 SkXfermode::D32Proc proc = (SkXfermode::D32Proc)state->fStorage[0];
261 const SkPM4f* src = (const SkPM4f*)state->fStorage[1];
262 proc(state->fXfer, dst.writable_addr32(x, y), src, count, aa);
263 }
264
265 static void F16_BlitBW(SkShader::Context::BlitState* state, int x, int y, const SkPixmap& dst,
266 int count) {
267 SkXfermode::F16Proc proc = (SkXfermode::F16Proc)state->fStorage[0];
268 const SkPM4f* src = (const SkPM4f*)state->fStorage[1];
269 proc(state->fXfer, dst.writable_addr64(x, y), src, count, nullptr);
270 }
271
272 static void F16_BlitAA(SkShader::Context::BlitState* state, int x, int y, const SkPixmap& dst,
273 int count, const SkAlpha aa[]) {
274 SkXfermode::F16Proc proc = (SkXfermode::F16Proc)state->fStorage[0];
275 const SkPM4f* src = (const SkPM4f*)state->fStorage[1];
276 proc(state->fXfer, dst.writable_addr64(x, y), src, count, aa);
277 }
278
279 static bool choose_blitprocs(const SkPM4f* pm4, const SkImageInfo& info,
280 SkShader::Context::BlitState* state) {
281 uint32_t flags = SkXfermode::kSrcIsSingle_D32Flag;
282 if (pm4->a() == 1) {
283 flags |= SkXfermode::kSrcIsOpaque_D32Flag;
284 }
285 switch (info.colorType()) {
286 case kN32_SkColorType:
287 if (info.isSRGB()) {
288 flags |= SkXfermode::kDstIsSRGB_D32Flag;
289 }
290 state->fStorage[0] = (void*)SkXfermode::GetD32Proc(state->fXfer, fla gs);
291 state->fStorage[1] = (void*)pm4;
292 state->fBlitBW = D32_BlitBW;
293 state->fBlitAA = D32_BlitAA;
294 return true;
295 case kRGBA_F16_SkColorType:
296 state->fStorage[0] = (void*)SkXfermode::GetF16Proc(state->fXfer, fla gs);
297 state->fStorage[1] = (void*)pm4;
298 state->fBlitBW = F16_BlitBW;
299 state->fBlitAA = F16_BlitAA;
300 return true;
301 default:
302 return false;
303 }
304 }
305
306 bool SkColorShader::ColorShaderContext::onChooseBlitProcs(const SkImageInfo& inf o,
307 BlitState* state) {
308 return choose_blitprocs(&fPM4f, info, state);
309 }
310
311 bool SkColor4Shader::Color4Context::onChooseBlitProcs(const SkImageInfo& info, B litState* state) {
312 return choose_blitprocs(&fPM4f, info, state);
313 }
OLDNEW
« no previous file with comments | « src/core/SkColorShader.h ('k') | src/core/SkGlobalInitialization_core.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698