1

When I read Android source code SkiaRecordingCanvas, I found that if a bitmap is marked as mutable, namely !isImmutable() == true, the bitmap will be cached in GPU by function SkiaPipeline::pinImages which calls the skia interface SKImage_pinAsTexture. But after I commented these lines in pinImages and re-compiled and pushed to the phone, I found the gifs displayed normally. The only difference is that the texture uploading is delayed from prepareTree to renderFrameImpl. So, why does Android use this method to cache the textures of mutable bitmaps?

bool SkiaPipeline::pinImages(std::vector<SkImage*>& mutableImages) {
    // for (SkImage* image : mutableImages) {
    //     if (SkImage_pinAsTexture(image, mRenderThread.getGrContext())) {
    //         mPinnedImages.emplace_back(sk_ref_sp(image));
    //     } else {
    //         return false;
    //     }
    // }
    return true;
}
HolyChen
  • 29
  • 1
  • 4

1 Answers1

1

The pinning and unpinning is designed to work even if the underlying bitmap changes.

Pinning it causes the image to eagerly get uploaded to the GPU. Unpinning it allows the GPU related memory to be freed. See the docs at https://github.com/google/skia/blob/dc3332a07906872f37ec3a592db7831178886527/src/core/SkImagePriv.h#L62-L86

By commenting out this code, you're making it so that the image won't (or at least, may not) get uploaded to the GPU until closer to when it is drawn, which may lead to more work being done at unfortunate times, especially on lower end devices. It's also not clear to me what the consequence of calling unpin without a matching pin.

Dan Field
  • 20,885
  • 5
  • 55
  • 71