[Scummvm-git-logs] scummvm master -> 25db76b2b2a28e0c2260289d5411512247981323

sev- noreply at scummvm.org
Wed Apr 24 22:44:35 UTC 2024


This automated email contains information about 3 new commits which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .

Summary:
c18bc24e79 GRAPHICS: Reduce the size of the YUV to RGB tables
eb4359c4a4 GRAPHICS: Further reduce the size of the YUV to RGB tables
25db76b2b2 GRAPHICS: Reuse YUV lookup tables for identical RGB component sizes


Commit: c18bc24e79a66f119980b5455adf43bc311b1baa
    https://github.com/scummvm/scummvm/commit/c18bc24e79a66f119980b5455adf43bc311b1baa
Author: Cameron Cawley (ccawley2011 at gmail.com)
Date: 2024-04-25T00:44:31+02:00

Commit Message:
GRAPHICS: Reduce the size of the YUV to RGB tables

Changed paths:
    graphics/yuv_to_rgb.cpp


diff --git a/graphics/yuv_to_rgb.cpp b/graphics/yuv_to_rgb.cpp
index d68217bce1f..da7eb9a1693 100644
--- a/graphics/yuv_to_rgb.cpp
+++ b/graphics/yuv_to_rgb.cpp
@@ -94,28 +94,27 @@ namespace Graphics {
 class YUVToRGBLookup {
 public:
 	YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode = false);
+	~YUVToRGBLookup();
 
 	Graphics::PixelFormat getFormat() const { return _format; }
 	YUVToRGBManager::LuminanceScale getScale() const { return _scale; }
-	const uint32 *getRGBToPix() const { return _rgbToPix; }
-	const uint32 *getAlphaToPix() const { return _alphaToPix; }
+	const void *getRGBToPix() const { return _rgbToPix; }
+	const void *getAlphaToPix() const { return _alphaToPix; }
 
 private:
 	Graphics::PixelFormat _format;
 	YUVToRGBManager::LuminanceScale _scale;
-	uint32 _rgbToPix[3 * 768]; // 9216 bytes
-	uint32 _alphaToPix[256];   // 958 bytes
+	void *_rgbToPix;
+	void *_alphaToPix;
 };
 
-YUVToRGBLookup::YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode) {
-	_format = format;
-	_scale = scale;
-
+template<typename PixelInt>
+void createTables(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode, PixelInt *rgbToPix, PixelInt *alphaToPix) {
 	int alphaValue = alphaMode ? 0 : 255;
 
-	uint32 *r_2_pix_alloc = &_rgbToPix[0 * 768];
-	uint32 *g_2_pix_alloc = &_rgbToPix[1 * 768];
-	uint32 *b_2_pix_alloc = &_rgbToPix[2 * 768];
+	PixelInt *r_2_pix_alloc = &rgbToPix[0 * 768];
+	PixelInt *g_2_pix_alloc = &rgbToPix[1 * 768];
+	PixelInt *b_2_pix_alloc = &rgbToPix[2 * 768];
 
 	if (scale == YUVToRGBManager::kScaleFull) {
 		// Set up entries 0-255 in rgb-to-pixel value tables.
@@ -159,12 +158,41 @@ YUVToRGBLookup::YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::Lu
 		}
 	}
 
-	// Set up entries 0-255 in alpha-to-pixel value table.
-	for (int i = 0; i < 256; i++) {
-		_alphaToPix[i] = format.ARGBToColor(i, 0, 0, 0);
+	if (alphaMode) {
+		// Set up entries 0-255 in alpha-to-pixel value table.
+		for (int i = 0; i < 256; i++) {
+			alphaToPix[i] = format.ARGBToColor(i, 0, 0, 0);
+		}
 	}
 }
 
+YUVToRGBLookup::YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode) {
+	_format = format;
+	_scale = scale;
+	_rgbToPix = nullptr;
+	_alphaToPix = nullptr;
+
+	_rgbToPix = malloc(format.bytesPerPixel * 3 * 768); // 4608 or 9216 bytes
+	assert(_rgbToPix);
+
+	if (alphaMode) {
+		_alphaToPix = malloc(format.bytesPerPixel * 256);   // 512 or 1024 bytes
+		assert(_alphaToPix);
+	}
+
+	assert(format.bytesPerPixel == 2 || format.bytesPerPixel == 4);
+	if (format.bytesPerPixel == 2)
+		createTables<uint16>(format, scale, alphaMode, (uint16 *)_rgbToPix, (uint16 *)_alphaToPix);
+	else
+		createTables<uint32>(format, scale, alphaMode, (uint32 *)_rgbToPix, (uint32 *)_alphaToPix);
+
+}
+
+YUVToRGBLookup::~YUVToRGBLookup() {
+	free(_rgbToPix);
+	free(_alphaToPix);
+}
+
 YUVToRGBManager::YUVToRGBManager() {
 	_lookup = 0;
 	_alphaMode = false;
@@ -213,11 +241,11 @@ void convertYUV444ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const uint32 *rgbToPix = lookup->getRGBToPix();
+	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
 
 	for (int h = 0; h < yHeight; h++) {
 		for (int w = 0; w < yWidth; w++) {
-			const uint32 *L;
+			const PixelInt *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -261,11 +289,11 @@ void convertYUV422ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const uint32 *rgbToPix = lookup->getRGBToPix();
+	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
 
 	for (int h = 0; h < yHeight; h++) {
 		for (int w = 0; w < halfWidth; w++) {
-			const uint32 *L;
+			const PixelInt *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -314,11 +342,11 @@ void convertYUV420ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const uint32 *rgbToPix = lookup->getRGBToPix();
+	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
 
 	for (int h = 0; h < halfHeight; h++) {
 		for (int w = 0; w < halfWidth; w++) {
-			const uint32 *L;
+			const PixelInt *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -374,12 +402,12 @@ void convertYUVA420ToRGBA(byte *dstPtr, int dstPitch, const YUVToRGBLookup *look
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const uint32 *rgbToPix = lookup->getRGBToPix();
-	const uint32 *aToPix = lookup->getAlphaToPix();
+	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
+	const PixelInt *aToPix = (const PixelInt *)lookup->getAlphaToPix();
 
 	for (int h = 0; h < halfHeight; h++) {
 		for (int w = 0; w < halfWidth; w++) {
-			const uint32 *L;
+			const PixelInt *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -455,7 +483,7 @@ void convertYUV410ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const uint32 *rgbToPix = lookup->getRGBToPix();
+	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
 
 	int quarterWidth = yWidth >> 2;
 
@@ -472,7 +500,7 @@ void convertYUV410ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 			// Declare some variables for the following macros
 			byte u, v;
 			int16 cr_r, crb_g, cb_b;
-			const uint32 *L;
+			const PixelInt *L;
 
 			READ_QUAD(uSrc, u);
 			READ_QUAD(vSrc, v);


Commit: eb4359c4a4df828fb2dc56b6297a829696400cf9
    https://github.com/scummvm/scummvm/commit/eb4359c4a4df828fb2dc56b6297a829696400cf9
Author: Cameron Cawley (ccawley2011 at gmail.com)
Date: 2024-04-25T00:44:31+02:00

Commit Message:
GRAPHICS: Further reduce the size of the YUV to RGB tables

Changed paths:
    graphics/yuv_to_rgb.cpp
    graphics/yuv_to_rgb.h


diff --git a/graphics/yuv_to_rgb.cpp b/graphics/yuv_to_rgb.cpp
index da7eb9a1693..72b14d42da7 100644
--- a/graphics/yuv_to_rgb.cpp
+++ b/graphics/yuv_to_rgb.cpp
@@ -93,35 +93,32 @@ namespace Graphics {
 
 class YUVToRGBLookup {
 public:
-	YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode = false);
-	~YUVToRGBLookup();
+	YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale);
 
 	Graphics::PixelFormat getFormat() const { return _format; }
 	YUVToRGBManager::LuminanceScale getScale() const { return _scale; }
-	const void *getRGBToPix() const { return _rgbToPix; }
-	const void *getAlphaToPix() const { return _alphaToPix; }
+	const byte *getClipTable() const { return _clipTable; }
 
 private:
 	Graphics::PixelFormat _format;
 	YUVToRGBManager::LuminanceScale _scale;
-	void *_rgbToPix;
-	void *_alphaToPix;
+	byte _clipTable[3 * 768];
 };
 
-template<typename PixelInt>
-void createTables(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode, PixelInt *rgbToPix, PixelInt *alphaToPix) {
-	int alphaValue = alphaMode ? 0 : 255;
+YUVToRGBLookup::YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale) {
+	_format = format;
+	_scale = scale;
 
-	PixelInt *r_2_pix_alloc = &rgbToPix[0 * 768];
-	PixelInt *g_2_pix_alloc = &rgbToPix[1 * 768];
-	PixelInt *b_2_pix_alloc = &rgbToPix[2 * 768];
+	byte *r_2_pix_alloc = &_clipTable[0 * 768];
+	byte *g_2_pix_alloc = &_clipTable[1 * 768];
+	byte *b_2_pix_alloc = &_clipTable[2 * 768];
 
 	if (scale == YUVToRGBManager::kScaleFull) {
 		// Set up entries 0-255 in rgb-to-pixel value tables.
 		for (int i = 0; i < 256; i++) {
-			r_2_pix_alloc[i + 256] = format.ARGBToColor(alphaValue, i, 0, 0);
-			g_2_pix_alloc[i + 256] = format.ARGBToColor(alphaValue, 0, i, 0);
-			b_2_pix_alloc[i + 256] = format.ARGBToColor(alphaValue, 0, 0, i);
+			r_2_pix_alloc[i + 256] = i >> format.rLoss;
+			g_2_pix_alloc[i + 256] = i >> format.gLoss;
+			b_2_pix_alloc[i + 256] = i >> format.bLoss;
 		}
 
 		// Spread out the values we have to the rest of the array so that we do
@@ -138,9 +135,9 @@ void createTables(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale
 		// Set up entries 16-235 in rgb-to-pixel value tables
 		for (int i = 16; i < 236; i++) {
 			int scaledValue = (i - 16) * 255 / 219;
-			r_2_pix_alloc[i + 256] = format.ARGBToColor(alphaValue, scaledValue, 0, 0);
-			g_2_pix_alloc[i + 256] = format.ARGBToColor(alphaValue, 0, scaledValue, 0);
-			b_2_pix_alloc[i + 256] = format.ARGBToColor(alphaValue, 0, 0, scaledValue);
+			r_2_pix_alloc[i + 256] = scaledValue >> format.rLoss;
+			g_2_pix_alloc[i + 256] = scaledValue >> format.gLoss;
+			b_2_pix_alloc[i + 256] = scaledValue >> format.bLoss;
 		}
 
 		// Spread out the values we have to the rest of the array so that we do
@@ -157,45 +154,10 @@ void createTables(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale
 			b_2_pix_alloc[i] = b_2_pix_alloc[256 + 236 - 1];
 		}
 	}
-
-	if (alphaMode) {
-		// Set up entries 0-255 in alpha-to-pixel value table.
-		for (int i = 0; i < 256; i++) {
-			alphaToPix[i] = format.ARGBToColor(i, 0, 0, 0);
-		}
-	}
-}
-
-YUVToRGBLookup::YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode) {
-	_format = format;
-	_scale = scale;
-	_rgbToPix = nullptr;
-	_alphaToPix = nullptr;
-
-	_rgbToPix = malloc(format.bytesPerPixel * 3 * 768); // 4608 or 9216 bytes
-	assert(_rgbToPix);
-
-	if (alphaMode) {
-		_alphaToPix = malloc(format.bytesPerPixel * 256);   // 512 or 1024 bytes
-		assert(_alphaToPix);
-	}
-
-	assert(format.bytesPerPixel == 2 || format.bytesPerPixel == 4);
-	if (format.bytesPerPixel == 2)
-		createTables<uint16>(format, scale, alphaMode, (uint16 *)_rgbToPix, (uint16 *)_alphaToPix);
-	else
-		createTables<uint32>(format, scale, alphaMode, (uint32 *)_rgbToPix, (uint32 *)_alphaToPix);
-
-}
-
-YUVToRGBLookup::~YUVToRGBLookup() {
-	free(_rgbToPix);
-	free(_alphaToPix);
 }
 
 YUVToRGBManager::YUVToRGBManager() {
 	_lookup = 0;
-	_alphaMode = false;
 
 	int16 *Cr_r_tab = &_colorTab[0 * 256];
 	int16 *Cr_g_tab = &_colorTab[1 * 256];
@@ -220,19 +182,18 @@ YUVToRGBManager::~YUVToRGBManager() {
 	delete _lookup;
 }
 
-const YUVToRGBLookup *YUVToRGBManager::getLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale, bool alphaMode) {
-	if (_lookup && _lookup->getFormat() == format && _lookup->getScale() == scale && _alphaMode == alphaMode)
+const YUVToRGBLookup *YUVToRGBManager::getLookup(Graphics::PixelFormat format, YUVToRGBManager::LuminanceScale scale) {
+	if (_lookup && _lookup->getFormat() == format && _lookup->getScale() == scale)
 		return _lookup;
 
-	_alphaMode = alphaMode;
 	delete _lookup;
-	_lookup = new YUVToRGBLookup(format, scale, alphaMode);
+	_lookup = new YUVToRGBLookup(format, scale);
 	return _lookup;
 }
 
 #define PUT_PIXEL(s, d) \
-	L = &rgbToPix[(s)]; \
-	*((PixelInt *)(d)) = (L[cr_r] | L[crb_g] | L[cb_b])
+	L = &clipTable[(s)]; \
+	*((PixelInt *)(d)) = ((L[cr_r] << r_shift) | (L[crb_g] << g_shift) | (L[cb_b] << b_shift) | a_mask)
 
 template<typename PixelInt>
 void convertYUV444ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, int16 *colorTab, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
@@ -241,11 +202,16 @@ void convertYUV444ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
+	const byte *clipTable = lookup->getClipTable();
+
+	const byte r_shift = lookup->getFormat().rShift;
+	const byte g_shift = lookup->getFormat().gShift;
+	const byte b_shift = lookup->getFormat().bShift;
+	const PixelInt a_mask = (0xFF >> lookup->getFormat().aLoss) << lookup->getFormat().aShift;
 
 	for (int h = 0; h < yHeight; h++) {
 		for (int w = 0; w < yWidth; w++) {
-			const PixelInt *L;
+			const byte *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -289,11 +255,16 @@ void convertYUV422ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
+	const byte *clipTable = lookup->getClipTable();
+
+	const byte r_shift = lookup->getFormat().rShift;
+	const byte g_shift = lookup->getFormat().gShift;
+	const byte b_shift = lookup->getFormat().bShift;
+	const PixelInt a_mask = (0xFF >> lookup->getFormat().aLoss) << lookup->getFormat().aShift;
 
 	for (int h = 0; h < yHeight; h++) {
 		for (int w = 0; w < halfWidth; w++) {
-			const PixelInt *L;
+			const byte *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -342,11 +313,16 @@ void convertYUV420ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
+	const byte *clipTable = lookup->getClipTable();
+
+	const byte r_shift = lookup->getFormat().rShift;
+	const byte g_shift = lookup->getFormat().gShift;
+	const byte b_shift = lookup->getFormat().bShift;
+	const PixelInt a_mask = (0xFF >> lookup->getFormat().aLoss) << lookup->getFormat().aShift;
 
 	for (int h = 0; h < halfHeight; h++) {
 		for (int w = 0; w < halfWidth; w++) {
-			const PixelInt *L;
+			const byte *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -389,8 +365,8 @@ void YUVToRGBManager::convert420(Graphics::Surface *dst, YUVToRGBManager::Lumina
 }
 
 #define PUT_PIXELA(s, a, d) \
-	L = &rgbToPix[(s)]; \
-	*((PixelInt *)(d)) = (L[cr_r] | L[crb_g] | L[cb_b] | aToPix[a])
+	L = &clipTable[(s)]; \
+	*((PixelInt *)(d)) = ((L[cr_r] << r_shift) | (L[crb_g] << g_shift) | (L[cb_b] << b_shift) | ((a >> a_loss) << a_shift))
 
 template<typename PixelInt>
 void convertYUVA420ToRGBA(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, int16 *colorTab, const byte *ySrc, const byte *uSrc, const byte *vSrc, const byte *aSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
@@ -402,12 +378,17 @@ void convertYUVA420ToRGBA(byte *dstPtr, int dstPitch, const YUVToRGBLookup *look
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
-	const PixelInt *aToPix = (const PixelInt *)lookup->getAlphaToPix();
+	const byte *clipTable = lookup->getClipTable();
+
+	const byte r_shift = lookup->getFormat().rShift;
+	const byte g_shift = lookup->getFormat().gShift;
+	const byte b_shift = lookup->getFormat().bShift;
+	const byte a_shift = lookup->getFormat().aShift;
+	const byte a_loss = lookup->getFormat().aLoss;
 
 	for (int h = 0; h < halfHeight; h++) {
 		for (int w = 0; w < halfWidth; w++) {
-			const PixelInt *L;
+			const byte *L;
 
 			int16 cr_r  = Cr_r_tab[*vSrc];
 			int16 crb_g = Cr_g_tab[*vSrc] + Cb_g_tab[*uSrc];
@@ -443,7 +424,7 @@ void YUVToRGBManager::convert420Alpha(Graphics::Surface *dst, YUVToRGBManager::L
 	assert((yWidth & 1) == 0);
 	assert((yHeight & 1) == 0);
 
-	const YUVToRGBLookup *lookup = getLookup(dst->format, scale, true);
+	const YUVToRGBLookup *lookup = getLookup(dst->format, scale);
 
 	// Use a templated function to avoid an if check on every pixel
 	if (dst->format.bytesPerPixel == 2)
@@ -483,7 +464,12 @@ void convertYUV410ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
-	const PixelInt *rgbToPix = (const PixelInt *)lookup->getRGBToPix();
+	const byte *clipTable = lookup->getClipTable();
+
+	const byte r_shift = lookup->getFormat().rShift;
+	const byte g_shift = lookup->getFormat().gShift;
+	const byte b_shift = lookup->getFormat().bShift;
+	const PixelInt a_mask = (0xFF >> lookup->getFormat().aLoss) << lookup->getFormat().aShift;
 
 	int quarterWidth = yWidth >> 2;
 
@@ -500,7 +486,7 @@ void convertYUV410ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup
 			// Declare some variables for the following macros
 			byte u, v;
 			int16 cr_r, crb_g, cb_b;
-			const PixelInt *L;
+			const byte *L;
 
 			READ_QUAD(uSrc, u);
 			READ_QUAD(vSrc, v);
diff --git a/graphics/yuv_to_rgb.h b/graphics/yuv_to_rgb.h
index c0d28c809ad..4eceb4f065f 100644
--- a/graphics/yuv_to_rgb.h
+++ b/graphics/yuv_to_rgb.h
@@ -140,11 +140,10 @@ private:
 	YUVToRGBManager();
 	~YUVToRGBManager();
 
-	const YUVToRGBLookup *getLookup(Graphics::PixelFormat format, LuminanceScale scale, bool alphaMode = false);
+	const YUVToRGBLookup *getLookup(Graphics::PixelFormat format, LuminanceScale scale);
 
 	YUVToRGBLookup *_lookup;
 	int16 _colorTab[4 * 256]; // 2048 bytes
-	bool _alphaMode;
 };
  /** @} */
 } // End of namespace Graphics


Commit: 25db76b2b2a28e0c2260289d5411512247981323
    https://github.com/scummvm/scummvm/commit/25db76b2b2a28e0c2260289d5411512247981323
Author: Cameron Cawley (ccawley2011 at gmail.com)
Date: 2024-04-25T00:44:31+02:00

Commit Message:
GRAPHICS: Reuse YUV lookup tables for identical RGB component sizes

Changed paths:
    graphics/yuv_to_rgb.cpp
    graphics/yuv_to_rgb.h


diff --git a/graphics/yuv_to_rgb.cpp b/graphics/yuv_to_rgb.cpp
index 72b14d42da7..135a887a25e 100644
--- a/graphics/yuv_to_rgb.cpp
+++ b/graphics/yuv_to_rgb.cpp
@@ -97,11 +97,13 @@ public:
 
 	Graphics::PixelFormat getFormat() const { return _format; }
 	YUVToRGBManager::LuminanceScale getScale() const { return _scale; }
+	const int16 *getColorTable() const { return _colorTab; }
 	const byte *getClipTable() const { return _clipTable; }
 
 private:
 	Graphics::PixelFormat _format;
 	YUVToRGBManager::LuminanceScale _scale;
+	int16 _colorTab[4 * 256]; // 2048 bytes
 	byte _clipTable[3 * 768];
 };
 
@@ -109,9 +111,16 @@ YUVToRGBLookup::YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::Lu
 	_format = format;
 	_scale = scale;
 
-	byte *r_2_pix_alloc = &_clipTable[0 * 768];
-	byte *g_2_pix_alloc = &_clipTable[1 * 768];
-	byte *b_2_pix_alloc = &_clipTable[2 * 768];
+	// Generate the tables for the display surface
+
+	uint r_offset = 0;
+	uint g_offset = (format.gLoss == format.rLoss) ? r_offset : r_offset + 768;
+	uint b_offset = (format.bLoss == format.gLoss) ? g_offset :
+	                (format.bLoss == format.rLoss) ? r_offset : g_offset + 768;
+
+	byte *r_2_pix_alloc = &_clipTable[r_offset];
+	byte *g_2_pix_alloc = &_clipTable[g_offset];
+	byte *b_2_pix_alloc = &_clipTable[b_offset];
 
 	if (scale == YUVToRGBManager::kScaleFull) {
 		// Set up entries 0-255 in rgb-to-pixel value tables.
@@ -154,30 +163,28 @@ YUVToRGBLookup::YUVToRGBLookup(Graphics::PixelFormat format, YUVToRGBManager::Lu
 			b_2_pix_alloc[i] = b_2_pix_alloc[256 + 236 - 1];
 		}
 	}
-}
-
-YUVToRGBManager::YUVToRGBManager() {
-	_lookup = 0;
 
 	int16 *Cr_r_tab = &_colorTab[0 * 256];
 	int16 *Cr_g_tab = &_colorTab[1 * 256];
 	int16 *Cb_g_tab = &_colorTab[2 * 256];
 	int16 *Cb_b_tab = &_colorTab[3 * 256];
 
-	// Generate the tables for the display surface
-
 	for (int i = 0; i < 256; i++) {
 		// Gamma correction (luminescence table) and chroma correction
 		// would be done here. See the Berkeley mpeg_play sources.
 
 		int16 CR = (i - 128), CB = CR;
-		Cr_r_tab[i] = (int16) ( (0.419 / 0.299) * CR) + 0 * 768 + 256;
-		Cr_g_tab[i] = (int16) (-(0.299 / 0.419) * CR) + 1 * 768 + 256;
+		Cr_r_tab[i] = (int16) ( (0.419 / 0.299) * CR) + r_offset + 256;
+		Cr_g_tab[i] = (int16) (-(0.299 / 0.419) * CR) + g_offset + 256;
 		Cb_g_tab[i] = (int16) (-(0.114 / 0.331) * CB);
-		Cb_b_tab[i] = (int16) ( (0.587 / 0.331) * CB) + 2 * 768 + 256;
+		Cb_b_tab[i] = (int16) ( (0.587 / 0.331) * CB) + b_offset + 256;
 	}
 }
 
+YUVToRGBManager::YUVToRGBManager() {
+	_lookup = 0;
+}
+
 YUVToRGBManager::~YUVToRGBManager() {
 	delete _lookup;
 }
@@ -196,9 +203,9 @@ const YUVToRGBLookup *YUVToRGBManager::getLookup(Graphics::PixelFormat format, Y
 	*((PixelInt *)(d)) = ((L[cr_r] << r_shift) | (L[crb_g] << g_shift) | (L[cb_b] << b_shift) | a_mask)
 
 template<typename PixelInt>
-void convertYUV444ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, int16 *colorTab, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
+void convertYUV444ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
 	// Keep the tables in pointers here to avoid a dereference on each pixel
-	const int16 *Cr_r_tab = colorTab;
+	const int16 *Cr_r_tab = lookup->getColorTable();
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
@@ -241,17 +248,17 @@ void YUVToRGBManager::convert444(Graphics::Surface *dst, YUVToRGBManager::Lumina
 
 	// Use a templated function to avoid an if check on every pixel
 	if (dst->format.bytesPerPixel == 2)
-		convertYUV444ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV444ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 	else
-		convertYUV444ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV444ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 }
 
 template<typename PixelInt>
-void convertYUV422ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, int16 *colorTab, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
+void convertYUV422ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
 	int halfWidth = yWidth >> 1;
 
 	// Keep the tables in pointers here to avoid a dereference on each pixel
-	const int16 *Cr_r_tab = colorTab;
+	const int16 *Cr_r_tab = lookup->getColorTable();
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
@@ -298,18 +305,18 @@ void YUVToRGBManager::convert422(Graphics::Surface *dst, YUVToRGBManager::Lumina
 
 	// Use a templated function to avoid an if check on every pixel
 	if (dst->format.bytesPerPixel == 2)
-		convertYUV422ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV422ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 	else
-		convertYUV422ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV422ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 }
 
 template<typename PixelInt>
-void convertYUV420ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, int16 *colorTab, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
+void convertYUV420ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
 	int halfHeight = yHeight >> 1;
 	int halfWidth = yWidth >> 1;
 
 	// Keep the tables in pointers here to avoid a dereference on each pixel
-	const int16 *Cr_r_tab = colorTab;
+	const int16 *Cr_r_tab = lookup->getColorTable();
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
@@ -359,9 +366,9 @@ void YUVToRGBManager::convert420(Graphics::Surface *dst, YUVToRGBManager::Lumina
 
 	// Use a templated function to avoid an if check on every pixel
 	if (dst->format.bytesPerPixel == 2)
-		convertYUV420ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV420ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 	else
-		convertYUV420ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV420ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 }
 
 #define PUT_PIXELA(s, a, d) \
@@ -369,12 +376,12 @@ void YUVToRGBManager::convert420(Graphics::Surface *dst, YUVToRGBManager::Lumina
 	*((PixelInt *)(d)) = ((L[cr_r] << r_shift) | (L[crb_g] << g_shift) | (L[cb_b] << b_shift) | ((a >> a_loss) << a_shift))
 
 template<typename PixelInt>
-void convertYUVA420ToRGBA(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, int16 *colorTab, const byte *ySrc, const byte *uSrc, const byte *vSrc, const byte *aSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
+void convertYUVA420ToRGBA(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, const byte *ySrc, const byte *uSrc, const byte *vSrc, const byte *aSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
 	int halfHeight = yHeight >> 1;
 	int halfWidth = yWidth >> 1;
 
 	// Keep the tables in pointers here to avoid a dereference on each pixel
-	const int16 *Cr_r_tab = colorTab;
+	const int16 *Cr_r_tab = lookup->getColorTable();
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
@@ -428,9 +435,9 @@ void YUVToRGBManager::convert420Alpha(Graphics::Surface *dst, YUVToRGBManager::L
 
 	// Use a templated function to avoid an if check on every pixel
 	if (dst->format.bytesPerPixel == 2)
-		convertYUVA420ToRGBA<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, aSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUVA420ToRGBA<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, aSrc, yWidth, yHeight, yPitch, uvPitch);
 	else
-		convertYUVA420ToRGBA<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, aSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUVA420ToRGBA<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, aSrc, yWidth, yHeight, yPitch, uvPitch);
 }
 
 #define READ_QUAD(ptr, prefix) \
@@ -458,9 +465,9 @@ void YUVToRGBManager::convert420Alpha(Graphics::Surface *dst, YUVToRGBManager::L
 	xDiff++
 
 template<typename PixelInt>
-void convertYUV410ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, int16 *colorTab, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
+void convertYUV410ToRGB(byte *dstPtr, int dstPitch, const YUVToRGBLookup *lookup, const byte *ySrc, const byte *uSrc, const byte *vSrc, int yWidth, int yHeight, int yPitch, int uvPitch) {
 	// Keep the tables in pointers here to avoid a dereference on each pixel
-	const int16 *Cr_r_tab = colorTab;
+	const int16 *Cr_r_tab = lookup->getColorTable();
 	const int16 *Cr_g_tab = Cr_r_tab + 256;
 	const int16 *Cb_g_tab = Cr_g_tab + 256;
 	const int16 *Cb_b_tab = Cb_g_tab + 256;
@@ -518,9 +525,9 @@ void YUVToRGBManager::convert410(Graphics::Surface *dst, YUVToRGBManager::Lumina
 
 	// Use a templated function to avoid an if check on every pixel
 	if (dst->format.bytesPerPixel == 2)
-		convertYUV410ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV410ToRGB<uint16>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 	else
-		convertYUV410ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, _colorTab, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
+		convertYUV410ToRGB<uint32>((byte *)dst->getPixels(), dst->pitch, lookup, ySrc, uSrc, vSrc, yWidth, yHeight, yPitch, uvPitch);
 }
 
 } // End of namespace Graphics
diff --git a/graphics/yuv_to_rgb.h b/graphics/yuv_to_rgb.h
index 4eceb4f065f..2d2e015341d 100644
--- a/graphics/yuv_to_rgb.h
+++ b/graphics/yuv_to_rgb.h
@@ -143,7 +143,6 @@ private:
 	const YUVToRGBLookup *getLookup(Graphics::PixelFormat format, LuminanceScale scale);
 
 	YUVToRGBLookup *_lookup;
-	int16 _colorTab[4 * 256]; // 2048 bytes
 };
  /** @} */
 } // End of namespace Graphics




More information about the Scummvm-git-logs mailing list