From 09b6fee360acb1b0d0ecc4b07a624713cfdc0483 Mon Sep 17 00:00:00 2001 From: Geoffrey McRae Date: Tue, 7 Nov 2023 13:42:38 +1100 Subject: [PATCH] [host] dxgi: fix HDR content downsampling --- host/platform/Windows/capture/DXGI/src/dxgi.c | 29 ++++++++++--------- .../Windows/capture/DXGI/src/pp/downsample.c | 2 +- host/platform/Windows/capture/DXGI/src/util.c | 28 ++++++++++++++++++ host/platform/Windows/capture/DXGI/src/util.h | 5 ++++ 4 files changed, 49 insertions(+), 15 deletions(-) diff --git a/host/platform/Windows/capture/DXGI/src/dxgi.c b/host/platform/Windows/capture/DXGI/src/dxgi.c index f455e451..73a07aea 100644 --- a/host/platform/Windows/capture/DXGI/src/dxgi.c +++ b/host/platform/Windows/capture/DXGI/src/dxgi.c @@ -739,28 +739,29 @@ static bool dxgi_init(void) if (!initVertexShader()) goto fail; - if (!ppInit(&DXGIPP_Downsample, - this->backend != ©BackendD3D11 && !this->hdr)) - { - DEBUG_ERROR("Failed to intiailize the downsample post processor"); - goto fail; - } - - // if HDR add the SDRWhiteLevel post processor to correct the output + bool shareable = this->backend != ©BackendD3D11; if (this->hdr) { - if (!ppInit(&DXGIPP_SDRWhiteLevel, this->backend != ©BackendD3D11)) + //HDR content needs to be corrected and converted to HDR10 + if (!ppInit(&DXGIPP_SDRWhiteLevel, shareable)) { DEBUG_ERROR("Failed to initialize the SDRWhiteLevel post processor"); goto fail; } } - else + + //Downsampling must happen before conversion to RGB24 + if (!ppInit(&DXGIPP_Downsample, shareable)) { - // only support DX11 for this atm - if (this->backend == ©BackendD3D11) - if (!ppInit(&DXGIPP_RGB24, false)) - DEBUG_WARN("Failed to initialize the RGB24 post processor"); + DEBUG_ERROR("Failed to intiailize the downsample post processor"); + goto fail; + } + + //If not HDR, pack to RGB24 + if (!this->hdr) + { + if (!ppInit(&DXGIPP_RGB24, shareable)) + DEBUG_WARN("Failed to initialize the RGB24 post processor"); } for (int i = 0; i < LGMP_Q_FRAME_LEN; ++i) diff --git a/host/platform/Windows/capture/DXGI/src/pp/downsample.c b/host/platform/Windows/capture/DXGI/src/pp/downsample.c index 6cb0e009..9626517c 100644 --- a/host/platform/Windows/capture/DXGI/src/pp/downsample.c +++ b/host/platform/Windows/capture/DXGI/src/pp/downsample.c @@ -171,7 +171,7 @@ static bool downsample_configure(void * opaque, .SampleDesc.Count = 1, .SampleDesc.Quality = 0, .Usage = D3D11_USAGE_DEFAULT, - .Format = DXGI_FORMAT_B8G8R8A8_UNORM, + .Format = getDXGIFormat(*format), .BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE, .CPUAccessFlags = 0, diff --git a/host/platform/Windows/capture/DXGI/src/util.c b/host/platform/Windows/capture/DXGI/src/util.c index 6036ecb6..bc765513 100644 --- a/host/platform/Windows/capture/DXGI/src/util.c +++ b/host/platform/Windows/capture/DXGI/src/util.c @@ -18,6 +18,7 @@ * Temple Place, Suite 330, Boston, MA 02111-1307 USA */ +#include "util.h" #include "common/debug.h" #include @@ -320,3 +321,30 @@ float getSDRWhiteLevel(const DISPLAYCONFIG_PATH_INFO * displayPathInfo) return nits; } + +DXGI_FORMAT getDXGIFormat(CaptureFormat format) +{ + switch(format) + { + case CAPTURE_FMT_RGBA: + return DXGI_FORMAT_R8G8B8A8_UNORM; + + case CAPTURE_FMT_BGRA: + return DXGI_FORMAT_B8G8R8A8_UNORM; + + case CAPTURE_FMT_RGBA10: + return DXGI_FORMAT_R10G10B10A2_UNORM; + + case CAPTURE_FMT_RGBA16F: + return DXGI_FORMAT_R16G16B16A16_FLOAT; + + case CAPTURE_FMT_BGR: + return DXGI_FORMAT_B8G8R8A8_UNORM; + + default: + break; + } + + DEBUG_ASSERT("Invalid capture format for DXGI"); + return 0; +} diff --git a/host/platform/Windows/capture/DXGI/src/util.h b/host/platform/Windows/capture/DXGI/src/util.h index 2e23700f..c02d0878 100644 --- a/host/platform/Windows/capture/DXGI/src/util.h +++ b/host/platform/Windows/capture/DXGI/src/util.h @@ -19,8 +19,11 @@ */ #include +#include #include +#include "interface/capture.h" + const char * getDXGIFormatStr(DXGI_FORMAT format); const char * getDXGIColorSpaceTypeStr(DXGI_COLOR_SPACE_TYPE type); @@ -30,3 +33,5 @@ bool compileShader(ID3DBlob ** dst, const char * entry, const char * target, bool getDisplayPathInfo(HMONITOR monitor, DISPLAYCONFIG_PATH_INFO * info); float getSDRWhiteLevel(const DISPLAYCONFIG_PATH_INFO * displayPathInfo); + +DXGI_FORMAT getDXGIFormat(CaptureFormat format);