mirror of
https://github.com/microsoft/DirectXTex.git
synced 2025-07-09 19:50:13 +02:00
DirectXTex: support writing DDS files where input Image struct rowPitch is not 1-byte aligned
This commit is contained in:
parent
76b79c42b5
commit
d6976ed850
@ -64,6 +64,7 @@ namespace DirectX
|
|||||||
{
|
{
|
||||||
CP_FLAGS_NONE = 0x0, // Normal operation
|
CP_FLAGS_NONE = 0x0, // Normal operation
|
||||||
CP_FLAGS_LEGACY_DWORD = 0x1, // Assume pitch is DWORD aligned instead of BYTE aligned
|
CP_FLAGS_LEGACY_DWORD = 0x1, // Assume pitch is DWORD aligned instead of BYTE aligned
|
||||||
|
CP_FLAGS_PARAGRAPH = 0x2, // Assume pitch is 16-byte aligned instead of BYTE aligned
|
||||||
CP_FLAGS_24BPP = 0x10000, // Override with a legacy 24 bits-per-pixel format size
|
CP_FLAGS_24BPP = 0x10000, // Override with a legacy 24 bits-per-pixel format size
|
||||||
CP_FLAGS_16BPP = 0x20000, // Override with a legacy 16 bits-per-pixel format size
|
CP_FLAGS_16BPP = 0x20000, // Override with a legacy 16 bits-per-pixel format size
|
||||||
CP_FLAGS_8BPP = 0x40000, // Override with a legacy 8 bits-per-pixel format size
|
CP_FLAGS_8BPP = 0x40000, // Override with a legacy 8 bits-per-pixel format size
|
||||||
@ -238,17 +239,17 @@ namespace DirectX
|
|||||||
|
|
||||||
ScratchImage& operator= (ScratchImage&& moveFrom);
|
ScratchImage& operator= (ScratchImage&& moveFrom);
|
||||||
|
|
||||||
HRESULT Initialize( _In_ const TexMetadata& mdata );
|
HRESULT Initialize( _In_ const TexMetadata& mdata, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
|
|
||||||
HRESULT Initialize1D( _In_ DXGI_FORMAT fmt, _In_ size_t length, _In_ size_t arraySize, _In_ size_t mipLevels );
|
HRESULT Initialize1D( _In_ DXGI_FORMAT fmt, _In_ size_t length, _In_ size_t arraySize, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
HRESULT Initialize2D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t arraySize, _In_ size_t mipLevels );
|
HRESULT Initialize2D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t arraySize, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
HRESULT Initialize3D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t depth, _In_ size_t mipLevels );
|
HRESULT Initialize3D( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t depth, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
HRESULT InitializeCube( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t nCubes, _In_ size_t mipLevels );
|
HRESULT InitializeCube( _In_ DXGI_FORMAT fmt, _In_ size_t width, _In_ size_t height, _In_ size_t nCubes, _In_ size_t mipLevels, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
|
|
||||||
HRESULT InitializeFromImage( _In_ const Image& srcImage, _In_ bool allow1D = false );
|
HRESULT InitializeFromImage( _In_ const Image& srcImage, _In_ bool allow1D = false, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
HRESULT InitializeArrayFromImages( _In_reads_(nImages) const Image* images, _In_ size_t nImages, _In_ bool allow1D = false );
|
HRESULT InitializeArrayFromImages( _In_reads_(nImages) const Image* images, _In_ size_t nImages, _In_ bool allow1D = false, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
HRESULT InitializeCubeFromImages( _In_reads_(nImages) const Image* images, _In_ size_t nImages );
|
HRESULT InitializeCubeFromImages( _In_reads_(nImages) const Image* images, _In_ size_t nImages, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
HRESULT Initialize3DFromImages( _In_reads_(depth) const Image* images, _In_ size_t depth );
|
HRESULT Initialize3DFromImages( _In_reads_(depth) const Image* images, _In_ size_t depth, _In_ DWORD flags = CP_FLAGS_NONE );
|
||||||
|
|
||||||
void Release();
|
void Release();
|
||||||
|
|
||||||
|
@ -1619,11 +1619,28 @@ HRESULT SaveToDDSMemory( const Image* images, size_t nimages, const TexMetadata&
|
|||||||
if ( FAILED(hr) )
|
if ( FAILED(hr) )
|
||||||
return hr;
|
return hr;
|
||||||
|
|
||||||
|
bool fastpath = true;
|
||||||
|
|
||||||
for( size_t i = 0; i < nimages; ++i )
|
for( size_t i = 0; i < nimages; ++i )
|
||||||
{
|
{
|
||||||
required += images[ i ].slicePitch;
|
|
||||||
if ( !images[ i ].pixels )
|
if ( !images[ i ].pixels )
|
||||||
return E_POINTER;
|
return E_POINTER;
|
||||||
|
|
||||||
|
if ( images[ i ].format != metadata.format )
|
||||||
|
return E_FAIL;
|
||||||
|
|
||||||
|
size_t ddsRowPitch, ddsSlicePitch;
|
||||||
|
ComputePitch( metadata.format, images[ i ].width, images[ i ].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE );
|
||||||
|
|
||||||
|
assert( images[ i ].rowPitch > 0 );
|
||||||
|
assert( images[ i ].slicePitch > 0 );
|
||||||
|
|
||||||
|
if ( ( images[ i ].rowPitch != ddsRowPitch ) || ( images[ i ].slicePitch != ddsSlicePitch ) )
|
||||||
|
{
|
||||||
|
fastpath = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
required += ddsSlicePitch;
|
||||||
}
|
}
|
||||||
|
|
||||||
assert( required > 0 );
|
assert( required > 0 );
|
||||||
@ -1669,14 +1686,47 @@ HRESULT SaveToDDSMemory( const Image* images, size_t nimages, const TexMetadata&
|
|||||||
return E_FAIL;
|
return E_FAIL;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t pixsize = images[ index ].slicePitch;
|
if ( fastpath )
|
||||||
if ( memcpy_s( pDestination, remaining, images[ index ].pixels, pixsize ) )
|
|
||||||
{
|
{
|
||||||
blob.Release();
|
size_t pixsize = images[ index ].slicePitch;
|
||||||
return E_FAIL;
|
if ( memcpy_s( pDestination, remaining, images[ index ].pixels, pixsize ) )
|
||||||
|
{
|
||||||
|
blob.Release();
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
pDestination += pixsize;
|
||||||
|
remaining -= pixsize;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
size_t ddsRowPitch, ddsSlicePitch;
|
||||||
|
ComputePitch( metadata.format, images[ index ].width, images[ index ].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE );
|
||||||
|
|
||||||
|
size_t rowPitch = images[ index ].rowPitch;
|
||||||
|
|
||||||
|
const uint8_t * __restrict sPtr = reinterpret_cast<const uint8_t*>(images[ index ].pixels);
|
||||||
|
uint8_t * __restrict dPtr = reinterpret_cast<uint8_t*>(pDestination);
|
||||||
|
|
||||||
|
size_t lines = ComputeScanlines( metadata.format, images[ index ].height );
|
||||||
|
size_t csize = std::min<size_t>( rowPitch, ddsRowPitch );
|
||||||
|
size_t tremaining = remaining;
|
||||||
|
for( size_t j = 0; j < lines; ++j )
|
||||||
|
{
|
||||||
|
if ( memcpy_s( dPtr, tremaining, sPtr, csize ) )
|
||||||
|
{
|
||||||
|
blob.Release();
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
sPtr += rowPitch;
|
||||||
|
dPtr += ddsRowPitch;
|
||||||
|
tremaining -= ddsRowPitch;
|
||||||
|
}
|
||||||
|
|
||||||
|
pDestination += ddsSlicePitch;
|
||||||
|
remaining -= ddsSlicePitch;
|
||||||
}
|
}
|
||||||
pDestination += pixsize;
|
|
||||||
remaining -= pixsize;
|
|
||||||
|
|
||||||
++index;
|
++index;
|
||||||
}
|
}
|
||||||
@ -1705,14 +1755,47 @@ HRESULT SaveToDDSMemory( const Image* images, size_t nimages, const TexMetadata&
|
|||||||
return E_FAIL;
|
return E_FAIL;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t pixsize = images[ index ].slicePitch;
|
if ( fastpath )
|
||||||
if ( memcpy_s( pDestination, remaining, images[ index ].pixels, pixsize ) )
|
|
||||||
{
|
{
|
||||||
blob.Release();
|
size_t pixsize = images[ index ].slicePitch;
|
||||||
return E_FAIL;
|
if ( memcpy_s( pDestination, remaining, images[ index ].pixels, pixsize ) )
|
||||||
|
{
|
||||||
|
blob.Release();
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
pDestination += pixsize;
|
||||||
|
remaining -= pixsize;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
size_t ddsRowPitch, ddsSlicePitch;
|
||||||
|
ComputePitch( metadata.format, images[ index ].width, images[ index ].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE );
|
||||||
|
|
||||||
|
size_t rowPitch = images[ index ].rowPitch;
|
||||||
|
|
||||||
|
const uint8_t * __restrict sPtr = reinterpret_cast<const uint8_t*>(images[ index ].pixels);
|
||||||
|
uint8_t * __restrict dPtr = reinterpret_cast<uint8_t*>(pDestination);
|
||||||
|
|
||||||
|
size_t lines = ComputeScanlines( metadata.format, images[ index ].height );
|
||||||
|
size_t csize = std::min<size_t>( rowPitch, ddsRowPitch );
|
||||||
|
size_t tremaining = remaining;
|
||||||
|
for( size_t j = 0; j < lines; ++j )
|
||||||
|
{
|
||||||
|
if ( memcpy_s( dPtr, tremaining, sPtr, csize ) )
|
||||||
|
{
|
||||||
|
blob.Release();
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
sPtr += rowPitch;
|
||||||
|
dPtr += ddsRowPitch;
|
||||||
|
tremaining -= ddsRowPitch;
|
||||||
|
}
|
||||||
|
|
||||||
|
pDestination += ddsSlicePitch;
|
||||||
|
remaining -= ddsSlicePitch;
|
||||||
}
|
}
|
||||||
pDestination += pixsize;
|
|
||||||
remaining -= pixsize;
|
|
||||||
|
|
||||||
++index;
|
++index;
|
||||||
}
|
}
|
||||||
@ -1788,16 +1871,50 @@ HRESULT SaveToDDSFile( const Image* images, size_t nimages, const TexMetadata& m
|
|||||||
if ( !images[ index ].pixels )
|
if ( !images[ index ].pixels )
|
||||||
return E_POINTER;
|
return E_POINTER;
|
||||||
|
|
||||||
size_t pixsize = images[ index ].slicePitch;
|
assert( images[ index ].rowPitch > 0 );
|
||||||
|
assert( images[ index ].slicePitch > 0 );
|
||||||
|
|
||||||
if ( !WriteFile( hFile.get(), images[ index ].pixels, static_cast<DWORD>( pixsize ), &bytesWritten, 0 ) )
|
size_t ddsRowPitch, ddsSlicePitch;
|
||||||
|
ComputePitch( metadata.format, images[ index ].width, images[ index ].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE );
|
||||||
|
|
||||||
|
if ( images[ index ].slicePitch == ddsSlicePitch )
|
||||||
{
|
{
|
||||||
return HRESULT_FROM_WIN32( GetLastError() );
|
if ( !WriteFile( hFile.get(), images[ index ].pixels, static_cast<DWORD>( ddsSlicePitch ), &bytesWritten, 0 ) )
|
||||||
|
{
|
||||||
|
return HRESULT_FROM_WIN32( GetLastError() );
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( bytesWritten != ddsSlicePitch )
|
||||||
|
{
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
if ( bytesWritten != pixsize )
|
|
||||||
{
|
{
|
||||||
return E_FAIL;
|
size_t rowPitch = images[ index ].rowPitch;
|
||||||
|
if ( rowPitch < ddsRowPitch )
|
||||||
|
{
|
||||||
|
// DDS uses 1-byte alignment, so if this is happening then the input pitch isn't actually a full line of data
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
const uint8_t * __restrict sPtr = reinterpret_cast<const uint8_t*>(images[ index ].pixels);
|
||||||
|
|
||||||
|
size_t lines = ComputeScanlines( metadata.format, images[ index ].height );
|
||||||
|
for( size_t j = 0; j < lines; ++j )
|
||||||
|
{
|
||||||
|
if ( !WriteFile( hFile.get(), sPtr, static_cast<DWORD>( ddsRowPitch ), &bytesWritten, 0 ) )
|
||||||
|
{
|
||||||
|
return HRESULT_FROM_WIN32( GetLastError() );
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( bytesWritten != ddsRowPitch )
|
||||||
|
{
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
sPtr += rowPitch;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1822,16 +1939,50 @@ HRESULT SaveToDDSFile( const Image* images, size_t nimages, const TexMetadata& m
|
|||||||
if ( !images[ index ].pixels )
|
if ( !images[ index ].pixels )
|
||||||
return E_POINTER;
|
return E_POINTER;
|
||||||
|
|
||||||
size_t pixsize = images[ index ].slicePitch;
|
assert( images[ index ].rowPitch > 0 );
|
||||||
|
assert( images[ index ].slicePitch > 0 );
|
||||||
|
|
||||||
if ( !WriteFile( hFile.get(), images[ index ].pixels, static_cast<DWORD>( pixsize ), &bytesWritten, 0 ) )
|
size_t ddsRowPitch, ddsSlicePitch;
|
||||||
|
ComputePitch( metadata.format, images[ index ].width, images[ index ].height, ddsRowPitch, ddsSlicePitch, CP_FLAGS_NONE );
|
||||||
|
|
||||||
|
if ( images[ index ].slicePitch == ddsSlicePitch )
|
||||||
{
|
{
|
||||||
return HRESULT_FROM_WIN32( GetLastError() );
|
if ( !WriteFile( hFile.get(), images[ index ].pixels, static_cast<DWORD>( ddsSlicePitch ), &bytesWritten, 0 ) )
|
||||||
|
{
|
||||||
|
return HRESULT_FROM_WIN32( GetLastError() );
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( bytesWritten != ddsSlicePitch )
|
||||||
|
{
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
if ( bytesWritten != pixsize )
|
|
||||||
{
|
{
|
||||||
return E_FAIL;
|
size_t rowPitch = images[ index ].rowPitch;
|
||||||
|
if ( rowPitch < ddsRowPitch )
|
||||||
|
{
|
||||||
|
// DDS uses 1-byte alignment, so if this is happening then the input pitch isn't actually a full line of data
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
const uint8_t * __restrict sPtr = reinterpret_cast<const uint8_t*>(images[ index ].pixels);
|
||||||
|
|
||||||
|
size_t lines = ComputeScanlines( metadata.format, images[ index ].height );
|
||||||
|
for( size_t j = 0; j < lines; ++j )
|
||||||
|
{
|
||||||
|
if ( !WriteFile( hFile.get(), sPtr, static_cast<DWORD>( ddsRowPitch ), &bytesWritten, 0 ) )
|
||||||
|
{
|
||||||
|
return HRESULT_FROM_WIN32( GetLastError() );
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( bytesWritten != ddsRowPitch )
|
||||||
|
{
|
||||||
|
return E_FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
sPtr += rowPitch;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -254,7 +254,7 @@ ScratchImage& ScratchImage::operator= (ScratchImage&& moveFrom)
|
|||||||
// Methods
|
// Methods
|
||||||
//-------------------------------------------------------------------------------------
|
//-------------------------------------------------------------------------------------
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::Initialize( const TexMetadata& mdata )
|
HRESULT ScratchImage::Initialize( const TexMetadata& mdata, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !IsValid(mdata.format) )
|
if ( !IsValid(mdata.format) )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -322,7 +322,7 @@ HRESULT ScratchImage::Initialize( const TexMetadata& mdata )
|
|||||||
_metadata.dimension = mdata.dimension;
|
_metadata.dimension = mdata.dimension;
|
||||||
|
|
||||||
size_t pixelSize, nimages;
|
size_t pixelSize, nimages;
|
||||||
_DetermineImageArray( _metadata, CP_FLAGS_NONE, nimages, pixelSize );
|
_DetermineImageArray( _metadata, flags, nimages, pixelSize );
|
||||||
|
|
||||||
_image = new (std::nothrow) Image[ nimages ];
|
_image = new (std::nothrow) Image[ nimages ];
|
||||||
if ( !_image )
|
if ( !_image )
|
||||||
@ -338,7 +338,7 @@ HRESULT ScratchImage::Initialize( const TexMetadata& mdata )
|
|||||||
return E_OUTOFMEMORY;
|
return E_OUTOFMEMORY;
|
||||||
}
|
}
|
||||||
_size = pixelSize;
|
_size = pixelSize;
|
||||||
if ( !_SetupImageArray( _memory, pixelSize, _metadata, CP_FLAGS_NONE, _image, nimages ) )
|
if ( !_SetupImageArray( _memory, pixelSize, _metadata, flags, _image, nimages ) )
|
||||||
{
|
{
|
||||||
Release();
|
Release();
|
||||||
return E_FAIL;
|
return E_FAIL;
|
||||||
@ -348,7 +348,7 @@ HRESULT ScratchImage::Initialize( const TexMetadata& mdata )
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::Initialize1D( DXGI_FORMAT fmt, size_t length, size_t arraySize, size_t mipLevels )
|
HRESULT ScratchImage::Initialize1D( DXGI_FORMAT fmt, size_t length, size_t arraySize, size_t mipLevels, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !length || !arraySize )
|
if ( !length || !arraySize )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -357,7 +357,7 @@ HRESULT ScratchImage::Initialize1D( DXGI_FORMAT fmt, size_t length, size_t array
|
|||||||
return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
|
return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
|
||||||
|
|
||||||
// 1D is a special case of the 2D case
|
// 1D is a special case of the 2D case
|
||||||
HRESULT hr = Initialize2D( fmt, length, 1, arraySize, mipLevels );
|
HRESULT hr = Initialize2D( fmt, length, 1, arraySize, mipLevels, flags );
|
||||||
if ( FAILED(hr) )
|
if ( FAILED(hr) )
|
||||||
return hr;
|
return hr;
|
||||||
|
|
||||||
@ -367,7 +367,7 @@ HRESULT ScratchImage::Initialize1D( DXGI_FORMAT fmt, size_t length, size_t array
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::Initialize2D( DXGI_FORMAT fmt, size_t width, size_t height, size_t arraySize, size_t mipLevels )
|
HRESULT ScratchImage::Initialize2D( DXGI_FORMAT fmt, size_t width, size_t height, size_t arraySize, size_t mipLevels, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !IsValid(fmt) || !width || !height || !arraySize )
|
if ( !IsValid(fmt) || !width || !height || !arraySize )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -391,7 +391,7 @@ HRESULT ScratchImage::Initialize2D( DXGI_FORMAT fmt, size_t width, size_t height
|
|||||||
_metadata.dimension = TEX_DIMENSION_TEXTURE2D;
|
_metadata.dimension = TEX_DIMENSION_TEXTURE2D;
|
||||||
|
|
||||||
size_t pixelSize, nimages;
|
size_t pixelSize, nimages;
|
||||||
_DetermineImageArray( _metadata, CP_FLAGS_NONE, nimages, pixelSize );
|
_DetermineImageArray( _metadata, flags, nimages, pixelSize );
|
||||||
|
|
||||||
_image = new (std::nothrow) Image[ nimages ];
|
_image = new (std::nothrow) Image[ nimages ];
|
||||||
if ( !_image )
|
if ( !_image )
|
||||||
@ -407,7 +407,7 @@ HRESULT ScratchImage::Initialize2D( DXGI_FORMAT fmt, size_t width, size_t height
|
|||||||
return E_OUTOFMEMORY;
|
return E_OUTOFMEMORY;
|
||||||
}
|
}
|
||||||
_size = pixelSize;
|
_size = pixelSize;
|
||||||
if ( !_SetupImageArray( _memory, pixelSize, _metadata, CP_FLAGS_NONE, _image, nimages ) )
|
if ( !_SetupImageArray( _memory, pixelSize, _metadata, flags, _image, nimages ) )
|
||||||
{
|
{
|
||||||
Release();
|
Release();
|
||||||
return E_FAIL;
|
return E_FAIL;
|
||||||
@ -417,7 +417,7 @@ HRESULT ScratchImage::Initialize2D( DXGI_FORMAT fmt, size_t width, size_t height
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::Initialize3D( DXGI_FORMAT fmt, size_t width, size_t height, size_t depth, size_t mipLevels )
|
HRESULT ScratchImage::Initialize3D( DXGI_FORMAT fmt, size_t width, size_t height, size_t depth, size_t mipLevels, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !IsValid(fmt) || !width || !height || !depth )
|
if ( !IsValid(fmt) || !width || !height || !depth )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -441,7 +441,7 @@ HRESULT ScratchImage::Initialize3D( DXGI_FORMAT fmt, size_t width, size_t height
|
|||||||
_metadata.dimension = TEX_DIMENSION_TEXTURE3D;
|
_metadata.dimension = TEX_DIMENSION_TEXTURE3D;
|
||||||
|
|
||||||
size_t pixelSize, nimages;
|
size_t pixelSize, nimages;
|
||||||
_DetermineImageArray( _metadata, CP_FLAGS_NONE, nimages, pixelSize );
|
_DetermineImageArray( _metadata, flags, nimages, pixelSize );
|
||||||
|
|
||||||
_image = new (std::nothrow) Image[ nimages ];
|
_image = new (std::nothrow) Image[ nimages ];
|
||||||
if ( !_image )
|
if ( !_image )
|
||||||
@ -460,7 +460,7 @@ HRESULT ScratchImage::Initialize3D( DXGI_FORMAT fmt, size_t width, size_t height
|
|||||||
}
|
}
|
||||||
_size = pixelSize;
|
_size = pixelSize;
|
||||||
|
|
||||||
if ( !_SetupImageArray( _memory, pixelSize, _metadata, CP_FLAGS_NONE, _image, nimages ) )
|
if ( !_SetupImageArray( _memory, pixelSize, _metadata, flags, _image, nimages ) )
|
||||||
{
|
{
|
||||||
Release();
|
Release();
|
||||||
return E_FAIL;
|
return E_FAIL;
|
||||||
@ -470,7 +470,7 @@ HRESULT ScratchImage::Initialize3D( DXGI_FORMAT fmt, size_t width, size_t height
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::InitializeCube( DXGI_FORMAT fmt, size_t width, size_t height, size_t nCubes, size_t mipLevels )
|
HRESULT ScratchImage::InitializeCube( DXGI_FORMAT fmt, size_t width, size_t height, size_t nCubes, size_t mipLevels, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !width || !height || !nCubes )
|
if ( !width || !height || !nCubes )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -479,7 +479,7 @@ HRESULT ScratchImage::InitializeCube( DXGI_FORMAT fmt, size_t width, size_t heig
|
|||||||
return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
|
return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
|
||||||
|
|
||||||
// A DirectX11 cubemap is just a 2D texture array that is a multiple of 6 for each cube
|
// A DirectX11 cubemap is just a 2D texture array that is a multiple of 6 for each cube
|
||||||
HRESULT hr = Initialize2D( fmt, width, height, nCubes * 6, mipLevels );
|
HRESULT hr = Initialize2D( fmt, width, height, nCubes * 6, mipLevels, flags );
|
||||||
if ( FAILED(hr) )
|
if ( FAILED(hr) )
|
||||||
return hr;
|
return hr;
|
||||||
|
|
||||||
@ -489,11 +489,11 @@ HRESULT ScratchImage::InitializeCube( DXGI_FORMAT fmt, size_t width, size_t heig
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::InitializeFromImage( const Image& srcImage, bool allow1D )
|
HRESULT ScratchImage::InitializeFromImage( const Image& srcImage, bool allow1D, DWORD flags )
|
||||||
{
|
{
|
||||||
HRESULT hr = ( srcImage.height > 1 || !allow1D )
|
HRESULT hr = ( srcImage.height > 1 || !allow1D )
|
||||||
? Initialize2D( srcImage.format, srcImage.width, srcImage.height, 1, 1 )
|
? Initialize2D( srcImage.format, srcImage.width, srcImage.height, 1, 1, flags )
|
||||||
: Initialize1D( srcImage.format, srcImage.width, 1, 1 );
|
: Initialize1D( srcImage.format, srcImage.width, 1, 1, flags );
|
||||||
|
|
||||||
if ( FAILED(hr) )
|
if ( FAILED(hr) )
|
||||||
return hr;
|
return hr;
|
||||||
@ -526,7 +526,7 @@ HRESULT ScratchImage::InitializeFromImage( const Image& srcImage, bool allow1D )
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::InitializeArrayFromImages( const Image* images, size_t nImages, bool allow1D )
|
HRESULT ScratchImage::InitializeArrayFromImages( const Image* images, size_t nImages, bool allow1D, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !images || !nImages )
|
if ( !images || !nImages )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -548,8 +548,8 @@ HRESULT ScratchImage::InitializeArrayFromImages( const Image* images, size_t nIm
|
|||||||
}
|
}
|
||||||
|
|
||||||
HRESULT hr = ( height > 1 || !allow1D )
|
HRESULT hr = ( height > 1 || !allow1D )
|
||||||
? Initialize2D( format, width, height, nImages, 1 )
|
? Initialize2D( format, width, height, nImages, 1, flags )
|
||||||
: Initialize1D( format, width, nImages, 1 );
|
: Initialize1D( format, width, nImages, 1, flags );
|
||||||
|
|
||||||
if ( FAILED(hr) )
|
if ( FAILED(hr) )
|
||||||
return hr;
|
return hr;
|
||||||
@ -586,7 +586,7 @@ HRESULT ScratchImage::InitializeArrayFromImages( const Image* images, size_t nIm
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::InitializeCubeFromImages( const Image* images, size_t nImages )
|
HRESULT ScratchImage::InitializeCubeFromImages( const Image* images, size_t nImages, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !images || !nImages )
|
if ( !images || !nImages )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -598,7 +598,7 @@ HRESULT ScratchImage::InitializeCubeFromImages( const Image* images, size_t nIma
|
|||||||
if ( IsVideo(images[0].format) || IsPalettized(images[0].format) )
|
if ( IsVideo(images[0].format) || IsPalettized(images[0].format) )
|
||||||
return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
|
return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
|
||||||
|
|
||||||
HRESULT hr = InitializeArrayFromImages( images, nImages, false );
|
HRESULT hr = InitializeArrayFromImages( images, nImages, false, flags );
|
||||||
if ( FAILED(hr) )
|
if ( FAILED(hr) )
|
||||||
return hr;
|
return hr;
|
||||||
|
|
||||||
@ -608,7 +608,7 @@ HRESULT ScratchImage::InitializeCubeFromImages( const Image* images, size_t nIma
|
|||||||
}
|
}
|
||||||
|
|
||||||
_Use_decl_annotations_
|
_Use_decl_annotations_
|
||||||
HRESULT ScratchImage::Initialize3DFromImages( const Image* images, size_t depth )
|
HRESULT ScratchImage::Initialize3DFromImages( const Image* images, size_t depth, DWORD flags )
|
||||||
{
|
{
|
||||||
if ( !images || !depth )
|
if ( !images || !depth )
|
||||||
return E_INVALIDARG;
|
return E_INVALIDARG;
|
||||||
@ -629,7 +629,7 @@ HRESULT ScratchImage::Initialize3DFromImages( const Image* images, size_t depth
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
HRESULT hr = Initialize3D( format, width, height, depth, 1 );
|
HRESULT hr = Initialize3D( format, width, height, depth, 1, flags );
|
||||||
if ( FAILED(hr) )
|
if ( FAILED(hr) )
|
||||||
return hr;
|
return hr;
|
||||||
|
|
||||||
|
@ -661,6 +661,11 @@ void ComputePitch( DXGI_FORMAT fmt, size_t width, size_t height,
|
|||||||
rowPitch = ( ( width * bpp + 31 ) / 32 ) * sizeof(uint32_t);
|
rowPitch = ( ( width * bpp + 31 ) / 32 ) * sizeof(uint32_t);
|
||||||
slicePitch = rowPitch * height;
|
slicePitch = rowPitch * height;
|
||||||
}
|
}
|
||||||
|
else if ( flags & CP_FLAGS_PARAGRAPH )
|
||||||
|
{
|
||||||
|
rowPitch = ( ( width * bpp + 127 ) / 128 ) * 16;
|
||||||
|
slicePitch = rowPitch * height;
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
rowPitch = ( width * bpp + 7 ) / 8;
|
rowPitch = ( width * bpp + 7 ) / 8;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user