Home | History | Annotate | Download | only in gpu
      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 "SkPM4f.h"
     23 #include "SkVertices.h"
     24 
     25 class GrCaps;
     26 class GrColorSpaceInfo;
     27 class GrColorSpaceXform;
     28 class GrContext;
     29 class GrFragmentProcessor;
     30 class GrPaint;
     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 /** Transform an SkColor (sRGB bytes) to GrColor4f for the specified color space info. */
     62 GrColor4f SkColorToPremulGrColor4f(SkColor, const GrColorSpaceInfo&);
     63 GrColor4f SkColorToPremulGrColor4fLegacy(SkColor);
     64 GrColor4f SkColorToUnpremulGrColor4f(SkColor, const GrColorSpaceInfo&);
     65 
     66 /** Replicates the SkColor's alpha to all four channels of the GrColor. */
     67 static inline GrColor SkColorAlphaToGrColor(SkColor c) {
     68     U8CPU a = SkColorGetA(c);
     69     return GrColorPackRGBA(a, a, a, a);
     70 }
     71 
     72 //////////////////////////////////////////////////////////////////////////////
     73 
     74 static inline SkPM4f GrColor4fToSkPM4f(const GrColor4f& c) {
     75     SkPM4f pm4f;
     76     pm4f.fVec[SkPM4f::R] = c.fRGBA[0];
     77     pm4f.fVec[SkPM4f::G] = c.fRGBA[1];
     78     pm4f.fVec[SkPM4f::B] = c.fRGBA[2];
     79     pm4f.fVec[SkPM4f::A] = c.fRGBA[3];
     80     return pm4f;
     81 }
     82 
     83 static inline GrColor4f SkPM4fToGrColor4f(const SkPM4f& c) {
     84     return GrColor4f{c.r(), c.g(), c.b(), c.a()};
     85 }
     86 
     87 ////////////////////////////////////////////////////////////////////////////////
     88 // Paint conversion
     89 
     90 /** Converts an SkPaint to a GrPaint for a given GrContext. The matrix is required in order
     91     to convert the SkShader (if any) on the SkPaint. The primitive itself has no color. */
     92 bool SkPaintToGrPaint(GrContext*,
     93                       const GrColorSpaceInfo& dstColorSpaceInfo,
     94                       const SkPaint& skPaint,
     95                       const SkMatrix& viewM,
     96                       GrPaint* grPaint);
     97 
     98 /** Same as above but ignores the SkShader (if any) on skPaint. */
     99 bool SkPaintToGrPaintNoShader(GrContext* context,
    100                               const GrColorSpaceInfo& dstColorSpaceInfo,
    101                               const SkPaint& skPaint,
    102                               GrPaint* grPaint);
    103 
    104 /** Replaces the SkShader (if any) on skPaint with the passed in GrFragmentProcessor. The processor
    105     should expect an unpremul input color and produce a premultiplied output color. There is
    106     no primitive color. */
    107 bool SkPaintToGrPaintReplaceShader(GrContext*,
    108                                    const GrColorSpaceInfo& dstColorSpaceInfo,
    109                                    const SkPaint& skPaint,
    110                                    std::unique_ptr<GrFragmentProcessor> shaderFP,
    111                                    GrPaint* grPaint);
    112 
    113 /** Blends the SkPaint's shader (or color if no shader) with the color which specified via a
    114     GrOp's GrPrimitiveProcesssor. */
    115 bool SkPaintToGrPaintWithXfermode(GrContext* context,
    116                                   const GrColorSpaceInfo& dstColorSpaceInfo,
    117                                   const SkPaint& skPaint,
    118                                   const SkMatrix& viewM,
    119                                   SkBlendMode primColorMode,
    120                                   GrPaint* grPaint);
    121 
    122 /** This is used when there is a primitive color, but the shader should be ignored. Currently,
    123     the expectation is that the primitive color will be premultiplied, though it really should be
    124     unpremultiplied so that interpolation is done in unpremul space. The paint's alpha will be
    125     applied to the primitive color after interpolation. */
    126 inline bool SkPaintToGrPaintWithPrimitiveColor(GrContext* context,
    127                                                const GrColorSpaceInfo& dstColorSpaceInfo,
    128                                                const SkPaint& skPaint, GrPaint* grPaint) {
    129     return SkPaintToGrPaintWithXfermode(context, dstColorSpaceInfo, skPaint, SkMatrix::I(),
    130                                         SkBlendMode::kDst, grPaint);
    131 }
    132 
    133 /** This is used when there may or may not be a shader, and the caller wants to plugin a texture
    134     lookup.  If there is a shader, then its output will only be used if the texture is alpha8. */
    135 bool SkPaintToGrPaintWithTexture(GrContext* context,
    136                                  const GrColorSpaceInfo& dstColorSpaceInfo,
    137                                  const SkPaint& paint,
    138                                  const SkMatrix& viewM,
    139                                  std::unique_ptr<GrFragmentProcessor> fp,
    140                                  bool textureIsAlphaOnly,
    141                                  GrPaint* grPaint);
    142 
    143 ////////////////////////////////////////////////////////////////////////////////
    144 // Misc Sk to Gr type conversions
    145 
    146 GrSurfaceDesc GrImageInfoToSurfaceDesc(const SkImageInfo&, const GrCaps&);
    147 GrPixelConfig SkImageInfo2GrPixelConfig(const SkColorType, SkColorSpace*, const GrCaps& caps);
    148 GrPixelConfig SkImageInfo2GrPixelConfig(const SkImageInfo& info, const GrCaps& caps);
    149 
    150 bool GrPixelConfigToColorType(GrPixelConfig, SkColorType*);
    151 
    152 GrSamplerState::Filter GrSkFilterQualityToGrFilterMode(SkFilterQuality paintFilterQuality,
    153                                                        const SkMatrix& viewM,
    154                                                        const SkMatrix& localM,
    155                                                        bool* doBicubic);
    156 
    157 //////////////////////////////////////////////////////////////////////////////
    158 
    159 static inline GrPrimitiveType SkVertexModeToGrPrimitiveType(SkVertices::VertexMode mode) {
    160     switch (mode) {
    161         case SkVertices::kTriangles_VertexMode:
    162             return GrPrimitiveType::kTriangles;
    163         case SkVertices::kTriangleStrip_VertexMode:
    164             return GrPrimitiveType::kTriangleStrip;
    165         case SkVertices::kTriangleFan_VertexMode:
    166             return GrPrimitiveType::kTriangleFan;
    167     }
    168     SK_ABORT("Invalid mode");
    169     return GrPrimitiveType::kPoints;
    170 }
    171 
    172 //////////////////////////////////////////////////////////////////////////////
    173 
    174 GR_STATIC_ASSERT((int)kZero_GrBlendCoeff == (int)SkBlendModeCoeff::kZero);
    175 GR_STATIC_ASSERT((int)kOne_GrBlendCoeff == (int)SkBlendModeCoeff::kOne);
    176 GR_STATIC_ASSERT((int)kSC_GrBlendCoeff == (int)SkBlendModeCoeff::kSC);
    177 GR_STATIC_ASSERT((int)kISC_GrBlendCoeff == (int)SkBlendModeCoeff::kISC);
    178 GR_STATIC_ASSERT((int)kDC_GrBlendCoeff == (int)SkBlendModeCoeff::kDC);
    179 GR_STATIC_ASSERT((int)kIDC_GrBlendCoeff == (int)SkBlendModeCoeff::kIDC);
    180 GR_STATIC_ASSERT((int)kSA_GrBlendCoeff == (int)SkBlendModeCoeff::kSA);
    181 GR_STATIC_ASSERT((int)kISA_GrBlendCoeff == (int)SkBlendModeCoeff::kISA);
    182 GR_STATIC_ASSERT((int)kDA_GrBlendCoeff == (int)SkBlendModeCoeff::kDA);
    183 GR_STATIC_ASSERT((int)kIDA_GrBlendCoeff == (int)SkBlendModeCoeff::kIDA);
    184 //GR_STATIC_ASSERT(SkXfermode::kCoeffCount == 10);
    185 
    186 #define SkXfermodeCoeffToGrBlendCoeff(X) ((GrBlendCoeff)(X))
    187 
    188 ////////////////////////////////////////////////////////////////////////////////
    189 // Texture management
    190 
    191 /** Returns a texture representing the bitmap that is compatible with the GrSamplerState. The
    192  *  texture is inserted into the cache (unless the bitmap is marked volatile) and can be
    193  *  retrieved again via this function.
    194  *  The 'scaleAdjust' in/out parameter will be updated to hold any rescaling that needs to be
    195  *  performed on the absolute texture coordinates (e.g., if the texture is resized out to
    196  *  the next power of two). It can be null if the caller is sure the bitmap won't be resized.
    197  */
    198 sk_sp<GrTextureProxy> GrRefCachedBitmapTextureProxy(GrContext*,
    199                                                     const SkBitmap&,
    200                                                     const GrSamplerState&,
    201                                                     SkScalar scaleAdjust[2]);
    202 
    203 /**
    204  * Creates a new texture for the bitmap. Does not concern itself with cache keys or texture params.
    205  * The bitmap must have CPU-accessible pixels. Attempts to take advantage of faster paths for
    206  * yuv planes.
    207  */
    208 sk_sp<GrTextureProxy> GrUploadBitmapToTextureProxy(GrProxyProvider*, const SkBitmap&,
    209                                                    SkColorSpace* dstColorSpace);
    210 
    211 sk_sp<GrTextureProxy> GrGenerateMipMapsAndUploadToTextureProxy(GrProxyProvider*, const SkBitmap&,
    212                                                                SkColorSpace* dstColorSpace);
    213 
    214 /**
    215  * Creates a new texture for the pixmap.
    216  */
    217 sk_sp<GrTextureProxy> GrUploadPixmapToTextureProxy(GrProxyProvider*,
    218                                                    const SkPixmap&, SkBudgeted, SkColorSpace*);
    219 
    220 /**
    221  * Creates a new texture with mipmap levels and copies the baseProxy into the base layer.
    222  */
    223 sk_sp<GrTextureProxy> GrCopyBaseMipMapToTextureProxy(GrContext*,
    224                                                      GrTextureProxy* baseProxy);
    225 
    226 /**
    227  * Creates a new texture populated with the mipmap levels.
    228  */
    229 sk_sp<GrTextureProxy> GrUploadMipMapToTextureProxy(GrProxyProvider*, const SkImageInfo&,
    230                                                    const GrMipLevel texels[],
    231                                                    int mipLevelCount,
    232                                                    SkDestinationSurfaceColorMode colorMode);
    233 
    234 // This is intended to replace:
    235 //    SkAutoLockPixels alp(bitmap, true);
    236 //    if (!bitmap.readyToDraw()) {
    237 //        return nullptr;
    238 //    }
    239 //    sk_sp<GrTexture> texture = GrMakeCachedBitmapTexture(fContext.get(), bitmap,
    240 //                                                         GrSamplerState::ClampNearest(),
    241 //                                                         nullptr);
    242 //    if (!texture) {
    243 //        return nullptr;
    244 //    }
    245 sk_sp<GrTextureProxy> GrMakeCachedBitmapProxy(GrProxyProvider*, const SkBitmap& bitmap);
    246 
    247 
    248 /**
    249  *  Our key includes the offset, width, and height so that bitmaps created by extractSubset()
    250  *  are unique.
    251  *
    252  *  The imageID is in the shared namespace (see SkNextID::ImageID())
    253  *      - SkBitmap/SkPixelRef
    254  *      - SkImage
    255  *      - SkImageGenerator
    256  *
    257  *  Note: width/height must fit in 16bits for this impl.
    258  */
    259 void GrMakeKeyFromImageID(GrUniqueKey* key, uint32_t imageID, const SkIRect& imageBounds);
    260 
    261 /** Call this after installing a GrUniqueKey on texture. It will cause the texture's key to be
    262     removed should the bitmap's contents change or be destroyed. */
    263 void GrInstallBitmapUniqueKeyInvalidator(const GrUniqueKey& key, SkPixelRef* pixelRef);
    264 
    265 //////////////////////////////////////////////////////////////////////////////
    266 
    267 /** When image filter code needs to construct a render target context to do intermediate rendering,
    268     we need a renderable pixel config. The source (SkSpecialImage) may not be in a renderable
    269     format, but we want to preserve the color space of that source. This picks an appropriate format
    270     to use. */
    271 GrPixelConfig GrRenderableConfigForColorSpace(const SkColorSpace*);
    272 
    273 #endif
    274