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

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

Issue 1810383004: allow more options for shader blitprocs (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: gcc hates my curlies 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 | « include/core/SkShader.h ('k') | src/core/SkColorShader.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 #include "SkCoreBlitters.h" 8 #include "SkCoreBlitters.h"
9 #include "SkColorPriv.h" 9 #include "SkColorPriv.h"
10 #include "SkShader.h" 10 #include "SkShader.h"
(...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after
127 for (int i = 0; i < height; ++i) { 127 for (int i = 0; i < height; ++i) {
128 fState.fProc1(fState.fXfer, device, &fState.fPM4f, width, maskRow); 128 fState.fProc1(fState.fXfer, device, &fState.fPM4f, width, maskRow);
129 device = (typename State::DstType*)((char*)device + dstRB); 129 device = (typename State::DstType*)((char*)device + dstRB);
130 maskRow += maskRB; 130 maskRow += maskRB;
131 } 131 }
132 } 132 }
133 }; 133 };
134 134
135 //////////////////////////////////////////////////////////////////////////////// /////////////////// 135 //////////////////////////////////////////////////////////////////////////////// ///////////////////
136 136
137 template <typename State, bool UseBProc> class SkState_Shader_Blitter : public S kShaderBlitter { 137 template <typename State> class SkState_Shader_Blitter : public SkShaderBlitter {
138 public: 138 public:
139 SkState_Shader_Blitter(const SkPixmap& device, const SkPaint& paint, 139 SkState_Shader_Blitter(const SkPixmap& device, const SkPaint& paint,
140 const SkShader::Context::BlitState& bstate, 140 const SkShader::Context::BlitState& bstate)
141 SkShader::Context::BlitProc bproc)
142 : INHERITED(device, paint, bstate.fCtx) 141 : INHERITED(device, paint, bstate.fCtx)
143 , fState(device.info(), paint, bstate.fCtx) 142 , fState(device.info(), paint, bstate.fCtx)
144 , fBState(bstate) 143 , fBState(bstate)
145 , fBProc(bproc) 144 , fBlitBW(bstate.fBlitBW)
145 , fBlitAA(bstate.fBlitAA)
146 {} 146 {}
147 147
148 void blitH(int x, int y, int width) override { 148 void blitH(int x, int y, int width) override {
149 SkASSERT(x >= 0 && y >= 0 && x + width <= fDevice.width()); 149 SkASSERT(x >= 0 && y >= 0 && x + width <= fDevice.width());
150 150
151 if (UseBProc) { 151 if (fBlitBW) {
152 fBProc(&fBState, x, y, fDevice, width, nullptr); 152 fBlitBW(&fBState, x, y, fDevice, width);
153 return; 153 return;
154 } 154 }
155 155
156 typename State::DstType* device = State::WritableAddr(fDevice, x, y); 156 typename State::DstType* device = State::WritableAddr(fDevice, x, y);
157 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width); 157 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width);
158 fState.fProcN(fState.fXfer, device, fState.fBuffer, width, nullptr); 158 fState.fProcN(fState.fXfer, device, fState.fBuffer, width, nullptr);
159 } 159 }
160 160
161 void blitV(int x, int y, int height, SkAlpha alpha) override { 161 void blitV(int x, int y, int height, SkAlpha alpha) override {
162 SkASSERT(x >= 0 && y >= 0 && y + height <= fDevice.height()); 162 SkASSERT(x >= 0 && y >= 0 && y + height <= fDevice.height());
163 163
164 if (UseBProc) { 164 if (fBlitAA) {
165 for (const int bottom = y + height; y < bottom; ++y) { 165 for (const int bottom = y + height; y < bottom; ++y) {
166 fBProc(&fBState, x, y, fDevice, 1, &alpha); 166 fBlitAA(&fBState, x, y, fDevice, 1, &alpha);
167 } 167 }
168 return; 168 return;
169 } 169 }
170 170
171 typename State::DstType* device = State::WritableAddr(fDevice, x, y); 171 typename State::DstType* device = State::WritableAddr(fDevice, x, y);
172 size_t deviceRB = fDevice.rowBytes(); 172 size_t deviceRB = fDevice.rowBytes();
173 173
174 if (fConstInY) { 174 if (fConstInY) {
175 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, 1); 175 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, 1);
176 } 176 }
177 for (const int bottom = y + height; y < bottom; ++y) { 177 for (const int bottom = y + height; y < bottom; ++y) {
178 if (!fConstInY) { 178 if (!fConstInY) {
179 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, 1); 179 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, 1);
180 } 180 }
181 fState.fProcN(fState.fXfer, device, fState.fBuffer, 1, &alpha); 181 fState.fProcN(fState.fXfer, device, fState.fBuffer, 1, &alpha);
182 device = (typename State::DstType*)((char*)device + deviceRB); 182 device = (typename State::DstType*)((char*)device + deviceRB);
183 } 183 }
184 } 184 }
185 185
186 void blitRect(int x, int y, int width, int height) override { 186 void blitRect(int x, int y, int width, int height) override {
187 SkASSERT(x >= 0 && y >= 0 && 187 SkASSERT(x >= 0 && y >= 0 &&
188 x + width <= fDevice.width() && y + height <= fDevice.height()) ; 188 x + width <= fDevice.width() && y + height <= fDevice.height()) ;
189 189
190 if (UseBProc) { 190 if (fBlitBW) {
191 for (const int bottom = y + height; y < bottom; ++y) { 191 for (const int bottom = y + height; y < bottom; ++y) {
192 fBProc(&fBState, x, y, fDevice, width, nullptr); 192 fBlitBW(&fBState, x, y, fDevice, width);
193 } 193 }
194 return; 194 return;
195 } 195 }
196 196
197 typename State::DstType* device = State::WritableAddr(fDevice, x, y); 197 typename State::DstType* device = State::WritableAddr(fDevice, x, y);
198 size_t deviceRB = fDevice.rowBytes(); 198 size_t deviceRB = fDevice.rowBytes();
199 199
200 if (fConstInY) { 200 if (fConstInY) {
201 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width); 201 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width);
202 } 202 }
203 for (const int bottom = y + height; y < bottom; ++y) { 203 for (const int bottom = y + height; y < bottom; ++y) {
204 if (!fConstInY) { 204 if (!fConstInY) {
205 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width); 205 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width);
206 } 206 }
207 fState.fProcN(fState.fXfer, device, fState.fBuffer, width, nullptr); 207 fState.fProcN(fState.fXfer, device, fState.fBuffer, width, nullptr);
208 device = (typename State::DstType*)((char*)device + deviceRB); 208 device = (typename State::DstType*)((char*)device + deviceRB);
209 } 209 }
210 } 210 }
211 211
212 void blitAntiH(int x, int y, const SkAlpha antialias[], const int16_t runs[] ) override { 212 void blitAntiH(int x, int y, const SkAlpha antialias[], const int16_t runs[] ) override {
213 typename State::DstType* device = State::WritableAddr(fDevice, x, y); 213 typename State::DstType* device = State::WritableAddr(fDevice, x, y);
214 214
215 for (;;) { 215 for (;;) {
216 int count = *runs; 216 int count = *runs;
217 if (count <= 0) { 217 if (count <= 0) {
218 break; 218 break;
219 } 219 }
220 int aa = *antialias; 220 int aa = *antialias;
221 if (aa) { 221 if (aa) {
222 if (UseBProc && (aa == 255)) { 222 if (fBlitBW && (aa == 255)) {
223 fBProc(&fBState, x, y, fDevice, count, nullptr); 223 fBlitBW(&fBState, x, y, fDevice, count);
224 } else { 224 } else {
225 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, count); 225 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, count);
226 if (aa == 255) { 226 if (aa == 255) {
227 fState.fProcN(fState.fXfer, device, fState.fBuffer, coun t, nullptr); 227 fState.fProcN(fState.fXfer, device, fState.fBuffer, coun t, nullptr);
228 } else { 228 } else {
229 for (int i = 0; i < count; ++i) { 229 for (int i = 0; i < count; ++i) {
230 fState.fProcN(fState.fXfer, &device[i], &fState.fBuf fer[i], 1, antialias); 230 fState.fProcN(fState.fXfer, &device[i], &fState.fBuf fer[i], 1, antialias);
231 } 231 }
232 } 232 }
233 } 233 }
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
275 } 275 }
276 276
277 SkASSERT(mask.fBounds.contains(clip)); 277 SkASSERT(mask.fBounds.contains(clip));
278 278
279 const int x = clip.fLeft; 279 const int x = clip.fLeft;
280 const int width = clip.width(); 280 const int width = clip.width();
281 int y = clip.fTop; 281 int y = clip.fTop;
282 const uint8_t* maskRow = (const uint8_t*)mask.getAddr(x, y); 282 const uint8_t* maskRow = (const uint8_t*)mask.getAddr(x, y);
283 const size_t maskRB = mask.fRowBytes; 283 const size_t maskRB = mask.fRowBytes;
284 284
285 if (UseBProc) { 285 if (fBlitAA) {
286 for (; y < clip.fBottom; ++y) { 286 for (; y < clip.fBottom; ++y) {
287 fBProc(&fBState, x, y, fDevice, width, maskRow); 287 fBlitAA(&fBState, x, y, fDevice, width, maskRow);
288 maskRow += maskRB; 288 maskRow += maskRB;
289 } 289 }
290 return; 290 return;
291 } 291 }
292 292
293 typename State::DstType* device = State::WritableAddr(fDevice, x, y); 293 typename State::DstType* device = State::WritableAddr(fDevice, x, y);
294 const size_t deviceRB = fDevice.rowBytes(); 294 const size_t deviceRB = fDevice.rowBytes();
295 295
296 if (fConstInY) { 296 if (fConstInY) {
297 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width); 297 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width);
298 } 298 }
299 for (; y < clip.fBottom; ++y) { 299 for (; y < clip.fBottom; ++y) {
300 if (!fConstInY) { 300 if (!fConstInY) {
301 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width); 301 fShaderContext->shadeSpan4f(x, y, fState.fBuffer, width);
302 } 302 }
303 fState.fProcN(fState.fXfer, device, fState.fBuffer, width, maskRow); 303 fState.fProcN(fState.fXfer, device, fState.fBuffer, width, maskRow);
304 device = (typename State::DstType*)((char*)device + deviceRB); 304 device = (typename State::DstType*)((char*)device + deviceRB);
305 maskRow += maskRB; 305 maskRow += maskRB;
306 } 306 }
307 } 307 }
308 308
309 protected: 309 protected:
310 State fState; 310 State fState;
311 SkShader::Context::BlitState fBState; 311 SkShader::Context::BlitState fBState;
312 SkShader::Context::BlitProc fBProc; 312 SkShader::Context::BlitBW fBlitBW;
313 SkShader::Context::BlitAA fBlitAA;
313 314
314 typedef SkShaderBlitter INHERITED; 315 typedef SkShaderBlitter INHERITED;
315 }; 316 };
316 317
317 //////////////////////////////////////////////////////////////////////////////// /////////////////// 318 //////////////////////////////////////////////////////////////////////////////// ///////////////////
318 //////////////////////////////////////////////////////////////////////////////// /////////////////// 319 //////////////////////////////////////////////////////////////////////////////// ///////////////////
319 320
320 static bool is_opaque(const SkPaint& paint, const SkShader::Context* shaderConte xt) { 321 static bool is_opaque(const SkPaint& paint, const SkShader::Context* shaderConte xt) {
321 return shaderContext ? SkToBool(shaderContext->getFlags() & SkShader::kOpaqu eAlpha_Flag) 322 return shaderContext ? SkToBool(shaderContext->getFlags() & SkShader::kOpaqu eAlpha_Flag)
322 : 0xFF == paint.getAlpha(); 323 : 0xFF == paint.getAlpha();
323 } 324 }
324 325
325 struct State4f { 326 struct State4f {
326 State4f(const SkImageInfo& info, const SkPaint& paint, const SkShader::Conte xt* shaderContext) { 327 State4f(const SkImageInfo& info, const SkPaint& paint, const SkShader::Conte xt* shaderContext) {
327 fXfer = paint.getXfermode(); 328 fXfer = paint.getXfermode();
328 if (shaderContext) { 329 if (shaderContext) {
329 fBuffer.reset(info.width()); 330 fBuffer.reset(info.width());
330 } else { 331 } else {
331 fPM4f = SkColor4f::FromColor(paint.getColor()).premul(); 332 fPM4f = SkColor4f::FromColor(paint.getColor()).premul();
332 } 333 }
333 fFlags = 0; 334 fFlags = 0;
334 } 335 }
335 336
336 SkXfermode* fXfer; 337 SkXfermode* fXfer;
337 SkPM4f fPM4f; 338 SkPM4f fPM4f;
338 SkAutoTMalloc<SkPM4f> fBuffer; 339 SkAutoTMalloc<SkPM4f> fBuffer;
339 uint32_t fFlags; 340 uint32_t fFlags;
340 341
341 SkShader::Context::BlitState fBState; 342 SkShader::Context::BlitState fBState;
342 SkShader::Context::BlitProc fBProc;
343 }; 343 };
344 344
345 struct State32 : State4f { 345 struct State32 : State4f {
346 typedef uint32_t DstType; 346 typedef uint32_t DstType;
347 347
348 SkXfermode::D32Proc fProc1; 348 SkXfermode::D32Proc fProc1;
349 SkXfermode::D32Proc fProcN; 349 SkXfermode::D32Proc fProcN;
350 350
351 State32(const SkImageInfo& info, const SkPaint& paint, const SkShader::Conte xt* shaderContext) 351 State32(const SkImageInfo& info, const SkPaint& paint, const SkShader::Conte xt* shaderContext)
352 : State4f(info, paint, shaderContext) 352 : State4f(info, paint, shaderContext)
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
406 } 406 }
407 }; 407 };
408 408
409 template <typename State> SkBlitter* create(const SkPixmap& device, const SkPain t& paint, 409 template <typename State> SkBlitter* create(const SkPixmap& device, const SkPain t& paint,
410 SkShader::Context* shaderContext, 410 SkShader::Context* shaderContext,
411 SkTBlitterAllocator* allocator) { 411 SkTBlitterAllocator* allocator) {
412 SkASSERT(allocator != nullptr); 412 SkASSERT(allocator != nullptr);
413 413
414 if (shaderContext) { 414 if (shaderContext) {
415 SkShader::Context::BlitState bstate; 415 SkShader::Context::BlitState bstate;
416 sk_bzero(&bstate, sizeof(bstate));
416 bstate.fCtx = shaderContext; 417 bstate.fCtx = shaderContext;
417 bstate.fXfer = paint.getXfermode(); 418 bstate.fXfer = paint.getXfermode();
418 419
419 auto bproc = shaderContext->chooseBlitProc(device.info(), &bstate); 420 (void)shaderContext->chooseBlitProcs(device.info(), &bstate);
420 if (bproc) { 421 return allocator->createT<SkState_Shader_Blitter<State>>(device, paint, bstate);
421 return allocator->createT<SkState_Shader_Blitter<State, true>>(devic e, paint, bstate,
422 bproc );
423 } else {
424 return allocator->createT<SkState_Shader_Blitter<State, false>>(devi ce, paint, bstate,
425 bpro c);
426 }
427 } else { 422 } else {
428 SkColor color = paint.getColor(); 423 SkColor color = paint.getColor();
429 if (0 == SkColorGetA(color)) { 424 if (0 == SkColorGetA(color)) {
430 return nullptr; 425 return nullptr;
431 } 426 }
432 return allocator->createT<SkState_Blitter<State>>(device, paint); 427 return allocator->createT<SkState_Blitter<State>>(device, paint);
433 } 428 }
434 } 429 }
435 430
436 SkBlitter* SkBlitter_ARGB32_Create(const SkPixmap& device, const SkPaint& paint, 431 SkBlitter* SkBlitter_ARGB32_Create(const SkPixmap& device, const SkPaint& paint,
437 SkShader::Context* shaderContext, 432 SkShader::Context* shaderContext,
438 SkTBlitterAllocator* allocator) { 433 SkTBlitterAllocator* allocator) {
439 return create<State32>(device, paint, shaderContext, allocator); 434 return create<State32>(device, paint, shaderContext, allocator);
440 } 435 }
441 436
442 SkBlitter* SkBlitter_ARGB64_Create(const SkPixmap& device, const SkPaint& paint, 437 SkBlitter* SkBlitter_ARGB64_Create(const SkPixmap& device, const SkPaint& paint,
443 SkShader::Context* shaderContext, 438 SkShader::Context* shaderContext,
444 SkTBlitterAllocator* allocator) { 439 SkTBlitterAllocator* allocator) {
445 return create<State64>(device, paint, shaderContext, allocator); 440 return create<State64>(device, paint, shaderContext, allocator);
446 } 441 }
OLDNEW
« no previous file with comments | « include/core/SkShader.h ('k') | src/core/SkColorShader.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698