1 /* 2 * Copyright 2017 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 SkGr_DEFINED 9 #define SkGr_DEFINED 10 11 #include "GrBlend.h" 12 #include "GrColor.h" 13 #include "GrSamplerState.h" 14 #include "GrTypes.h" 15 #include "SkBlendModePriv.h" 16 #include "SkCanvas.h" 17 #include "SkColor.h" 18 #include "SkColorData.h" 19 #include "SkFilterQuality.h" 20 #include "SkImageInfo.h" 21 #include "SkMatrix.h" 22 #include "SkVertices.h" 23 24 class GrCaps; 25 class GrColorSpaceInfo; 26 class GrColorSpaceXform; 27 class GrContext; 28 class GrFragmentProcessor; 29 class GrPaint; 30 class GrRecordingContext; 31 class GrResourceProvider; 32 class GrTextureProxy; 33 class GrUniqueKey; 34 class SkBitmap; 35 class SkData; 36 class SkPaint; 37 class SkPixelRef; 38 class SkPixmap; 39 struct SkIRect; 40 41 //////////////////////////////////////////////////////////////////////////////// 42 // Color type conversions 43 44 static inline GrColor SkColorToPremulGrColor(SkColor c) { 45 SkPMColor pm = SkPreMultiplyColor(c); 46 unsigned r = SkGetPackedR32(pm); 47 unsigned g = SkGetPackedG32(pm); 48 unsigned b = SkGetPackedB32(pm); 49 unsigned a = SkGetPackedA32(pm); 50 return GrColorPackRGBA(r, g, b, a); 51 } 52 53 static inline GrColor SkColorToUnpremulGrColor(SkColor c) { 54 unsigned r = SkColorGetR(c); 55 unsigned g = SkColorGetG(c); 56 unsigned b = SkColorGetB(c); 57 unsigned a = SkColorGetA(c); 58 return GrColorPackRGBA(r, g, b, a); 59 } 60 61 /** Similar, but using SkPMColor4f. */ 62 SkPMColor4f SkColorToPMColor4f(SkColor, const GrColorSpaceInfo&); 63 64 /** Converts an SkColor4f to the destination color space. Pins the color if the destination is 65 normalized, or the device does not support half-float vertex attributes. */ 66 SkColor4f SkColor4fPrepForDst(SkColor4f, const GrColorSpaceInfo&, const GrCaps&); 67 68 //////////////////////////////////////////////////////////////////////////////// 69 // Paint conversion 70 71 /** Converts an SkPaint to a GrPaint for a given GrRecordingContext. The matrix is required in order 72 to convert the SkShader (if any) on the SkPaint. The primitive itself has no color. */ 73 bool SkPaintToGrPaint(GrRecordingContext*, 74 const GrColorSpaceInfo& dstColorSpaceInfo, 75 const SkPaint& skPaint, 76 const SkMatrix& viewM, 77 GrPaint* grPaint); 78 79 /** Same as above but ignores the SkShader (if any) on skPaint. */ 80 bool SkPaintToGrPaintNoShader(GrRecordingContext*, 81 const GrColorSpaceInfo& dstColorSpaceInfo, 82 const SkPaint& skPaint, 83 GrPaint* grPaint); 84 85 /** Replaces the SkShader (if any) on skPaint with the passed in GrFragmentProcessor. The processor 86 should expect an unpremul input color and produce a premultiplied output color. There is 87 no primitive color. */ 88 bool SkPaintToGrPaintReplaceShader(GrRecordingContext*, 89 const GrColorSpaceInfo& dstColorSpaceInfo, 90 const SkPaint& skPaint, 91 std::unique_ptr<GrFragmentProcessor> shaderFP, 92 GrPaint* grPaint); 93 94 /** Blends the SkPaint's shader (or color if no shader) with the color which specified via a 95 GrOp's GrPrimitiveProcesssor. */ 96 bool SkPaintToGrPaintWithXfermode(GrRecordingContext*, 97 const GrColorSpaceInfo& dstColorSpaceInfo, 98 const SkPaint& skPaint, 99 const SkMatrix& viewM, 100 SkBlendMode primColorMode, 101 GrPaint* grPaint); 102 103 /** This is used when there is a primitive color, but the shader should be ignored. Currently, 104 the expectation is that the primitive color will be premultiplied, though it really should be 105 unpremultiplied so that interpolation is done in unpremul space. The paint's alpha will be 106 applied to the primitive color after interpolation. */ 107 inline bool SkPaintToGrPaintWithPrimitiveColor(GrRecordingContext* context, 108 const GrColorSpaceInfo& dstColorSpaceInfo, 109 const SkPaint& skPaint, 110 GrPaint* grPaint) { 111 return SkPaintToGrPaintWithXfermode(context, dstColorSpaceInfo, skPaint, SkMatrix::I(), 112 SkBlendMode::kDst, grPaint); 113 } 114 115 /** This is used when there may or may not be a shader, and the caller wants to plugin a texture 116 lookup. If there is a shader, then its output will only be used if the texture is alpha8. */ 117 bool SkPaintToGrPaintWithTexture(GrRecordingContext*, 118 const GrColorSpaceInfo& dstColorSpaceInfo, 119 const SkPaint& skPaint, 120 const SkMatrix& viewM, 121 std::unique_ptr<GrFragmentProcessor> fp, 122 bool textureIsAlphaOnly, 123 GrPaint* grPaint); 124 125 //////////////////////////////////////////////////////////////////////////////// 126 // Misc Sk to Gr type conversions 127 128 GrSurfaceDesc GrImageInfoToSurfaceDesc(const SkImageInfo&); 129 GrPixelConfig SkColorType2GrPixelConfig(const SkColorType); 130 GrPixelConfig SkImageInfo2GrPixelConfig(const SkImageInfo& info); 131 132 bool GrPixelConfigToColorType(GrPixelConfig, SkColorType*); 133 134 GrSamplerState::Filter GrSkFilterQualityToGrFilterMode(SkFilterQuality paintFilterQuality, 135 const SkMatrix& viewM, 136 const SkMatrix& localM, 137 bool sharpenMipmappedTextures, 138 bool* doBicubic); 139 140 ////////////////////////////////////////////////////////////////////////////// 141 142 static inline GrPrimitiveType SkVertexModeToGrPrimitiveType(SkVertices::VertexMode mode) { 143 switch (mode) { 144 case SkVertices::kTriangles_VertexMode: 145 return GrPrimitiveType::kTriangles; 146 case SkVertices::kTriangleStrip_VertexMode: 147 return GrPrimitiveType::kTriangleStrip; 148 case SkVertices::kTriangleFan_VertexMode: 149 break; 150 } 151 SK_ABORT("Invalid mode"); 152 return GrPrimitiveType::kPoints; 153 } 154 155 ////////////////////////////////////////////////////////////////////////////// 156 157 GR_STATIC_ASSERT((int)kZero_GrBlendCoeff == (int)SkBlendModeCoeff::kZero); 158 GR_STATIC_ASSERT((int)kOne_GrBlendCoeff == (int)SkBlendModeCoeff::kOne); 159 GR_STATIC_ASSERT((int)kSC_GrBlendCoeff == (int)SkBlendModeCoeff::kSC); 160 GR_STATIC_ASSERT((int)kISC_GrBlendCoeff == (int)SkBlendModeCoeff::kISC); 161 GR_STATIC_ASSERT((int)kDC_GrBlendCoeff == (int)SkBlendModeCoeff::kDC); 162 GR_STATIC_ASSERT((int)kIDC_GrBlendCoeff == (int)SkBlendModeCoeff::kIDC); 163 GR_STATIC_ASSERT((int)kSA_GrBlendCoeff == (int)SkBlendModeCoeff::kSA); 164 GR_STATIC_ASSERT((int)kISA_GrBlendCoeff == (int)SkBlendModeCoeff::kISA); 165 GR_STATIC_ASSERT((int)kDA_GrBlendCoeff == (int)SkBlendModeCoeff::kDA); 166 GR_STATIC_ASSERT((int)kIDA_GrBlendCoeff == (int)SkBlendModeCoeff::kIDA); 167 //GR_STATIC_ASSERT(SkXfermode::kCoeffCount == 10); 168 169 //////////////////////////////////////////////////////////////////////////////// 170 // Texture management 171 172 /** Returns a texture representing the bitmap that is compatible with the GrSamplerState. The 173 * texture is inserted into the cache (unless the bitmap is marked volatile) and can be 174 * retrieved again via this function. 175 * The 'scaleAdjust' in/out parameter will be updated to hold any rescaling that needs to be 176 * performed on the absolute texture coordinates (e.g., if the texture is resized out to 177 * the next power of two). It can be null if the caller is sure the bitmap won't be resized. 178 */ 179 sk_sp<GrTextureProxy> GrRefCachedBitmapTextureProxy(GrRecordingContext*, 180 const SkBitmap&, 181 const GrSamplerState&, 182 SkScalar scaleAdjust[2]); 183 184 /** 185 * Creates a new texture for the bitmap. Does not concern itself with cache keys or texture params. 186 * The bitmap must have CPU-accessible pixels. Attempts to take advantage of faster paths for 187 * yuv planes. 188 */ 189 sk_sp<GrTextureProxy> GrUploadBitmapToTextureProxy(GrProxyProvider*, const SkBitmap&); 190 191 /** 192 * Creates a new texture with mipmap levels and copies the baseProxy into the base layer. 193 */ 194 sk_sp<GrTextureProxy> GrCopyBaseMipMapToTextureProxy(GrRecordingContext*, 195 GrTextureProxy* baseProxy); 196 197 /* 198 * Create a texture proxy from the provided bitmap by wrapping it in an image and calling 199 * GrMakeCachedImageProxy. 200 */ 201 sk_sp<GrTextureProxy> GrMakeCachedBitmapProxy(GrProxyProvider*, const SkBitmap& bitmap, 202 SkBackingFit fit = SkBackingFit::kExact); 203 204 /* 205 * Create a texture proxy from the provided 'srcImage' and add it to the texture cache 206 * using the key also extracted from 'srcImage'. 207 */ 208 sk_sp<GrTextureProxy> GrMakeCachedImageProxy(GrProxyProvider*, sk_sp<SkImage> srcImage, 209 SkBackingFit fit = SkBackingFit::kExact); 210 211 /** 212 * Our key includes the offset, width, and height so that bitmaps created by extractSubset() 213 * are unique. 214 * 215 * The imageID is in the shared namespace (see SkNextID::ImageID()) 216 * - SkBitmap/SkPixelRef 217 * - SkImage 218 * - SkImageGenerator 219 * 220 * Note: width/height must fit in 16bits for this impl. 221 */ 222 void GrMakeKeyFromImageID(GrUniqueKey* key, uint32_t imageID, const SkIRect& imageBounds); 223 224 /** Call this after installing a GrUniqueKey on texture. It will cause the texture's key to be 225 removed should the bitmap's contents change or be destroyed. */ 226 void GrInstallBitmapUniqueKeyInvalidator(const GrUniqueKey& key, uint32_t contextID, 227 SkPixelRef* pixelRef); 228 229 #endif 230