1 /* 2 * Copyright 2012 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 #ifndef SkGradientShaderPriv_DEFINED 9 #define SkGradientShaderPriv_DEFINED 10 11 #include "include/effects/SkGradientShader.h" 12 13 #include "include/core/SkMatrix.h" 14 #include "include/private/SkTArray.h" 15 #include "include/private/SkTemplates.h" 16 #include "src/core/SkArenaAlloc.h" 17 #include "src/shaders/SkShaderBase.h" 18 19 class SkColorSpace; 20 class SkRasterPipeline; 21 class SkReadBuffer; 22 class SkWriteBuffer; 23 24 class SkGradientShaderBase : public SkShaderBase { 25 public: 26 struct Descriptor { DescriptorDescriptor27 Descriptor() { 28 sk_bzero(this, sizeof(*this)); 29 fTileMode = SkTileMode::kClamp; 30 } 31 32 const SkMatrix* fLocalMatrix; 33 const SkColor4f* fColors; 34 sk_sp<SkColorSpace> fColorSpace; 35 const SkScalar* fPos; 36 int fCount; 37 SkTileMode fTileMode; 38 uint32_t fGradFlags; 39 40 void flatten(SkWriteBuffer&) const; 41 }; 42 43 class DescriptorScope : public Descriptor { 44 public: DescriptorScope()45 DescriptorScope() {} 46 47 bool unflatten(SkReadBuffer&); 48 49 // fColors and fPos always point into local memory, so they can be safely mutated 50 // mutableColors()51 SkColor4f* mutableColors() { return const_cast<SkColor4f*>(fColors); } mutablePos()52 SkScalar* mutablePos() { return const_cast<SkScalar*>(fPos); } 53 54 private: 55 SkSTArray<16, SkColor4f, true> fColorStorage; 56 SkSTArray<16, SkScalar , true> fPosStorage; 57 SkMatrix fLocalMatrixStorage; 58 }; 59 60 SkGradientShaderBase(const Descriptor& desc, const SkMatrix& ptsToUnit); 61 ~SkGradientShaderBase() override; 62 63 bool isOpaque() const override; 64 getGradFlags()65 uint32_t getGradFlags() const { return fGradFlags; } 66 getGradientMatrix()67 const SkMatrix& getGradientMatrix() const { return fPtsToUnit; } 68 69 protected: 70 class GradientShaderBase4fContext; 71 72 SkGradientShaderBase(SkReadBuffer& ); 73 void flatten(SkWriteBuffer&) const override; 74 75 void commonAsAGradient(GradientInfo*) const; 76 77 bool onAsLuminanceColor(SkColor*) const override; 78 79 bool onAppendStages(const SkStageRec&) const override; 80 81 virtual void appendGradientStages(SkArenaAlloc* alloc, SkRasterPipeline* tPipeline, 82 SkRasterPipeline* postPipeline) const = 0; 83 84 template <typename T, typename... Args> CheckedMakeContext(SkArenaAlloc * alloc,Args &&...args)85 static Context* CheckedMakeContext(SkArenaAlloc* alloc, Args&&... args) { 86 auto* ctx = alloc->make<T>(std::forward<Args>(args)...); 87 if (!ctx->isValid()) { 88 return nullptr; 89 } 90 return ctx; 91 } 92 93 const SkMatrix fPtsToUnit; 94 SkTileMode fTileMode; 95 uint8_t fGradFlags; 96 97 public: getPos(int i)98 SkScalar getPos(int i) const { 99 SkASSERT(i < fColorCount); 100 return fOrigPos ? fOrigPos[i] : SkIntToScalar(i) / (fColorCount - 1); 101 } 102 getLegacyColor(int i)103 SkColor getLegacyColor(int i) const { 104 SkASSERT(i < fColorCount); 105 return fOrigColors4f[i].toSkColor(); 106 } 107 colorsCanConvertToSkColor()108 bool colorsCanConvertToSkColor() const { 109 bool canConvert = true; 110 for (int i = 0; i < fColorCount; ++i) { 111 canConvert &= fOrigColors4f[i].fitsInBytes(); 112 } 113 return canConvert; 114 } 115 116 SkColor4f* fOrigColors4f; // original colors, as floats 117 SkScalar* fOrigPos; // original positions 118 int fColorCount; 119 sk_sp<SkColorSpace> fColorSpace; // color space of gradient stops 120 colorsAreOpaque()121 bool colorsAreOpaque() const { return fColorsAreOpaque; } 122 getTileMode()123 SkTileMode getTileMode() const { return fTileMode; } 124 125 private: 126 // Reserve inline space for up to 4 stops. 127 static constexpr size_t kInlineStopCount = 4; 128 static constexpr size_t kInlineStorageSize = (sizeof(SkColor4f) + sizeof(SkScalar)) 129 * kInlineStopCount; 130 SkAutoSTMalloc<kInlineStorageSize, uint8_t> fStorage; 131 132 bool fColorsAreOpaque; 133 134 typedef SkShaderBase INHERITED; 135 }; 136 137 /////////////////////////////////////////////////////////////////////////////// 138 139 struct SkColor4fXformer { 140 SkColor4fXformer(const SkColor4f* colors, int colorCount, SkColorSpace* src, SkColorSpace* dst); 141 142 const SkColor4f* fColors; 143 SkSTArray<4, SkColor4f, true> fStorage; 144 }; 145 146 #endif 147