[client] egl: prepare for DXGI HDR10 support

This commit is contained in:
Geoffrey McRae 2023-10-27 01:03:22 +11:00
parent 200b7b732c
commit 2f36aaff5c
6 changed files with 24 additions and 9 deletions

View File

@ -73,6 +73,7 @@ typedef struct LG_RendererFormat
{ {
FrameType type; // frame type FrameType type; // frame type
bool hdr; // if the frame is HDR or not bool hdr; // if the frame is HDR or not
bool hdrPQ; // if the HDR content is PQ mapped
unsigned int screenWidth; // actual width of the host unsigned int screenWidth; // actual width of the host
unsigned int screenHeight; // actual height of the host unsigned int screenHeight; // actual height of the host
unsigned int frameWidth; // width of frame transmitted unsigned int frameWidth; // width of frame transmitted

View File

@ -53,6 +53,7 @@ struct DesktopShader
GLint uIsHDR; GLint uIsHDR;
GLint uMapHDRtoSDR; GLint uMapHDRtoSDR;
GLint uMapHDRGain; GLint uMapHDRGain;
GLint uMapHDRPQ;
}; };
struct EGL_Desktop struct EGL_Desktop
@ -68,6 +69,7 @@ struct EGL_Desktop
// internals // internals
int width, height; int width, height;
bool hdr; bool hdr;
bool hdrPQ;
LG_RendererRotate rotate; LG_RendererRotate rotate;
bool useSpice; bool useSpice;
@ -125,6 +127,7 @@ static bool egl_initDesktopShader(
shader->uIsHDR = egl_shaderGetUniform(shader->shader, "isHDR" ); shader->uIsHDR = egl_shaderGetUniform(shader->shader, "isHDR" );
shader->uMapHDRtoSDR = egl_shaderGetUniform(shader->shader, "mapHDRtoSDR" ); shader->uMapHDRtoSDR = egl_shaderGetUniform(shader->shader, "mapHDRtoSDR" );
shader->uMapHDRGain = egl_shaderGetUniform(shader->shader, "mapHDRGain" ); shader->uMapHDRGain = egl_shaderGetUniform(shader->shader, "mapHDRGain" );
shader->uMapHDRPQ = egl_shaderGetUniform(shader->shader, "mapHDRPQ" );
return true; return true;
} }
@ -342,6 +345,7 @@ bool egl_desktopSetup(EGL_Desktop * desktop, const LG_RendererFormat format)
desktop->width = format.frameWidth; desktop->width = format.frameWidth;
desktop->height = format.frameHeight; desktop->height = format.frameHeight;
desktop->hdr = format.hdr; desktop->hdr = format.hdr;
desktop->hdrPQ = format.hdrPQ;
if (!egl_textureSetup( if (!egl_textureSetup(
desktop->texture, desktop->texture,
@ -538,6 +542,11 @@ bool egl_desktopRender(EGL_Desktop * desktop, unsigned int outputWidth,
.type = EGL_UNIFORM_TYPE_1F, .type = EGL_UNIFORM_TYPE_1F,
.location = shader->uMapHDRGain, .location = shader->uMapHDRGain,
.f = { mapHDRGain } .f = { mapHDRGain }
},
{
.type = EGL_UNIFORM_TYPE_1I,
.location = shader->uMapHDRPQ,
.f = { desktop->hdrPQ }
} }
}; };

View File

@ -23,6 +23,7 @@ uniform int cbMode;
uniform bool isHDR; uniform bool isHDR;
uniform bool mapHDRtoSDR; uniform bool mapHDRtoSDR;
uniform float mapHDRGain; uniform float mapHDRGain;
uniform bool mapHDRPQ;
void main() void main()
{ {
@ -43,7 +44,7 @@ void main()
} }
if (isHDR && mapHDRtoSDR) if (isHDR && mapHDRtoSDR)
color.rgb = mapToSDR(color.rgb, mapHDRGain); color.rgb = mapToSDR(color.rgb, mapHDRGain, mapHDRPQ);
if (cbMode > 0) if (cbMode > 0)
color = cbTransform(color, cbMode); color = cbTransform(color, cbMode);

View File

@ -40,7 +40,7 @@ float midGain(vec3 pixel)
min(pixel.r, pixel.g)); // min = b min(pixel.r, pixel.g)); // min = b
} }
vec3 compress(vec3 pixel, float gain) vec3 compress(vec3 pixel)
{ {
float maxGain = maxGain(pixel); float maxGain = maxGain(pixel);
return pixel * (maxGain < knee ? maxGain : return pixel * (maxGain < knee ? maxGain :
@ -99,8 +99,10 @@ vec3 bt2020to709(vec3 bt2020)
bt2020.r * -0.0182 + bt2020.g * -0.1006 + bt2020.b * 1.1187); bt2020.r * -0.0182 + bt2020.g * -0.1006 + bt2020.b * 1.1187);
} }
vec3 mapToSDR(vec3 color, float gain) vec3 mapToSDR(vec3 color, float gain, bool pq)
{ {
vec3 lin = bt2020to709(pq2lin(color.rgb, gain)); if (pq)
return lin2srgb(compress(lin, gain)); color = pq2lin(color.rgb, gain);
color = bt2020to709(color);
return lin2srgb(compress(color));
} }

View File

@ -630,6 +630,7 @@ int main_frameThread(void * unused)
lgrFormat.stride = frame->stride; lgrFormat.stride = frame->stride;
lgrFormat.pitch = frame->pitch; lgrFormat.pitch = frame->pitch;
lgrFormat.hdr = frame->flags & FRAME_FLAG_HDR; lgrFormat.hdr = frame->flags & FRAME_FLAG_HDR;
lgrFormat.hdrPQ = frame->flags & FRAME_FLAG_HDR_PQ;
if (frame->flags & FRAME_FLAG_TRUNCATED) if (frame->flags & FRAME_FLAG_TRUNCATED)
{ {

View File

@ -133,10 +133,11 @@ KVMFRCursor;
enum enum
{ {
FRAME_FLAG_BLOCK_SCREENSAVER = 0x1, FRAME_FLAG_BLOCK_SCREENSAVER = 0x1 ,
FRAME_FLAG_REQUEST_ACTIVATION = 0x2, FRAME_FLAG_REQUEST_ACTIVATION = 0x2 ,
FRAME_FLAG_TRUNCATED = 0x4, // ivshmem was too small for the frame FRAME_FLAG_TRUNCATED = 0x4 , // ivshmem was too small for the frame
FRAME_FLAG_HDR = 0x8 // RGBA10 may not be HDR FRAME_FLAG_HDR = 0x8 , // RGBA10 may not be HDR
FRAME_FLAG_HDR_PQ = 0x10 // HDR PQ has been applied to the frame
}; };
typedef uint32_t KVMFRFrameFlags; typedef uint32_t KVMFRFrameFlags;