summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorGravatar bunnei2015-11-19 19:00:42 -0500
committerGravatar bunnei2016-02-05 17:18:36 -0500
commit781b0465795fb80404e2790be2d10bfb1f7149aa (patch)
tree33dc7c84f56ff9dc86aaf88aa4869812ee0f9643 /src
parentgl_shader_gen: Refactor lighting config to match Pica register naming. (diff)
downloadyuzu-781b0465795fb80404e2790be2d10bfb1f7149aa.tar.gz
yuzu-781b0465795fb80404e2790be2d10bfb1f7149aa.tar.xz
yuzu-781b0465795fb80404e2790be2d10bfb1f7149aa.zip
gl_shader_gen: Add support for D0 LUT scaling.
Diffstat (limited to 'src')
-rw-r--r--src/video_core/pica.h68
-rw-r--r--src/video_core/renderer_opengl/gl_rasterizer.h4
-rw-r--r--src/video_core/renderer_opengl/gl_shader_gen.cpp2
3 files changed, 71 insertions, 3 deletions
diff --git a/src/video_core/pica.h b/src/video_core/pica.h
index b1cf072f1..5d27da5d1 100644
--- a/src/video_core/pica.h
+++ b/src/video_core/pica.h
@@ -657,6 +657,44 @@ struct Regs {
657 DistanceAttenuation = 16, 657 DistanceAttenuation = 16,
658 }; 658 };
659 659
660 /**
661 * Pica fragment lighting supports using different LUTs for each lighting component:
662 * Reflectance R, G, and B channels, distribution function for specular components 0 and 1,
663 * fresnel factor, and spotlight attenuation. Furthermore, which LUTs are used for each channel
664 * (or whether a channel is enabled at all) is specified by various pre-defined lighting
665 * configurations. With configurations that require more LUTs, more cycles are required on HW to
666 * perform lighting computations.
667 */
668 enum class LightingConfig {
669 Config0 = 0, ///< Reflect Red, Distribution 0, Spotlight
670 Config1 = 1, ///< Reflect Red, Fresnel, Spotlight
671 Config2 = 2, ///< Reflect Red, Distribution 0/1
672 Config3 = 3, ///< Distribution 0/1, Fresnel
673 Config4 = 4, ///< Reflect Red/Green/Blue, Distribution 0/1, Spotlight
674 Config5 = 5, ///< Reflect Red/Green/Blue, Distribution 0, Fresnel, Spotlight
675 Config6 = 6, ///< Reflect Red, Distribution 0/1, Fresnel, Spotlight
676 Config7 = 8, ///< Reflect Red/Green/Blue, Distribution 0/1, Fresnel, Spotlight
677 ///< NOTE: '8' is intentional, '7' does not appear to be a valid configuration
678 };
679
680 /// Selects which lighting components are affected by fresnel
681 enum class LightingFresnelSelector {
682 None = 0, ///< Fresnel is disabled
683 PrimaryAlpha = 1, ///< Primary (diffuse) lighting alpha is affected by fresnel
684 SecondaryAlpha = 2, ///< Secondary (specular) lighting alpha is affected by fresnel
685 Both = PrimaryAlpha | SecondaryAlpha, ///< Both primary and secondary lighting alphas are affected by fresnel
686 };
687
688 /// Factor used to scale the output of a lighting LUT
689 enum class LightingScale {
690 Scale1 = 0, ///< Scale is 1x
691 Scale2 = 1, ///< Scale is 2x
692 Scale4 = 2, ///< Scale is 4x
693 Scale8 = 3, ///< Scale is 8x
694 Scale1_4 = 6, ///< Scale is 0.25x
695 Scale1_2 = 7, ///< Scale is 0.5x
696 };
697
660 enum class LightingLutInput { 698 enum class LightingLutInput {
661 NH = 0, // Cosine of the angle between the normal and half-angle vectors 699 NH = 0, // Cosine of the angle between the normal and half-angle vectors
662 VH = 1, // Cosine of the angle between the view and half-angle vectors 700 VH = 1, // Cosine of the angle between the view and half-angle vectors
@@ -775,7 +813,35 @@ struct Regs {
775 BitField<24, 3, u32> rr; 813 BitField<24, 3, u32> rr;
776 } lut_input; 814 } lut_input;
777 815
778 INSERT_PADDING_WORDS(0x7); 816 union {
817 BitField< 0, 3, LightingScale> d0;
818 BitField< 4, 3, LightingScale> d1;
819 BitField< 8, 3, LightingScale> sp;
820 BitField<12, 3, LightingScale> fr;
821 BitField<16, 3, LightingScale> rb;
822 BitField<20, 3, LightingScale> rg;
823 BitField<24, 3, LightingScale> rr;
824
825 static float GetScale(LightingScale scale) {
826 switch (scale) {
827 case LightingScale::Scale1:
828 return 1.0f;
829 case LightingScale::Scale2:
830 return 2.0f;
831 case LightingScale::Scale4:
832 return 4.0f;
833 case LightingScale::Scale8:
834 return 8.0f;
835 case LightingScale::Scale1_4:
836 return 0.25f;
837 case LightingScale::Scale1_2:
838 return 0.5f;
839 }
840 return 0.0f;
841 }
842 } lut_scale;
843
844 INSERT_PADDING_WORDS(0x6);
779 845
780 union { 846 union {
781 // There are 8 light enable "slots", corresponding to the total number of lights 847 // There are 8 light enable "slots", corresponding to the total number of lights
diff --git a/src/video_core/renderer_opengl/gl_rasterizer.h b/src/video_core/renderer_opengl/gl_rasterizer.h
index 2042be786..72ded8f22 100644
--- a/src/video_core/renderer_opengl/gl_rasterizer.h
+++ b/src/video_core/renderer_opengl/gl_rasterizer.h
@@ -90,6 +90,7 @@ struct PicaShaderConfig {
90 res.lighting.lut_d0.enable = regs.lighting.lut_enable_d0 == 0; 90 res.lighting.lut_d0.enable = regs.lighting.lut_enable_d0 == 0;
91 res.lighting.lut_d0.abs_input = regs.lighting.abs_lut_input.d0 == 0; 91 res.lighting.lut_d0.abs_input = regs.lighting.abs_lut_input.d0 == 0;
92 res.lighting.lut_d0.type = (Pica::Regs::LightingLutInput)regs.lighting.lut_input.d0.Value(); 92 res.lighting.lut_d0.type = (Pica::Regs::LightingLutInput)regs.lighting.lut_input.d0.Value();
93 res.lighting.lut_d0.scale = regs.lighting.lut_scale.GetScale(regs.lighting.lut_scale.d0);
93 res.lighting.clamp_highlights = regs.lighting.clamp_highlights != 0; 94 res.lighting.clamp_highlights = regs.lighting.clamp_highlights != 0;
94 95
95 return res; 96 return res;
@@ -130,7 +131,8 @@ struct PicaShaderConfig {
130 bool enable = false; 131 bool enable = false;
131 bool abs_input = false; 132 bool abs_input = false;
132 Pica::Regs::LightingLutInput type = Pica::Regs::LightingLutInput::NH; 133 Pica::Regs::LightingLutInput type = Pica::Regs::LightingLutInput::NH;
133 } lut_d0; 134 float scale = 1.0f;
135 } lut_d0, lut_d1, lut_fr;
134 } lighting; 136 } lighting;
135 }; 137 };
136}; 138};
diff --git a/src/video_core/renderer_opengl/gl_shader_gen.cpp b/src/video_core/renderer_opengl/gl_shader_gen.cpp
index a2770cc6e..9044a3813 100644
--- a/src/video_core/renderer_opengl/gl_shader_gen.cpp
+++ b/src/video_core/renderer_opengl/gl_shader_gen.cpp
@@ -412,7 +412,7 @@ static void WriteLighting(std::string& out, const PicaShaderConfig& config) {
412 std::string d0_lut_value = "1.0"; 412 std::string d0_lut_value = "1.0";
413 if (config.lighting.lut_d0.enable) { 413 if (config.lighting.lut_d0.enable) {
414 std::string d0_lut_index = GetLutIndex(light_config.num, config.lighting.lut_d0.type, config.lighting.lut_d0.abs_input); 414 std::string d0_lut_index = GetLutIndex(light_config.num, config.lighting.lut_d0.type, config.lighting.lut_d0.abs_input);
415 d0_lut_value = GetLutValue(Regs::LightingSampler::Distribution0, d0_lut_index); 415 d0_lut_value = "(" + std::to_string(config.lighting.lut_d0.scale) + " * " + GetLutValue(Regs::LightingSampler::Distribution0, d0_lut_index) + ")";
416 } 416 }
417 417
418 // Compute secondary fragment color (specular lighting) function 418 // Compute secondary fragment color (specular lighting) function