1 //-------------------------------------------------------------------------------------
4 // DirectX Texture Library
6 // THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
7 // ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
8 // THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
11 // Copyright (c) Microsoft Corporation. All rights reserved.
13 // http://go.microsoft.com/fwlink/?LinkId=248926
14 //-------------------------------------------------------------------------------------
16 #if defined(_MSC_VER) && (_MSC_VER > 1000)
21 #pragma warning(disable : 4005)
27 #include <dxgiformat.h>
30 #define DIRECTX_TEX_VERSION 100
34 //---------------------------------------------------------------------------------
35 // DXGI Format Utilities
36 bool IsValid( _In_ DXGI_FORMAT fmt );
37 bool IsCompressed( _In_ DXGI_FORMAT fmt );
38 bool IsPacked( _In_ DXGI_FORMAT fmt );
39 bool IsVideo( _In_ DXGI_FORMAT fmt );
40 bool IsSRGB( _In_ DXGI_FORMAT fmt );
41 bool IsTypeless( _In_ DXGI_FORMAT fmt );
43 size_t BitsPerPixel( _In_ DXGI_FORMAT fmt );
47 CP_FLAGS_NONE = 0x0, // Normal operation
48 CP_FLAGS_LEGACY_DWORD = 0x1, // Assume pitch is DWORD aligned instead of BYTE aligned
49 CP_FLAGS_24BPP = 0x10000, // Override with a legacy 24 bits-per-pixel format size
50 CP_FLAGS_16BPP = 0x20000, // Override with a legacy 16 bits-per-pixel format size
51 CP_FLAGS_8BPP = 0x40000, // Override with a legacy 8 bits-per-pixel format size
54 void ComputePitch( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height,
55 _Out_ size_t& rowPitch, _Out_ size_t& slicePitch, _In_ DWORD flags = CP_FLAGS_NONE );
57 size_t ComputeScanlines( _In_ DXGI_FORMAT fmt, _In_ size_t height );
59 DXGI_FORMAT MakeSRGB( _In_ DXGI_FORMAT fmt );
60 DXGI_FORMAT MakeTypeless( _In_ DXGI_FORMAT fmt );
61 DXGI_FORMAT MakeTypelessUNORM( _In_ DXGI_FORMAT fmt );
62 DXGI_FORMAT MakeTypelessFLOAT( _In_ DXGI_FORMAT fmt );
64 //---------------------------------------------------------------------------------
67 // Subset here matches D3D10_RESOURCE_DIMENSION and D3D11_RESOURCE_DIMENSION
69 TEX_DIMENSION_TEXTURE1D = 2,
70 TEX_DIMENSION_TEXTURE2D = 3,
71 TEX_DIMENSION_TEXTURE3D = 4,
75 // Subset here matches D3D10_RESOURCE_MISC_FLAG and D3D11_RESOURCE_MISC_FLAG
77 TEX_MISC_TEXTURECUBE = 0x4L,
83 size_t height; // Should be 1 for 1D textures
84 size_t depth; // Should be 1 for 1D or 2D textures
85 size_t arraySize; // For cubemap, this is a multiple of 6
89 TEX_DIMENSION dimension;
91 size_t ComputeIndex( _In_ size_t mip, _In_ size_t item, _In_ size_t slice ) const;
92 // Returns size_t(-1) to indicate an out-of-range error
99 DDS_FLAGS_LEGACY_DWORD = 0x1,
100 // Assume pitch is DWORD aligned instead of BYTE aligned (used by some legacy DDS files)
102 DDS_FLAGS_NO_LEGACY_EXPANSION = 0x2,
103 // Do not implicitly convert legacy formats that result in larger pixel sizes (24 bpp, 3:3:2, A8L8, A4L4, P8, A8P8)
105 DDS_FLAGS_NO_R10B10G10A2_FIXUP = 0x4,
106 // Do not use work-around for long-standing D3DX DDS file format issue which reversed the 10:10:10:2 color order masks
108 DDS_FLAGS_FORCE_RGB = 0x8,
109 // Convert DXGI 1.1 BGR formats to DXGI_FORMAT_R8G8B8A8_UNORM to avoid use of optional WDDM 1.1 formats
111 DDS_FLAGS_NO_16BPP = 0x10,
112 // Conversions avoid use of 565, 5551, and 4444 formats and instead expand to 8888 to avoid use of optional WDDM 1.2 formats
114 DDS_FLAGS_FORCE_DX10_EXT = 0x10000,
115 // Always use the 'DX10' header extension for DDS writer (i.e. don't try to write DX9 compatible DDS files)
120 WIC_FLAGS_NONE = 0x0,
122 WIC_FLAGS_FORCE_RGB = 0x1,
123 // Loads DXGI 1.1 BGR formats as DXGI_FORMAT_R8G8B8A8_UNORM to avoid use of optional WDDM 1.1 formats
125 WIC_FLAGS_NO_X2_BIAS = 0x2,
126 // Loads DXGI 1.1 X2 10:10:10:2 format as DXGI_FORMAT_R10G10B10A2_UNORM
128 WIC_FLAGS_NO_16BPP = 0x4,
129 // Loads 565, 5551, and 4444 formats as 8888 to avoid use of optional WDDM 1.2 formats
131 WIC_FLAGS_ALLOW_MONO = 0x8,
132 // Loads 1-bit monochrome (black & white) as R1_UNORM rather than 8-bit greyscale
134 WIC_FLAGS_ALL_FRAMES = 0x10,
135 // Loads all images in a multi-frame file, converting/resizing to match the first frame as needed, defaults to 0th frame otherwise
137 WIC_FLAGS_DITHER = 0x10000,
138 // Use ordered 4x4 dithering for any required conversions
140 WIC_FLAGS_DITHER_DIFFUSION = 0x20000,
141 // Use error-diffusion dithering for any required conversions
143 WIC_FLAGS_FILTER_POINT = 0x100000,
144 WIC_FLAGS_FILTER_LINEAR = 0x200000,
145 WIC_FLAGS_FILTER_CUBIC = 0x300000,
146 WIC_FLAGS_FILTER_FANT = 0x400000, // Combination of Linear and Box filter
147 // Filtering mode to use for any required image resizing (only needed when loading arrays of differently sized images; defaults to Fant)
150 HRESULT GetMetadataFromDDSMemory( _In_bytecount_(size) LPCVOID pSource, _In_ size_t size, _In_ DWORD flags,
151 _Out_ TexMetadata& metadata );
152 HRESULT GetMetadataFromDDSFile( _In_z_ LPCWSTR szFile, DWORD flags,
153 _Out_ TexMetadata& metadata );
155 HRESULT GetMetadataFromTGAMemory( _In_bytecount_(size) LPCVOID pSource, _In_ size_t size,
156 _Out_ TexMetadata& metadata );
157 HRESULT GetMetadataFromTGAFile( _In_z_ LPCWSTR szFile,
158 _Out_ TexMetadata& metadata );
160 HRESULT GetMetadataFromWICMemory( _In_bytecount_(size) LPCVOID pSource, _In_ size_t size, _In_ DWORD flags,
161 _Out_ TexMetadata& metadata );
162 HRESULT GetMetadataFromWICFile( _In_z_ LPCWSTR szFile, _In_ DWORD flags,
163 _Out_ TexMetadata& metadata );
165 //---------------------------------------------------------------------------------
166 // Bitmap image container
180 ScratchImage() : _nimages(0), _size(0), _image(0), _memory(0) {}
181 ~ScratchImage() { Release(); }
183 HRESULT Initialize( _In_ const TexMetadata& mdata );
185 HRESULT Initialize1D( _In_ DXGI_FORMAT fmt, _In_ size_t length, _In_ size_t arraySize, _In_ size_t mipLevels );
186 HRESULT Initialize2D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t arraySize, _In_ size_t mipLevels );
187 HRESULT Initialize3D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t depth, _In_ size_t mipLevels );
188 HRESULT InitializeCube( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t nCubes, _In_ size_t mipLevels );
190 HRESULT InitializeFromImage( _In_ const Image& srcImage, _In_ bool allow1D = false );
191 HRESULT InitializeArrayFromImages( _In_count_(nImages) const Image* images, _In_ size_t nImages, _In_ bool allow1D = false );
192 HRESULT InitializeCubeFromImages( _In_count_(nImages) const Image* images, _In_ size_t nImages );
193 HRESULT Initialize3DFromImages( _In_count_(depth) const Image* images, _In_ size_t depth );
197 bool OverrideFormat( _In_ DXGI_FORMAT f );
199 const TexMetadata& GetMetadata() const { return _metadata; }
200 const Image* GetImage(_In_ size_t mip, _In_ size_t item, _In_ size_t slice) const;
202 const Image* GetImages() const { return _image; }
203 size_t GetImageCount() const { return _nimages; }
205 uint8_t* GetPixels() const { return _memory; }
206 size_t GetPixelsSize() const { return _size; }
211 TexMetadata _metadata;
215 // Hide copy constructor and assignment operator
216 ScratchImage( const ScratchImage& );
217 ScratchImage& operator=( const ScratchImage& );
220 //---------------------------------------------------------------------------------
221 // Memory blob (allocated buffer pointer is always 16-byte aligned)
225 Blob() : _buffer(0), _size(0) {}
226 ~Blob() { Release(); }
228 HRESULT Initialize( _In_ size_t size );
232 void *GetBufferPointer() const { return _buffer; }
233 size_t GetBufferSize() const { return _size; }
239 // Hide copy constructor and assignment operator
241 Blob& operator=( const Blob& );
244 //---------------------------------------------------------------------------------
248 HRESULT LoadFromDDSMemory( _In_bytecount_(size) LPCVOID pSource, _In_ size_t size, _In_ DWORD flags,
249 _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image );
250 HRESULT LoadFromDDSFile( _In_z_ LPCWSTR szFile, _In_ DWORD flags,
251 _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image );
253 HRESULT SaveToDDSMemory( _In_ const Image& image, _In_ DWORD flags,
255 HRESULT SaveToDDSMemory( _In_count_(nimages) const Image* images, _In_ size_t nimages, _In_ const TexMetadata& metadata, _In_ DWORD flags,
258 HRESULT SaveToDDSFile( _In_ const Image& image, _In_ DWORD flags, _In_z_ LPCWSTR szFile );
259 HRESULT SaveToDDSFile( _In_count_(nimages) const Image* images, _In_ size_t nimages, _In_ const TexMetadata& metadata, _In_ DWORD flags, _In_z_ LPCWSTR szFile );
262 HRESULT LoadFromTGAMemory( _In_bytecount_(size) LPCVOID pSource, _In_ size_t size,
263 _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image );
264 HRESULT LoadFromTGAFile( _In_z_ LPCWSTR szFile,
265 _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image );
267 HRESULT SaveToTGAMemory( _In_ const Image& image, _Out_ Blob& blob );
268 HRESULT SaveToTGAFile( _In_ const Image& image, _In_z_ LPCWSTR szFile );
271 HRESULT LoadFromWICMemory( _In_bytecount_(size) LPCVOID pSource, _In_ size_t size, _In_ DWORD flags,
272 _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image );
273 HRESULT LoadFromWICFile( _In_z_ LPCWSTR szFile, _In_ DWORD flags,
274 _Out_opt_ TexMetadata* metadata, _Out_ ScratchImage& image );
276 HRESULT SaveToWICMemory( _In_ const Image& image, _In_ DWORD flags, _In_ REFGUID guidContainerFormat,
277 _Out_ Blob& blob, _In_opt_ const GUID* targetFormat = nullptr );
278 HRESULT SaveToWICMemory( _In_count_(nimages) const Image* images, _In_ size_t nimages, _In_ DWORD flags, _In_ REFGUID guidContainerFormat,
279 _Out_ Blob& blob, _In_opt_ const GUID* targetFormat = nullptr );
281 HRESULT SaveToWICFile( _In_ const Image& image, _In_ DWORD flags, _In_ REFGUID guidContainerFormat,
282 _In_z_ LPCWSTR szFile, _In_opt_ const GUID* targetFormat = nullptr );
283 HRESULT SaveToWICFile( _In_count_(nimages) const Image* images, _In_ size_t nimages, _In_ DWORD flags, _In_ REFGUID guidContainerFormat,
284 _In_z_ LPCWSTR szFile, _In_opt_ const GUID* targetFormat = nullptr );
288 WIC_CODEC_BMP =1, // Windows Bitmap (.bmp)
289 WIC_CODEC_JPEG, // Joint Photographic Experts Group (.jpg, .jpeg)
290 WIC_CODEC_PNG, // Portable Network Graphics (.png)
291 WIC_CODEC_TIFF, // Tagged Image File Format (.tif, .tiff)
292 WIC_CODEC_GIF, // Graphics Interchange Format (.gif)
293 WIC_CODEC_WMP, // Windows Media Photo / HD Photo / JPEG XR (.hdp, .jxr, .wdp)
294 WIC_CODEC_ICO, // Windows Icon (.ico)
297 REFGUID GetWICCodec( _In_ WICCodecs codec );
299 //---------------------------------------------------------------------------------
300 // Texture conversion, resizing, mipmap generation, and block compression
304 TEX_FR_ROTATE0 = 0x0,
305 TEX_FR_ROTATE90 = 0x1,
306 TEX_FR_ROTATE180 = 0x2,
307 TEX_FR_ROTATE270 = 0x3,
308 TEX_FR_FLIP_HORIZONTAL = 0x08,
309 TEX_FR_FLIP_VERTICAL = 0x10,
312 HRESULT FlipRotate( _In_ const Image& srcImage, _In_ DWORD flags, _Out_ ScratchImage& image );
313 HRESULT FlipRotate( _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
314 _In_ DWORD flags, _Out_ ScratchImage& result );
315 // Flip and/or rotate image
317 enum TEX_FILTER_FLAGS
319 TEX_FILTER_DEFAULT = 0,
321 // Clamp filtering only
323 TEX_FILTER_SEPARATE_ALPHA = 0x100,
324 // Resize color and alpha channel independently
326 TEX_FILTER_DITHER = 0x10000,
327 // Use ordered 4x4 dithering for any required conversions
328 TEX_FILTER_DITHER_DIFFUSION = 0x20000,
329 // Use error-diffusion dithering for any required conversions
331 TEX_FILTER_POINT = 0x100000,
332 TEX_FILTER_LINEAR = 0x200000,
333 TEX_FILTER_CUBIC = 0x300000,
334 TEX_FILTER_FANT = 0x400000, // Equiv to Box filtering for mipmap generation
335 // Filtering mode to use for any required image resizing
337 TEX_FILTER_SRGB_IN = 0x1000000,
338 TEX_FILTER_SRGB_OUT = 0x2000000,
339 TEX_FILTER_SRGB = 0x3000000,
340 // sRGB <-> RGB for use in conversion operations
341 // if the input format type is IsSRGB(), then SRGB_IN is on by default
342 // if the output format type is IsSRGB(), then SRGB_OUT is on by default
345 HRESULT Resize( _In_ const Image& srcImage, _In_ size_t width, _In_ size_t height, _In_ DWORD filter,
346 _Out_ ScratchImage& image );
347 HRESULT Resize( _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
348 _In_ size_t width, _In_ size_t height, _In_ DWORD filter, _Out_ ScratchImage& result );
349 // Resize the image to width x height. Defaults to Fant filtering.
350 // Note for a complex resize, the result will always have mipLevels == 1
352 HRESULT Convert( _In_ const Image& srcImage, _In_ DXGI_FORMAT format, _In_ DWORD filter, _In_ float threshold,
353 _Out_ ScratchImage& image );
354 HRESULT Convert( _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
355 _In_ DXGI_FORMAT format, _In_ DWORD filter, _In_ float threshold, _Out_ ScratchImage& result );
356 // Convert the image to a new format
358 HRESULT GenerateMipMaps( _In_ const Image& baseImage, _In_ DWORD filter, _In_ size_t levels,
359 _Out_ ScratchImage& mipChain, bool allow1D = false );
360 HRESULT GenerateMipMaps( _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
361 _In_ DWORD filter, _In_ size_t levels, _Out_ ScratchImage& mipChain );
362 // levels of '0' indicates a full mipchain, otherwise is generates that number of total levels (including the source base image)
363 // Defaults to Fant filtering which is equivalent to a box filter
365 HRESULT GenerateMipMaps3D( _In_count_(depth) const Image* baseImages, _In_ size_t depth, _In_ DWORD filter, _In_ size_t levels,
366 _Out_ ScratchImage& mipChain );
367 HRESULT GenerateMipMaps3D( _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
368 _In_ DWORD filter, _In_ size_t levels, _Out_ ScratchImage& mipChain );
369 // levels of '0' indicates a full mipchain, otherwise is generates that number of total levels (including the source base image)
370 // Defaults to Fant filtering which is equivalent to a box filter
372 enum TEX_COMPRESS_FLAGS
374 TEX_COMPRESS_DEFAULT = 0,
376 TEX_COMPRESS_RGB_DITHER = 0x10000,
377 // Enables dithering RGB colors for BC1-3 compression
379 TEX_COMPRESS_A_DITHER = 0x20000,
380 // Enables dithering alpha for BC1-3 compression
382 TEX_COMPRESS_DITHER = 0x30000,
383 // Enables both RGB and alpha dithering for BC1-3 compression
385 TEX_COMPRESS_UNIFORM = 0x40000,
386 // Uniform color weighting for BC1-3 compression; by default uses perceptual weighting
388 TEX_COMPRESS_PARALLEL = 0x10000000,
389 // Compress is free to use multithreading to improve performance (by default it does not use multithreading)
392 HRESULT Compress( _In_ const Image& srcImage, _In_ DXGI_FORMAT format, _In_ DWORD compress, _In_ float alphaRef,
393 _Out_ ScratchImage& cImage );
394 HRESULT Compress( _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
395 _In_ DXGI_FORMAT format, _In_ DWORD compress, _In_ float alphaRef, _Out_ ScratchImage& cImages );
396 // Note that alphaRef is only used by BC1. 0.5f is a typical value to use
398 HRESULT Decompress( _In_ const Image& cImage, _In_ DXGI_FORMAT format, _Out_ ScratchImage& image );
399 HRESULT Decompress( _In_count_(nimages) const Image* cImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
400 _In_ DXGI_FORMAT format, _Out_ ScratchImage& images );
402 //---------------------------------------------------------------------------------
403 // Normal map operations
409 CNMAP_CHANNEL_RED = 0x1,
410 CNMAP_CHANNEL_GREEN = 0x2,
411 CNMAP_CHANNEL_BLUE = 0x3,
412 CNMAP_CHANNEL_ALPHA = 0x4,
413 CNMAP_CHANNEL_LUMINANCE = 0x5,
414 // Channel selection when evaluting color value for height
415 // Luminance is a combination of red, green, and blue
417 CNMAP_MIRROR_U = 0x1000,
418 CNMAP_MIRROR_V = 0x2000,
419 CNMAP_MIRROR = 0x3000,
420 // Use mirror semantics for scanline references (defaults to wrap)
422 CNMAP_INVERT_SIGN = 0x4000,
423 // Inverts normal sign
425 CNMAP_COMPUTE_OCCLUSION = 0x8000,
426 // Computes a crude occlusion term stored in the alpha channel
429 HRESULT ComputeNormalMap( _In_ const Image& srcImage, _In_ DWORD flags, _In_ float amplitude,
430 _In_ DXGI_FORMAT format, _Out_ ScratchImage& normalMap );
431 HRESULT ComputeNormalMap( _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
432 _In_ DWORD flags, _In_ float amplitude, _In_ DXGI_FORMAT format, _Out_ ScratchImage& normalMaps );
434 //---------------------------------------------------------------------------------
435 // Misc image operations
444 Rect( size_t _x, size_t _y, size_t _w, size_t _h ) : x(_x), y(_y), w(_w), h(_h) {}
447 HRESULT CopyRectangle( _In_ const Image& srcImage, _In_ const Rect& srcRect, _In_ const Image& dstImage,
448 _In_ DWORD filter, _In_ size_t xOffset, _In_ size_t yOffset );
450 HRESULT ComputeMSE( _In_ const Image& image1, _In_ const Image& image2, _Out_ float& mse, _Out_opt_cap_c_(4) float* mseV );
452 //---------------------------------------------------------------------------------
453 // Direct3D 11 functions
454 bool IsSupportedTexture( _In_ ID3D11Device* pDevice, _In_ const TexMetadata& metadata );
456 HRESULT CreateTexture( _In_ ID3D11Device* pDevice, _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
457 _Deref_out_ ID3D11Resource** ppResource );
459 HRESULT CreateShaderResourceView( _In_ ID3D11Device* pDevice, _In_count_(nimages) const Image* srcImages, _In_ size_t nimages, _In_ const TexMetadata& metadata,
460 _Deref_out_ ID3D11ShaderResourceView** ppSRV );
462 HRESULT CaptureTexture( _In_ ID3D11Device* pDevice, _In_ ID3D11DeviceContext* pContext, _In_ ID3D11Resource* pSource, _Out_ ScratchImage& result );
464 #include "DirectXTex.inl"