- Implementing RGB666 colormatching to replace less precise RGB555 in some parts of the code.

This commit is contained in:
Rachael Alexanderson 2016-12-17 04:11:52 -05:00
parent f6b0f2648c
commit 821b10a254
18 changed files with 366 additions and 625 deletions

View file

@ -28,6 +28,7 @@
#include "f_wipe.h"
#include "c_cvars.h"
#include "templates.h"
#include "v_palette.h"
//
// SCREEN WIPE PACKAGE
@ -299,12 +300,15 @@ bool wipe_doBurn (int ticks)
else
{
int bglevel = 64-fglevel;
DWORD *fg2rgb = Col2RGB8[fglevel];
DWORD *bg2rgb = Col2RGB8[bglevel];
DWORD fg = fg2rgb[fromnew[x]];
DWORD bg = bg2rgb[fromold[x]];
fg = (fg+bg) | 0x1f07c1f;
to[x] = RGB32k.All[fg & (fg>>15)];
const PalEntry* pal = GPalette.BaseColors;
DWORD fg = fromnew[x];
DWORD bg = fromold[x];
int r = MIN((pal[fg].r * fglevel + pal[bg].r * bglevel) >> 8, 63);
int g = MIN((pal[fg].g * fglevel + pal[bg].g * bglevel) >> 8, 63);
int b = MIN((pal[fg].b * fglevel + pal[bg].b * bglevel) >> 8, 63);
to[x] = RGB256k.RGB[r][g][b];
done = false;
}
}
@ -342,20 +346,21 @@ bool wipe_doFade (int ticks)
{
int x, y;
int bglevel = 64 - fade;
DWORD *fg2rgb = Col2RGB8[fade];
DWORD *bg2rgb = Col2RGB8[bglevel];
BYTE *fromnew = (BYTE *)wipe_scr_end;
BYTE *fromold = (BYTE *)wipe_scr_start;
BYTE *to = screen->GetBuffer();
const PalEntry *pal = GPalette.BaseColors;
for (y = 0; y < SCREENHEIGHT; y++)
{
for (x = 0; x < SCREENWIDTH; x++)
{
DWORD fg = fg2rgb[fromnew[x]];
DWORD bg = bg2rgb[fromold[x]];
fg = (fg+bg) | 0x1f07c1f;
to[x] = RGB32k.All[fg & (fg>>15)];
DWORD fg = fromnew[x];
DWORD bg = fromold[x];
int r = MIN((pal[fg].r * (64-bglevel) + pal[bg].r * bglevel) >> 8, 63);
int g = MIN((pal[fg].g * (64-bglevel) + pal[bg].g * bglevel) >> 8, 63);
int b = MIN((pal[fg].b * (64-bglevel) + pal[bg].b * bglevel) >> 8, 63);
to[x] = RGB256k.RGB[r][g][b];
}
fromnew += SCREENWIDTH;
fromold += SCREENWIDTH;

View file

@ -238,22 +238,16 @@ namespace swrenderer
}
if (flags & STYLEF_InvertSource)
{
dc_srcblend = Col2RGB8_Inverse[fglevel >> 10];
dc_destblend = Col2RGB8_LessPrecision[bglevel >> 10];
dc_srcalpha = fglevel;
dc_destalpha = bglevel;
}
else if (op == STYLEOP_Add && fglevel + bglevel <= FRACUNIT)
{
dc_srcblend = Col2RGB8[fglevel >> 10];
dc_destblend = Col2RGB8[bglevel >> 10];
dc_srcalpha = fglevel;
dc_destalpha = bglevel;
}
else
{
dc_srcblend = Col2RGB8_LessPrecision[fglevel >> 10];
dc_destblend = Col2RGB8_LessPrecision[bglevel >> 10];
dc_srcalpha = fglevel;
dc_destalpha = bglevel;
}
@ -450,7 +444,7 @@ namespace swrenderer
uint32_t g = GPART(color);
uint32_t b = BPART(color);
// dc_color is used by the rt_* routines. It is indexed into dc_srcblend.
dc_color = RGB32k.RGB[r >> 3][g >> 3][b >> 3];
dc_color = RGB256k.RGB[r >> 2][g >> 2][b >> 2];
if (style.Flags & STYLEF_InvertSource)
{
r = 255 - r;
@ -1362,8 +1356,4 @@ namespace swrenderer
}
}
void R_DrawParticle(vissprite_t *sprite)
{
R_DrawParticle_C(sprite);
}
}

View file

@ -203,5 +203,4 @@ namespace swrenderer
void R_MapTiltedPlane(int y, int x1);
void R_MapColoredPlane(int y, int x1);
void R_DrawParticle(vissprite_t *);
}

View file

@ -4,6 +4,7 @@
**---------------------------------------------------------------------------
** Copyright 1998-2016 Randy Heit
** Copyright 2016 Magnus Norddahl
** Copyright 2016 Rachael Alexanderson
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
@ -314,10 +315,10 @@ namespace swrenderer
uint8_t pix = source[frac >> bits];
if (pix != 0)
{
uint32_t fg = fg2rgb[colormap[pix]];
uint32_t bg = bg2rgb[*dest];
fg = (fg + bg) | 0x1f07c1f;
*dest = RGB32k.All[fg & (fg >> 15)];
uint32_t r = MIN(GPalette.BaseColors[colormap[pix]].r + GPalette.BaseColors[*dest].r, 255);
uint32_t g = MIN(GPalette.BaseColors[colormap[pix]].g + GPalette.BaseColors[*dest].g, 255);
uint32_t b = MIN(GPalette.BaseColors[colormap[pix]].b + GPalette.BaseColors[*dest].b, 255);
*dest = RGB256k.RGB[r>>2][g>>2][b>>2];
}
frac += fracstep;
dest += pitch;
@ -357,10 +358,10 @@ namespace swrenderer
uint8_t pix = _bufplce[i][vplce[i] >> bits];
if (pix != 0)
{
uint32_t fg = fg2rgb[_palookupoffse[i][pix]];
uint32_t bg = bg2rgb[dest[i]];
fg = (fg + bg) | 0x1f07c1f;
dest[i] = RGB32k.All[fg & (fg >> 15)];
uint32_t r = MIN(GPalette.BaseColors[_palookupoffse[i][pix]].r + GPalette.BaseColors[dest[i]].r, 255);
uint32_t g = MIN(GPalette.BaseColors[_palookupoffse[i][pix]].g + GPalette.BaseColors[dest[i]].g, 255);
uint32_t b = MIN(GPalette.BaseColors[_palookupoffse[i][pix]].b + GPalette.BaseColors[dest[i]].b, 255);
dest[i] = RGB256k.RGB[r>>2][g>>2][b>>2];
}
vplce[i] += vince[i];
}
@ -396,15 +397,10 @@ namespace swrenderer
uint8_t pix = source[frac >> bits];
if (pix != 0)
{
uint32_t a = fg2rgb[colormap[pix]] + bg2rgb[*dest];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest = RGB32k.All[a & (a >> 15)];
uint32_t r = MIN(GPalette.BaseColors[colormap[pix]].r + GPalette.BaseColors[*dest].r, 255);
uint32_t g = MIN(GPalette.BaseColors[colormap[pix]].g + GPalette.BaseColors[*dest].g, 255);
uint32_t b = MIN(GPalette.BaseColors[colormap[pix]].b + GPalette.BaseColors[*dest].b, 255);
*dest = RGB256k.RGB[r>>2][g>>2][b>>2];
}
frac += fracstep;
dest += pitch;
@ -444,15 +440,10 @@ namespace swrenderer
uint8_t pix = _bufplce[i][vplce[i] >> bits];
if (pix != 0)
{
uint32_t a = fg2rgb[_palookupoffse[i][pix]] + bg2rgb[dest[i]];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
dest[i] = RGB32k.All[a & (a >> 15)];
uint32_t r = MIN(GPalette.BaseColors[_palookupoffse[i][pix]].r + GPalette.BaseColors[dest[i]].r, 255);
uint32_t g = MIN(GPalette.BaseColors[_palookupoffse[i][pix]].g + GPalette.BaseColors[dest[i]].g, 255);
uint32_t b = MIN(GPalette.BaseColors[_palookupoffse[i][pix]].b + GPalette.BaseColors[dest[i]].b, 255);
dest[i] = RGB256k.RGB[r>>2][g>>2][b>>2];
}
vplce[i] += vince[i];
}
@ -488,14 +479,10 @@ namespace swrenderer
uint8_t pix = source[frac >> bits];
if (pix != 0)
{
uint32_t a = (fg2rgb[colormap[pix]] | 0x40100400) - bg2rgb[*dest];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[a & (a >> 15)];
int r = clamp(-GPalette.BaseColors[colormap[pix]].r + GPalette.BaseColors[*dest].r, 0, 255);
int g = clamp(-GPalette.BaseColors[colormap[pix]].g + GPalette.BaseColors[*dest].g, 0, 255);
int b = clamp(-GPalette.BaseColors[colormap[pix]].b + GPalette.BaseColors[*dest].b, 0, 255);
*dest = RGB256k.RGB[r>>2][g>>2][b>>2];
}
frac += fracstep;
dest += pitch;
@ -535,14 +522,10 @@ namespace swrenderer
uint8_t pix = _bufplce[i][vplce[i] >> bits];
if (pix != 0)
{
uint32_t a = (fg2rgb[_palookupoffse[i][pix]] | 0x40100400) - bg2rgb[dest[i]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[i] = RGB32k.All[a & (a >> 15)];
int r = clamp(-GPalette.BaseColors[_palookupoffse[i][pix]].r + GPalette.BaseColors[dest[i]].r, 0, 255);
int g = clamp(-GPalette.BaseColors[_palookupoffse[i][pix]].g + GPalette.BaseColors[dest[i]].g, 0, 255);
int b = clamp(-GPalette.BaseColors[_palookupoffse[i][pix]].b + GPalette.BaseColors[dest[i]].b, 0, 255);
dest[i] = RGB256k.RGB[r>>2][g>>2][b>>2];
}
vplce[i] += vince[i];
}
@ -578,14 +561,10 @@ namespace swrenderer
uint8_t pix = source[frac >> bits];
if (pix != 0)
{
uint32_t a = (bg2rgb[*dest] | 0x40100400) - fg2rgb[colormap[pix]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[a & (a >> 15)];
int r = clamp(GPalette.BaseColors[colormap[pix]].r - GPalette.BaseColors[*dest].r, 0, 255);
int g = clamp(GPalette.BaseColors[colormap[pix]].g - GPalette.BaseColors[*dest].g, 0, 255);
int b = clamp(GPalette.BaseColors[colormap[pix]].b - GPalette.BaseColors[*dest].b, 0, 255);
*dest = RGB256k.RGB[r>>2][g>>2][b>>2];
}
frac += fracstep;
dest += pitch;
@ -625,14 +604,10 @@ namespace swrenderer
uint8_t pix = _bufplce[i][vplce[i] >> bits];
if (pix != 0)
{
uint32_t a = (bg2rgb[dest[i]] | 0x40100400) - fg2rgb[_palookupoffse[i][pix]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[i] = RGB32k.All[a & (a >> 15)];
uint32_t r = clamp(GPalette.BaseColors[_palookupoffse[i][pix]].r - GPalette.BaseColors[dest[i]].r, 0, 255);
uint32_t g = clamp(GPalette.BaseColors[_palookupoffse[i][pix]].g - GPalette.BaseColors[dest[i]].g, 0, 255);
uint32_t b = clamp(GPalette.BaseColors[_palookupoffse[i][pix]].b - GPalette.BaseColors[dest[i]].b, 0, 255);
dest[i] = RGB256k.RGB[r>>2][g>>2][b>>2];
}
vplce[i] += vince[i];
}
@ -716,7 +691,7 @@ namespace swrenderer
c_red = (c_red * alpha_bottom + solid_bottom_r * inv_alpha_bottom) >> 8;
c_green = (c_green * alpha_bottom + solid_bottom_g * inv_alpha_bottom) >> 8;
c_blue = (c_blue * alpha_bottom + solid_bottom_b * inv_alpha_bottom) >> 8;
*dest = RGB32k.RGB[(c_red >> 3)][(c_green >> 3)][(c_blue >> 3)];
*dest = RGB256k.RGB[(c_red >> 2)][(c_green >> 2)][(c_blue >> 2)];
}
frac += fracstep;
@ -744,8 +719,8 @@ namespace swrenderer
int solid_bottom_r = RPART(solid_bottom);
int solid_bottom_g = GPART(solid_bottom);
int solid_bottom_b = BPART(solid_bottom);
uint32_t solid_top_fill = RGB32k.RGB[(solid_top_r >> 3)][(solid_top_g >> 3)][(solid_top_b >> 3)];
uint32_t solid_bottom_fill = RGB32k.RGB[(solid_bottom_r >> 3)][(solid_bottom_g >> 3)][(solid_bottom_b >> 3)];
uint32_t solid_top_fill = RGB256k.RGB[(solid_top_r >> 2)][(solid_top_g >> 2)][(solid_top_b >> 2)];
uint32_t solid_bottom_fill = RGB256k.RGB[(solid_bottom_r >> 2)][(solid_bottom_g >> 2)][(solid_bottom_b >> 2)];
solid_top_fill = (solid_top_fill << 24) | (solid_top_fill << 16) | (solid_top_fill << 8) | solid_top_fill;
solid_bottom_fill = (solid_bottom_fill << 24) | (solid_bottom_fill << 16) | (solid_bottom_fill << 8) | solid_bottom_fill;
@ -805,8 +780,7 @@ namespace swrenderer
c_red = (c_red * alpha_top + solid_top_r * inv_alpha_top) >> 8;
c_green = (c_green * alpha_top + solid_top_g * inv_alpha_top) >> 8;
c_blue = (c_blue * alpha_top + solid_top_b * inv_alpha_top) >> 8;
output[col] = RGB32k.RGB[(c_red >> 3)][(c_green >> 3)][(c_blue >> 3)];
output[col] = RGB256k.RGB[(c_red >> 2)][(c_green >> 2)][(c_blue >> 2)];
frac[col] += fracstep[col];
}
*((uint32_t*)dest) = *((uint32_t*)output);
@ -847,7 +821,7 @@ namespace swrenderer
c_red = (c_red * alpha_bottom + solid_bottom_r * inv_alpha_bottom) >> 8;
c_green = (c_green * alpha_bottom + solid_bottom_g * inv_alpha_bottom) >> 8;
c_blue = (c_blue * alpha_bottom + solid_bottom_b * inv_alpha_bottom) >> 8;
output[col] = RGB32k.RGB[(c_red >> 3)][(c_green >> 3)][(c_blue >> 3)];
output[col] = RGB256k.RGB[(c_red >> 2)][(c_green >> 2)][(c_blue >> 2)];
frac[col] += fracstep[col];
}
@ -929,7 +903,7 @@ namespace swrenderer
c_red = (c_red * alpha_bottom + solid_bottom_r * inv_alpha_bottom) >> 8;
c_green = (c_green * alpha_bottom + solid_bottom_g * inv_alpha_bottom) >> 8;
c_blue = (c_blue * alpha_bottom + solid_bottom_b * inv_alpha_bottom) >> 8;
*dest = RGB32k.RGB[(c_red >> 3)][(c_green >> 3)][(c_blue >> 3)];
*dest = RGB256k.RGB[(c_red >> 2)][(c_green >> 2)][(c_blue >> 2)];
}
frac += fracstep;
@ -959,8 +933,8 @@ namespace swrenderer
int solid_bottom_r = RPART(solid_bottom);
int solid_bottom_g = GPART(solid_bottom);
int solid_bottom_b = BPART(solid_bottom);
uint32_t solid_top_fill = RGB32k.RGB[(solid_top_r >> 3)][(solid_top_g >> 3)][(solid_top_b >> 3)];
uint32_t solid_bottom_fill = RGB32k.RGB[(solid_bottom_r >> 3)][(solid_bottom_g >> 3)][(solid_bottom_b >> 3)];
uint32_t solid_top_fill = RGB256k.RGB[(solid_top_r >> 2)][(solid_top_g >> 2)][(solid_top_b >> 2)];
uint32_t solid_bottom_fill = RGB256k.RGB[(solid_bottom_r >> 2)][(solid_bottom_g >> 2)][(solid_bottom_b >> 2)];
solid_top_fill = (solid_top_fill << 24) | (solid_top_fill << 16) | (solid_top_fill << 8) | solid_top_fill;
solid_bottom_fill = (solid_bottom_fill << 24) | (solid_bottom_fill << 16) | (solid_bottom_fill << 8) | solid_bottom_fill;
@ -1026,7 +1000,7 @@ namespace swrenderer
c_red = (c_red * alpha_top + solid_top_r * inv_alpha_top) >> 8;
c_green = (c_green * alpha_top + solid_top_g * inv_alpha_top) >> 8;
c_blue = (c_blue * alpha_top + solid_top_b * inv_alpha_top) >> 8;
output[col] = RGB32k.RGB[(c_red >> 3)][(c_green >> 3)][(c_blue >> 3)];
output[col] = RGB256k.RGB[(c_red >> 2)][(c_green >> 2)][(c_blue >> 2)];
frac[col] += fracstep[col];
}
@ -1080,7 +1054,7 @@ namespace swrenderer
c_red = (c_red * alpha_bottom + solid_bottom_r * inv_alpha_bottom) >> 8;
c_green = (c_green * alpha_bottom + solid_bottom_g * inv_alpha_bottom) >> 8;
c_blue = (c_blue * alpha_bottom + solid_bottom_b * inv_alpha_bottom) >> 8;
output[col] = RGB32k.RGB[(c_red >> 3)][(c_green >> 3)][(c_blue >> 3)];
output[col] = RGB256k.RGB[(c_red >> 2)][(c_green >> 2)][(c_blue >> 2)];
frac[col] += fracstep[col];
}
@ -1116,6 +1090,8 @@ namespace swrenderer
_srcblend = dc_srcblend;
_destblend = dc_destblend;
_srccolor = dc_srccolor;
_srcalpha = dc_srcalpha;
_destalpha = dc_destalpha;
}
void DrawColumnPalCommand::Execute(DrawerThread *thread)
@ -1210,11 +1186,17 @@ namespace swrenderer
dest = thread->dest_for_thread(_dest_y, pitch, dest);
pitch *= thread->num_cores;
const PalEntry* pal = GPalette.BaseColors;
do
{
uint32_t bg;
bg = (fg + bg2rgb[*dest]) | 0x1f07c1f;
*dest = RGB32k.All[bg & (bg >> 15)];
int src_r = ((_srccolor >> 16) & 0xff) * _srcalpha;
int src_g = ((_srccolor >> 0) & 0xff) * _srcalpha;
int src_b = ((_srccolor >> 8) & 0xff) * _srcalpha;
int r = clamp((src_r + pal[*dest].r * _destalpha)>>18, 0, 255);
int g = clamp((src_g + pal[*dest].g * _destalpha)>>18, 0, 255);
int b = clamp((src_b + pal[*dest].b * _destalpha)>>18, 0, 255);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
} while (--count);
@ -1242,17 +1224,17 @@ namespace swrenderer
dest = thread->dest_for_thread(_dest_y, pitch, dest);
pitch *= thread->num_cores;
const PalEntry* pal = GPalette.BaseColors;
do
{
uint32_t a = fg + bg2rgb[*dest];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest = RGB32k.All[a & (a >> 15)];
int src_r = ((_srccolor >> 16) & 0xff) * _srcalpha;
int src_g = ((_srccolor >> 0) & 0xff) * _srcalpha;
int src_b = ((_srccolor >> 8) & 0xff) * _srcalpha;
int r = clamp((src_r + pal[*dest].r * _destalpha)>>18, 0, 255);
int g = clamp((src_g + pal[*dest].g * _destalpha)>>18, 0, 255);
int b = clamp((src_b + pal[*dest].b * _destalpha)>>18, 0, 255);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
} while (--count);
}
@ -1265,11 +1247,7 @@ namespace swrenderer
count = _count;
dest = _dest;
uint32_t *bg2rgb;
uint32_t fg;
bg2rgb = _destblend;
fg = _srccolor | 0x40100400;
int pitch = _pitch;
count = thread->count_for_thread(_dest_y, count);
@ -1279,16 +1257,19 @@ namespace swrenderer
dest = thread->dest_for_thread(_dest_y, pitch, dest);
pitch *= thread->num_cores;
const PalEntry* palette = GPalette.BaseColors;
do
{
uint32_t a = fg - bg2rgb[*dest];
uint32_t b = a;
int src_r = ((_srccolor >> 16) & 0xff) * _srcalpha;
int src_g = ((_srccolor >> 0) & 0xff) * _srcalpha;
int src_b = ((_srccolor >> 8) & 0xff) * _srcalpha;
int bg = *dest;
int r = MAX((src_r * _srcalpha - palette[bg].r * _destalpha)>>18, 0);
int g = MAX((src_g * _srcalpha - palette[bg].g * _destalpha)>>18, 0);
int b = MAX((src_b * _srcalpha - palette[bg].b * _destalpha)>>18, 0);
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[a & (a >> 15)];
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
} while (--count);
}
@ -1303,11 +1284,7 @@ namespace swrenderer
return;
dest = _dest;
uint32_t *bg2rgb;
uint32_t fg;
bg2rgb = _destblend;
fg = _srccolor;
int pitch = _pitch;
count = thread->count_for_thread(_dest_y, count);
@ -1317,16 +1294,19 @@ namespace swrenderer
dest = thread->dest_for_thread(_dest_y, pitch, dest);
pitch *= thread->num_cores;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t a = (bg2rgb[*dest] | 0x40100400) - fg;
uint32_t b = a;
int src_r = ((_srccolor >> 16) & 0xff) * _srcalpha;
int src_g = ((_srccolor >> 0) & 0xff) * _srcalpha;
int src_b = ((_srccolor >> 8) & 0xff) * _srcalpha;
int bg = *dest;
int r = MAX((src_r * _srcalpha - palette[bg].r * _destalpha)>>18, 0);
int g = MAX((src_g * _srcalpha - palette[bg].g * _destalpha)>>18, 0);
int b = MAX((src_b * _srcalpha - palette[bg].b * _destalpha)>>18, 0);
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[a & (a >> 15)];
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
} while (--count);
}
@ -1354,20 +1334,18 @@ namespace swrenderer
fracstep *= thread->num_cores;
pitch *= thread->num_cores;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t fg = colormap[source[frac >> FRACBITS]];
uint32_t bg = *dest;
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg + bg) | 0x1f07c1f;
*dest = RGB32k.All[fg & (fg >> 15)];
uint32_t r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
uint32_t g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
uint32_t b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1434,21 +1412,20 @@ namespace swrenderer
fracstep *= thread->num_cores;
pitch *= thread->num_cores;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const uint8_t *translation = _translation;
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t fg = colormap[translation[source[frac >> FRACBITS]]];
uint32_t bg = *dest;
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg + bg) | 0x1f07c1f;
*dest = RGB32k.All[fg & (fg >> 15)];
uint32_t r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
uint32_t g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
uint32_t b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1478,14 +1455,17 @@ namespace swrenderer
const uint8_t *source = _source;
const uint8_t *colormap = _colormap;
uint32_t *fgstart = &Col2RGB8[0][_color];
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t val = colormap[source[frac >> FRACBITS]];
uint32_t fg = fgstart[val << 8];
val = (Col2RGB8[64 - val][*dest] + fg) | 0x1f07c1f;
*dest = RGB32k.All[val & (val >> 15)];
uint32_t val = source[frac >> FRACBITS];
int r = (palette[*dest].r * (255-val) + palette[_color].r * val) >> 10;
int g = (palette[*dest].g * (255-val) + palette[_color].g * val) >> 10;
int b = (palette[*dest].b * (255-val) + palette[_color].b * val) >> 10;
*dest = RGB256k.RGB[clamp(r,0,63)][clamp(g,0,63)][clamp(b,0,63)];
dest += pitch;
frac += fracstep;
@ -1517,20 +1497,16 @@ namespace swrenderer
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t a = fg2rgb[colormap[source[frac >> FRACBITS]]] + bg2rgb[*dest];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest = RGB32k.All[a & (a >> 15)];
int fg = colormap[source[frac >> FRACBITS]];
int bg = *dest;
int r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
int g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
int b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1562,20 +1538,16 @@ namespace swrenderer
const uint8_t *translation = _translation;
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t a = fg2rgb[colormap[translation[source[frac >> FRACBITS]]]] + bg2rgb[*dest];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest = RGB32k.All[(a >> 15) & a];
int fg = colormap[translation[source[frac >> FRACBITS]]];
int bg = *dest;
int r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
int g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
int b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1606,19 +1578,16 @@ namespace swrenderer
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t a = (fg2rgb[colormap[source[frac >> FRACBITS]]] | 0x40100400) - bg2rgb[*dest];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[a & (a >> 15)];
int fg = colormap[source[frac >> FRACBITS]];
int bg = *dest;
int r = MAX((palette[fg].r * _srcalpha - palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha - palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha - palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1650,19 +1619,16 @@ namespace swrenderer
const uint8_t *translation = _translation;
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t a = (fg2rgb[colormap[translation[source[frac >> FRACBITS]]]] | 0x40100400) - bg2rgb[*dest];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[(a >> 15) & a];
int fg = colormap[translation[source[frac >> FRACBITS]]];
int bg = *dest;
int r = MAX((palette[fg].r * _srcalpha - palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha - palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha - palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1693,19 +1659,16 @@ namespace swrenderer
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t a = (bg2rgb[*dest] | 0x40100400) - fg2rgb[colormap[source[frac >> FRACBITS]]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[a & (a >> 15)];
int fg = colormap[source[frac >> FRACBITS]];
int bg = *dest;
int r = MAX((-palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((-palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((-palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1737,19 +1700,16 @@ namespace swrenderer
const uint8_t *translation = _translation;
const uint8_t *colormap = _colormap;
const uint8_t *source = _source;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
do
{
uint32_t a = (bg2rgb[*dest] | 0x40100400) - fg2rgb[colormap[translation[source[frac >> FRACBITS]]]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[(a >> 15) & a];
int fg = colormap[translation[source[frac >> FRACBITS]]];
int bg = *dest;
int r = MAX((-palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((-palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((-palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
dest += pitch;
frac += fracstep;
} while (--count);
@ -1865,6 +1825,8 @@ namespace swrenderer
_srcblend = dc_srcblend;
_destblend = dc_destblend;
_color = ds_color;
_srcalpha = dc_srcalpha;
_destalpha = dc_destalpha;
}
void DrawSpanPalCommand::Execute(DrawerThread *thread)
@ -2010,8 +1972,6 @@ namespace swrenderer
const uint8_t *colormap = _colormap;
int count;
int spot;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
xfrac = _xfrac;
yfrac = _yfrac;
@ -2023,6 +1983,8 @@ namespace swrenderer
xstep = _xstep;
ystep = _ystep;
const PalEntry *palette = GPalette.BaseColors;
if (_xbits == 6 && _ybits == 6)
{
// 64x64 is the most common case by far, so special case it.
@ -2031,10 +1993,11 @@ namespace swrenderer
spot = ((xfrac >> (32 - 6 - 6))&(63 * 64)) + (yfrac >> (32 - 6));
uint32_t fg = colormap[source[spot]];
uint32_t bg = *dest;
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg + bg) | 0x1f07c1f;
*dest++ = RGB32k.All[fg & (fg >> 15)];
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest++ = RGB256k.RGB[r][g][b];
xfrac += xstep;
yfrac += ystep;
} while (--count);
@ -2049,10 +2012,11 @@ namespace swrenderer
spot = ((xfrac >> xshift) & xmask) + (yfrac >> yshift);
uint32_t fg = colormap[source[spot]];
uint32_t bg = *dest;
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg + bg) | 0x1f07c1f;
*dest++ = RGB32k.All[fg & (fg >> 15)];
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest++ = RGB256k.RGB[r][g][b];
xfrac += xstep;
yfrac += ystep;
} while (--count);
@ -2073,8 +2037,8 @@ namespace swrenderer
const uint8_t *colormap = _colormap;
int count;
int spot;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
xfrac = _xfrac;
yfrac = _yfrac;
@ -2099,10 +2063,10 @@ namespace swrenderer
{
uint32_t fg = colormap[texdata];
uint32_t bg = *dest;
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg + bg) | 0x1f07c1f;
*dest = RGB32k.All[fg & (fg >> 15)];
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
}
dest++;
xfrac += xstep;
@ -2124,10 +2088,10 @@ namespace swrenderer
{
uint32_t fg = colormap[texdata];
uint32_t bg = *dest;
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg + bg) | 0x1f07c1f;
*dest = RGB32k.All[fg & (fg >> 15)];
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
}
dest++;
xfrac += xstep;
@ -2150,8 +2114,7 @@ namespace swrenderer
const uint8_t *colormap = _colormap;
int count;
int spot;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
xfrac = _xfrac;
yfrac = _yfrac;
@ -2169,15 +2132,13 @@ namespace swrenderer
do
{
spot = ((xfrac >> (32 - 6 - 6))&(63 * 64)) + (yfrac >> (32 - 6));
uint32_t a = fg2rgb[colormap[source[spot]]] + bg2rgb[*dest];
uint32_t b = a;
uint32_t fg = colormap[source[spot]];
uint32_t bg = *dest;
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest++ = RGB256k.RGB[r][g][b];
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest++ = RGB32k.All[a & (a >> 15)];
xfrac += xstep;
yfrac += ystep;
} while (--count);
@ -2190,15 +2151,13 @@ namespace swrenderer
do
{
spot = ((xfrac >> xshift) & xmask) + (yfrac >> yshift);
uint32_t a = fg2rgb[colormap[source[spot]]] + bg2rgb[*dest];
uint32_t b = a;
uint32_t fg = colormap[source[spot]];
uint32_t bg = *dest;
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest++ = RGB256k.RGB[r][g][b];
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest++ = RGB32k.All[a & (a >> 15)];
xfrac += xstep;
yfrac += ystep;
} while (--count);
@ -2219,8 +2178,7 @@ namespace swrenderer
const uint8_t *colormap = _colormap;
int count;
int spot;
uint32_t *fg2rgb = _srcblend;
uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
xfrac = _xfrac;
yfrac = _yfrac;
@ -2243,15 +2201,12 @@ namespace swrenderer
texdata = source[spot];
if (texdata != 0)
{
uint32_t a = fg2rgb[colormap[texdata]] + bg2rgb[*dest];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest = RGB32k.All[a & (a >> 15)];
uint32_t fg = colormap[texdata];
uint32_t bg = *dest;
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
}
dest++;
xfrac += xstep;
@ -2271,15 +2226,12 @@ namespace swrenderer
texdata = source[spot];
if (texdata != 0)
{
uint32_t a = fg2rgb[colormap[texdata]] + bg2rgb[*dest];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest = RGB32k.All[a & (a >> 15)];
uint32_t fg = colormap[texdata];
uint32_t bg = *dest;
int r = MAX((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
}
dest++;
xfrac += xstep;

View file

@ -106,6 +106,8 @@ namespace swrenderer
uint32_t *_srcblend;
uint32_t *_destblend;
uint32_t _srccolor;
fixed_t _srcalpha;
fixed_t _destalpha;
};
class DrawColumnPalCommand : public PalColumnCommand { public: void Execute(DrawerThread *thread) override; };
@ -164,6 +166,8 @@ namespace swrenderer
uint32_t *_srcblend;
uint32_t *_destblend;
int _color;
fixed_t _srcalpha;
fixed_t _destalpha;
};
class DrawSpanPalCommand : public PalSpanCommand { public: void Execute(DrawerThread *thread) override; };
@ -303,6 +307,8 @@ namespace swrenderer
const uint32_t *_srcblend;
const uint32_t *_destblend;
const uint8_t *_translation;
fixed_t _srcalpha;
fixed_t _destalpha;
int _color;
};

View file

@ -4,6 +4,8 @@
**
**---------------------------------------------------------------------------
** Copyright 1998-2006 Randy Heit
** Copyright 2016 Magnus Norddahl
** Copyright 2016 Rachael Alexanderson
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
@ -173,6 +175,8 @@ namespace swrenderer
_colormap = dc_colormap;
_srcblend = dc_srcblend;
_destblend = dc_destblend;
_srcalpha = dc_srcalpha;
_destalpha = dc_destalpha;
_translation = dc_translation;
_color = dc_color;
}
@ -440,21 +444,20 @@ namespace swrenderer
if (count <= 0)
return;
const uint32_t *fg2rgb = _srcblend;
const uint32_t *bg2rgb = _destblend;
dest = ylookup[yl + thread->skipped_by_thread(yl)] + sx + _destorg;
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4 + hx];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t fg = colormap[*source];
uint32_t bg = *dest;
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg+bg) | 0x1f07c1f;
*dest = RGB32k.All[fg & (fg>>15)];
int r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
int g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
int b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
*dest = RGB256k.RGB[r][g][b];
source += 4;
dest += pitch;
} while (--count);
@ -472,42 +475,22 @@ namespace swrenderer
if (count <= 0)
return;
const uint32_t *fg2rgb = _srcblend;
const uint32_t *bg2rgb = _destblend;
dest = ylookup[yl + thread->skipped_by_thread(yl)] + sx + _destorg;
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t fg = colormap[source[0]];
uint32_t bg = dest[0];
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg+bg) | 0x1f07c1f;
dest[0] = RGB32k.All[fg & (fg>>15)];
fg = colormap[source[1]];
bg = dest[1];
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg+bg) | 0x1f07c1f;
dest[1] = RGB32k.All[fg & (fg>>15)];
fg = colormap[source[2]];
bg = dest[2];
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg+bg) | 0x1f07c1f;
dest[2] = RGB32k.All[fg & (fg>>15)];
fg = colormap[source[3]];
bg = dest[3];
fg = fg2rgb[fg];
bg = bg2rgb[bg];
fg = (fg+bg) | 0x1f07c1f;
dest[3] = RGB32k.All[fg & (fg>>15)];
for (int ks = 0; ks < 4; ks++)
{ // [SP] this 4col function was a block of copy-pasted code. 4 times. I regret nothing.
uint32_t fg = colormap[source[ks]];
uint32_t bg = dest[ks];
int r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
int g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
int b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
dest[ks] = RGB256k.RGB[r][g][b];
}
source += 4;
dest += pitch;
@ -527,17 +510,18 @@ namespace swrenderer
if (count <= 0)
return;
fgstart = &Col2RGB8[0][_color];
colormap = _colormap;
dest = ylookup[yl + thread->skipped_by_thread(yl)] + sx + _destorg;
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4 + hx];
pitch = _pitch * thread->num_cores;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t val = colormap[*source];
uint32_t fg = fgstart[val<<8];
val = (Col2RGB8[64-val][*dest] + fg) | 0x1f07c1f;
*dest = RGB32k.All[val & (val>>15)];
uint32_t val = *source;
int r = (palette[*dest].r * (255-val) + palette[_color].r * val) >> 10;
int g = (palette[*dest].g * (255-val) + palette[_color].g * val) >> 10;
int b = (palette[*dest].b * (255-val) + palette[_color].b * val) >> 10;
*dest = RGB256k.RGB[clamp(r,0,63)][clamp(g,0,63)][clamp(b,0,63)];
source += 4;
dest += pitch;
} while (--count);
@ -556,30 +540,23 @@ namespace swrenderer
if (count <= 0)
return;
fgstart = &Col2RGB8[0][_color];
colormap = _colormap;
dest = ylookup[yl + thread->skipped_by_thread(yl)] + sx + _destorg;
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4];
pitch = _pitch * thread->num_cores;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t val;
val = colormap[source[0]];
val = (Col2RGB8[64-val][dest[0]] + fgstart[val<<8]) | 0x1f07c1f;
dest[0] = RGB32k.All[val & (val>>15)];
val = colormap[source[1]];
val = (Col2RGB8[64-val][dest[1]] + fgstart[val<<8]) | 0x1f07c1f;
dest[1] = RGB32k.All[val & (val>>15)];
val = colormap[source[2]];
val = (Col2RGB8[64-val][dest[2]] + fgstart[val<<8]) | 0x1f07c1f;
dest[2] = RGB32k.All[val & (val>>15)];
val = colormap[source[3]];
val = (Col2RGB8[64-val][dest[3]] + fgstart[val<<8]) | 0x1f07c1f;
dest[3] = RGB32k.All[val & (val>>15)];
for (int ks = 0; ks < 4; ks++)
{
val = source[ks];
int r = (palette[dest[ks]].r * (255-val) + palette[_color].r * val) >> 10;
int g = (palette[dest[ks]].g * (255-val) + palette[_color].g * val) >> 10;
int b = (palette[dest[ks]].b * (255-val) + palette[_color].b * val) >> 10;
dest[ks] = RGB256k.RGB[clamp(r,0,63)][clamp(g,0,63)][clamp(b,0,63)];
}
source += 4;
dest += pitch;
@ -598,23 +575,19 @@ namespace swrenderer
if (count <= 0)
return;
const uint32_t *fg2rgb = _srcblend;
const uint32_t *bg2rgb = _destblend;
dest = ylookup[yl + thread->skipped_by_thread(yl)] + sx + _destorg;
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4 + hx];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t a = fg2rgb[colormap[*source]] + bg2rgb[*dest];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
*dest = RGB32k.All[(a>>15) & a];
int fg = colormap[*source];
int bg = *dest;
int r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
int g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
int b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
*dest = RGB256k.RGB[r][g][b];
source += 4;
dest += pitch;
} while (--count);
@ -636,47 +609,18 @@ namespace swrenderer
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const uint32_t *fg2rgb = _srcblend;
const uint32_t *bg2rgb = _destblend;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t a = fg2rgb[colormap[source[0]]] + bg2rgb[dest[0]];
uint32_t b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
dest[0] = RGB32k.All[(a>>15) & a];
a = fg2rgb[colormap[source[1]]] + bg2rgb[dest[1]];
b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
dest[1] = RGB32k.All[(a>>15) & a];
a = fg2rgb[colormap[source[2]]] + bg2rgb[dest[2]];
b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
dest[2] = RGB32k.All[(a>>15) & a];
a = fg2rgb[colormap[source[3]]] + bg2rgb[dest[3]];
b = a;
a |= 0x01f07c1f;
b &= 0x40100400;
a &= 0x3fffffff;
b = b - (b >> 5);
a |= b;
dest[3] = RGB32k.All[(a>>15) & a];
for (int ks = 0; ks < 4; ks++)
{
int fg = colormap[source[ks]];
int bg = dest[ks];
int r = MIN((palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 63);
int g = MIN((palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 63);
int b = MIN((palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 63);
dest[ks] = RGB256k.RGB[r][g][b];
}
source += 4;
dest += pitch;
@ -701,16 +645,15 @@ namespace swrenderer
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4 + hx];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t a = (fg2rgb[colormap[*source]] | 0x40100400) - bg2rgb[*dest];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[(a>>15) & a];
int fg = colormap[*source];
int bg = *dest;
int r = MAX((palette[fg].r * _srcalpha - palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha - palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha - palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
source += 4;
dest += pitch;
} while (--count);
@ -734,40 +677,18 @@ namespace swrenderer
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t a = (fg2rgb[colormap[source[0]]] | 0x40100400) - bg2rgb[dest[0]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[0] = RGB32k.All[(a>>15) & a];
a = (fg2rgb[colormap[source[1]]] | 0x40100400) - bg2rgb[dest[1]];
b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[1] = RGB32k.All[(a>>15) & a];
a = (fg2rgb[colormap[source[2]]] | 0x40100400) - bg2rgb[dest[2]];
b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[2] = RGB32k.All[(a>>15) & a];
a = (fg2rgb[colormap[source[3]]] | 0x40100400) - bg2rgb[dest[3]];
b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[3] = RGB32k.All[(a>>15) & a];
for (int ks = 0; ks < 4; ks++)
{
int fg = colormap[source[ks]];
int bg = dest[ks];
int r = MAX((palette[fg].r * _srcalpha - palette[bg].r * _destalpha)>>18, 0);
int g = MAX((palette[fg].g * _srcalpha - palette[bg].g * _destalpha)>>18, 0);
int b = MAX((palette[fg].b * _srcalpha - palette[bg].b * _destalpha)>>18, 0);
dest[ks] = RGB256k.RGB[r][g][b];
}
source += 4;
dest += pitch;
@ -792,16 +713,15 @@ namespace swrenderer
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4 + hx];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t a = (bg2rgb[*dest] | 0x40100400) - fg2rgb[colormap[*source]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
*dest = RGB32k.All[(a>>15) & a];
int fg = colormap[*source];
int bg = *dest;
int r = MAX((-palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((-palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((-palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
*dest = RGB256k.RGB[r][g][b];
source += 4;
dest += pitch;
} while (--count);
@ -825,40 +745,18 @@ namespace swrenderer
source = &thread->dc_temp[thread->temp_line_for_thread(yl)*4];
pitch = _pitch * thread->num_cores;
colormap = _colormap;
const PalEntry *palette = GPalette.BaseColors;
do {
uint32_t a = (bg2rgb[dest[0]] | 0x40100400) - fg2rgb[colormap[source[0]]];
uint32_t b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[0] = RGB32k.All[(a>>15) & a];
a = (bg2rgb[dest[1]] | 0x40100400) - fg2rgb[colormap[source[1]]];
b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[1] = RGB32k.All[(a>>15) & a];
a = (bg2rgb[dest[2]] | 0x40100400) - fg2rgb[colormap[source[2]]];
b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[2] = RGB32k.All[(a>>15) & a];
a = (bg2rgb[dest[3]] | 0x40100400) - fg2rgb[colormap[source[3]]];
b = a;
b &= 0x40100400;
b = b - (b >> 5);
a &= b;
a |= 0x01f07c1f;
dest[3] = RGB32k.All[(a>>15) & a];
for (int ks = 0; ks < 4; ks++)
{
int fg = colormap[source[ks]];
int bg = dest[ks];
int r = MAX((-palette[fg].r * _srcalpha + palette[bg].r * _destalpha)>>18, 0);
int g = MAX((-palette[fg].g * _srcalpha + palette[bg].g * _destalpha)>>18, 0);
int b = MAX((-palette[fg].b * _srcalpha + palette[bg].b * _destalpha)>>18, 0);
dest[ks] = RGB256k.RGB[r][g][b];
}
source += 4;
dest += pitch;

View file

@ -1509,14 +1509,14 @@ void R_DrawNormalPlane (visplane_t *pl, double _xscale, double _yscale, fixed_t
if (!additive)
{
spanfunc = R_DrawSpanMaskedTranslucent;
dc_srcblend = Col2RGB8[alpha>>10];
dc_destblend = Col2RGB8[(OPAQUE-alpha)>>10];
dc_srcalpha = alpha;
dc_destalpha = OPAQUE-alpha;
}
else
{
spanfunc = R_DrawSpanMaskedAddClamp;
dc_srcblend = Col2RGB8_LessPrecision[alpha>>10];
dc_destblend = Col2RGB8_LessPrecision[FRACUNIT>>10];
dc_srcalpha = alpha;
dc_destalpha = FRACUNIT;
}
}
else
@ -1531,14 +1531,14 @@ void R_DrawNormalPlane (visplane_t *pl, double _xscale, double _yscale, fixed_t
if (!additive)
{
spanfunc = R_DrawSpanTranslucent;
dc_srcblend = Col2RGB8[alpha>>10];
dc_destblend = Col2RGB8[(OPAQUE-alpha)>>10];
dc_srcalpha = alpha;
dc_destalpha = OPAQUE-alpha;
}
else
{
spanfunc = R_DrawSpanAddClamp;
dc_srcblend = Col2RGB8_LessPrecision[alpha>>10];
dc_destblend = Col2RGB8_LessPrecision[FRACUNIT>>10];
dc_srcalpha = alpha;
dc_destalpha = FRACUNIT;
}
}
else

View file

@ -2636,12 +2636,12 @@ static void R_DrawMaskedSegsBehindParticle (const vissprite_t *vis)
}
}
void R_DrawParticle_C (vissprite_t *vis)
//inline int clamp(int x, int y, int z) { return ((x < y) ? x : (z < y) ? z : y); }
void R_DrawParticle (vissprite_t *vis)
{
DWORD *bg2rgb;
int spacing;
BYTE *dest;
DWORD fg;
BYTE color = vis->Style.colormap[vis->startfrac];
int yl = vis->y1;
int ycount = vis->y2 - yl + 1;
@ -2653,33 +2653,10 @@ void R_DrawParticle_C (vissprite_t *vis)
DrawerCommandQueue::WaitForWorkers();
// vis->renderflags holds translucency level (0-255)
{
fixed_t fglevel, bglevel;
DWORD *fg2rgb;
fixed_t fglevel, bglevel;
fglevel = ((vis->renderflags + 1) << 8) & ~0x3ff;
bglevel = FRACUNIT-fglevel;
fg2rgb = Col2RGB8[fglevel>>10];
bg2rgb = Col2RGB8[bglevel>>10];
fg = fg2rgb[color];
}
/*
spacing = RenderTarget->GetPitch() - countbase;
dest = ylookup[yl] + x1 + dc_destorg;
do
{
int count = countbase;
do
{
DWORD bg = bg2rgb[*dest];
bg = (fg+bg) | 0x1f07c1f;
*dest++ = RGB32k.All[bg & (bg>>15)];
} while (--count);
dest += spacing;
} while (--ycount);*/
fglevel = ((vis->renderflags + 1) << 8) & ~0x3ff;
bglevel = FRACUNIT-fglevel;
// original was row-wise
// width = countbase
@ -2695,9 +2672,11 @@ void R_DrawParticle_C (vissprite_t *vis)
dest = ylookup[yl] + x + dc_destorg;
for (int y = 0; y < ycount; y++)
{
DWORD bg = bg2rgb[*dest];
bg = (fg+bg) | 0x1f07c1f;
*dest = RGB32k.All[bg & (bg>>15)];
uint32_t dest_r = MIN((GPalette.BaseColors[*dest].r * bglevel + GPalette.BaseColors[color].r * fglevel) >> 18, 63);
uint32_t dest_g = MIN((GPalette.BaseColors[*dest].g * bglevel + GPalette.BaseColors[color].g * fglevel) >> 18, 63);
uint32_t dest_b = MIN((GPalette.BaseColors[*dest].b * bglevel + GPalette.BaseColors[color].b * fglevel) >> 18, 63);
*dest = RGB256k.RGB[dest_r][dest_g][dest_b];
dest += spacing;
}
}

View file

@ -101,7 +101,7 @@ struct vissprite_t
vissprite_t() {}
};
void R_DrawParticle_C (vissprite_t *);
void R_DrawParticle (vissprite_t *);
void R_ProjectParticle (particle_t *, const sector_t *sector, int shade, int fakeside);
extern int MaxVisSprites;

View file

@ -551,7 +551,7 @@ void FDDSTexture::ReadRGB (FWadLump &lump, BYTE *tcbuf)
DWORD r = (c & RMask) << RShiftL; r |= r >> RShiftR;
DWORD g = (c & GMask) << GShiftL; g |= g >> GShiftR;
DWORD b = (c & BMask) << BShiftL; b |= b >> BShiftR;
*pixelp = RGB32k.RGB[r >> 27][g >> 27][b >> 27];
*pixelp = RGB256k.RGB[r >> 26][g >> 26][b >> 26];
}
else
{
@ -637,7 +637,7 @@ void FDDSTexture::DecompressDXT1 (FWadLump &lump, BYTE *tcbuf)
// Pick colors from the palette for each of the four colors.
/*if (!tcbuf)*/ for (i = 3; i >= 0; --i)
{
palcol[i] = color[i].a ? RGB32k.RGB[color[i].r >> 3][color[i].g >> 3][color[i].b >> 3] : 0;
palcol[i] = color[i].a ? RGB256k.RGB[color[i].r >> 2][color[i].g >> 2][color[i].b >> 2] : 0;
}
// Now decode this 4x4 block to the pixel buffer.
for (y = 0; y < 4; ++y)
@ -717,7 +717,7 @@ void FDDSTexture::DecompressDXT3 (FWadLump &lump, bool premultiplied, BYTE *tcbu
// Pick colors from the palette for each of the four colors.
if (!tcbuf) for (i = 3; i >= 0; --i)
{
palcol[i] = RGB32k.RGB[color[i].r >> 3][color[i].g >> 3][color[i].b >> 3];
palcol[i] = RGB256k.RGB[color[i].r >> 2][color[i].g >> 2][color[i].b >> 2];
}
// Now decode this 4x4 block to the pixel buffer.
for (y = 0; y < 4; ++y)
@ -822,7 +822,7 @@ void FDDSTexture::DecompressDXT5 (FWadLump &lump, bool premultiplied, BYTE *tcbu
// Pick colors from the palette for each of the four colors.
if (!tcbuf) for (i = 3; i >= 0; --i)
{
palcol[i] = RGB32k.RGB[color[i].r >> 3][color[i].g >> 3][color[i].b >> 3];
palcol[i] = RGB256k.RGB[color[i].r >> 2][color[i].g >> 2][color[i].b >> 2];
}
// Now decode this 4x4 block to the pixel buffer.
for (y = 0; y < 4; ++y)

View file

@ -406,7 +406,7 @@ void FJPEGTexture::MakeTexture ()
case JCS_RGB:
for (int x = Width; x > 0; --x)
{
*out = RGB32k.RGB[in[0]>>3][in[1]>>3][in[2]>>3];
*out = RGB256k.RGB[in[0]>>2][in[1]>>2][in[2]>>2];
out += Height;
in += 3;
}
@ -430,7 +430,7 @@ void FJPEGTexture::MakeTexture ()
int r = in[3] - (((256-in[0])*in[3]) >> 8);
int g = in[3] - (((256-in[1])*in[3]) >> 8);
int b = in[3] - (((256-in[2])*in[3]) >> 8);
*out = RGB32k.RGB[r >> 3][g >> 3][b >> 3];
*out = RGB256k.RGB[r >> 2][g >> 2][b >> 2];
out += Height;
in += 4;
}

View file

@ -531,7 +531,7 @@ void FMultiPatchTexture::MakeTexture ()
{
if (*out == 0 && in[3] != 0)
{
*out = RGB32k.RGB[in[2]>>3][in[1]>>3][in[0]>>3];
*out = RGB256k.RGB[in[2]>>2][in[1]>>2][in[0]>>2];
}
out += Height;
in += 4;

View file

@ -528,7 +528,7 @@ void FPCXTexture::MakeTexture()
{
for(int x=0; x < Width; x++)
{
Pixels[y+Height*x] = RGB32k.RGB[row[0]>>3][row[1]>>3][row[2]>>3];
Pixels[y+Height*x] = RGB256k.RGB[row[0]>>2][row[1]>>2][row[2]>>2];
row+=3;
}
}

View file

@ -536,7 +536,7 @@ void FPNGTexture::MakeTexture ()
{
if (!HaveTrans)
{
*out++ = RGB32k.RGB[in[0]>>3][in[1]>>3][in[2]>>3];
*out++ = RGB256k.RGB[in[0]>>2][in[1]>>2][in[2]>>2];
}
else
{
@ -548,7 +548,7 @@ void FPNGTexture::MakeTexture ()
}
else
{
*out++ = RGB32k.RGB[in[0]>>3][in[1]>>3][in[2]>>3];
*out++ = RGB256k.RGB[in[0]>>2][in[1]>>2][in[2]>>2];
}
}
in += pitch;
@ -593,7 +593,7 @@ void FPNGTexture::MakeTexture ()
{
for (y = Height; y > 0; --y)
{
*out++ = in[3] < 128 ? 0 : RGB32k.RGB[in[0]>>3][in[1]>>3][in[2]>>3];
*out++ = in[3] < 128 ? 0 : RGB256k.RGB[in[0]>>2][in[1]>>2][in[2]>>2];
in += pitch;
}
in -= backstep;

View file

@ -393,7 +393,7 @@ void FTGATexture::MakeTexture ()
for(int x=0;x<Width;x++)
{
int v = LittleLong(*p);
Pixels[x*Height+y] = RGB32k.RGB[(v>>10) & 0x1f][(v>>5) & 0x1f][v & 0x1f];
Pixels[x*Height+y] = RGB256k.RGB[((v>>10) & 0x1f)*2][((v>>5) & 0x1f)*2][(v & 0x1f)*2];
p+=step_x;
}
}
@ -405,7 +405,7 @@ void FTGATexture::MakeTexture ()
BYTE * p = ptr + y * Pitch;
for(int x=0;x<Width;x++)
{
Pixels[x*Height+y] = RGB32k.RGB[p[2]>>3][p[1]>>3][p[0]>>3];
Pixels[x*Height+y] = RGB256k.RGB[p[2]>>2][p[1]>>2][p[0]>>2];
p+=step_x;
}
}
@ -419,7 +419,7 @@ void FTGATexture::MakeTexture ()
BYTE * p = ptr + y * Pitch;
for(int x=0;x<Width;x++)
{
Pixels[x*Height+y] = RGB32k.RGB[p[2]>>3][p[1]>>3][p[0]>>3];
Pixels[x*Height+y] = RGB256k.RGB[p[2]>>2][p[1]>>2][p[0]>>2];
p+=step_x;
}
}
@ -431,7 +431,7 @@ void FTGATexture::MakeTexture ()
BYTE * p = ptr + y * Pitch;
for(int x=0;x<Width;x++)
{
Pixels[x*Height+y] = p[3] >= 128? RGB32k.RGB[p[2]>>3][p[1]>>3][p[0]>>3] : 0;
Pixels[x*Height+y] = p[3] >= 128? RGB256k.RGB[p[2]>>2][p[1]>>2][p[0]>>2] : 0;
p+=step_x;
}
}

View file

@ -965,27 +965,6 @@ void DCanvas::PUTTRANSDOT (int xx, int yy, int basecolor, int level)
static int oldyy;
static int oldyyshifted;
#if 0
if(xx < 32)
cc += 7-(xx>>2);
else if(xx > (finit_width - 32))
cc += 7-((finit_width-xx) >> 2);
// if(cc==oldcc) //make sure that we don't double fade the corners.
// {
if(yy < 32)
cc += 7-(yy>>2);
else if(yy > (finit_height - 32))
cc += 7-((finit_height-yy) >> 2);
// }
if(cc > cm && cm != NULL)
{
cc = cm;
}
else if(cc > oldcc+6) // don't let the color escape from the fade table...
{
cc=oldcc+6;
}
#endif
if (yy == oldyy+1)
{
oldyy++;
@ -1003,12 +982,12 @@ void DCanvas::PUTTRANSDOT (int xx, int yy, int basecolor, int level)
}
BYTE *spot = GetBuffer() + oldyyshifted + xx;
DWORD *bg2rgb = Col2RGB8[1+level];
DWORD *fg2rgb = Col2RGB8[63-level];
DWORD fg = fg2rgb[basecolor];
DWORD bg = bg2rgb[*spot];
bg = (fg+bg) | 0x1f07c1f;
*spot = RGB32k.All[bg&(bg>>15)];
uint32_t r = (GPalette.BaseColors[*spot].r * (64 - level) + GPalette.BaseColors[basecolor].r * level) / 64;
uint32_t g = (GPalette.BaseColors[*spot].g * (64 - level) + GPalette.BaseColors[basecolor].g * level) / 64;
uint32_t b = (GPalette.BaseColors[*spot].b * (64 - level) + GPalette.BaseColors[basecolor].b * level) / 64;
*spot = (BYTE)RGB256k.RGB[r][g][b];
}
void DCanvas::DrawLine(int x0, int y0, int x1, int y1, int palColor, uint32 realcolor)

View file

@ -143,9 +143,10 @@ extern "C" {
DWORD Col2RGB8[65][256];
DWORD *Col2RGB8_LessPrecision[65];
DWORD Col2RGB8_Inverse[65][256];
ColorTable32k RGB32k;
ColorTable256k RGB256k;
}
static DWORD Col2RGB8_2[63][256];
// [RH] The framebuffer is no longer a mere byte array.
@ -345,8 +346,6 @@ void DCanvas::Dim (PalEntry color, float damount, int x1, int y1, int w, int h)
if (damount == 0.f)
return;
DWORD *bg2rgb;
DWORD fg;
int gap;
BYTE *spot;
int x, y;
@ -368,28 +367,23 @@ void DCanvas::Dim (PalEntry color, float damount, int x1, int y1, int w, int h)
return;
}
{
int amount;
amount = (int)(damount * 64);
bg2rgb = Col2RGB8[64-amount];
fg = (((color.r * amount) >> 4) << 20) |
((color.g * amount) >> 4) |
(((color.b * amount) >> 4) << 10);
}
spot = Buffer + x1 + y1*Pitch;
gap = Pitch - w;
int alpha = (int)((float)64 * damount);
int ialpha = 64 - alpha;
int dimmedcolor_r = color.r * alpha;
int dimmedcolor_g = color.g * alpha;
int dimmedcolor_b = color.b * alpha;
for (y = h; y != 0; y--)
{
for (x = w; x != 0; x--)
{
DWORD bg;
bg = bg2rgb[(*spot)&0xff];
bg = (fg+bg) | 0x1f07c1f;
*spot = RGB32k.All[bg&(bg>>15)];
uint32_t r = (dimmedcolor_r + GPalette.BaseColors[*spot].r * ialpha) >> 8;
uint32_t g = (dimmedcolor_g + GPalette.BaseColors[*spot].g * ialpha) >> 8;
uint32_t b = (dimmedcolor_b + GPalette.BaseColors[*spot].b * ialpha) >> 8;
*spot = (BYTE)RGB256k.RGB[r][g][b];
spot++;
}
spot += gap;
@ -664,42 +658,12 @@ static void BuildTransTable (const PalEntry *palette)
{
int r, g, b;
// create the RGB555 lookup table
for (r = 0; r < 32; r++)
for (g = 0; g < 32; g++)
for (b = 0; b < 32; b++)
RGB32k.RGB[r][g][b] = ColorMatcher.Pick ((r<<3)|(r>>2), (g<<3)|(g>>2), (b<<3)|(b>>2));
// create the RGB666 lookup table
for (r = 0; r < 64; r++)
for (g = 0; g < 64; g++)
for (b = 0; b < 64; b++)
RGB256k.RGB[r][g][b] = ColorMatcher.Pick ((r<<2)|(r>>4), (g<<2)|(g>>4), (b<<2)|(b>>4));
int x, y;
// create the swizzled palette
for (x = 0; x < 65; x++)
for (y = 0; y < 256; y++)
Col2RGB8[x][y] = (((palette[y].r*x)>>4)<<20) |
((palette[y].g*x)>>4) |
(((palette[y].b*x)>>4)<<10);
// create the swizzled palette with the lsb of red and blue forced to 0
// (for green, a 1 is okay since it never gets added into)
for (x = 1; x < 64; x++)
{
Col2RGB8_LessPrecision[x] = Col2RGB8_2[x-1];
for (y = 0; y < 256; y++)
{
Col2RGB8_2[x-1][y] = Col2RGB8[x][y] & 0x3feffbff;
}
}
Col2RGB8_LessPrecision[0] = Col2RGB8[0];
Col2RGB8_LessPrecision[64] = Col2RGB8[64];
// create the inverse swizzled palette
for (x = 0; x < 65; x++)
for (y = 0; y < 256; y++)
{
Col2RGB8_Inverse[x][y] = (((((255-palette[y].r)*x)>>4)<<20) |
(((255-palette[y].g)*x)>>4) |
((((255-palette[y].b)*x)>>4)<<10)) & 0x3feffbff;
}
}
//==========================================================================

View file

@ -448,44 +448,13 @@ EXTERN_CVAR (Float, Gamma)
// Translucency tables
// RGB32k is a normal R5G5B5 -> palette lookup table.
// Use a union so we can "overflow" without warnings.
// Otherwise, we get stuff like this from Clang (when compiled
// with -fsanitize=bounds) while running:
// src/v_video.cpp:390:12: runtime error: index 1068 out of bounds for type 'BYTE [32]'
// src/r_draw.cpp:273:11: runtime error: index 1057 out of bounds for type 'BYTE [32]'
union ColorTable32k
// [SP] RGB666 support
union ColorTable256k
{
BYTE RGB[32][32][32];
BYTE All[32 *32 *32];
BYTE RGB[64][64][64];
BYTE All[64 *64 *64];
};
extern "C" ColorTable32k RGB32k;
// Col2RGB8 is a pre-multiplied palette for color lookup. It is stored in a
// special R10B10G10 format for efficient blending computation.
// --RRRRRrrr--BBBBBbbb--GGGGGggg-- at level 64
// --------rrrr------bbbb------gggg at level 1
extern "C" DWORD Col2RGB8[65][256];
// Col2RGB8_LessPrecision is the same as Col2RGB8, but the LSB for red
// and blue are forced to zero, so if the blend overflows, it won't spill
// over into the next component's value.
// --RRRRRrrr-#BBBBBbbb-#GGGGGggg-- at level 64
// --------rrr#------bbb#------gggg at level 1
extern "C" DWORD *Col2RGB8_LessPrecision[65];
// Col2RGB8_Inverse is the same as Col2RGB8_LessPrecision, except the source
// palette has been inverted.
extern "C" DWORD Col2RGB8_Inverse[65][256];
// "Magic" numbers used during the blending:
// --000001111100000111110000011111 = 0x01f07c1f
// -0111111111011111111101111111111 = 0x3FEFFBFF
// -1000000000100000000010000000000 = 0x40100400
// ------10000000001000000000100000 = 0x40100400 >> 5
// --11111-----11111-----11111----- = 0x40100400 - (0x40100400 >> 5) aka "white"
// --111111111111111111111111111111 = 0x3FFFFFFF
extern "C" ColorTable256k RGB256k;
// Allocates buffer screens, call before R_Init.
void V_Init (bool restart);