OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2012 The Android Open Source Project | 2 * Copyright 2012 The Android Open Source Project |
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 "SkMorphologyImageFilter.h" | 8 #include "SkMorphologyImageFilter.h" |
9 #include "SkBitmap.h" | 9 #include "SkBitmap.h" |
10 #include "SkColorPriv.h" | 10 #include "SkColorPriv.h" |
(...skipping 440 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
451 MorphologyType type = d->fRandom->nextBool() ? GrMorphologyEffect::kErode_Mo
rphologyType : | 451 MorphologyType type = d->fRandom->nextBool() ? GrMorphologyEffect::kErode_Mo
rphologyType : |
452 GrMorphologyEffect::kDilate_Morph
ologyType; | 452 GrMorphologyEffect::kDilate_Morph
ologyType; |
453 | 453 |
454 return GrMorphologyEffect::Create(d->fTextures[texIdx], dir, radius, type); | 454 return GrMorphologyEffect::Create(d->fTextures[texIdx], dir, radius, type); |
455 } | 455 } |
456 | 456 |
457 namespace { | 457 namespace { |
458 | 458 |
459 | 459 |
460 void apply_morphology_rect(GrDrawContext* drawContext, | 460 void apply_morphology_rect(GrDrawContext* drawContext, |
461 GrRenderTarget* rt, | |
462 const GrClip& clip, | 461 const GrClip& clip, |
463 GrTexture* texture, | 462 GrTexture* texture, |
464 const SkIRect& srcRect, | 463 const SkIRect& srcRect, |
465 const SkIRect& dstRect, | 464 const SkIRect& dstRect, |
466 int radius, | 465 int radius, |
467 GrMorphologyEffect::MorphologyType morphType, | 466 GrMorphologyEffect::MorphologyType morphType, |
468 float bounds[2], | 467 float bounds[2], |
469 Gr1DKernelEffect::Direction direction) { | 468 Gr1DKernelEffect::Direction direction) { |
470 GrPaint paint; | 469 GrPaint paint; |
471 paint.addColorFragmentProcessor(GrMorphologyEffect::Create(texture, | 470 paint.addColorFragmentProcessor(GrMorphologyEffect::Create(texture, |
472 direction, | 471 direction, |
473 radius, | 472 radius, |
474 morphType, | 473 morphType, |
475 bounds))->unref()
; | 474 bounds))->unref()
; |
476 drawContext->drawNonAARectToRect(rt, clip, paint, SkMatrix::I(), SkRect::Mak
e(dstRect), | 475 drawContext->drawNonAARectToRect(clip, paint, SkMatrix::I(), SkRect::Make(ds
tRect), |
477 SkRect::Make(srcRect)); | 476 SkRect::Make(srcRect)); |
478 } | 477 } |
479 | 478 |
480 void apply_morphology_rect_no_bounds(GrDrawContext* drawContext, | 479 void apply_morphology_rect_no_bounds(GrDrawContext* drawContext, |
481 GrRenderTarget* rt, | |
482 const GrClip& clip, | 480 const GrClip& clip, |
483 GrTexture* texture, | 481 GrTexture* texture, |
484 const SkIRect& srcRect, | 482 const SkIRect& srcRect, |
485 const SkIRect& dstRect, | 483 const SkIRect& dstRect, |
486 int radius, | 484 int radius, |
487 GrMorphologyEffect::MorphologyType morphTyp
e, | 485 GrMorphologyEffect::MorphologyType morphTyp
e, |
488 Gr1DKernelEffect::Direction direction) { | 486 Gr1DKernelEffect::Direction direction) { |
489 GrPaint paint; | 487 GrPaint paint; |
490 paint.addColorFragmentProcessor(GrMorphologyEffect::Create(texture, | 488 paint.addColorFragmentProcessor(GrMorphologyEffect::Create(texture, |
491 direction, | 489 direction, |
492 radius, | 490 radius, |
493 morphType))->unre
f(); | 491 morphType))->unre
f(); |
494 drawContext->drawNonAARectToRect(rt, clip, paint, SkMatrix::I(), SkRect::Mak
e(dstRect), | 492 drawContext->drawNonAARectToRect(clip, paint, SkMatrix::I(), SkRect::Make(ds
tRect), |
495 SkRect::Make(srcRect)); | 493 SkRect::Make(srcRect)); |
496 } | 494 } |
497 | 495 |
498 void apply_morphology_pass(GrDrawContext* drawContext, | 496 void apply_morphology_pass(GrDrawContext* drawContext, |
499 GrRenderTarget* rt, | |
500 const GrClip& clip, | 497 const GrClip& clip, |
501 GrTexture* texture, | 498 GrTexture* texture, |
502 const SkIRect& srcRect, | 499 const SkIRect& srcRect, |
503 const SkIRect& dstRect, | 500 const SkIRect& dstRect, |
504 int radius, | 501 int radius, |
505 GrMorphologyEffect::MorphologyType morphType, | 502 GrMorphologyEffect::MorphologyType morphType, |
506 Gr1DKernelEffect::Direction direction) { | 503 Gr1DKernelEffect::Direction direction) { |
507 float bounds[2] = { 0.0f, 1.0f }; | 504 float bounds[2] = { 0.0f, 1.0f }; |
508 SkIRect lowerSrcRect = srcRect, lowerDstRect = dstRect; | 505 SkIRect lowerSrcRect = srcRect, lowerDstRect = dstRect; |
509 SkIRect middleSrcRect = srcRect, middleDstRect = dstRect; | 506 SkIRect middleSrcRect = srcRect, middleDstRect = dstRect; |
(...skipping 12 matching lines...) Expand all Loading... |
522 bounds[1] = (SkIntToScalar(srcRect.bottom()) - 0.5f) / texture->height()
; | 519 bounds[1] = (SkIntToScalar(srcRect.bottom()) - 0.5f) / texture->height()
; |
523 lowerSrcRect.fBottom = srcRect.top() + radius; | 520 lowerSrcRect.fBottom = srcRect.top() + radius; |
524 lowerDstRect.fBottom = dstRect.top() + radius; | 521 lowerDstRect.fBottom = dstRect.top() + radius; |
525 upperSrcRect.fTop = srcRect.bottom() - radius; | 522 upperSrcRect.fTop = srcRect.bottom() - radius; |
526 upperDstRect.fTop = dstRect.bottom() - radius; | 523 upperDstRect.fTop = dstRect.bottom() - radius; |
527 middleSrcRect.inset(0, radius); | 524 middleSrcRect.inset(0, radius); |
528 middleDstRect.inset(0, radius); | 525 middleDstRect.inset(0, radius); |
529 } | 526 } |
530 if (middleSrcRect.fLeft - middleSrcRect.fRight >= 0) { | 527 if (middleSrcRect.fLeft - middleSrcRect.fRight >= 0) { |
531 // radius covers srcRect; use bounds over entire draw | 528 // radius covers srcRect; use bounds over entire draw |
532 apply_morphology_rect(drawContext, rt, clip, texture, srcRect, dstRect,
radius, | 529 apply_morphology_rect(drawContext, clip, texture, srcRect, dstRect, radi
us, |
533 morphType, bounds, direction); | 530 morphType, bounds, direction); |
534 } else { | 531 } else { |
535 // Draw upper and lower margins with bounds; middle without. | 532 // Draw upper and lower margins with bounds; middle without. |
536 apply_morphology_rect(drawContext, rt, clip, texture, lowerSrcRect, lowe
rDstRect, radius, | 533 apply_morphology_rect(drawContext, clip, texture, lowerSrcRect, lowerDst
Rect, radius, |
537 morphType, bounds, direction); | 534 morphType, bounds, direction); |
538 apply_morphology_rect(drawContext, rt, clip, texture, upperSrcRect, uppe
rDstRect, radius, | 535 apply_morphology_rect(drawContext, clip, texture, upperSrcRect, upperDst
Rect, radius, |
539 morphType, bounds, direction); | 536 morphType, bounds, direction); |
540 apply_morphology_rect_no_bounds(drawContext, rt, clip, texture, middleSr
cRect, middleDstRect, | 537 apply_morphology_rect_no_bounds(drawContext, clip, texture, middleSrcRec
t, middleDstRect, |
541 radius, morphType, direction); | 538 radius, morphType, direction); |
542 } | 539 } |
543 } | 540 } |
544 | 541 |
545 bool apply_morphology(const SkBitmap& input, | 542 bool apply_morphology(const SkBitmap& input, |
546 const SkIRect& rect, | 543 const SkIRect& rect, |
547 GrMorphologyEffect::MorphologyType morphType, | 544 GrMorphologyEffect::MorphologyType morphType, |
548 SkISize radius, | 545 SkISize radius, |
549 SkBitmap* dst) { | 546 SkBitmap* dst) { |
550 SkAutoTUnref<GrTexture> srcTexture(SkRef(input.getTexture())); | 547 SkAutoTUnref<GrTexture> srcTexture(SkRef(input.getTexture())); |
(...skipping 10 matching lines...) Expand all Loading... |
561 desc.fWidth = rect.width(); | 558 desc.fWidth = rect.width(); |
562 desc.fHeight = rect.height(); | 559 desc.fHeight = rect.height(); |
563 desc.fConfig = kSkia8888_GrPixelConfig; | 560 desc.fConfig = kSkia8888_GrPixelConfig; |
564 SkIRect srcRect = rect; | 561 SkIRect srcRect = rect; |
565 | 562 |
566 if (radius.fWidth > 0) { | 563 if (radius.fWidth > 0) { |
567 GrTexture* scratch = context->textureProvider()->createApproxTexture(des
c); | 564 GrTexture* scratch = context->textureProvider()->createApproxTexture(des
c); |
568 if (nullptr == scratch) { | 565 if (nullptr == scratch) { |
569 return false; | 566 return false; |
570 } | 567 } |
571 SkAutoTUnref<GrDrawContext> dstDrawContext(context->drawContext()); | 568 SkAutoTUnref<GrDrawContext> dstDrawContext(context->drawContext(scratch-
>asRenderTarget())); |
572 if (!dstDrawContext) { | 569 if (!dstDrawContext) { |
573 return false; | 570 return false; |
574 } | 571 } |
575 | 572 |
576 apply_morphology_pass(dstDrawContext, scratch->asRenderTarget(), clip, s
rcTexture, | 573 apply_morphology_pass(dstDrawContext, clip, srcTexture, |
577 srcRect, dstRect, radius.fWidth, morphType, | 574 srcRect, dstRect, radius.fWidth, morphType, |
578 Gr1DKernelEffect::kX_Direction); | 575 Gr1DKernelEffect::kX_Direction); |
579 SkIRect clearRect = SkIRect::MakeXYWH(dstRect.fLeft, dstRect.fBottom, | 576 SkIRect clearRect = SkIRect::MakeXYWH(dstRect.fLeft, dstRect.fBottom, |
580 dstRect.width(), radius.fHeight); | 577 dstRect.width(), radius.fHeight); |
581 GrColor clearColor = GrMorphologyEffect::kErode_MorphologyType == morphT
ype ? | 578 GrColor clearColor = GrMorphologyEffect::kErode_MorphologyType == morphT
ype ? |
582 SK_ColorWHITE : | 579 SK_ColorWHITE : |
583 SK_ColorTRANSPARENT; | 580 SK_ColorTRANSPARENT; |
584 dstDrawContext->clear(scratch->asRenderTarget(), &clearRect, clearColor,
false); | 581 dstDrawContext->clear(&clearRect, clearColor, false); |
585 | 582 |
586 srcTexture.reset(scratch); | 583 srcTexture.reset(scratch); |
587 srcRect = dstRect; | 584 srcRect = dstRect; |
588 } | 585 } |
589 if (radius.fHeight > 0) { | 586 if (radius.fHeight > 0) { |
590 GrTexture* scratch = context->textureProvider()->createApproxTexture(des
c); | 587 GrTexture* scratch = context->textureProvider()->createApproxTexture(des
c); |
591 if (nullptr == scratch) { | 588 if (nullptr == scratch) { |
592 return false; | 589 return false; |
593 } | 590 } |
594 SkAutoTUnref<GrDrawContext> dstDrawContext(context->drawContext()); | 591 SkAutoTUnref<GrDrawContext> dstDrawContext(context->drawContext(scratch-
>asRenderTarget())); |
595 if (!dstDrawContext) { | 592 if (!dstDrawContext) { |
596 return false; | 593 return false; |
597 } | 594 } |
598 | 595 |
599 apply_morphology_pass(dstDrawContext, scratch->asRenderTarget(), clip, s
rcTexture, | 596 apply_morphology_pass(dstDrawContext, clip, srcTexture, |
600 srcRect, dstRect, radius.fHeight, morphType, | 597 srcRect, dstRect, radius.fHeight, morphType, |
601 Gr1DKernelEffect::kY_Direction); | 598 Gr1DKernelEffect::kY_Direction); |
602 | 599 |
603 srcTexture.reset(scratch); | 600 srcTexture.reset(scratch); |
604 } | 601 } |
605 SkImageFilter::WrapTexture(srcTexture, rect.width(), rect.height(), dst); | 602 SkImageFilter::WrapTexture(srcTexture, rect.width(), rect.height(), dst); |
606 return true; | 603 return true; |
607 } | 604 } |
608 | 605 |
609 }; | 606 }; |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
657 SkBitmap* result, SkIPoint* offset) con
st { | 654 SkBitmap* result, SkIPoint* offset) con
st { |
658 return this->filterImageGPUGeneric(true, proxy, src, ctx, result, offset); | 655 return this->filterImageGPUGeneric(true, proxy, src, ctx, result, offset); |
659 } | 656 } |
660 | 657 |
661 bool SkErodeImageFilter::filterImageGPU(Proxy* proxy, const SkBitmap& src, const
Context& ctx, | 658 bool SkErodeImageFilter::filterImageGPU(Proxy* proxy, const SkBitmap& src, const
Context& ctx, |
662 SkBitmap* result, SkIPoint* offset) cons
t { | 659 SkBitmap* result, SkIPoint* offset) cons
t { |
663 return this->filterImageGPUGeneric(false, proxy, src, ctx, result, offset); | 660 return this->filterImageGPUGeneric(false, proxy, src, ctx, result, offset); |
664 } | 661 } |
665 | 662 |
666 #endif | 663 #endif |
OLD | NEW |