Ignore alpha channel during color conversion.

Most GFX graphics do not carry alpha data. Keep the original
alpha value unless specified otherwise.

(cherry picked from commit 115532ef5a71676a946c9d268dd1294daf99e52d)
This commit is contained in:
akallabeth 2021-01-12 09:41:09 +01:00 committed by akallabeth
parent e45621fed6
commit 9eeb64ed9f
6 changed files with 118 additions and 27 deletions

View File

@ -809,6 +809,27 @@ extern "C"
return TRUE;
}
static INLINE BOOL WriteColorIgnoreAlpha(BYTE* dst, UINT32 format, UINT32 color)
{
switch (format)
{
case PIXEL_FORMAT_ABGR32:
case PIXEL_FORMAT_ARGB32:
{
const UINT32 tmp = (dst[0] << 24) | (color & 0x00FFFFFF);
return WriteColor(dst, format, tmp);
}
case PIXEL_FORMAT_BGRA32:
case PIXEL_FORMAT_RGBA32:
{
const UINT32 tmp = (dst[3]) | (color & 0xFFFFFF00);
return WriteColor(dst, format, tmp);
}
default:
return WriteColor(dst, format, color);
}
}
/***
*
* Converts a pixel in internal representation format srcFormat to internal

View File

@ -37,7 +37,7 @@ static pstatus_t general_YCoCgToRGB_8u_AC4R(const BYTE* pSrc, INT32 srcStep, BYT
const BYTE* sptr = pSrc;
INT16 Cg, Co, Y, T, R, G, B;
const DWORD formatSize = GetBytesPerPixel(DstFormat);
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat);
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat, TRUE);
int cll = shift - 1; /* -1 builds in the /2's */
UINT32 srcPad = srcStep - (width * 4);
UINT32 dstPad = dstStep - (width * formatSize);
@ -59,7 +59,7 @@ static pstatus_t general_YCoCgToRGB_8u_AC4R(const BYTE* pSrc, INT32 srcStep, BYT
B = T + Co;
G = Y + Cg;
R = T - Co;
dptr = (*writePixel)(dptr, formatSize, DstFormat, CLIP(R), CLIP(G), CLIP(B), A);
dptr = writePixel(dptr, formatSize, DstFormat, CLIP(R), CLIP(G), CLIP(B), A);
}
sptr += srcPad;

View File

@ -385,7 +385,7 @@ static pstatus_t general_YUV444ToRGB_8u_P3AC4R_general(const BYTE* const pSrc[3]
UINT32 x, y;
UINT32 nWidth, nHeight;
const DWORD formatSize = GetBytesPerPixel(DstFormat);
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat);
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat, FALSE);
nWidth = roi->width;
nHeight = roi->height;
@ -404,7 +404,7 @@ static pstatus_t general_YUV444ToRGB_8u_P3AC4R_general(const BYTE* const pSrc[3]
const BYTE r = YUV2R(Y, U, V);
const BYTE g = YUV2G(Y, U, V);
const BYTE b = YUV2B(Y, U, V);
pRGB = (*writePixel)(pRGB, formatSize, DstFormat, r, g, b, 0xFF);
pRGB = writePixel(pRGB, formatSize, DstFormat, r, g, b, 0);
}
}
@ -437,7 +437,7 @@ static pstatus_t general_YUV444ToRGB_8u_P3AC4R_BGRX(const BYTE* const pSrc[3],
const BYTE r = YUV2R(Y, U, V);
const BYTE g = YUV2G(Y, U, V);
const BYTE b = YUV2B(Y, U, V);
pRGB = writePixelBGRX(pRGB, formatSize, DstFormat, r, g, b, 0xFF);
pRGB = writePixelBGRX(pRGB, formatSize, DstFormat, r, g, b, 0);
}
}
@ -481,7 +481,7 @@ static pstatus_t general_YUV420ToRGB_8u_P3AC4R(const BYTE* const pSrc[3], const
UINT32 nWidth, nHeight;
UINT32 lastRow, lastCol;
const DWORD formatSize = GetBytesPerPixel(DstFormat);
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat);
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat, FALSE);
pY = pSrc[0];
pU = pSrc[1];
pV = pSrc[2];
@ -517,7 +517,7 @@ static pstatus_t general_YUV420ToRGB_8u_P3AC4R(const BYTE* const pSrc[3], const
r = YUV2R(Y, U, V);
g = YUV2G(Y, U, V);
b = YUV2B(Y, U, V);
pRGB = (*writePixel)(pRGB, formatSize, DstFormat, r, g, b, 0xFF);
pRGB = writePixel(pRGB, formatSize, DstFormat, r, g, b, 0);
/* 2nd pixel */
if (!(lastCol & 0x02))
@ -526,7 +526,7 @@ static pstatus_t general_YUV420ToRGB_8u_P3AC4R(const BYTE* const pSrc[3], const
r = YUV2R(Y, U, V);
g = YUV2G(Y, U, V);
b = YUV2B(Y, U, V);
pRGB = (*writePixel)(pRGB, formatSize, DstFormat, r, g, b, 0xFF);
pRGB = writePixel(pRGB, formatSize, DstFormat, r, g, b, 0);
}
else
{
@ -560,7 +560,7 @@ static pstatus_t general_YUV420ToRGB_8u_P3AC4R(const BYTE* const pSrc[3], const
r = YUV2R(Y, U, V);
g = YUV2G(Y, U, V);
b = YUV2B(Y, U, V);
pRGB = (*writePixel)(pRGB, formatSize, DstFormat, r, g, b, 0xFF);
pRGB = writePixel(pRGB, formatSize, DstFormat, r, g, b, 0);
/* 4th pixel */
if (!(lastCol & 0x02))
@ -569,7 +569,7 @@ static pstatus_t general_YUV420ToRGB_8u_P3AC4R(const BYTE* const pSrc[3], const
r = YUV2R(Y, U, V);
g = YUV2G(Y, U, V);
b = YUV2B(Y, U, V);
pRGB = (*writePixel)(pRGB, formatSize, DstFormat, r, g, b, 0xFF);
pRGB = writePixel(pRGB, formatSize, DstFormat, r, g, b, 0);
}
else
{

View File

@ -191,7 +191,7 @@ static pstatus_t ssse3_YUV420ToRGB_BGRX(const BYTE* const* pSrc, const UINT32* s
const BYTE r = YUV2R(Y, U, V);
const BYTE g = YUV2G(Y, U, V);
const BYTE b = YUV2B(Y, U, V);
dst = (__m128i*)writePixelBGRX((BYTE*)dst, 4, PIXEL_FORMAT_BGRX32, r, g, b, 0xFF);
dst = (__m128i*)writePixelBGRX((BYTE*)dst, 4, PIXEL_FORMAT_BGRX32, r, g, b, 0);
if (x % 2)
{
@ -257,7 +257,7 @@ static pstatus_t ssse3_YUV444ToRGB_8u_P3AC4R_BGRX(const BYTE* const* pSrc, const
const BYTE r = YUV2R(Y, U, V);
const BYTE g = YUV2G(Y, U, V);
const BYTE b = YUV2B(Y, U, V);
dst = (__m128i*)writePixelBGRX((BYTE*)dst, 4, PIXEL_FORMAT_BGRX32, r, g, b, 0xFF);
dst = (__m128i*)writePixelBGRX((BYTE*)dst, 4, PIXEL_FORMAT_BGRX32, r, g, b, 0);
}
}

View File

@ -60,7 +60,7 @@ static pstatus_t general_yCbCrToRGB_16s8u_P3AC4R_BGRX(const INT16* const pSrc[3]
R = ((INT16)((CrR + Y) >> divisor) >> 5);
G = ((INT16)((Y - CbG - CrG) >> divisor) >> 5);
B = ((INT16)((CbB + Y) >> divisor) >> 5);
pRGB = writePixelBGRX(pRGB, formatSize, DstFormat, CLIP(R), CLIP(G), CLIP(B), 0xFF);
pRGB = writePixelBGRX(pRGB, formatSize, DstFormat, CLIP(R), CLIP(G), CLIP(B), 0);
}
pY += srcPad;
@ -83,7 +83,7 @@ static pstatus_t general_yCbCrToRGB_16s8u_P3AC4R_general(const INT16* const pSrc
const INT16* pCr = pSrc[2];
const size_t srcPad = (srcStep - (roi->width * 2)) / 2;
const size_t dstPad = (dstStep - (roi->width * 4));
const fkt_writePixel writePixel = getPixelWriteFunction(DstFormat);
const fkt_writePixel writePixel = getPixelWriteFunction(DstFormat, FALSE);
const DWORD formatSize = GetBytesPerPixel(DstFormat);
for (y = 0; y < roi->height; y++)
@ -102,7 +102,7 @@ static pstatus_t general_yCbCrToRGB_16s8u_P3AC4R_general(const INT16* const pSrc
R = (INT64)((CrR + Y) >> (divisor + 5));
G = (INT64)((Y - CbG - CrG) >> (divisor + 5));
B = (INT64)((CbB + Y) >> (divisor + 5));
pRGB = (*writePixel)(pRGB, formatSize, DstFormat, CLIP(R), CLIP(G), CLIP(B), 0xFF);
pRGB = writePixel(pRGB, formatSize, DstFormat, CLIP(R), CLIP(G), CLIP(B), 0);
}
pY += srcPad;
@ -283,10 +283,10 @@ static INLINE void writeScanlineGeneric(BYTE* dst, DWORD formatSize, UINT32 DstF
const INT16* r, const INT16* g, const INT16* b, DWORD width)
{
DWORD x;
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat);
fkt_writePixel writePixel = getPixelWriteFunction(DstFormat, FALSE);
for (x = 0; x < width; x++)
dst = (*writePixel)(dst, formatSize, DstFormat, *r++, *g++, *b++, 0xFF);
dst = writePixel(dst, formatSize, DstFormat, *r++, *g++, *b++, 0);
}
static INLINE void writeScanlineRGB(BYTE* dst, DWORD formatSize, UINT32 DstFormat, const INT16* r,

View File

@ -47,14 +47,43 @@
: _mm_load_si128((__m128i*)(_ptr_)))
#endif
static INLINE BYTE* writePixelBGRA(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
*dst++ = B;
*dst++ = G;
*dst++ = R;
*dst++ = A;
return dst;
}
static INLINE BYTE* writePixelBGRX(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
WINPR_UNUSED(A);
*dst++ = B;
*dst++ = G;
*dst++ = R;
dst++; /* Do not touch alpha */
return dst;
}
static INLINE BYTE* writePixelRGBA(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
*dst++ = R;
*dst++ = G;
*dst++ = B;
*dst++ = A;
return dst;
}
@ -64,10 +93,26 @@ static INLINE BYTE* writePixelRGBX(BYTE* dst, DWORD formatSize, UINT32 format, B
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
WINPR_UNUSED(A);
*dst++ = R;
*dst++ = G;
*dst++ = B;
dst++; /* Do not touch alpha */
return dst;
}
static INLINE BYTE* writePixelABGR(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
*dst++ = A;
*dst++ = B;
*dst++ = G;
*dst++ = R;
return dst;
}
@ -76,57 +121,82 @@ static INLINE BYTE* writePixelXBGR(BYTE* dst, DWORD formatSize, UINT32 format, B
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
*dst++ = A;
WINPR_UNUSED(A);
dst++; /* Do not touch alpha */
*dst++ = B;
*dst++ = G;
*dst++ = R;
return dst;
}
static INLINE BYTE* writePixelARGB(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
*dst++ = A;
*dst++ = R;
*dst++ = G;
*dst++ = B;
return dst;
}
static INLINE BYTE* writePixelXRGB(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
{
WINPR_UNUSED(formatSize);
WINPR_UNUSED(format);
*dst++ = A;
WINPR_UNUSED(A);
dst++; /* Do not touch alpha */
*dst++ = R;
*dst++ = G;
*dst++ = B;
return dst;
}
static INLINE BYTE* writePixelGeneric(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
static INLINE BYTE* writePixelGenericAlpha(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R,
BYTE G, BYTE B, BYTE A)
{
UINT32 color = FreeRDPGetColor(format, R, G, B, A);
WriteColor(dst, format, color);
return dst + formatSize;
}
static INLINE BYTE* writePixelGeneric(BYTE* dst, DWORD formatSize, UINT32 format, BYTE R, BYTE G,
BYTE B, BYTE A)
{
UINT32 color = FreeRDPGetColor(format, R, G, B, A);
WriteColorIgnoreAlpha(dst, format, color);
return dst + formatSize;
}
typedef BYTE* (*fkt_writePixel)(BYTE*, DWORD, UINT32, BYTE, BYTE, BYTE, BYTE);
static INLINE fkt_writePixel getPixelWriteFunction(DWORD format)
static INLINE fkt_writePixel getPixelWriteFunction(DWORD format, BOOL useAlpha)
{
switch (format)
{
case PIXEL_FORMAT_ARGB32:
case PIXEL_FORMAT_XRGB32:
return writePixelXRGB;
return useAlpha ? writePixelARGB : writePixelXRGB;
case PIXEL_FORMAT_ABGR32:
case PIXEL_FORMAT_XBGR32:
return writePixelXBGR;
return useAlpha ? writePixelABGR : writePixelXBGR;
case PIXEL_FORMAT_RGBA32:
case PIXEL_FORMAT_RGBX32:
return writePixelRGBX;
return useAlpha ? writePixelRGBA : writePixelRGBX;
case PIXEL_FORMAT_BGRA32:
case PIXEL_FORMAT_BGRX32:
return writePixelBGRX;
return useAlpha ? writePixelBGRA : writePixelBGRX;
default:
return writePixelGeneric;
return useAlpha ? writePixelGenericAlpha : writePixelGeneric;
}
}