1 /* 2 * Copyright 2024 Google LLC 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 skgpu_graphite_ComputePathAtlas_DEFINED 9 #define skgpu_graphite_ComputePathAtlas_DEFINED 10 11 #include "src/gpu/graphite/PathAtlas.h" 12 13 #include "src/base/SkTInternalLList.h" 14 #include "src/core/SkTHash.h" 15 #include "src/gpu/AtlasTypes.h" 16 #include "src/gpu/RectanizerSkyline.h" 17 #include "src/gpu/ResourceKey.h" 18 #include "src/gpu/graphite/DrawAtlas.h" 19 #include "src/gpu/graphite/task/ComputeTask.h" 20 21 #ifdef SK_ENABLE_VELLO_SHADERS 22 #include "src/gpu/graphite/compute/VelloRenderer.h" 23 #endif 24 25 #include <memory> 26 27 namespace skgpu::graphite { 28 29 class DispatchGroup; 30 31 /** 32 * Base class for PathAtlas implementations that rasterize coverage masks on the GPU using compute 33 * shaders. 34 * 35 * When a new shape gets added, it gets tracked as input to a series of GPU compute passes. This 36 * data is recorded by `recordDispatches()` into a DispatchGroup which can be added to a 37 * ComputeTask. 38 * 39 * After a successful call to `recordDispatches()`, the client is free to call `reset()` and start 40 * adding new shapes for a future atlas render. 41 */ 42 class ComputePathAtlas : public PathAtlas { 43 public: 44 // Returns the currently preferred ComputePathAtlas implementation. 45 static std::unique_ptr<ComputePathAtlas> CreateDefault(Recorder*); 46 47 virtual bool recordDispatches(Recorder*, ComputeTask::DispatchGroupList*) const = 0; 48 49 // Clear all scheduled atlas draws and free up atlas allocations, if necessary. After this call 50 // the atlas can be considered cleared and available for new shape insertions. However this 51 // method does not have any bearing on the contents of any atlas textures themselves, which may 52 // be in use by GPU commands that are in-flight or yet to be submitted. 53 void reset(); 54 55 protected: 56 explicit ComputePathAtlas(Recorder*); 57 texture()58 const TextureProxy* texture() const { return fTexture.get(); } 59 const TextureProxy* addRect(skvx::half2 maskSize, 60 SkIPoint16* outPos); 61 bool isSuitableForAtlasing(const Rect& transformedShapeBounds, 62 const Rect& clipBounds) const override; 63 64 virtual void onReset() = 0; 65 66 private: 67 bool initializeTextureIfNeeded(); 68 69 ////////////////// 70 // Uncached data 71 skgpu::RectanizerSkyline fRectanizer; 72 73 // ComputePathAtlas lazily requests a texture from the AtlasProvider when the first shape gets 74 // added to it and references the same texture for the duration of its lifetime. A reference to 75 // this texture is stored here, which is used by AtlasShapeRenderStep when encoding the render 76 // pass. 77 sk_sp<TextureProxy> fTexture; 78 }; 79 80 } // namespace skgpu::graphite 81 82 #endif // skgpu_graphite_ComputePathAtlas_DEFINED 83