/src/serenity/Userland/Libraries/LibGfx/ImageFormats/DDSLoader.h
Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * Copyright (c) 2021, the SerenityOS developers. |
3 | | * |
4 | | * SPDX-License-Identifier: BSD-2-Clause |
5 | | */ |
6 | | |
7 | | #pragma once |
8 | | |
9 | | #include <AK/MemoryStream.h> |
10 | | #include <LibGfx/ImageFormats/ImageDecoder.h> |
11 | | |
12 | | namespace Gfx { |
13 | | |
14 | | enum MiscFlags : u32 { |
15 | | DDS_RESOURCE_MISC_TEXTURECUBE = 0x4, |
16 | | }; |
17 | | |
18 | | enum Misc2Flags : u32 { |
19 | | DDS_ALPHA_MODE_UNKNOWN = 0x0, |
20 | | DDS_ALPHA_MODE_STRAIGHT = 0x1, |
21 | | DDS_ALPHA_MODE_PREMULTIPLIED = 0x2, |
22 | | DDS_ALPHA_MODE_OPAQUE = 0x3, |
23 | | DDS_ALPHA_MODE_CUSTOM = 0x4, |
24 | | }; |
25 | | |
26 | | enum Caps1Flags : u32 { |
27 | | DDSCAPS_COMPLEX = 0x8, |
28 | | DDSCAPS_TEXTURE = 0x1000, |
29 | | DDSCAPS_MIPMAP = 0x400000, |
30 | | }; |
31 | | |
32 | | enum Caps2Flags : u32 { |
33 | | DDSCAPS2_CUBEMAP = 0x200, |
34 | | DDSCAPS2_CUBEMAP_POSITIVEX = 0x400, |
35 | | DDSCAPS2_CUBEMAP_NEGATIVEX = 0x800, |
36 | | DDSCAPS2_CUBEMAP_POSITIVEY = 0x1000, |
37 | | DDSCAPS2_CUBEMAP_NEGATIVEY = 0x2000, |
38 | | DDSCAPS2_CUBEMAP_POSITIVEZ = 0x4000, |
39 | | DDSCAPS2_CUBEMAP_NEGATIVEZ = 0x8000, |
40 | | DDSCAPS2_VOLUME = 0x200000, |
41 | | }; |
42 | | |
43 | | enum ResourceDimensions : u32 { |
44 | | DDS_DIMENSION_UNKNOWN, |
45 | | DDS_DIMENSION_BUFFER, |
46 | | DDS_DIMENSION_TEXTURE1D = 2, |
47 | | DDS_DIMENSION_TEXTURE2D = 3, |
48 | | DDS_DIMENSION_TEXTURE3D = 4, |
49 | | }; |
50 | | |
51 | | enum DXGIFormat : u32 { |
52 | | DXGI_FORMAT_UNKNOWN = 0, |
53 | | DXGI_FORMAT_R32G32B32A32_TYPELESS, |
54 | | DXGI_FORMAT_R32G32B32A32_FLOAT, |
55 | | DXGI_FORMAT_R32G32B32A32_UINT, |
56 | | DXGI_FORMAT_R32G32B32A32_SINT, |
57 | | DXGI_FORMAT_R32G32B32_TYPELESS, |
58 | | DXGI_FORMAT_R32G32B32_FLOAT, |
59 | | DXGI_FORMAT_R32G32B32_UINT, |
60 | | DXGI_FORMAT_R32G32B32_SINT, |
61 | | DXGI_FORMAT_R16G16B16A16_TYPELESS, |
62 | | DXGI_FORMAT_R16G16B16A16_FLOAT, |
63 | | DXGI_FORMAT_R16G16B16A16_UNORM, |
64 | | DXGI_FORMAT_R16G16B16A16_UINT, |
65 | | DXGI_FORMAT_R16G16B16A16_SNORM, |
66 | | DXGI_FORMAT_R16G16B16A16_SINT, |
67 | | DXGI_FORMAT_R32G32_TYPELESS, |
68 | | DXGI_FORMAT_R32G32_FLOAT, |
69 | | DXGI_FORMAT_R32G32_UINT, |
70 | | DXGI_FORMAT_R32G32_SINT, |
71 | | DXGI_FORMAT_R32G8X24_TYPELESS, |
72 | | DXGI_FORMAT_D32_FLOAT_S8X24_UINT, |
73 | | DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS, |
74 | | DXGI_FORMAT_X32_TYPELESS_G8X24_UINT, |
75 | | DXGI_FORMAT_R10G10B10A2_TYPELESS, |
76 | | DXGI_FORMAT_R10G10B10A2_UNORM, |
77 | | DXGI_FORMAT_R10G10B10A2_UINT, |
78 | | DXGI_FORMAT_R11G11B10_FLOAT, |
79 | | DXGI_FORMAT_R8G8B8A8_TYPELESS, |
80 | | DXGI_FORMAT_R8G8B8A8_UNORM, |
81 | | DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, |
82 | | DXGI_FORMAT_R8G8B8A8_UINT, |
83 | | DXGI_FORMAT_R8G8B8A8_SNORM, |
84 | | DXGI_FORMAT_R8G8B8A8_SINT, |
85 | | DXGI_FORMAT_R16G16_TYPELESS, |
86 | | DXGI_FORMAT_R16G16_FLOAT, |
87 | | DXGI_FORMAT_R16G16_UNORM, |
88 | | DXGI_FORMAT_R16G16_UINT, |
89 | | DXGI_FORMAT_R16G16_SNORM, |
90 | | DXGI_FORMAT_R16G16_SINT, |
91 | | DXGI_FORMAT_R32_TYPELESS, |
92 | | DXGI_FORMAT_D32_FLOAT, |
93 | | DXGI_FORMAT_R32_FLOAT, |
94 | | DXGI_FORMAT_R32_UINT, |
95 | | DXGI_FORMAT_R32_SINT, |
96 | | DXGI_FORMAT_R24G8_TYPELESS, |
97 | | DXGI_FORMAT_D24_UNORM_S8_UINT, |
98 | | DXGI_FORMAT_R24_UNORM_X8_TYPELESS, |
99 | | DXGI_FORMAT_X24_TYPELESS_G8_UINT, |
100 | | DXGI_FORMAT_R8G8_TYPELESS, |
101 | | DXGI_FORMAT_R8G8_UNORM, |
102 | | DXGI_FORMAT_R8G8_UINT, |
103 | | DXGI_FORMAT_R8G8_SNORM, |
104 | | DXGI_FORMAT_R8G8_SINT, |
105 | | DXGI_FORMAT_R16_TYPELESS, |
106 | | DXGI_FORMAT_R16_FLOAT, |
107 | | DXGI_FORMAT_D16_UNORM, |
108 | | DXGI_FORMAT_R16_UNORM, |
109 | | DXGI_FORMAT_R16_UINT, |
110 | | DXGI_FORMAT_R16_SNORM, |
111 | | DXGI_FORMAT_R16_SINT, |
112 | | DXGI_FORMAT_R8_TYPELESS, |
113 | | DXGI_FORMAT_R8_UNORM, |
114 | | DXGI_FORMAT_R8_UINT, |
115 | | DXGI_FORMAT_R8_SNORM, |
116 | | DXGI_FORMAT_R8_SINT, |
117 | | DXGI_FORMAT_A8_UNORM, |
118 | | DXGI_FORMAT_R1_UNORM, |
119 | | DXGI_FORMAT_R9G9B9E5_SHAREDEXP, |
120 | | DXGI_FORMAT_R8G8_B8G8_UNORM, |
121 | | DXGI_FORMAT_G8R8_G8B8_UNORM, |
122 | | DXGI_FORMAT_BC1_TYPELESS, |
123 | | DXGI_FORMAT_BC1_UNORM, |
124 | | DXGI_FORMAT_BC1_UNORM_SRGB, |
125 | | DXGI_FORMAT_BC2_TYPELESS, |
126 | | DXGI_FORMAT_BC2_UNORM, |
127 | | DXGI_FORMAT_BC2_UNORM_SRGB, |
128 | | DXGI_FORMAT_BC3_TYPELESS, |
129 | | DXGI_FORMAT_BC3_UNORM, |
130 | | DXGI_FORMAT_BC3_UNORM_SRGB, |
131 | | DXGI_FORMAT_BC4_TYPELESS, |
132 | | DXGI_FORMAT_BC4_UNORM, |
133 | | DXGI_FORMAT_BC4_SNORM, |
134 | | DXGI_FORMAT_BC5_TYPELESS, |
135 | | DXGI_FORMAT_BC5_UNORM, |
136 | | DXGI_FORMAT_BC5_SNORM, |
137 | | DXGI_FORMAT_B5G6R5_UNORM, |
138 | | DXGI_FORMAT_B5G5R5A1_UNORM, |
139 | | DXGI_FORMAT_B8G8R8A8_UNORM, |
140 | | DXGI_FORMAT_B8G8R8X8_UNORM, |
141 | | DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM, |
142 | | DXGI_FORMAT_B8G8R8A8_TYPELESS, |
143 | | DXGI_FORMAT_B8G8R8A8_UNORM_SRGB, |
144 | | DXGI_FORMAT_B8G8R8X8_TYPELESS, |
145 | | DXGI_FORMAT_B8G8R8X8_UNORM_SRGB, |
146 | | DXGI_FORMAT_BC6H_TYPELESS, |
147 | | DXGI_FORMAT_BC6H_UF16, |
148 | | DXGI_FORMAT_BC6H_SF16, |
149 | | DXGI_FORMAT_BC7_TYPELESS, |
150 | | DXGI_FORMAT_BC7_UNORM, |
151 | | DXGI_FORMAT_BC7_UNORM_SRGB, |
152 | | DXGI_FORMAT_AYUV, |
153 | | DXGI_FORMAT_Y410, |
154 | | DXGI_FORMAT_Y416, |
155 | | DXGI_FORMAT_NV12, |
156 | | DXGI_FORMAT_P010, |
157 | | DXGI_FORMAT_P016, |
158 | | DXGI_FORMAT_420_OPAQUE, |
159 | | DXGI_FORMAT_YUY2, |
160 | | DXGI_FORMAT_Y210, |
161 | | DXGI_FORMAT_Y216, |
162 | | DXGI_FORMAT_NV11, |
163 | | DXGI_FORMAT_AI44, |
164 | | DXGI_FORMAT_IA44, |
165 | | DXGI_FORMAT_P8, |
166 | | DXGI_FORMAT_A8P8, |
167 | | DXGI_FORMAT_B4G4R4A4_UNORM, |
168 | | DXGI_FORMAT_P208, |
169 | | DXGI_FORMAT_V208, |
170 | | DXGI_FORMAT_V408, |
171 | | DXGI_FORMAT_SAMPLER_FEEDBACK_MIN_MIP_OPAQUE, |
172 | | DXGI_FORMAT_SAMPLER_FEEDBACK_MIP_REGION_USED_OPAQUE, |
173 | | DXGI_FORMAT_FORCE_UINT |
174 | | }; |
175 | | |
176 | | enum DDSFlags : u32 { |
177 | | DDSD_CAPS = 0x1, |
178 | | DDSD_HEIGHT = 0x2, |
179 | | DDSD_WIDTH = 0x4, |
180 | | DDSD_PITCH = 0x8, |
181 | | DDSD_PIXELFORMAT = 0x1000, |
182 | | DDSD_MIPMAPCOUNT = 0x20000, |
183 | | DDSD_LINEARSIZE = 0x80000, |
184 | | DDSD_DEPTH = 0x800000, |
185 | | }; |
186 | | |
187 | | enum PixelFormatFlags : u32 { |
188 | | DDPF_ALPHAPIXELS = 0x1, |
189 | | DDPF_ALPHA = 0x2, |
190 | | DDPF_FOURCC = 0x4, |
191 | | DDPF_PALETTEINDEXED8 = 0x20, |
192 | | DDPF_RGB = 0x40, |
193 | | DDPF_YUV = 0x200, |
194 | | DDPF_LUMINANCE = 0x20000, |
195 | | DDPF_BUMPDUDV = 0x80000, |
196 | | DDPF_NORMAL = 0x80000000, |
197 | | }; |
198 | | |
199 | | struct [[gnu::packed]] DDSPixelFormat { |
200 | | u32 size {}; |
201 | | u32 flags {}; |
202 | | u32 four_cc {}; |
203 | | u32 rgb_bit_count {}; |
204 | | u32 r_bit_mask {}; |
205 | | u32 g_bit_mask {}; |
206 | | u32 b_bit_mask {}; |
207 | | u32 a_bit_mask {}; |
208 | | }; |
209 | | |
210 | | struct [[gnu::packed]] DDSHeader { |
211 | | u32 size {}; |
212 | | u32 flags {}; |
213 | | u32 height {}; |
214 | | u32 width {}; |
215 | | u32 pitch {}; |
216 | | u32 depth {}; |
217 | | u32 mip_map_count {}; |
218 | | u32 reserved[11]; |
219 | | DDSPixelFormat pixel_format; |
220 | | u32 caps1 {}; |
221 | | u32 caps2 {}; |
222 | | u32 caps3 {}; |
223 | | u32 caps4 {}; |
224 | | u32 reserved2 {}; |
225 | | }; |
226 | | |
227 | | struct [[gnu::packed]] DDSHeaderDXT10 { |
228 | | DXGIFormat format {}; |
229 | | u32 resource_dimension {}; |
230 | | u32 misc_flag {}; |
231 | | u32 array_size {}; |
232 | | u32 misc_flag2 {}; |
233 | | }; |
234 | | |
235 | | struct DDSLoadingContext; |
236 | | |
237 | | class DDSImageDecoderPlugin final : public ImageDecoderPlugin { |
238 | | public: |
239 | | static bool sniff(ReadonlyBytes); |
240 | | static ErrorOr<NonnullOwnPtr<ImageDecoderPlugin>> create(ReadonlyBytes); |
241 | | |
242 | | virtual ~DDSImageDecoderPlugin() override; |
243 | | |
244 | | virtual IntSize size() override; |
245 | | |
246 | | virtual ErrorOr<ImageFrameDescriptor> frame(size_t index, Optional<IntSize> ideal_size = {}) override; |
247 | | |
248 | | private: |
249 | | DDSImageDecoderPlugin(FixedMemoryStream); |
250 | | |
251 | | OwnPtr<DDSLoadingContext> m_context; |
252 | | }; |
253 | | |
254 | | } |
255 | | |
256 | | template<> |
257 | | struct AK::Traits<Gfx::DDSHeader> : public AK::DefaultTraits<Gfx::DDSHeader> { |
258 | 0 | static constexpr bool is_trivially_serializable() { return true; } |
259 | | }; |
260 | | |
261 | | template<> |
262 | | struct AK::Traits<Gfx::DDSHeaderDXT10> : public AK::DefaultTraits<Gfx::DDSHeaderDXT10> { |
263 | 0 | static constexpr bool is_trivially_serializable() { return true; } |
264 | | }; |