summaryrefslogtreecommitdiff
path: root/thirdparty/directxtex/DirectXTex/DirectXTexMisc.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'thirdparty/directxtex/DirectXTex/DirectXTexMisc.cpp')
-rw-r--r--thirdparty/directxtex/DirectXTex/DirectXTexMisc.cpp109
1 files changed, 99 insertions, 10 deletions
diff --git a/thirdparty/directxtex/DirectXTex/DirectXTexMisc.cpp b/thirdparty/directxtex/DirectXTex/DirectXTexMisc.cpp
index 988fb1fb..3285ba5d 100644
--- a/thirdparty/directxtex/DirectXTex/DirectXTexMisc.cpp
+++ b/thirdparty/directxtex/DirectXTex/DirectXTexMisc.cpp
@@ -17,10 +17,12 @@
namespace DirectX
{
+static const XMVECTORF32 g_Gamma22 = { 2.2f, 2.2f, 2.2f, 1.f };
//-------------------------------------------------------------------------------------
static HRESULT _ComputeMSE( _In_ const Image& image1, _In_ const Image& image2,
- _Out_ float& mse, _Out_opt_cap_c_(4) float* mseV )
+ _Out_ float& mse, _Out_writes_opt_(4) float* mseV,
+ _In_ DWORD flags )
{
if ( !image1.pixels || !image2.pixels )
return E_POINTER;
@@ -34,13 +36,55 @@ static HRESULT _ComputeMSE( _In_ const Image& image1, _In_ const Image& image2,
if ( !scanline )
return E_OUTOFMEMORY;
+ // Flags implied from image formats
+ switch( image1.format )
+ {
+ case DXGI_FORMAT_B8G8R8X8_UNORM:
+ flags |= CMSE_IGNORE_ALPHA;
+ break;
+
+ case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
+ flags |= CMSE_IMAGE1_SRGB | CMSE_IGNORE_ALPHA;
+ break;
+
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ case DXGI_FORMAT_BC1_UNORM_SRGB:
+ case DXGI_FORMAT_BC2_UNORM_SRGB:
+ case DXGI_FORMAT_BC3_UNORM_SRGB:
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ case DXGI_FORMAT_BC7_UNORM_SRGB:
+ flags |= CMSE_IMAGE1_SRGB;
+ break;
+ }
+
+ switch( image2.format )
+ {
+ case DXGI_FORMAT_B8G8R8X8_UNORM:
+ flags |= CMSE_IGNORE_ALPHA;
+ break;
+
+ case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
+ flags |= CMSE_IMAGE2_SRGB | CMSE_IGNORE_ALPHA;
+ break;
+
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ case DXGI_FORMAT_BC1_UNORM_SRGB:
+ case DXGI_FORMAT_BC2_UNORM_SRGB:
+ case DXGI_FORMAT_BC3_UNORM_SRGB:
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ case DXGI_FORMAT_BC7_UNORM_SRGB:
+ flags |= CMSE_IMAGE2_SRGB;
+ break;
+ }
+
const uint8_t *pSrc1 = image1.pixels;
const size_t rowPitch1 = image1.rowPitch;
const uint8_t *pSrc2 = image2.pixels;
const size_t rowPitch2 = image2.rowPitch;
- XMVECTOR acc = XMVectorZero();
+ XMVECTOR acc = g_XMZero;
+ static XMVECTORF32 two = { 2.0f, 2.0f, 2.0f, 2.0f };
for( size_t h = 0; h < image1.height; ++h )
{
@@ -52,10 +96,47 @@ static HRESULT _ComputeMSE( _In_ const Image& image1, _In_ const Image& image2,
if ( !_LoadScanline( ptr2, width, pSrc2, rowPitch2, image2.format ) )
return E_FAIL;
- for( size_t i = 0; i < width; ++i, ++ptr1, ++ptr2 )
+ for( size_t i = 0; i < width; ++i )
{
+ XMVECTOR v1 = *(ptr1++);
+ if ( flags & CMSE_IMAGE1_SRGB )
+ {
+ v1 = XMVectorPow( v1, g_Gamma22 );
+ }
+ if ( flags & CMSE_IMAGE1_X2_BIAS )
+ {
+ v1 = XMVectorMultiplyAdd( v1, two, g_XMNegativeOne );
+ }
+
+ XMVECTOR v2 = *(ptr2++);
+ if ( flags & CMSE_IMAGE2_SRGB )
+ {
+ v2 = XMVectorPow( v2, g_Gamma22 );
+ }
+ if ( flags & CMSE_IMAGE2_X2_BIAS )
+ {
+ v1 = XMVectorMultiplyAdd( v2, two, g_XMNegativeOne );
+ }
+
// sum[ (I1 - I2)^2 ]
- XMVECTOR v = XMVectorSubtract( *ptr1, *ptr2 );
+ XMVECTOR v = XMVectorSubtract( v1, v2 );
+ if ( flags & CMSE_IGNORE_RED )
+ {
+ v = XMVectorSelect( v, g_XMZero, g_XMMaskX );
+ }
+ if ( flags & CMSE_IGNORE_GREEN )
+ {
+ v = XMVectorSelect( v, g_XMZero, g_XMMaskY );
+ }
+ if ( flags & CMSE_IGNORE_BLUE )
+ {
+ v = XMVectorSelect( v, g_XMZero, g_XMMaskZ );
+ }
+ if ( flags & CMSE_IGNORE_ALPHA )
+ {
+ v = XMVectorSelect( v, g_XMZero, g_XMMaskW );
+ }
+
acc = XMVectorMultiplyAdd( v, v, acc );
}
@@ -89,12 +170,15 @@ static HRESULT _ComputeMSE( _In_ const Image& image1, _In_ const Image& image2,
//-------------------------------------------------------------------------------------
// Copies a rectangle from one image into another
//-------------------------------------------------------------------------------------
+_Use_decl_annotations_
HRESULT CopyRectangle( const Image& srcImage, const Rect& srcRect, const Image& dstImage, DWORD filter, size_t xOffset, size_t yOffset )
{
if ( !srcImage.pixels || !dstImage.pixels )
return E_POINTER;
- if ( IsCompressed( srcImage.format ) || IsCompressed( dstImage.format ) )
+ if ( IsCompressed( srcImage.format ) || IsCompressed( dstImage.format )
+ || IsPlanar( srcImage.format ) || IsPlanar( dstImage.format )
+ || IsPalettized( srcImage.format ) || IsPalettized( dstImage.format ) )
return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
// Validate rectangle/offset
@@ -193,7 +277,8 @@ HRESULT CopyRectangle( const Image& srcImage, const Rect& srcRect, const Image&
//-------------------------------------------------------------------------------------
// Computes the Mean-Squared-Error (MSE) between two images
//-------------------------------------------------------------------------------------
-HRESULT ComputeMSE( const Image& image1, const Image& image2, float& mse, float* mseV )
+_Use_decl_annotations_
+HRESULT ComputeMSE( const Image& image1, const Image& image2, float& mse, float* mseV, DWORD flags )
{
if ( !image1.pixels || !image2.pixels )
return E_POINTER;
@@ -201,6 +286,10 @@ HRESULT ComputeMSE( const Image& image1, const Image& image2, float& mse, float*
if ( image1.width != image2.width || image1.height != image2.height )
return E_INVALIDARG;
+ if ( IsPlanar( image1.format ) || IsPlanar( image2.format )
+ || IsPalettized( image1.format ) || IsPalettized( image2.format ) )
+ return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED );
+
if ( IsCompressed(image1.format) )
{
if ( IsCompressed(image2.format) )
@@ -221,7 +310,7 @@ HRESULT ComputeMSE( const Image& image1, const Image& image2, float& mse, float*
if ( !img1 || !img2 )
return E_POINTER;
- return _ComputeMSE( *img1, *img2, mse, mseV );
+ return _ComputeMSE( *img1, *img2, mse, mseV, flags );
}
else
{
@@ -235,7 +324,7 @@ HRESULT ComputeMSE( const Image& image1, const Image& image2, float& mse, float*
if ( !img )
return E_POINTER;
- return _ComputeMSE( *img, image2, mse, mseV );
+ return _ComputeMSE( *img, image2, mse, mseV, flags );
}
}
else
@@ -252,12 +341,12 @@ HRESULT ComputeMSE( const Image& image1, const Image& image2, float& mse, float*
if ( !img )
return E_POINTER;
- return _ComputeMSE( image1, *img, mse, mseV );
+ return _ComputeMSE( image1, *img, mse, mseV, flags );
}
else
{
// Case 4: neither image is compressed
- return _ComputeMSE( image1, image2, mse, mseV );
+ return _ComputeMSE( image1, image2, mse, mseV, flags );
}
}
}