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

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

Issue 207683004: Extract most of the mutable state of SkShader into a separate Context object. (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: rebase Created 6 years, 8 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/SkBlitter.h ('k') | src/core/SkBlitter_A8.cpp » ('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 /* 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 "SkBlitter.h" 10 #include "SkBlitter.h"
11 #include "SkAntiRun.h" 11 #include "SkAntiRun.h"
12 #include "SkColor.h" 12 #include "SkColor.h"
13 #include "SkColorFilter.h" 13 #include "SkColorFilter.h"
14 #include "SkCoreBlitters.h" 14 #include "SkCoreBlitters.h"
15 #include "SkFilterShader.h" 15 #include "SkFilterShader.h"
16 #include "SkReadBuffer.h" 16 #include "SkReadBuffer.h"
17 #include "SkWriteBuffer.h" 17 #include "SkWriteBuffer.h"
18 #include "SkMask.h" 18 #include "SkMask.h"
19 #include "SkMaskFilter.h" 19 #include "SkMaskFilter.h"
20 #include "SkString.h" 20 #include "SkString.h"
21 #include "SkTLazy.h" 21 #include "SkTLazy.h"
22 #include "SkUtils.h" 22 #include "SkUtils.h"
23 #include "SkXfermode.h" 23 #include "SkXfermode.h"
24 24
25 SkBlitter::~SkBlitter() {} 25 SkBlitter::~SkBlitter() {}
26 26
27 bool SkBlitter::isNullBlitter() const { return false; } 27 bool SkBlitter::isNullBlitter() const { return false; }
28 28
29 bool SkBlitter::resetShaderContext(const SkBitmap& device, const SkPaint& paint,
30 const SkMatrix& matrix) {
31 return true;
32 }
33
34 SkShader::Context* SkBlitter::getShaderContext() const {
35 return NULL;
36 }
37
29 const SkBitmap* SkBlitter::justAnOpaqueColor(uint32_t* value) { 38 const SkBitmap* SkBlitter::justAnOpaqueColor(uint32_t* value) {
30 return NULL; 39 return NULL;
31 } 40 }
32 41
33 void SkBlitter::blitH(int x, int y, int width) { 42 void SkBlitter::blitH(int x, int y, int width) {
34 SkDEBUGFAIL("unimplemented"); 43 SkDEBUGFAIL("unimplemented");
35 } 44 }
36 45
37 void SkBlitter::blitAntiH(int x, int y, const SkAlpha antialias[], 46 void SkBlitter::blitAntiH(int x, int y, const SkAlpha antialias[],
38 const int16_t runs[]) { 47 const int16_t runs[]) {
(...skipping 522 matching lines...) Expand 10 before | Expand all | Expand 10 after
561 570
562 /////////////////////////////////////////////////////////////////////////////// 571 ///////////////////////////////////////////////////////////////////////////////
563 572
564 #include "SkColorShader.h" 573 #include "SkColorShader.h"
565 #include "SkColorPriv.h" 574 #include "SkColorPriv.h"
566 575
567 class Sk3DShader : public SkShader { 576 class Sk3DShader : public SkShader {
568 public: 577 public:
569 Sk3DShader(SkShader* proxy) : fProxy(proxy) { 578 Sk3DShader(SkShader* proxy) : fProxy(proxy) {
570 SkSafeRef(proxy); 579 SkSafeRef(proxy);
571 fMask = NULL;
572 } 580 }
573 581
574 virtual ~Sk3DShader() { 582 virtual ~Sk3DShader() {
575 SkSafeUnref(fProxy); 583 SkSafeUnref(fProxy);
576 } 584 }
577 585
578 void setMask(const SkMask* mask) { fMask = mask; } 586 virtual size_t contextSize() const SK_OVERRIDE {
587 size_t size = sizeof(Sk3DShaderContext);
588 if (fProxy) {
589 size += fProxy->contextSize();
590 }
591 return size;
592 }
579 593
580 virtual bool setContext(const SkBitmap& device, const SkPaint& paint, 594 virtual bool validContext(const SkBitmap& device, const SkPaint& paint,
581 const SkMatrix& matrix) SK_OVERRIDE { 595 const SkMatrix& matrix, SkMatrix* totalInverse = N ULL) const
582 if (!this->INHERITED::setContext(device, paint, matrix)) { 596 SK_OVERRIDE
597 {
598 if (!this->INHERITED::validContext(device, paint, matrix, totalInverse)) {
583 return false; 599 return false;
584 } 600 }
585 if (fProxy) { 601 if (fProxy) {
586 if (!fProxy->setContext(device, paint, matrix)) { 602 return fProxy->validContext(device, paint, matrix);
587 // must keep our set/end context calls balanced
588 this->INHERITED::endContext();
589 return false;
590 }
591 } else {
592 fPMColor = SkPreMultiplyColor(paint.getColor());
593 } 603 }
594 return true; 604 return true;
595 } 605 }
596 606
597 virtual void endContext() SK_OVERRIDE { 607 virtual SkShader::Context* createContext(const SkBitmap& device,
608 const SkPaint& paint,
609 const SkMatrix& matrix,
610 void* storage) const SK_OVERRIDE
611 {
612 if (!this->validContext(device, paint, matrix)) {
613 return NULL;
614 }
615
616 SkShader::Context* proxyContext;
598 if (fProxy) { 617 if (fProxy) {
599 fProxy->endContext(); 618 char* proxyContextStorage = (char*) storage + sizeof(Sk3DShaderConte xt);
619 proxyContext = fProxy->createContext(device, paint, matrix, proxyCon textStorage);
620 SkASSERT(proxyContext);
621 } else {
622 proxyContext = NULL;
600 } 623 }
601 this->INHERITED::endContext(); 624 return SkNEW_PLACEMENT_ARGS(storage, Sk3DShaderContext, (*this, device, paint, matrix,
625 proxyContext));
602 } 626 }
603 627
604 virtual void shadeSpan(int x, int y, SkPMColor span[], int count) SK_OVERRID E { 628 class Sk3DShaderContext : public SkShader::Context {
605 if (fProxy) { 629 public:
606 fProxy->shadeSpan(x, y, span, count); 630 // Calls proxyContext's destructor but will NOT free its memory.
631 Sk3DShaderContext(const Sk3DShader& shader, const SkBitmap& device, cons t SkPaint& paint,
632 const SkMatrix& matrix, SkShader::Context* proxyContex t)
633 : INHERITED(shader, device, paint, matrix)
634 , fMask(NULL)
635 , fProxyContext(proxyContext)
636 {
637 if (!fProxyContext) {
638 fPMColor = SkPreMultiplyColor(paint.getColor());
639 }
607 } 640 }
608 641
609 if (fMask == NULL) { 642 virtual ~Sk3DShaderContext() {
610 if (fProxy == NULL) { 643 if (fProxyContext) {
611 sk_memset32(span, fPMColor, count); 644 fProxyContext->~Context();
612 } 645 }
613 return;
614 } 646 }
615 647
616 SkASSERT(fMask->fBounds.contains(x, y)); 648 void setMask(const SkMask* mask) { fMask = mask; }
617 SkASSERT(fMask->fBounds.contains(x + count - 1, y));
618 649
619 size_t size = fMask->computeImageSize(); 650 virtual void shadeSpan(int x, int y, SkPMColor span[], int count) SK_OVE RRIDE {
620 const uint8_t* alpha = fMask->getAddr8(x, y); 651 if (fProxyContext) {
621 const uint8_t* mulp = alpha + size; 652 fProxyContext->shadeSpan(x, y, span, count);
622 const uint8_t* addp = mulp + size; 653 }
623 654
624 if (fProxy) { 655 if (fMask == NULL) {
625 for (int i = 0; i < count; i++) { 656 if (fProxyContext == NULL) {
626 if (alpha[i]) { 657 sk_memset32(span, fPMColor, count);
627 SkPMColor c = span[i]; 658 }
628 if (c) { 659 return;
629 unsigned a = SkGetPackedA32(c); 660 }
630 unsigned r = SkGetPackedR32(c);
631 unsigned g = SkGetPackedG32(c);
632 unsigned b = SkGetPackedB32(c);
633 661
662 SkASSERT(fMask->fBounds.contains(x, y));
663 SkASSERT(fMask->fBounds.contains(x + count - 1, y));
664
665 size_t size = fMask->computeImageSize();
666 const uint8_t* alpha = fMask->getAddr8(x, y);
667 const uint8_t* mulp = alpha + size;
668 const uint8_t* addp = mulp + size;
669
670 if (fProxyContext) {
671 for (int i = 0; i < count; i++) {
672 if (alpha[i]) {
673 SkPMColor c = span[i];
674 if (c) {
675 unsigned a = SkGetPackedA32(c);
676 unsigned r = SkGetPackedR32(c);
677 unsigned g = SkGetPackedG32(c);
678 unsigned b = SkGetPackedB32(c);
679
680 unsigned mul = SkAlpha255To256(mulp[i]);
681 unsigned add = addp[i];
682
683 r = SkFastMin32(SkAlphaMul(r, mul) + add, a);
684 g = SkFastMin32(SkAlphaMul(g, mul) + add, a);
685 b = SkFastMin32(SkAlphaMul(b, mul) + add, a);
686
687 span[i] = SkPackARGB32(a, r, g, b);
688 }
689 } else {
690 span[i] = 0;
691 }
692 }
693 } else { // color
694 unsigned a = SkGetPackedA32(fPMColor);
695 unsigned r = SkGetPackedR32(fPMColor);
696 unsigned g = SkGetPackedG32(fPMColor);
697 unsigned b = SkGetPackedB32(fPMColor);
698 for (int i = 0; i < count; i++) {
699 if (alpha[i]) {
634 unsigned mul = SkAlpha255To256(mulp[i]); 700 unsigned mul = SkAlpha255To256(mulp[i]);
635 unsigned add = addp[i]; 701 unsigned add = addp[i];
636 702
637 r = SkFastMin32(SkAlphaMul(r, mul) + add, a); 703 span[i] = SkPackARGB32( a,
638 g = SkFastMin32(SkAlphaMul(g, mul) + add, a); 704 SkFastMin32(SkAlphaMul(r, mul) + add, a) ,
639 b = SkFastMin32(SkAlphaMul(b, mul) + add, a); 705 SkFastMin32(SkAlphaMul(g, mul) + add, a) ,
640 706 SkFastMin32(SkAlphaMul(b, mul) + add, a) );
641 span[i] = SkPackARGB32(a, r, g, b); 707 } else {
708 span[i] = 0;
642 } 709 }
643 } else {
644 span[i] = 0;
645 }
646 }
647 } else { // color
648 unsigned a = SkGetPackedA32(fPMColor);
649 unsigned r = SkGetPackedR32(fPMColor);
650 unsigned g = SkGetPackedG32(fPMColor);
651 unsigned b = SkGetPackedB32(fPMColor);
652 for (int i = 0; i < count; i++) {
653 if (alpha[i]) {
654 unsigned mul = SkAlpha255To256(mulp[i]);
655 unsigned add = addp[i];
656
657 span[i] = SkPackARGB32( a,
658 SkFastMin32(SkAlphaMul(r, mul) + add, a),
659 SkFastMin32(SkAlphaMul(g, mul) + add, a),
660 SkFastMin32(SkAlphaMul(b, mul) + add, a));
661 } else {
662 span[i] = 0;
663 } 710 }
664 } 711 }
665 } 712 }
666 } 713
714 private:
715 // Unowned.
716 const SkMask* fMask;
717 // Memory is unowned, but we need to call the destructor.
718 SkShader::Context* fProxyContext;
719 SkPMColor fPMColor;
720
721 typedef SkShader::Context INHERITED;
722 };
667 723
668 #ifndef SK_IGNORE_TO_STRING 724 #ifndef SK_IGNORE_TO_STRING
669 virtual void toString(SkString* str) const SK_OVERRIDE { 725 virtual void toString(SkString* str) const SK_OVERRIDE {
670 str->append("Sk3DShader: ("); 726 str->append("Sk3DShader: (");
671 727
672 if (NULL != fProxy) { 728 if (NULL != fProxy) {
673 str->append("Proxy: "); 729 str->append("Proxy: ");
674 fProxy->toString(str); 730 fProxy->toString(str);
675 } 731 }
676 732
677 this->INHERITED::toString(str); 733 this->INHERITED::toString(str);
678 734
679 str->append(")"); 735 str->append(")");
680 } 736 }
681 #endif 737 #endif
682 738
683 SK_DECLARE_PUBLIC_FLATTENABLE_DESERIALIZATION_PROCS(Sk3DShader) 739 SK_DECLARE_PUBLIC_FLATTENABLE_DESERIALIZATION_PROCS(Sk3DShader)
684 740
685 protected: 741 protected:
686 Sk3DShader(SkReadBuffer& buffer) : INHERITED(buffer) { 742 Sk3DShader(SkReadBuffer& buffer) : INHERITED(buffer) {
687 fProxy = buffer.readShader(); 743 fProxy = buffer.readShader();
688 fPMColor = buffer.readColor(); 744 // Leaving this here until we bump the picture version, though this
689 fMask = NULL; 745 // shader should never be recorded.
746 buffer.readColor();
690 } 747 }
691 748
692 virtual void flatten(SkWriteBuffer& buffer) const SK_OVERRIDE { 749 virtual void flatten(SkWriteBuffer& buffer) const SK_OVERRIDE {
693 this->INHERITED::flatten(buffer); 750 this->INHERITED::flatten(buffer);
694 buffer.writeFlattenable(fProxy); 751 buffer.writeFlattenable(fProxy);
695 buffer.writeColor(fPMColor); 752 // Leaving this here until we bump the picture version, though this
753 // shader should never be recorded.
754 buffer.writeColor(SkColor());
696 } 755 }
697 756
698 private: 757 private:
699 SkShader* fProxy; 758 SkShader* fProxy;
700 SkPMColor fPMColor;
701 const SkMask* fMask;
702 759
703 typedef SkShader INHERITED; 760 typedef SkShader INHERITED;
704 }; 761 };
705 762
706 class Sk3DBlitter : public SkBlitter { 763 class Sk3DBlitter : public SkBlitter {
707 public: 764 public:
708 Sk3DBlitter(SkBlitter* proxy, Sk3DShader* shader) 765 Sk3DBlitter(SkBlitter* proxy, Sk3DShader::Sk3DShaderContext* shaderContext)
709 : fProxy(proxy) 766 : fProxy(proxy)
710 , f3DShader(SkRef(shader)) 767 , f3DShaderContext(shaderContext)
711 {} 768 {}
712 769
713 virtual void blitH(int x, int y, int width) { 770 virtual void blitH(int x, int y, int width) {
714 fProxy->blitH(x, y, width); 771 fProxy->blitH(x, y, width);
715 } 772 }
716 773
717 virtual void blitAntiH(int x, int y, const SkAlpha antialias[], 774 virtual void blitAntiH(int x, int y, const SkAlpha antialias[],
718 const int16_t runs[]) { 775 const int16_t runs[]) {
719 fProxy->blitAntiH(x, y, antialias, runs); 776 fProxy->blitAntiH(x, y, antialias, runs);
720 } 777 }
721 778
722 virtual void blitV(int x, int y, int height, SkAlpha alpha) { 779 virtual void blitV(int x, int y, int height, SkAlpha alpha) {
723 fProxy->blitV(x, y, height, alpha); 780 fProxy->blitV(x, y, height, alpha);
724 } 781 }
725 782
726 virtual void blitRect(int x, int y, int width, int height) { 783 virtual void blitRect(int x, int y, int width, int height) {
727 fProxy->blitRect(x, y, width, height); 784 fProxy->blitRect(x, y, width, height);
728 } 785 }
729 786
730 virtual void blitMask(const SkMask& mask, const SkIRect& clip) { 787 virtual void blitMask(const SkMask& mask, const SkIRect& clip) {
731 if (mask.fFormat == SkMask::k3D_Format) { 788 if (mask.fFormat == SkMask::k3D_Format) {
732 f3DShader->setMask(&mask); 789 f3DShaderContext->setMask(&mask);
733 790
734 ((SkMask*)&mask)->fFormat = SkMask::kA8_Format; 791 ((SkMask*)&mask)->fFormat = SkMask::kA8_Format;
735 fProxy->blitMask(mask, clip); 792 fProxy->blitMask(mask, clip);
736 ((SkMask*)&mask)->fFormat = SkMask::k3D_Format; 793 ((SkMask*)&mask)->fFormat = SkMask::k3D_Format;
737 794
738 f3DShader->setMask(NULL); 795 f3DShaderContext->setMask(NULL);
739 } else { 796 } else {
740 fProxy->blitMask(mask, clip); 797 fProxy->blitMask(mask, clip);
741 } 798 }
742 } 799 }
743 800
744 private: 801 private:
745 // fProxy is unowned. It will be deleted by SkSmallAllocator. 802 // Both pointers are unowned. They will be deleted by SkSmallAllocator.
746 SkBlitter* fProxy; 803 SkBlitter* fProxy;
747 SkAutoTUnref<Sk3DShader> f3DShader; 804 Sk3DShader::Sk3DShaderContext* f3DShaderContext;
748 }; 805 };
749 806
750 /////////////////////////////////////////////////////////////////////////////// 807 ///////////////////////////////////////////////////////////////////////////////
751 808
752 #include "SkCoreBlitters.h" 809 #include "SkCoreBlitters.h"
753 810
754 static bool just_solid_color(const SkPaint& paint) { 811 static bool just_solid_color(const SkPaint& paint) {
755 if (paint.getAlpha() == 0xFF && paint.getColorFilter() == NULL) { 812 if (paint.getAlpha() == 0xFF && paint.getColorFilter() == NULL) {
756 SkShader* shader = paint.getShader(); 813 SkShader* shader = paint.getShader();
757 if (NULL == shader || 814 if (NULL == shader) {
758 (shader->getFlags() & SkShader::kOpaqueAlpha_Flag)) {
759 return true; 815 return true;
760 } 816 }
761 } 817 }
762 return false; 818 return false;
763 } 819 }
764 820
765 /** By analyzing the paint (with an xfermode), we may decide we can take 821 /** By analyzing the paint (with an xfermode), we may decide we can take
766 special action. This enum lists our possible actions 822 special action. This enum lists our possible actions
767 */ 823 */
768 enum XferInterp { 824 enum XferInterp {
(...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after
886 942
887 if (cf) { 943 if (cf) {
888 SkASSERT(shader); 944 SkASSERT(shader);
889 shader = SkNEW_ARGS(SkFilterShader, (shader, cf)); 945 shader = SkNEW_ARGS(SkFilterShader, (shader, cf));
890 paint.writable()->setShader(shader)->unref(); 946 paint.writable()->setShader(shader)->unref();
891 // blitters should ignore the presence/absence of a filter, since 947 // blitters should ignore the presence/absence of a filter, since
892 // if there is one, the shader will take care of it. 948 // if there is one, the shader will take care of it.
893 } 949 }
894 950
895 /* 951 /*
896 * We need to have balanced calls to the shader: 952 * We create a SkShader::Context object, and store it on the blitter.
897 * setContext
898 * endContext
899 * We make the first call here, in case it fails we can abort the draw.
900 * The endContext() call is made by the blitter (assuming setContext did
901 * not fail) in its destructor.
902 */ 953 */
903 if (shader && !shader->setContext(device, *paint, matrix)) { 954 SkShader::Context* shaderContext;
904 blitter = allocator->createT<SkNullBlitter>(); 955 if (shader) {
905 return blitter; 956 // Try to create the ShaderContext
957 void* storage = allocator->reserveT<SkShader::Context>(shader->contextSi ze());
958 shaderContext = shader->createContext(device, *paint, matrix, storage);
959 if (!shaderContext) {
960 allocator->freeLast();
961 blitter = allocator->createT<SkNullBlitter>();
962 return blitter;
963 }
964 SkASSERT(shaderContext);
965 SkASSERT((void*) shaderContext == storage);
966 } else {
967 shaderContext = NULL;
906 } 968 }
907 969
908 970
909 switch (device.colorType()) { 971 switch (device.colorType()) {
910 case kAlpha_8_SkColorType: 972 case kAlpha_8_SkColorType:
911 if (drawCoverage) { 973 if (drawCoverage) {
912 SkASSERT(NULL == shader); 974 SkASSERT(NULL == shader);
913 SkASSERT(NULL == paint->getXfermode()); 975 SkASSERT(NULL == paint->getXfermode());
914 blitter = allocator->createT<SkA8_Coverage_Blitter>(device, *pai nt); 976 blitter = allocator->createT<SkA8_Coverage_Blitter>(device, *pai nt);
915 } else if (shader) { 977 } else if (shader) {
916 blitter = allocator->createT<SkA8_Shader_Blitter>(device, *paint ); 978 blitter = allocator->createT<SkA8_Shader_Blitter>(device, *paint , shaderContext);
917 } else { 979 } else {
918 blitter = allocator->createT<SkA8_Blitter>(device, *paint); 980 blitter = allocator->createT<SkA8_Blitter>(device, *paint);
919 } 981 }
920 break; 982 break;
921 983
922 case kRGB_565_SkColorType: 984 case kRGB_565_SkColorType:
923 blitter = SkBlitter_ChooseD565(device, *paint, allocator); 985 blitter = SkBlitter_ChooseD565(device, *paint, shaderContext, alloca tor);
924 break; 986 break;
925 987
926 case kN32_SkColorType: 988 case kN32_SkColorType:
927 if (shader) { 989 if (shader) {
928 blitter = allocator->createT<SkARGB32_Shader_Blitter>(device, *p aint); 990 blitter = allocator->createT<SkARGB32_Shader_Blitter>(
991 device, *paint, shaderContext);
929 } else if (paint->getColor() == SK_ColorBLACK) { 992 } else if (paint->getColor() == SK_ColorBLACK) {
930 blitter = allocator->createT<SkARGB32_Black_Blitter>(device, *pa int); 993 blitter = allocator->createT<SkARGB32_Black_Blitter>(device, *pa int);
931 } else if (paint->getAlpha() == 0xFF) { 994 } else if (paint->getAlpha() == 0xFF) {
932 blitter = allocator->createT<SkARGB32_Opaque_Blitter>(device, *p aint); 995 blitter = allocator->createT<SkARGB32_Opaque_Blitter>(device, *p aint);
933 } else { 996 } else {
934 blitter = allocator->createT<SkARGB32_Blitter>(device, *paint); 997 blitter = allocator->createT<SkARGB32_Blitter>(device, *paint);
935 } 998 }
936 break; 999 break;
937 1000
938 default: 1001 default:
939 SkDEBUGFAIL("unsupported device config"); 1002 SkDEBUGFAIL("unsupported device config");
940 blitter = allocator->createT<SkNullBlitter>(); 1003 blitter = allocator->createT<SkNullBlitter>();
941 break; 1004 break;
942 } 1005 }
943 1006
944 if (shader3D) { 1007 if (shader3D) {
945 SkBlitter* innerBlitter = blitter; 1008 SkBlitter* innerBlitter = blitter;
946 // innerBlitter was allocated by allocator, which will delete it. 1009 // innerBlitter was allocated by allocator, which will delete it.
947 blitter = allocator->createT<Sk3DBlitter>(innerBlitter, shader3D); 1010 // We know shaderContext is of type Sk3DShaderContext because it belongs to shader3D.
1011 blitter = allocator->createT<Sk3DBlitter>(innerBlitter,
1012 static_cast<Sk3DShader::Sk3DShaderContext*>(shaderContext));
948 } 1013 }
949 return blitter; 1014 return blitter;
950 } 1015 }
951 1016
952 /////////////////////////////////////////////////////////////////////////////// 1017 ///////////////////////////////////////////////////////////////////////////////
953 1018
954 const uint16_t gMask_0F0F = 0xF0F; 1019 const uint16_t gMask_0F0F = 0xF0F;
955 const uint32_t gMask_00FF00FF = 0xFF00FF; 1020 const uint32_t gMask_00FF00FF = 0xFF00FF;
956 1021
957 /////////////////////////////////////////////////////////////////////////////// 1022 ///////////////////////////////////////////////////////////////////////////////
958 1023
959 SkShaderBlitter::SkShaderBlitter(const SkBitmap& device, const SkPaint& paint) 1024 SkShaderBlitter::SkShaderBlitter(const SkBitmap& device, const SkPaint& paint,
960 : INHERITED(device) { 1025 SkShader::Context* shaderContext)
961 fShader = paint.getShader(); 1026 : INHERITED(device)
1027 , fShader(paint.getShader())
1028 , fShaderContext(shaderContext) {
962 SkASSERT(fShader); 1029 SkASSERT(fShader);
963 SkASSERT(fShader->setContextHasBeenCalled()); 1030 SkASSERT(fShaderContext);
964 1031
965 fShader->ref(); 1032 fShader->ref();
966 fShaderFlags = fShader->getFlags(); 1033 fShaderFlags = fShaderContext->getFlags();
967 } 1034 }
968 1035
969 SkShaderBlitter::~SkShaderBlitter() { 1036 SkShaderBlitter::~SkShaderBlitter() {
970 SkASSERT(fShader->setContextHasBeenCalled());
971 fShader->endContext();
972 fShader->unref(); 1037 fShader->unref();
973 } 1038 }
1039
1040 bool SkShaderBlitter::resetShaderContext(const SkBitmap& device, const SkPaint& paint,
1041 const SkMatrix& matrix) {
1042 if (!fShader->validContext(device, paint, matrix)) {
1043 return false;
1044 }
1045
1046 // Only destroy the old context if we have a new one. We need to ensure to h ave a
1047 // live context in fShaderContext because the storage is owned by an SkSmall Allocator
1048 // outside of this class.
1049 // The new context will be of the same size as the old one because we use th e same
1050 // shader to create it. It is therefore safe to re-use the storage.
1051 fShaderContext->~Context();
1052 fShaderContext = fShader->createContext(device, paint, matrix, (void*)fShade rContext);
1053 SkASSERT(fShaderContext);
1054
1055 return true;
1056 }
OLDNEW
« no previous file with comments | « src/core/SkBlitter.h ('k') | src/core/SkBlitter_A8.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698