Skip to content

Commit

Permalink
Test: use software renderer blending logic in fbfetch blend
Browse files Browse the repository at this point in the history
  • Loading branch information
Pokechu22 committed Dec 28, 2022
1 parent ef20cad commit 9625ae9
Show file tree
Hide file tree
Showing 2 changed files with 69 additions and 51 deletions.
112 changes: 64 additions & 48 deletions Source/Core/VideoCommon/PixelShaderGen.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1844,75 +1844,91 @@ static void WriteBlend(ShaderCode& out, const pixel_shader_uid_data* uid_data)
{
using Common::EnumMap;
static constexpr EnumMap<const char*, SrcBlendFactor::InvDstAlpha> blend_src_factor{
"float3(0,0,0);", // ZERO
"float3(1,1,1);", // ONE
"initial_ocol0.rgb;", // DSTCLR
"float3(1,1,1) - initial_ocol0.rgb;", // INVDSTCLR
"src_color.aaa;", // SRCALPHA
"float3(1,1,1) - src_color.aaa;", // INVSRCALPHA
"initial_ocol0.aaa;", // DSTALPHA
"float3(1,1,1) - initial_ocol0.aaa;", // INVDSTALPHA
"float3(0,0,0)", // ZERO
"float3(1,1,1)", // ONE
"initial_ocol0.rgb", // DSTCLR
"float3(1,1,1) - initial_ocol0.rgb", // INVDSTCLR
"src_color.aaa", // SRCALPHA
"float3(1,1,1) - src_color.aaa", // INVSRCALPHA
"initial_ocol0.aaa", // DSTALPHA
"float3(1,1,1) - initial_ocol0.aaa", // INVDSTALPHA
};
static constexpr EnumMap<const char*, SrcBlendFactor::InvDstAlpha> blend_src_factor_alpha{
"0.0;", // ZERO
"1.0;", // ONE
"initial_ocol0.a;", // DSTCLR
"1.0 - initial_ocol0.a;", // INVDSTCLR
"src_color.a;", // SRCALPHA
"1.0 - src_color.a;", // INVSRCALPHA
"initial_ocol0.a;", // DSTALPHA
"1.0 - initial_ocol0.a;", // INVDSTALPHA
"0.0", // ZERO
"1.0", // ONE
"initial_ocol0.a", // DSTCLR
"1.0 - initial_ocol0.a", // INVDSTCLR
"src_color.a", // SRCALPHA
"1.0 - src_color.a", // INVSRCALPHA
"initial_ocol0.a", // DSTALPHA
"1.0 - initial_ocol0.a", // INVDSTALPHA
};
static constexpr EnumMap<const char*, DstBlendFactor::InvDstAlpha> blend_dst_factor{
"float3(0,0,0);", // ZERO
"float3(1,1,1);", // ONE
"ocol0.rgb;", // SRCCLR
"float3(1,1,1) - ocol0.rgb;", // INVSRCCLR
"src_color.aaa;", // SRCALPHA
"float3(1,1,1) - src_color.aaa;", // INVSRCALPHA
"initial_ocol0.aaa;", // DSTALPHA
"float3(1,1,1) - initial_ocol0.aaa;", // INVDSTALPHA
"float3(0,0,0)", // ZERO
"float3(1,1,1)", // ONE
"ocol0.rgb", // SRCCLR
"float3(1,1,1) - ocol0.rgb", // INVSRCCLR
"src_color.aaa", // SRCALPHA
"float3(1,1,1) - src_color.aaa", // INVSRCALPHA
"initial_ocol0.aaa", // DSTALPHA
"float3(1,1,1) - initial_ocol0.aaa", // INVDSTALPHA
};
static constexpr EnumMap<const char*, DstBlendFactor::InvDstAlpha> blend_dst_factor_alpha{
"0.0;", // ZERO
"1.0;", // ONE
"ocol0.a;", // SRCCLR
"1.0 - ocol0.a;", // INVSRCCLR
"src_color.a;", // SRCALPHA
"1.0 - src_color.a;", // INVSRCALPHA
"initial_ocol0.a;", // DSTALPHA
"1.0 - initial_ocol0.a;", // INVDSTALPHA
"0.0", // ZERO
"1.0", // ONE
"ocol0.a", // SRCCLR
"1.0 - ocol0.a", // INVSRCCLR
"src_color.a", // SRCALPHA
"1.0 - src_color.a", // INVSRCALPHA
"initial_ocol0.a", // DSTALPHA
"1.0 - initial_ocol0.a", // INVDSTALPHA
};
out.Write("\tfloat4 src_color = {};\n"
"\tfloat4 blend_src;",
"\tint4 blend_src;",
uid_data->useDstAlpha ? "ocol1" : "ocol0");
out.Write("\tblend_src.rgb = {}\n", blend_src_factor[uid_data->blend_src_factor]);
out.Write("\tblend_src.a = {}\n", blend_src_factor_alpha[uid_data->blend_src_factor_alpha]);
out.Write("\tfloat4 blend_dst;\n");
out.Write("\tblend_dst.rgb = {}\n", blend_dst_factor[uid_data->blend_dst_factor]);
out.Write("\tblend_dst.a = {}\n", blend_dst_factor_alpha[uid_data->blend_dst_factor_alpha]);

out.Write("\tfloat4 blend_result;\n");
out.Write("\tblend_src.rgb = int3({} * 255.0);\n",
blend_src_factor[uid_data->blend_src_factor]);
out.Write("\tblend_src.a = int({} * 255.0);\n",
blend_src_factor_alpha[uid_data->blend_src_factor_alpha]);
out.Write("\tint4 blend_dst;\n");
out.Write("\tblend_dst.rgb = int3({} * 255.0);\n",
blend_dst_factor[uid_data->blend_dst_factor]);
out.Write("\tblend_dst.a = int({} * 255.0);\n",
blend_dst_factor_alpha[uid_data->blend_dst_factor_alpha]);

// add MSB of factors to make their range 0 -> 256
out.Write("\tblend_src += blend_src >> 7;\n"
"\tblend_dst += blend_dst >> 7;\n");

out.Write("\tint4 blend_result;\n");
if (uid_data->blend_subtract)
{
out.Write("\tblend_result.rgb = initial_ocol0.rgb * blend_dst.rgb - ocol0.rgb * "
"blend_src.rgb;\n");
// TODO: libogc docs say src/dest factor are ignored in subtract mode
// (we may be handling this elsewhere?)
out.Write("\tblend_result.rgb = int3(initial_ocol0.rgb * 255.0) * blend_dst.rgb "
"- int3(ocol0.rgb * 255.0) * blend_src.rgb;\n");
}
else
{
out.Write(
"\tblend_result.rgb = initial_ocol0.rgb * blend_dst.rgb + ocol0.rgb * blend_src.rgb;\n");
out.Write("\tblend_result.rgb = int3(initial_ocol0.rgb * 255.0) * blend_dst.rgb "
"+ int3(ocol0.rgb * 255.0) * blend_src.rgb;\n");
}

if (uid_data->blend_subtract_alpha)
out.Write("\tblend_result.a = initial_ocol0.a * blend_dst.a - ocol0.a * blend_src.a;\n");
{
out.Write("\tblend_result.a = int(initial_ocol0.a * 255.0) * blend_dst.a "
"- int(ocol0.a * 255.0) * blend_src.a;\n");
}
else
out.Write("\tblend_result.a = initial_ocol0.a * blend_dst.a + ocol0.a * blend_src.a;\n");
{
out.Write("\tblend_result.a = int(initial_ocol0.a * 255.0) * blend_dst.a "
"+ int(ocol0.a * 255.0) * blend_src.a;\n");
}
}
else
{
out.Write("\tfloat4 blend_result = ocol0;\n");
out.Write("\tint4 blend_result = int4(ocol0 * 255.0) * 256;\n");
}

out.Write("\treal_ocol0 = blend_result;\n");
out.Write("\treal_ocol0 = float4(clamp(blend_result >> 8, 0, 255)) / 255.0;\n");
}
8 changes: 5 additions & 3 deletions Source/Core/VideoCommon/ShaderCache.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -641,13 +641,13 @@ static GXPipelineUid ApplyDriverBugs(const GXPipelineUid& in)

if (g_ActiveConfig.backend_info.bSupportsFramebufferFetch)
{
bool fbfetch_blend = false;
bool fbfetch_blend = blend.blendenable;
if ((DriverDetails::HasBug(DriverDetails::BUG_BROKEN_DISCARD_WITH_EARLY_Z) ||
!g_ActiveConfig.backend_info.bSupportsEarlyZ) &&
ps->ztest == EmulatedZ::ForcedEarly)
{
ps->ztest = EmulatedZ::EarlyWithFBFetch;
fbfetch_blend |= static_cast<bool>(out.blending_state.blendenable);
fbfetch_blend |= static_cast<bool>(blend.blendenable);
ps->no_dual_src = true;
}
fbfetch_blend |= blend.logicopenable && !g_ActiveConfig.backend_info.bSupportsLogicOp;
Expand All @@ -670,7 +670,9 @@ static GXPipelineUid ApplyDriverBugs(const GXPipelineUid& in)
ps->blend_dst_factor_alpha = blend.dstfactoralpha;
ps->blend_subtract = blend.subtract;
ps->blend_subtract_alpha = blend.subtractAlpha;
blend.blendenable = false;
blend.hex = 0;
blend.colorupdate = in.blending_state.colorupdate.Value();
blend.alphaupdate = in.blending_state.alphaupdate.Value();
}
}
}
Expand Down

0 comments on commit 9625ae9

Please sign in to comment.