• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2021 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_TextureInfo_DEFINED
9 #define skgpu_graphite_TextureInfo_DEFINED
10 
11 #include "include/core/SkString.h"
12 #include "include/core/SkTextureCompressionType.h"
13 #include "include/gpu/graphite/GraphiteTypes.h"
14 #include "include/private/base/SkAPI.h"
15 #include "include/private/base/SkAnySubclass.h"
16 
17 struct SkISize;
18 
19 namespace skgpu::graphite {
20 
21 enum class TextureFormat : uint8_t;
22 
23 /**
24  * TextureInfo is a backend-agnostic wrapper around the properties of a texture, sans dimensions.
25  * It is designed this way to be compilable w/o bringing in a specific backend's build files, and
26  * without requiring heap allocations of virtual types.
27  */
28 class SK_API TextureInfo {
29 private:
30     class Data;
31     friend class MtlTextureInfo;
32     friend class DawnTextureInfo;
33     friend class VulkanTextureInfo;
34 
35     // Size is the largest of the Data subclasses assuming a 64-bit compiler.
36     inline constexpr static size_t kMaxSubclassSize = 112;
37     using AnyTextureInfoData = SkAnySubclass<Data, kMaxSubclassSize>;
38 
39     // Base properties for all backend-specific properties. Clients managing textures directly
40     // should use the public subclasses of Data directly, e.g. MtlTextureInfo/DawnTextureInfo.
41     //
42     // Each backend subclass must expose to TextureInfo[Priv]:
43     //   static constexpr BackendApi kBackend;
44     //   Protected isProtected() const;
45     //   TextureFormat viewFormat() const;
46     //   bool serialize(SkWStream*) const;
47     //   bool deserialize(SkStream*);
48     class Data {
49     public:
50         virtual ~Data() = default;
51 
Data(uint32_t sampleCount,skgpu::Mipmapped mipmapped)52         Data(uint32_t sampleCount, skgpu::Mipmapped mipmapped)
53                 : fSampleCount(sampleCount)
54                 , fMipmapped(mipmapped) {}
55 
56         Data() = default;
57         Data(const Data&) = default;
58 
59         Data& operator=(const Data&) = default;
60 
61         // NOTE: These fields are accessible via the backend-specific subclasses.
62         uint32_t fSampleCount = 1;
63         Mipmapped fMipmapped = Mipmapped::kNo;
64 
65     private:
66         friend class TextureInfo;
67         friend class TextureInfoPriv;
68 
69         virtual SkString toBackendString() const = 0;
70 
71         virtual void copyTo(AnyTextureInfoData&) const = 0;
72         // Passed in TextureInfo will have data of the same backend type and subclass, and
73         // base properties of Data have already been checked for equality/compatibility.
74         virtual bool isCompatible(const TextureInfo& that, bool requireExact) const = 0;
75     };
76 
77 public:
78     TextureInfo() = default;
79     ~TextureInfo() = default;
80 
81     TextureInfo(const TextureInfo&);
82     TextureInfo& operator=(const TextureInfo&);
83 
84     bool operator==(const TextureInfo& that) const {
85         return this->isCompatible(that, /*requireExact=*/true);
86     }
87     bool operator!=(const TextureInfo& that) const { return !(*this == that); }
88 
isValid()89     bool isValid() const { return fData.has_value(); }
backend()90     BackendApi backend() const {
91         SkASSERT(fData.has_value() || fBackend == BackendApi::kUnsupported);
92         return fBackend;
93     }
94 
numSamples()95     uint32_t numSamples() const { return fData.has_value() ? fData->fSampleCount : 1; }
mipmapped()96     Mipmapped mipmapped() const { return fData.has_value() ? fData->fMipmapped   : Mipmapped::kNo; }
isProtected()97     Protected isProtected() const { return fProtected; }
98 
99     // Return true if `that` describes a texture that is compatible with this info and can validly
100     // be used to fulfill a promise image that was created with this TextureInfo.
canBeFulfilledBy(const TextureInfo & that)101     bool canBeFulfilledBy(const TextureInfo& that) const {
102         return this->isCompatible(that, /*requireExact=*/false);
103     }
104 
105     // Return a string containing the full description of this TextureInfo.
106     SkString toString() const;
107 
108 private:
109     friend class TextureInfoPriv;
110 
111     template <typename BackendTextureData,
112               std::enable_if_t<std::is_base_of_v<Data, BackendTextureData>, bool> = true>
TextureInfo(const BackendTextureData & data)113     explicit TextureInfo(const BackendTextureData& data)
114             : fBackend(BackendTextureData::kBackend)
115             , fViewFormat(data.viewFormat())
116             , fProtected(data.isProtected()) {
117         fData.emplace<BackendTextureData>(data);
118     }
119 
120     bool isCompatible(const TextureInfo& that, bool requireExact) const;
121 
122     skgpu::BackendApi  fBackend = BackendApi::kUnsupported;
123     AnyTextureInfoData fData;
124 
125     // Derived properties from the backend data, cached to avoid a virtual function call
126     TextureFormat fViewFormat;
127     Protected fProtected = Protected::kNo;
128 };
129 
130 } // namespace skgpu::graphite
131 
132 #endif // skgpu_graphite_TextureInfo_DEFINED
133