diff options
| author | 2015-10-06 18:01:53 -0400 | |
|---|---|---|
| committer | 2015-10-21 21:53:16 -0400 | |
| commit | a74774257eafd37f2efae5b745930c3950a3aa04 (patch) | |
| tree | 9229e0c816b3fa25cbcdfa9e07f788aac544b086 /src | |
| parent | renderer_opengl: Refactor shader generation/caching to be more organized + va... (diff) | |
| download | yuzu-a74774257eafd37f2efae5b745930c3950a3aa04.tar.gz yuzu-a74774257eafd37f2efae5b745930c3950a3aa04.tar.xz yuzu-a74774257eafd37f2efae5b745930c3950a3aa04.zip | |
gl_shader_gen: Various cleanups + moved TEV stage generation to its own function.
Diffstat (limited to 'src')
| -rw-r--r-- | src/video_core/renderer_opengl/gl_shader_gen.cpp | 331 |
1 files changed, 170 insertions, 161 deletions
diff --git a/src/video_core/renderer_opengl/gl_shader_gen.cpp b/src/video_core/renderer_opengl/gl_shader_gen.cpp index 059f127af..4854c347e 100644 --- a/src/video_core/renderer_opengl/gl_shader_gen.cpp +++ b/src/video_core/renderer_opengl/gl_shader_gen.cpp | |||
| @@ -6,268 +6,313 @@ | |||
| 6 | #include "video_core/renderer_opengl/gl_rasterizer.h" | 6 | #include "video_core/renderer_opengl/gl_rasterizer.h" |
| 7 | #include "video_core/renderer_opengl/gl_shader_gen.h" | 7 | #include "video_core/renderer_opengl/gl_shader_gen.h" |
| 8 | 8 | ||
| 9 | using Pica::Regs; | ||
| 10 | using TevStageConfig = Regs::TevStageConfig; | ||
| 11 | |||
| 9 | namespace GLShader { | 12 | namespace GLShader { |
| 10 | 13 | ||
| 11 | static bool IsPassThroughTevStage(const Pica::Regs::TevStageConfig& stage) { | 14 | static bool IsPassThroughTevStage(const TevStageConfig& stage) { |
| 12 | return (stage.color_op == Pica::Regs::TevStageConfig::Operation::Replace && | 15 | return (stage.color_op == TevStageConfig::Operation::Replace && |
| 13 | stage.alpha_op == Pica::Regs::TevStageConfig::Operation::Replace && | 16 | stage.alpha_op == TevStageConfig::Operation::Replace && |
| 14 | stage.color_source1 == Pica::Regs::TevStageConfig::Source::Previous && | 17 | stage.color_source1 == TevStageConfig::Source::Previous && |
| 15 | stage.alpha_source1 == Pica::Regs::TevStageConfig::Source::Previous && | 18 | stage.alpha_source1 == TevStageConfig::Source::Previous && |
| 16 | stage.color_modifier1 == Pica::Regs::TevStageConfig::ColorModifier::SourceColor && | 19 | stage.color_modifier1 == TevStageConfig::ColorModifier::SourceColor && |
| 17 | stage.alpha_modifier1 == Pica::Regs::TevStageConfig::AlphaModifier::SourceAlpha && | 20 | stage.alpha_modifier1 == TevStageConfig::AlphaModifier::SourceAlpha && |
| 18 | stage.GetColorMultiplier() == 1 && | 21 | stage.GetColorMultiplier() == 1 && |
| 19 | stage.GetAlphaMultiplier() == 1); | 22 | stage.GetAlphaMultiplier() == 1); |
| 20 | } | 23 | } |
| 21 | 24 | ||
| 22 | static void AppendSource(std::string& shader, Pica::Regs::TevStageConfig::Source source, const std::string& index_name) { | 25 | static void AppendSource(std::string& out, TevStageConfig::Source source, |
| 23 | using Source = Pica::Regs::TevStageConfig::Source; | 26 | const std::string& index_name) { |
| 27 | using Source = TevStageConfig::Source; | ||
| 24 | switch (source) { | 28 | switch (source) { |
| 25 | case Source::PrimaryColor: | 29 | case Source::PrimaryColor: |
| 26 | shader += "o[2]"; | 30 | out += "o[2]"; |
| 27 | break; | 31 | break; |
| 28 | case Source::PrimaryFragmentColor: | 32 | case Source::PrimaryFragmentColor: |
| 29 | // HACK: Until we implement fragment lighting, use primary_color | 33 | // HACK: Until we implement fragment lighting, use primary_color |
| 30 | shader += "o[2]"; | 34 | out += "o[2]"; |
| 31 | break; | 35 | break; |
| 32 | case Source::SecondaryFragmentColor: | 36 | case Source::SecondaryFragmentColor: |
| 33 | // HACK: Until we implement fragment lighting, use zero | 37 | // HACK: Until we implement fragment lighting, use zero |
| 34 | shader += "vec4(0.0, 0.0, 0.0, 0.0)"; | 38 | out += "vec4(0.0, 0.0, 0.0, 0.0)"; |
| 35 | break; | 39 | break; |
| 36 | case Source::Texture0: | 40 | case Source::Texture0: |
| 37 | shader += "texture(tex[0], o[3].xy)"; | 41 | out += "texture(tex[0], o[3].xy)"; |
| 38 | break; | 42 | break; |
| 39 | case Source::Texture1: | 43 | case Source::Texture1: |
| 40 | shader += "texture(tex[1], o[3].zw)"; | 44 | out += "texture(tex[1], o[3].zw)"; |
| 41 | break; | 45 | break; |
| 42 | case Source::Texture2: // TODO: Unverified | 46 | case Source::Texture2: // TODO: Unverified |
| 43 | shader += "texture(tex[2], o[5].zw)"; | 47 | out += "texture(tex[2], o[5].zw)"; |
| 44 | break; | 48 | break; |
| 45 | case Source::PreviousBuffer: | 49 | case Source::PreviousBuffer: |
| 46 | shader += "g_combiner_buffer"; | 50 | out += "g_combiner_buffer"; |
| 47 | break; | 51 | break; |
| 48 | case Source::Constant: | 52 | case Source::Constant: |
| 49 | shader += "const_color[" + index_name + "]"; | 53 | out += "const_color[" + index_name + "]"; |
| 50 | break; | 54 | break; |
| 51 | case Source::Previous: | 55 | case Source::Previous: |
| 52 | shader += "g_last_tex_env_out"; | 56 | out += "g_last_tex_env_out"; |
| 53 | break; | 57 | break; |
| 54 | default: | 58 | default: |
| 55 | shader += "vec4(0.0)"; | 59 | out += "vec4(0.0)"; |
| 56 | LOG_CRITICAL(Render_OpenGL, "Unknown source op %u", source); | 60 | LOG_CRITICAL(Render_OpenGL, "Unknown source op %u", source); |
| 57 | break; | 61 | break; |
| 58 | } | 62 | } |
| 59 | } | 63 | } |
| 60 | 64 | ||
| 61 | static void AppendColorModifier(std::string& shader, Pica::Regs::TevStageConfig::ColorModifier modifier, | 65 | static void AppendColorModifier(std::string& out, TevStageConfig::ColorModifier modifier, |
| 62 | Pica::Regs::TevStageConfig::Source source, const std::string& index_name) { | 66 | TevStageConfig::Source source, const std::string& index_name) { |
| 63 | using ColorModifier = Pica::Regs::TevStageConfig::ColorModifier; | 67 | using ColorModifier = TevStageConfig::ColorModifier; |
| 64 | switch (modifier) { | 68 | switch (modifier) { |
| 65 | case ColorModifier::SourceColor: | 69 | case ColorModifier::SourceColor: |
| 66 | AppendSource(shader, source, index_name); | 70 | AppendSource(out, source, index_name); |
| 67 | shader += ".rgb"; | 71 | out += ".rgb"; |
| 68 | break; | 72 | break; |
| 69 | case ColorModifier::OneMinusSourceColor: | 73 | case ColorModifier::OneMinusSourceColor: |
| 70 | shader += "vec3(1.0) - "; | 74 | out += "vec3(1.0) - "; |
| 71 | AppendSource(shader, source, index_name); | 75 | AppendSource(out, source, index_name); |
| 72 | shader += ".rgb"; | 76 | out += ".rgb"; |
| 73 | break; | 77 | break; |
| 74 | case ColorModifier::SourceAlpha: | 78 | case ColorModifier::SourceAlpha: |
| 75 | AppendSource(shader, source, index_name); | 79 | AppendSource(out, source, index_name); |
| 76 | shader += ".aaa"; | 80 | out += ".aaa"; |
| 77 | break; | 81 | break; |
| 78 | case ColorModifier::OneMinusSourceAlpha: | 82 | case ColorModifier::OneMinusSourceAlpha: |
| 79 | shader += "vec3(1.0) - "; | 83 | out += "vec3(1.0) - "; |
| 80 | AppendSource(shader, source, index_name); | 84 | AppendSource(out, source, index_name); |
| 81 | shader += ".aaa"; | 85 | out += ".aaa"; |
| 82 | break; | 86 | break; |
| 83 | case ColorModifier::SourceRed: | 87 | case ColorModifier::SourceRed: |
| 84 | AppendSource(shader, source, index_name); | 88 | AppendSource(out, source, index_name); |
| 85 | shader += ".rrr"; | 89 | out += ".rrr"; |
| 86 | break; | 90 | break; |
| 87 | case ColorModifier::OneMinusSourceRed: | 91 | case ColorModifier::OneMinusSourceRed: |
| 88 | shader += "vec3(1.0) - "; | 92 | out += "vec3(1.0) - "; |
| 89 | AppendSource(shader, source, index_name); | 93 | AppendSource(out, source, index_name); |
| 90 | shader += ".rrr"; | 94 | out += ".rrr"; |
| 91 | break; | 95 | break; |
| 92 | case ColorModifier::SourceGreen: | 96 | case ColorModifier::SourceGreen: |
| 93 | AppendSource(shader, source, index_name); | 97 | AppendSource(out, source, index_name); |
| 94 | shader += ".ggg"; | 98 | out += ".ggg"; |
| 95 | break; | 99 | break; |
| 96 | case ColorModifier::OneMinusSourceGreen: | 100 | case ColorModifier::OneMinusSourceGreen: |
| 97 | shader += "vec3(1.0) - "; | 101 | out += "vec3(1.0) - "; |
| 98 | AppendSource(shader, source, index_name); | 102 | AppendSource(out, source, index_name); |
| 99 | shader += ".ggg"; | 103 | out += ".ggg"; |
| 100 | break; | 104 | break; |
| 101 | case ColorModifier::SourceBlue: | 105 | case ColorModifier::SourceBlue: |
| 102 | AppendSource(shader, source, index_name); | 106 | AppendSource(out, source, index_name); |
| 103 | shader += ".bbb"; | 107 | out += ".bbb"; |
| 104 | break; | 108 | break; |
| 105 | case ColorModifier::OneMinusSourceBlue: | 109 | case ColorModifier::OneMinusSourceBlue: |
| 106 | shader += "vec3(1.0) - "; | 110 | out += "vec3(1.0) - "; |
| 107 | AppendSource(shader, source, index_name); | 111 | AppendSource(out, source, index_name); |
| 108 | shader += ".bbb"; | 112 | out += ".bbb"; |
| 109 | break; | 113 | break; |
| 110 | default: | 114 | default: |
| 111 | shader += "vec3(0.0)"; | 115 | out += "vec3(0.0)"; |
| 112 | LOG_CRITICAL(Render_OpenGL, "Unknown color modifier op %u", modifier); | 116 | LOG_CRITICAL(Render_OpenGL, "Unknown color modifier op %u", modifier); |
| 113 | break; | 117 | break; |
| 114 | } | 118 | } |
| 115 | } | 119 | } |
| 116 | 120 | ||
| 117 | static void AppendAlphaModifier(std::string& shader, Pica::Regs::TevStageConfig::AlphaModifier modifier, | 121 | static void AppendAlphaModifier(std::string& out, TevStageConfig::AlphaModifier modifier, |
| 118 | Pica::Regs::TevStageConfig::Source source, const std::string& index_name) { | 122 | TevStageConfig::Source source, const std::string& index_name) { |
| 119 | using AlphaModifier = Pica::Regs::TevStageConfig::AlphaModifier; | 123 | using AlphaModifier = TevStageConfig::AlphaModifier; |
| 120 | switch (modifier) { | 124 | switch (modifier) { |
| 121 | case AlphaModifier::SourceAlpha: | 125 | case AlphaModifier::SourceAlpha: |
| 122 | AppendSource(shader, source, index_name); | 126 | AppendSource(out, source, index_name); |
| 123 | shader += ".a"; | 127 | out += ".a"; |
| 124 | break; | 128 | break; |
| 125 | case AlphaModifier::OneMinusSourceAlpha: | 129 | case AlphaModifier::OneMinusSourceAlpha: |
| 126 | shader += "1.0 - "; | 130 | out += "1.0 - "; |
| 127 | AppendSource(shader, source, index_name); | 131 | AppendSource(out, source, index_name); |
| 128 | shader += ".a"; | 132 | out += ".a"; |
| 129 | break; | 133 | break; |
| 130 | case AlphaModifier::SourceRed: | 134 | case AlphaModifier::SourceRed: |
| 131 | AppendSource(shader, source, index_name); | 135 | AppendSource(out, source, index_name); |
| 132 | shader += ".r"; | 136 | out += ".r"; |
| 133 | break; | 137 | break; |
| 134 | case AlphaModifier::OneMinusSourceRed: | 138 | case AlphaModifier::OneMinusSourceRed: |
| 135 | shader += "1.0 - "; | 139 | out += "1.0 - "; |
| 136 | AppendSource(shader, source, index_name); | 140 | AppendSource(out, source, index_name); |
| 137 | shader += ".r"; | 141 | out += ".r"; |
| 138 | break; | 142 | break; |
| 139 | case AlphaModifier::SourceGreen: | 143 | case AlphaModifier::SourceGreen: |
| 140 | AppendSource(shader, source, index_name); | 144 | AppendSource(out, source, index_name); |
| 141 | shader += ".g"; | 145 | out += ".g"; |
| 142 | break; | 146 | break; |
| 143 | case AlphaModifier::OneMinusSourceGreen: | 147 | case AlphaModifier::OneMinusSourceGreen: |
| 144 | shader += "1.0 - "; | 148 | out += "1.0 - "; |
| 145 | AppendSource(shader, source, index_name); | 149 | AppendSource(out, source, index_name); |
| 146 | shader += ".g"; | 150 | out += ".g"; |
| 147 | break; | 151 | break; |
| 148 | case AlphaModifier::SourceBlue: | 152 | case AlphaModifier::SourceBlue: |
| 149 | AppendSource(shader, source, index_name); | 153 | AppendSource(out, source, index_name); |
| 150 | shader += ".b"; | 154 | out += ".b"; |
| 151 | break; | 155 | break; |
| 152 | case AlphaModifier::OneMinusSourceBlue: | 156 | case AlphaModifier::OneMinusSourceBlue: |
| 153 | shader += "1.0 - "; | 157 | out += "1.0 - "; |
| 154 | AppendSource(shader, source, index_name); | 158 | AppendSource(out, source, index_name); |
| 155 | shader += ".b"; | 159 | out += ".b"; |
| 156 | break; | 160 | break; |
| 157 | default: | 161 | default: |
| 158 | shader += "vec3(0.0)"; | 162 | out += "vec3(0.0)"; |
| 159 | LOG_CRITICAL(Render_OpenGL, "Unknown alpha modifier op %u", modifier); | 163 | LOG_CRITICAL(Render_OpenGL, "Unknown alpha modifier op %u", modifier); |
| 160 | break; | 164 | break; |
| 161 | } | 165 | } |
| 162 | } | 166 | } |
| 163 | 167 | ||
| 164 | static void AppendColorCombiner(std::string& shader, Pica::Regs::TevStageConfig::Operation operation, | 168 | static void AppendColorCombiner(std::string& out, TevStageConfig::Operation operation, |
| 165 | const std::string& variable_name) { | 169 | const std::string& variable_name) { |
| 166 | using Operation = Pica::Regs::TevStageConfig::Operation; | 170 | using Operation = TevStageConfig::Operation; |
| 167 | 171 | ||
| 168 | switch (operation) { | 172 | switch (operation) { |
| 169 | case Operation::Replace: | 173 | case Operation::Replace: |
| 170 | shader += variable_name + "[0]"; | 174 | out += variable_name + "[0]"; |
| 171 | break; | 175 | break; |
| 172 | case Operation::Modulate: | 176 | case Operation::Modulate: |
| 173 | shader += variable_name + "[0] * " + variable_name + "[1]"; | 177 | out += variable_name + "[0] * " + variable_name + "[1]"; |
| 174 | break; | 178 | break; |
| 175 | case Operation::Add: | 179 | case Operation::Add: |
| 176 | shader += "min(" + variable_name + "[0] + " + variable_name + "[1], vec3(1.0))"; | 180 | out += "min(" + variable_name + "[0] + " + variable_name + "[1], vec3(1.0))"; |
| 177 | break; | 181 | break; |
| 178 | case Operation::AddSigned: | 182 | case Operation::AddSigned: |
| 179 | shader += "clamp(" + variable_name + "[0] + " + variable_name + "[1] - vec3(0.5), vec3(0.0), vec3(1.0))"; | 183 | out += "clamp(" + variable_name + "[0] + " + variable_name + "[1] - vec3(0.5), vec3(0.0), vec3(1.0))"; |
| 180 | break; | 184 | break; |
| 181 | case Operation::Lerp: | 185 | case Operation::Lerp: |
| 182 | shader += variable_name + "[0] * " + variable_name + "[2] + " + variable_name + "[1] * (vec3(1.0) - " + variable_name + "[2])"; | 186 | out += variable_name + "[0] * " + variable_name + "[2] + " + variable_name + "[1] * (vec3(1.0) - " + variable_name + "[2])"; |
| 183 | break; | 187 | break; |
| 184 | case Operation::Subtract: | 188 | case Operation::Subtract: |
| 185 | shader += "max(" + variable_name + "[0] - " + variable_name + "[1], vec3(0.0))"; | 189 | out += "max(" + variable_name + "[0] - " + variable_name + "[1], vec3(0.0))"; |
| 186 | break; | 190 | break; |
| 187 | case Operation::MultiplyThenAdd: | 191 | case Operation::MultiplyThenAdd: |
| 188 | shader += "min(" + variable_name + "[0] * " + variable_name + "[1] + " + variable_name + "[2], vec3(1.0))"; | 192 | out += "min(" + variable_name + "[0] * " + variable_name + "[1] + " + variable_name + "[2], vec3(1.0))"; |
| 189 | break; | 193 | break; |
| 190 | case Operation::AddThenMultiply: | 194 | case Operation::AddThenMultiply: |
| 191 | shader += "min(" + variable_name + "[0] + " + variable_name + "[1], vec3(1.0)) * " + variable_name + "[2]"; | 195 | out += "min(" + variable_name + "[0] + " + variable_name + "[1], vec3(1.0)) * " + variable_name + "[2]"; |
| 192 | break; | 196 | break; |
| 193 | default: | 197 | default: |
| 194 | shader += "vec3(0.0)"; | 198 | out += "vec3(0.0)"; |
| 195 | LOG_CRITICAL(Render_OpenGL, "Unknown color comb op %u", operation); | 199 | LOG_CRITICAL(Render_OpenGL, "Unknown color combiner operation: %u", operation); |
| 196 | break; | 200 | break; |
| 197 | } | 201 | } |
| 198 | } | 202 | } |
| 199 | 203 | ||
| 200 | static void AppendAlphaCombiner(std::string& shader, Pica::Regs::TevStageConfig::Operation operation, | 204 | static void AppendAlphaCombiner(std::string& out, TevStageConfig::Operation operation, |
| 201 | const std::string& variable_name) { | 205 | const std::string& variable_name) { |
| 202 | using Operation = Pica::Regs::TevStageConfig::Operation; | 206 | using Operation = TevStageConfig::Operation; |
| 203 | switch (operation) { | 207 | switch (operation) { |
| 204 | case Operation::Replace: | 208 | case Operation::Replace: |
| 205 | shader += variable_name + "[0]"; | 209 | out += variable_name + "[0]"; |
| 206 | break; | 210 | break; |
| 207 | case Operation::Modulate: | 211 | case Operation::Modulate: |
| 208 | shader += variable_name + "[0] * " + variable_name + "[1]"; | 212 | out += variable_name + "[0] * " + variable_name + "[1]"; |
| 209 | break; | 213 | break; |
| 210 | case Operation::Add: | 214 | case Operation::Add: |
| 211 | shader += "min(" + variable_name + "[0] + " + variable_name + "[1], 1.0)"; | 215 | out += "min(" + variable_name + "[0] + " + variable_name + "[1], 1.0)"; |
| 212 | break; | 216 | break; |
| 213 | case Operation::AddSigned: | 217 | case Operation::AddSigned: |
| 214 | shader += "clamp(" + variable_name + "[0] + " + variable_name + "[1] - 0.5, 0.0, 1.0)"; | 218 | out += "clamp(" + variable_name + "[0] + " + variable_name + "[1] - 0.5, 0.0, 1.0)"; |
| 215 | break; | 219 | break; |
| 216 | case Operation::Lerp: | 220 | case Operation::Lerp: |
| 217 | shader += variable_name + "[0] * " + variable_name + "[2] + " + variable_name + "[1] * (1.0 - " + variable_name + "[2])"; | 221 | out += variable_name + "[0] * " + variable_name + "[2] + " + variable_name + "[1] * (1.0 - " + variable_name + "[2])"; |
| 218 | break; | 222 | break; |
| 219 | case Operation::Subtract: | 223 | case Operation::Subtract: |
| 220 | shader += "max(" + variable_name + "[0] - " + variable_name + "[1], 0.0)"; | 224 | out += "max(" + variable_name + "[0] - " + variable_name + "[1], 0.0)"; |
| 221 | break; | 225 | break; |
| 222 | case Operation::MultiplyThenAdd: | 226 | case Operation::MultiplyThenAdd: |
| 223 | shader += "min(" + variable_name + "[0] * " + variable_name + "[1] + " + variable_name + "[2], 1.0)"; | 227 | out += "min(" + variable_name + "[0] * " + variable_name + "[1] + " + variable_name + "[2], 1.0)"; |
| 224 | break; | 228 | break; |
| 225 | case Operation::AddThenMultiply: | 229 | case Operation::AddThenMultiply: |
| 226 | shader += "min(" + variable_name + "[0] + " + variable_name + "[1], 1.0) * " + variable_name + "[2]"; | 230 | out += "min(" + variable_name + "[0] + " + variable_name + "[1], 1.0) * " + variable_name + "[2]"; |
| 227 | break; | 231 | break; |
| 228 | default: | 232 | default: |
| 229 | shader += "0.0"; | 233 | out += "0.0"; |
| 230 | LOG_CRITICAL(Render_OpenGL, "Unknown alpha combiner op %u", operation); | 234 | LOG_CRITICAL(Render_OpenGL, "Unknown alpha combiner operation: %u", operation); |
| 231 | break; | 235 | break; |
| 232 | } | 236 | } |
| 233 | } | 237 | } |
| 234 | 238 | ||
| 235 | static void AppendAlphaTestCondition(std::string& shader, Pica::Regs::CompareFunc func) { | 239 | static void AppendAlphaTestCondition(std::string& out, Regs::CompareFunc func) { |
| 236 | using CompareFunc = Pica::Regs::CompareFunc; | 240 | using CompareFunc = Regs::CompareFunc; |
| 237 | switch (func) { | 241 | switch (func) { |
| 238 | case CompareFunc::Never: | 242 | case CompareFunc::Never: |
| 239 | shader += "true"; | 243 | out += "true"; |
| 240 | break; | 244 | break; |
| 241 | case CompareFunc::Always: | 245 | case CompareFunc::Always: |
| 242 | shader += "false"; | 246 | out += "false"; |
| 243 | break; | 247 | break; |
| 244 | case CompareFunc::Equal: | 248 | case CompareFunc::Equal: |
| 245 | shader += "int(g_last_tex_env_out.a * 255.0f) != alphatest_ref"; | 249 | out += "int(g_last_tex_env_out.a * 255.0f) != alphatest_ref"; |
| 246 | break; | 250 | break; |
| 247 | case CompareFunc::NotEqual: | 251 | case CompareFunc::NotEqual: |
| 248 | shader += "int(g_last_tex_env_out.a * 255.0f) == alphatest_ref"; | 252 | out += "int(g_last_tex_env_out.a * 255.0f) == alphatest_ref"; |
| 249 | break; | 253 | break; |
| 250 | case CompareFunc::LessThan: | 254 | case CompareFunc::LessThan: |
| 251 | shader += "int(g_last_tex_env_out.a * 255.0f) >= alphatest_ref"; | 255 | out += "int(g_last_tex_env_out.a * 255.0f) >= alphatest_ref"; |
| 252 | break; | 256 | break; |
| 253 | case CompareFunc::LessThanOrEqual: | 257 | case CompareFunc::LessThanOrEqual: |
| 254 | shader += "int(g_last_tex_env_out.a * 255.0f) > alphatest_ref"; | 258 | out += "int(g_last_tex_env_out.a * 255.0f) > alphatest_ref"; |
| 255 | break; | 259 | break; |
| 256 | case CompareFunc::GreaterThan: | 260 | case CompareFunc::GreaterThan: |
| 257 | shader += "int(g_last_tex_env_out.a * 255.0f) <= alphatest_ref"; | 261 | out += "int(g_last_tex_env_out.a * 255.0f) <= alphatest_ref"; |
| 258 | break; | 262 | break; |
| 259 | case CompareFunc::GreaterThanOrEqual: | 263 | case CompareFunc::GreaterThanOrEqual: |
| 260 | shader += "int(g_last_tex_env_out.a * 255.0f) < alphatest_ref"; | 264 | out += "int(g_last_tex_env_out.a * 255.0f) < alphatest_ref"; |
| 261 | break; | 265 | break; |
| 262 | default: | 266 | default: |
| 263 | shader += "false"; | 267 | out += "false"; |
| 264 | LOG_CRITICAL(Render_OpenGL, "Unknown alpha test condition %u", func); | 268 | LOG_CRITICAL(Render_OpenGL, "Unknown alpha test condition %u", func); |
| 265 | break; | 269 | break; |
| 266 | } | 270 | } |
| 267 | } | 271 | } |
| 268 | 272 | ||
| 273 | static void WriteTevStage(std::string& out, const ShaderCacheKey& config, unsigned index) { | ||
| 274 | auto& stage = config.tev_stages[index]; | ||
| 275 | if (!IsPassThroughTevStage(stage)) { | ||
| 276 | std::string index_name = std::to_string(index); | ||
| 277 | |||
| 278 | out += "vec3 color_results_" + index_name + "[3] = vec3[3]("; | ||
| 279 | AppendColorModifier(out, stage.color_modifier1, stage.color_source1, index_name); | ||
| 280 | out += ", "; | ||
| 281 | AppendColorModifier(out, stage.color_modifier2, stage.color_source2, index_name); | ||
| 282 | out += ", "; | ||
| 283 | AppendColorModifier(out, stage.color_modifier3, stage.color_source3, index_name); | ||
| 284 | out += ");\n"; | ||
| 285 | |||
| 286 | out += "vec3 color_output_" + index_name + " = "; | ||
| 287 | AppendColorCombiner(out, stage.color_op, "color_results_" + index_name); | ||
| 288 | out += ";\n"; | ||
| 289 | |||
| 290 | out += "float alpha_results_" + index_name + "[3] = float[3]("; | ||
| 291 | AppendAlphaModifier(out, stage.alpha_modifier1, stage.alpha_source1, index_name); | ||
| 292 | out += ", "; | ||
| 293 | AppendAlphaModifier(out, stage.alpha_modifier2, stage.alpha_source2, index_name); | ||
| 294 | out += ", "; | ||
| 295 | AppendAlphaModifier(out, stage.alpha_modifier3, stage.alpha_source3, index_name); | ||
| 296 | out += ");\n"; | ||
| 297 | |||
| 298 | out += "float alpha_output_" + index_name + " = "; | ||
| 299 | AppendAlphaCombiner(out, stage.alpha_op, "alpha_results_" + index_name); | ||
| 300 | out += ";\n"; | ||
| 301 | |||
| 302 | out += "g_last_tex_env_out = vec4(min(color_output_" + index_name + " * " + | ||
| 303 | std::to_string(stage.GetColorMultiplier()) + ".0, 1.0), min(alpha_output_" + index_name + " * " + | ||
| 304 | std::to_string(stage.GetAlphaMultiplier()) + ".0, 1.0));\n"; | ||
| 305 | } | ||
| 306 | |||
| 307 | if (config.TevStageUpdatesCombinerBufferColor(index)) | ||
| 308 | out += "g_combiner_buffer.rgb = g_last_tex_env_out.rgb;\n"; | ||
| 309 | |||
| 310 | if (config.TevStageUpdatesCombinerBufferAlpha(index)) | ||
| 311 | out += "g_combiner_buffer.a = g_last_tex_env_out.a;\n"; | ||
| 312 | } | ||
| 313 | |||
| 269 | std::string GenerateFragmentShader(const ShaderCacheKey& config) { | 314 | std::string GenerateFragmentShader(const ShaderCacheKey& config) { |
| 270 | std::string shader = R"( | 315 | std::string out = R"( |
| 271 | #version 150 core | 316 | #version 150 core |
| 272 | 317 | ||
| 273 | #define NUM_VTX_ATTR 7 | 318 | #define NUM_VTX_ATTR 7 |
| @@ -288,63 +333,27 @@ vec4 g_last_tex_env_out = vec4(0.0, 0.0, 0.0, 0.0); | |||
| 288 | )"; | 333 | )"; |
| 289 | 334 | ||
| 290 | // Do not do any sort of processing if it's obvious we're not going to pass the alpha test | 335 | // Do not do any sort of processing if it's obvious we're not going to pass the alpha test |
| 291 | if (config.alpha_test_func == Pica::Regs::CompareFunc::Never) { | 336 | if (config.alpha_test_func == Regs::CompareFunc::Never) { |
| 292 | shader += "discard;"; | 337 | out += "discard;"; |
| 293 | return shader; | 338 | return out; |
| 294 | } | 339 | } |
| 295 | 340 | ||
| 296 | auto& tev_stages = config.tev_stages; | 341 | for (std::size_t index = 0; index < config.tev_stages.size(); ++index) |
| 297 | for (unsigned tev_stage_index = 0; tev_stage_index < tev_stages.size(); ++tev_stage_index) { | 342 | WriteTevStage(out, config, (unsigned)index); |
| 298 | auto& tev_stage = tev_stages[tev_stage_index]; | ||
| 299 | if (!IsPassThroughTevStage(tev_stage)) { | ||
| 300 | std::string index_name = std::to_string(tev_stage_index); | ||
| 301 | |||
| 302 | shader += "vec3 color_results_" + index_name + "[3] = vec3[3]("; | ||
| 303 | AppendColorModifier(shader, tev_stage.color_modifier1, tev_stage.color_source1, index_name); | ||
| 304 | shader += ", "; | ||
| 305 | AppendColorModifier(shader, tev_stage.color_modifier2, tev_stage.color_source2, index_name); | ||
| 306 | shader += ", "; | ||
| 307 | AppendColorModifier(shader, tev_stage.color_modifier3, tev_stage.color_source3, index_name); | ||
| 308 | shader += ");\n"; | ||
| 309 | |||
| 310 | shader += "vec3 color_output_" + index_name + " = "; | ||
| 311 | AppendColorCombiner(shader, tev_stage.color_op, "color_results_" + index_name); | ||
| 312 | shader += ";\n"; | ||
| 313 | |||
| 314 | shader += "float alpha_results_" + index_name + "[3] = float[3]("; | ||
| 315 | AppendAlphaModifier(shader, tev_stage.alpha_modifier1, tev_stage.alpha_source1, index_name); | ||
| 316 | shader += ", "; | ||
| 317 | AppendAlphaModifier(shader, tev_stage.alpha_modifier2, tev_stage.alpha_source2, index_name); | ||
| 318 | shader += ", "; | ||
| 319 | AppendAlphaModifier(shader, tev_stage.alpha_modifier3, tev_stage.alpha_source3, index_name); | ||
| 320 | shader += ");\n"; | ||
| 321 | |||
| 322 | shader += "float alpha_output_" + index_name + " = "; | ||
| 323 | AppendAlphaCombiner(shader, tev_stage.alpha_op, "alpha_results_" + index_name); | ||
| 324 | shader += ";\n"; | ||
| 325 | |||
| 326 | shader += "g_last_tex_env_out = vec4(min(color_output_" + index_name + " * " + std::to_string(tev_stage.GetColorMultiplier()) + ".0, 1.0), min(alpha_output_" + index_name + " * " + std::to_string(tev_stage.GetAlphaMultiplier()) + ".0, 1.0));\n"; | ||
| 327 | } | ||
| 328 | |||
| 329 | if (config.TevStageUpdatesCombinerBufferColor(tev_stage_index)) | ||
| 330 | shader += "g_combiner_buffer.rgb = g_last_tex_env_out.rgb;\n"; | ||
| 331 | |||
| 332 | if (config.TevStageUpdatesCombinerBufferAlpha(tev_stage_index)) | ||
| 333 | shader += "g_combiner_buffer.a = g_last_tex_env_out.a;\n"; | ||
| 334 | } | ||
| 335 | 343 | ||
| 336 | if (config.alpha_test_func != Pica::Regs::CompareFunc::Always) { | 344 | if (config.alpha_test_func != Regs::CompareFunc::Always) { |
| 337 | shader += "if ("; | 345 | out += "if ("; |
| 338 | AppendAlphaTestCondition(shader, config.alpha_test_func); | 346 | AppendAlphaTestCondition(out, config.alpha_test_func); |
| 339 | shader += ") {\n discard;\n }\n"; | 347 | out += ") {\n discard;\n }\n"; |
| 340 | } | 348 | } |
| 341 | 349 | ||
| 342 | shader += "color = g_last_tex_env_out;\n}"; | 350 | out += "color = g_last_tex_env_out;\n}"; |
| 343 | return shader; | 351 | |
| 352 | return out; | ||
| 344 | } | 353 | } |
| 345 | 354 | ||
| 346 | std::string GenerateVertexShader() { | 355 | std::string GenerateVertexShader() { |
| 347 | static const std::string shader_str = R"( | 356 | static const std::string out = R"( |
| 348 | #version 150 core | 357 | #version 150 core |
| 349 | 358 | ||
| 350 | #define NUM_VTX_ATTR 7 | 359 | #define NUM_VTX_ATTR 7 |
| @@ -365,7 +374,7 @@ void main() { | |||
| 365 | gl_Position = vec4(vert_position.x, -vert_position.y, -vert_position.z, vert_position.w); | 374 | gl_Position = vec4(vert_position.x, -vert_position.y, -vert_position.z, vert_position.w); |
| 366 | } | 375 | } |
| 367 | )"; | 376 | )"; |
| 368 | return shader_str; | 377 | return out; |
| 369 | } | 378 | } |
| 370 | 379 | ||
| 371 | } // namespace GLShaderGen | 380 | } // namespace GLShader |