mirror of
https://github.com/libretro/ppsspp.git
synced 2025-02-16 23:20:12 +00:00
Clean up (and slightly speed up) blinear scaling
This commit is contained in:
parent
655e7dbfbb
commit
75bbe9df9f
@ -135,29 +135,29 @@ namespace {
|
||||
}
|
||||
|
||||
// this is sadly much faster than an inline function with a loop, at least in VC10
|
||||
#define MIX_PIXELS(p0, p1, p2, factors) \
|
||||
((R(p0)*factors[0] + R(p1)*factors[1] + R(p2)*factors[2])/255 << 0 ) | \
|
||||
((G(p0)*factors[0] + G(p1)*factors[1] + G(p2)*factors[2])/255 << 8 ) | \
|
||||
((B(p0)*factors[0] + B(p1)*factors[1] + B(p2)*factors[2])/255 << 16 ) | \
|
||||
((A(p0)*factors[0] + A(p1)*factors[1] + A(p2)*factors[2])/255 << 24 )
|
||||
#define MIX_PIXELS(_p0, _p1, _factors) \
|
||||
( (R(_p0)*(_factors)[0] + R(_p1)*(_factors)[1])/255 << 0 ) | \
|
||||
( (G(_p0)*(_factors)[0] + G(_p1)*(_factors)[1])/255 << 8 ) | \
|
||||
( (B(_p0)*(_factors)[0] + B(_p1)*(_factors)[1])/255 << 16 ) | \
|
||||
( (A(_p0)*(_factors)[0] + A(_p1)*(_factors)[1])/255 << 24 )
|
||||
|
||||
void mix(u32* data, u32* source, u32* mask, u32 maskmax, int width, int l, int u) {
|
||||
for(int y = l; y < u; ++y) {
|
||||
for(int x = 0; x < width; ++x) {
|
||||
int pos = y*width + x;
|
||||
u8 mixFactors[3] = {0, (std::min(mask[pos], maskmax)*255)/maskmax, 0 };
|
||||
u8 mixFactors[2] = { 0, (std::min(mask[pos], maskmax)*255)/maskmax };
|
||||
mixFactors[0] = 255-mixFactors[1];
|
||||
data[pos] = MIX_PIXELS(data[pos], source[pos], 0, mixFactors);
|
||||
data[pos] = MIX_PIXELS(data[pos], source[pos], mixFactors);
|
||||
if(A(source[pos]) == 0) data[pos] = data[pos] & 0x00FFFFFF; // xBRZ always does a better job with hard alpha
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const static u8 BILINEAR_FACTORS[4][5][3] = {
|
||||
{ { 76,179, 0}, { 0,179, 76}, { 0, 0, 0}, { 0, 0, 0}, { 0, 0, 0} }, // x2
|
||||
{ { 85,170, 0}, { 0,255, 0}, { 0,170, 85}, { 0, 0, 0}, { 0, 0, 0} }, // x3
|
||||
{ {102,153, 0}, { 51,204, 0}, { 0,204, 51}, { 0,153,102}, { 0, 0, 0} }, // x4
|
||||
{ {102,153, 0}, { 51,204, 0}, { 0,255, 0}, { 0,204, 51}, { 0,153,102} }, // x5
|
||||
const static u8 BILINEAR_FACTORS[4][3][2] = {
|
||||
{ { 44,211}, { 0, 0}, { 0, 0} }, // x2
|
||||
{ { 64,191}, { 0,255}, { 0, 0} }, // x3
|
||||
{ { 77,178}, { 26,229}, { 0, 0} }, // x4
|
||||
{ {102,153}, { 51,204}, { 0,255} }, // x5
|
||||
};
|
||||
// integral bilinear upscaling by factor f, horizontal part
|
||||
template<int f>
|
||||
@ -170,8 +170,12 @@ namespace {
|
||||
u32 left = data[inpos - (x==0 ?0:1)];
|
||||
u32 center = data[inpos];
|
||||
u32 right = data[inpos + (x==w-1?0:1)];
|
||||
for(int i=0; i<f; ++i) { // hope the compiler unrolls this
|
||||
out[y*outw + x*f + i] = MIX_PIXELS(left, center, right, BILINEAR_FACTORS[f-2][i]);
|
||||
int i=0;
|
||||
for(; i<f/2+f%2; ++i) { // first half of the new pixels + center, hope the compiler unrolls this
|
||||
out[y*outw + x*f + i] = MIX_PIXELS(left, center, BILINEAR_FACTORS[f-2][i]);
|
||||
}
|
||||
for(; i<f ; ++i) { // second half of the new pixels, hope the compiler unrolls this
|
||||
out[y*outw + x*f + i] = MIX_PIXELS(right, center, BILINEAR_FACTORS[f-2][f-1-i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -192,12 +196,18 @@ namespace {
|
||||
static_assert(f>1 && f<=5, "Bilinear scaling only implemented for 2x, 3x, 4x, and 5x");
|
||||
int outw = w*f;
|
||||
for(int y = l; y < u; ++y) {
|
||||
u32 uy = y - (y==gl ?0:1);
|
||||
u32 ly = y + (y==gu-1?0:1);
|
||||
for(int x = 0; x < outw; ++x) {
|
||||
u32 upper = data[(y - (y==gl ?0:1)) * outw + x];
|
||||
u32 upper = data[uy * outw + x];
|
||||
u32 center = data[y * outw + x];
|
||||
u32 lower = data[(y + (y==gu-1?0:1)) * outw + x];
|
||||
for(int i=0; i<f; ++i) { // hope the compiler unrolls this
|
||||
out[(y*f + i)*outw + x] = MIX_PIXELS(upper, center, lower, BILINEAR_FACTORS[f-2][i]);
|
||||
u32 lower = data[ly * outw + x];
|
||||
int i=0;
|
||||
for(; i<f/2+f%2; ++i) { // first half of the new pixels + center, hope the compiler unrolls this
|
||||
out[(y*f + i)*outw + x] = MIX_PIXELS(upper, center, BILINEAR_FACTORS[f-2][i]);
|
||||
}
|
||||
for(; i<f ; ++i) { // second half of the new pixels, hope the compiler unrolls this
|
||||
out[(y*f + i)*outw + x] = MIX_PIXELS(lower, center, BILINEAR_FACTORS[f-2][f-1-i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user