mirror of
https://github.com/hrydgard/ppsspp.git
synced 2025-04-02 11:01:50 -04:00
Merge pull request #7573 from unknownbrackets/gpu-minor
Small optimizations to software transform
This commit is contained in:
commit
9db4c5f34d
9 changed files with 91 additions and 51 deletions
|
@ -158,7 +158,7 @@ void SoftwareTransform(
|
|||
// not really sure what a sensible value might be.
|
||||
fog_slope = fog_slope < 0.0f ? -10000.0f : 10000.0f;
|
||||
}
|
||||
if (my_isnan(fog_slope)) {
|
||||
if (my_isnan(fog_slope)) {
|
||||
// Workaround for https://github.com/hrydgard/ppsspp/issues/5384#issuecomment-38365988
|
||||
// Just put the fog far away at a large finite distance.
|
||||
// Infinities and NaNs are rather unpredictable in shaders on many GPUs
|
||||
|
@ -170,34 +170,50 @@ void SoftwareTransform(
|
|||
VertexReader reader(decoded, decVtxFormat, vertType);
|
||||
// We flip in the fragment shader for GE_TEXMAP_TEXTURE_MATRIX.
|
||||
const bool flipV = gstate_c.flipTexture && gstate.getUVGenMode() != GE_TEXMAP_TEXTURE_MATRIX;
|
||||
for (int index = 0; index < maxIndex; index++) {
|
||||
reader.Goto(index);
|
||||
|
||||
float v[3] = {0, 0, 0};
|
||||
Vec4f c0 = Vec4f(1, 1, 1, 1);
|
||||
Vec4f c1 = Vec4f(0, 0, 0, 0);
|
||||
float uv[3] = {0, 0, 1};
|
||||
float fogCoef = 1.0f;
|
||||
|
||||
if (throughmode) {
|
||||
if (throughmode) {
|
||||
for (int index = 0; index < maxIndex; index++) {
|
||||
// Do not touch the coordinates or the colors. No lighting.
|
||||
reader.ReadPos(v);
|
||||
reader.Goto(index);
|
||||
// TODO: Write to a flexible buffer, we don't always need all four components.
|
||||
TransformedVertex &vert = transformed[index];
|
||||
reader.ReadPos(vert.pos);
|
||||
|
||||
if (reader.hasColor0()) {
|
||||
reader.ReadColor0(&c0.x);
|
||||
// c1 is already 0.
|
||||
reader.ReadColor0_8888(vert.color0);
|
||||
} else {
|
||||
c0 = Vec4f::FromRGBA(gstate.getMaterialAmbientRGBA());
|
||||
vert.color0_32 = gstate.getMaterialAmbientRGBA();
|
||||
}
|
||||
|
||||
if (reader.hasUV()) {
|
||||
reader.ReadUV(uv);
|
||||
reader.ReadUV(vert.uv);
|
||||
|
||||
uv[0] *= uscale;
|
||||
uv[1] *= vscale;
|
||||
vert.u *= uscale;
|
||||
vert.v *= vscale;
|
||||
}
|
||||
else
|
||||
{
|
||||
vert.u = 0.0f;
|
||||
vert.v = 0.0f;
|
||||
}
|
||||
fogCoef = 1.0f;
|
||||
// Scale UV?
|
||||
} else {
|
||||
|
||||
if (flipV) {
|
||||
vert.v = 1.0f - vert.v;
|
||||
}
|
||||
|
||||
// Ignore color1 and fog, never used in throughmode anyway.
|
||||
// The w of uv is also never used (hardcoded to 1.0.)
|
||||
}
|
||||
} else {
|
||||
for (int index = 0; index < maxIndex; index++) {
|
||||
reader.Goto(index);
|
||||
|
||||
float v[3] = {0, 0, 0};
|
||||
Vec4f c0 = Vec4f(1, 1, 1, 1);
|
||||
Vec4f c1 = Vec4f(0, 0, 0, 0);
|
||||
float uv[3] = {0, 0, 1};
|
||||
float fogCoef = 1.0f;
|
||||
|
||||
// We do software T&L for now
|
||||
float out[3];
|
||||
float pos[3];
|
||||
|
@ -369,17 +385,17 @@ void SoftwareTransform(
|
|||
// Transform the coord by the view matrix.
|
||||
Vec3ByMatrix43(v, out, gstate.viewMatrix);
|
||||
fogCoef = (v[2] + fog_end) * fog_slope;
|
||||
}
|
||||
|
||||
// TODO: Write to a flexible buffer, we don't always need all four components.
|
||||
memcpy(&transformed[index].x, v, 3 * sizeof(float));
|
||||
transformed[index].fog = fogCoef;
|
||||
memcpy(&transformed[index].u, uv, 3 * sizeof(float));
|
||||
if (flipV) {
|
||||
transformed[index].v = 1.0f - transformed[index].v;
|
||||
// TODO: Write to a flexible buffer, we don't always need all four components.
|
||||
memcpy(&transformed[index].x, v, 3 * sizeof(float));
|
||||
transformed[index].fog = fogCoef;
|
||||
memcpy(&transformed[index].u, uv, 3 * sizeof(float));
|
||||
if (flipV) {
|
||||
transformed[index].v = 1.0f - transformed[index].v;
|
||||
}
|
||||
transformed[index].color0_32 = c0.ToRGBA();
|
||||
transformed[index].color1_32 = c1.ToRGBA();
|
||||
}
|
||||
transformed[index].color0_32 = c0.ToRGBA();
|
||||
transformed[index].color1_32 = c1.ToRGBA();
|
||||
}
|
||||
|
||||
// Here's the best opportunity to try to detect rectangles used to clear the screen, and
|
||||
|
|
|
@ -75,8 +75,18 @@ struct DecVtxFormat {
|
|||
// This struct too.
|
||||
struct TransformedVertex
|
||||
{
|
||||
float x, y, z, fog; // in case of morph, preblend during decode
|
||||
float u; float v; float w; // scaled by uscale, vscale, if there
|
||||
union {
|
||||
struct {
|
||||
float x, y, z, fog; // in case of morph, preblend during decode
|
||||
};
|
||||
float pos[4];
|
||||
};
|
||||
union {
|
||||
struct {
|
||||
float u; float v; float w; // scaled by uscale, vscale, if there
|
||||
};
|
||||
float uv[3];
|
||||
};
|
||||
union {
|
||||
u8 color0[4]; // prelit
|
||||
u32 color0_32;
|
||||
|
|
|
@ -416,7 +416,7 @@ void ComputeFragmentShaderIDDX9(FragmentShaderIDDX9 *id) {
|
|||
// We only need one clear shader, so let's ignore the rest of the bits.
|
||||
id0 = 1;
|
||||
} else {
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled();
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled() && !gstate.isModeThrough();
|
||||
bool enableFog = gstate.isFogEnabled() && !gstate.isModeThrough();
|
||||
bool enableAlphaTest = gstate.isAlphaTestEnabled() && !IsAlphaTestTriviallyTrue() && !g_Config.bDisableAlphaTest;
|
||||
bool enableColorTest = gstate.isColorTestEnabled() && !IsColorTestTriviallyTrue();
|
||||
|
@ -504,7 +504,7 @@ void ComputeFragmentShaderIDDX9(FragmentShaderIDDX9 *id) {
|
|||
void GenerateFragmentShaderDX9(char *buffer) {
|
||||
char *p = buffer;
|
||||
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled();
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled() && !gstate.isModeThrough();
|
||||
bool doTexture = gstate.isTextureMapEnabled() && !gstate.isModeClear();
|
||||
bool enableFog = gstate.isFogEnabled() && !gstate.isModeThrough() && !gstate.isModeClear();
|
||||
bool enableAlphaTest = gstate.isAlphaTestEnabled() && !IsAlphaTestTriviallyTrue() && !gstate.isModeClear() && !g_Config.bDisableAlphaTest;
|
||||
|
|
|
@ -133,7 +133,7 @@ void GenerateVertexShaderDX9(int prim, char *buffer, bool useHWTransform) {
|
|||
char *p = buffer;
|
||||
const u32 vertType = gstate.vertType;
|
||||
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled();
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled() && !gstate.isModeThrough();
|
||||
bool doTexture = gstate.isTextureMapEnabled() && !gstate.isModeClear();
|
||||
bool doTextureProjection = gstate.getUVGenMode() == GE_TEXMAP_TEXTURE_MATRIX;
|
||||
bool doShadeMapping = gstate.getUVGenMode() == GE_TEXMAP_ENVIRONMENT_MAP;
|
||||
|
@ -232,10 +232,7 @@ void GenerateVertexShaderDX9(int prim, char *buffer, bool useHWTransform) {
|
|||
WRITE(p, "%s", boneWeightAttrDecl[TranslateNumBones(vertTypeGetNumBoneWeights(vertType))]);
|
||||
}
|
||||
if (doTexture && hasTexcoord) {
|
||||
if (doTextureProjection)
|
||||
WRITE(p, " float3 texcoord : TEXCOORD0;\n");
|
||||
else
|
||||
WRITE(p, " float2 texcoord : TEXCOORD0;\n");
|
||||
WRITE(p, " float2 texcoord : TEXCOORD0;\n");
|
||||
}
|
||||
if (hasColor) {
|
||||
WRITE(p, " float4 color0 : COLOR0;\n");
|
||||
|
@ -249,10 +246,19 @@ void GenerateVertexShaderDX9(int prim, char *buffer, bool useHWTransform) {
|
|||
} else {
|
||||
WRITE(p, "struct VS_IN {\n");
|
||||
WRITE(p, " float4 position : POSITION;\n");
|
||||
WRITE(p, " float3 texcoord : TEXCOORD0;\n");
|
||||
WRITE(p, " float4 color0 : COLOR0;\n");
|
||||
if (doTexture && hasTexcoord) {
|
||||
if (doTextureProjection && !throughmode)
|
||||
WRITE(p, " float3 texcoord : TEXCOORD0;\n");
|
||||
else
|
||||
WRITE(p, " float2 texcoord : TEXCOORD0;\n");
|
||||
}
|
||||
if (hasColor) {
|
||||
WRITE(p, " float4 color0 : COLOR0;\n");
|
||||
}
|
||||
// only software transform supplies color1 as vertex data
|
||||
WRITE(p, " float4 color1 : COLOR1;\n");
|
||||
if (lmode) {
|
||||
WRITE(p, " float4 color1 : COLOR1;\n");
|
||||
}
|
||||
WRITE(p, "};\n");
|
||||
}
|
||||
|
||||
|
@ -265,7 +271,7 @@ void GenerateVertexShaderDX9(int prim, char *buffer, bool useHWTransform) {
|
|||
WRITE(p, " float2 v_texcoord: TEXCOORD0;\n");
|
||||
}
|
||||
WRITE(p, " float4 v_color0 : COLOR0;\n");
|
||||
if (lmode)
|
||||
if (lmode)
|
||||
WRITE(p, " float3 v_color1 : COLOR1;\n");
|
||||
|
||||
if (enableFog) {
|
||||
|
@ -279,7 +285,11 @@ void GenerateVertexShaderDX9(int prim, char *buffer, bool useHWTransform) {
|
|||
// Simple pass-through of vertex data to fragment shader
|
||||
if (doTexture) {
|
||||
if (doTextureProjection) {
|
||||
WRITE(p, " Out.v_texcoord = In.texcoord;\n");
|
||||
if (throughmode) {
|
||||
WRITE(p, " Out.v_texcoord = float3(In.texcoord.x, In.texcoord.y, 1.0);\n");
|
||||
} else {
|
||||
WRITE(p, " Out.v_texcoord = In.texcoord;\n");
|
||||
}
|
||||
} else {
|
||||
WRITE(p, " Out.v_texcoord = In.texcoord.xy;\n");
|
||||
}
|
||||
|
|
|
@ -209,7 +209,7 @@ GLuint DepalShaderCache::GetDepalettizeShader(GEBufferFormat pixelFormat) {
|
|||
GLint u_pal = glGetUniformLocation(program, "pal");
|
||||
|
||||
glUniform1i(u_tex, 0);
|
||||
glUniform1i(u_pal, 1);
|
||||
glUniform1i(u_pal, 3);
|
||||
|
||||
GLint linkStatus = GL_FALSE;
|
||||
glGetProgramiv(program, GL_LINK_STATUS, &linkStatus);
|
||||
|
|
|
@ -398,7 +398,7 @@ void ComputeFragmentShaderID(ShaderID *id) {
|
|||
// We only need one clear shader, so let's ignore the rest of the bits.
|
||||
id0 = 1;
|
||||
} else {
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled();
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled() && !gstate.isModeThrough();
|
||||
bool enableFog = gstate.isFogEnabled() && !gstate.isModeThrough();
|
||||
bool enableAlphaTest = gstate.isAlphaTestEnabled() && !IsAlphaTestTriviallyTrue() && !g_Config.bDisableAlphaTest;
|
||||
bool enableColorTest = gstate.isColorTestEnabled() && !IsColorTestTriviallyTrue();
|
||||
|
@ -571,7 +571,7 @@ void GenerateFragmentShader(char *buffer) {
|
|||
varying = "in";
|
||||
}
|
||||
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled();
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled() && !gstate.isModeThrough();
|
||||
bool doTexture = gstate.isTextureMapEnabled() && !gstate.isModeClear();
|
||||
bool enableFog = gstate.isFogEnabled() && !gstate.isModeThrough() && !gstate.isModeClear();
|
||||
bool enableAlphaTest = gstate.isAlphaTestEnabled() && !IsAlphaTestTriviallyTrue() && !gstate.isModeClear() && !g_Config.bDisableAlphaTest;
|
||||
|
|
|
@ -979,7 +979,7 @@ void FramebufferManager::BindFramebufferColor(int stage, VirtualFramebuffer *fra
|
|||
fbo_bind_color_as_texture(framebuffer->fbo, 0);
|
||||
}
|
||||
|
||||
if (stage != GL_TEXTURE1) {
|
||||
if (stage != GL_TEXTURE0) {
|
||||
glActiveTexture(stage);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1109,7 +1109,7 @@ void TextureCache::SetTextureFramebuffer(TexCacheEntry *entry, VirtualFramebuffe
|
|||
glEnableVertexAttribArray(a_position);
|
||||
glEnableVertexAttribArray(a_texcoord0);
|
||||
|
||||
glActiveTexture(GL_TEXTURE1);
|
||||
glActiveTexture(GL_TEXTURE3);
|
||||
glBindTexture(GL_TEXTURE_2D, clutTexture);
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
|
||||
|
|
|
@ -214,7 +214,7 @@ void GenerateVertexShader(int prim, u32 vertType, char *buffer, bool useHWTransf
|
|||
boneWeightDecl = boneWeightInDecl;
|
||||
}
|
||||
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled();
|
||||
bool lmode = gstate.isUsingSecondaryColor() && gstate.isLightingEnabled() && !gstate.isModeThrough();
|
||||
bool doTexture = gstate.isTextureMapEnabled() && !gstate.isModeClear();
|
||||
bool doTextureProjection = gstate.getUVGenMode() == GE_TEXMAP_TEXTURE_MATRIX;
|
||||
bool doShadeMapping = gstate.getUVGenMode() == GE_TEXMAP_ENVIRONMENT_MAP;
|
||||
|
@ -257,7 +257,7 @@ void GenerateVertexShader(int prim, u32 vertType, char *buffer, bool useHWTransf
|
|||
WRITE(p, "%s mediump vec3 normal;\n", attribute);
|
||||
|
||||
if (doTexture && hasTexcoord) {
|
||||
if (!useHWTransform && doTextureProjection)
|
||||
if (!useHWTransform && doTextureProjection && !throughmode)
|
||||
WRITE(p, "%s vec3 texcoord;\n", attribute);
|
||||
else
|
||||
WRITE(p, "%s vec2 texcoord;\n", attribute);
|
||||
|
@ -362,7 +362,11 @@ void GenerateVertexShader(int prim, u32 vertType, char *buffer, bool useHWTransf
|
|||
if (!useHWTransform) {
|
||||
// Simple pass-through of vertex data to fragment shader
|
||||
if (doTexture) {
|
||||
WRITE(p, " v_texcoord = texcoord;\n");
|
||||
if (throughmode && doTextureProjection) {
|
||||
WRITE(p, " v_texcoord = vec3(texcoord, 1.0);\n");
|
||||
} else {
|
||||
WRITE(p, " v_texcoord = texcoord;\n");
|
||||
}
|
||||
}
|
||||
if (hasColor) {
|
||||
WRITE(p, " v_color0 = color0;\n");
|
||||
|
|
Loading…
Add table
Reference in a new issue