summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorGravatar bunnei2015-11-13 23:04:19 -0500
committerGravatar bunnei2016-02-05 17:17:30 -0500
commite34fa6365ff87af247b0ae8ed880c4032bcb2ed0 (patch)
tree5ca6d502f680761246eca4033daf1c7ad658a4aa /src
parentrenderer_opengl: Implement HW fragment lighting LUTs within our default UBO. (diff)
downloadyuzu-e34fa6365ff87af247b0ae8ed880c4032bcb2ed0.tar.gz
yuzu-e34fa6365ff87af247b0ae8ed880c4032bcb2ed0.tar.xz
yuzu-e34fa6365ff87af247b0ae8ed880c4032bcb2ed0.zip
renderer_opengl: Implement HW fragment lighting distance attenuation.
Diffstat (limited to 'src')
-rw-r--r--src/video_core/renderer_opengl/gl_rasterizer.h36
-rw-r--r--src/video_core/renderer_opengl/gl_shader_gen.cpp19
2 files changed, 38 insertions, 17 deletions
diff --git a/src/video_core/renderer_opengl/gl_rasterizer.h b/src/video_core/renderer_opengl/gl_rasterizer.h
index fa4a78cb1..ba0b05802 100644
--- a/src/video_core/renderer_opengl/gl_rasterizer.h
+++ b/src/video_core/renderer_opengl/gl_rasterizer.h
@@ -78,9 +78,13 @@ struct PicaShaderConfig {
78 78
79 for (unsigned light_index = 0; light_index < res.num_lights; ++light_index) { 79 for (unsigned light_index = 0; light_index < res.num_lights; ++light_index) {
80 unsigned num = regs.lighting.light_enable.GetNum(light_index); 80 unsigned num = regs.lighting.light_enable.GetNum(light_index);
81 const auto& light = regs.lighting.light[num];
81 res.light_src[light_index].num = num; 82 res.light_src[light_index].num = num;
82 res.light_src[light_index].directional = regs.lighting.light[num].w; 83 res.light_src[light_index].directional = light.w;
83 res.light_src[light_index].two_sided_diffuse = regs.lighting.light[num].two_sided_diffuse; 84 res.light_src[light_index].two_sided_diffuse = light.two_sided_diffuse;
85 res.light_src[light_index].dist_atten_enabled = regs.lighting.dist_atten_enable.IsEnabled(num);
86 res.light_src[light_index].dist_atten_bias = Pica::float20::FromRawFloat20(light.dist_atten_bias).ToFloat32();
87 res.light_src[light_index].dist_atten_scale = Pica::float20::FromRawFloat20(light.dist_atten_scale).ToFloat32();
84 } 88 }
85 89
86 return res; 90 return res;
@@ -98,19 +102,23 @@ struct PicaShaderConfig {
98 return std::memcmp(this, &o, sizeof(PicaShaderConfig)) == 0; 102 return std::memcmp(this, &o, sizeof(PicaShaderConfig)) == 0;
99 }; 103 };
100 104
101 Pica::Regs::CompareFunc alpha_test_func;
102 std::array<Pica::Regs::TevStageConfig, 6> tev_stages = {};
103 u8 combiner_buffer_input;
104
105 struct { 105 struct {
106 unsigned num; 106 Pica::Regs::CompareFunc alpha_test_func = Pica::Regs::CompareFunc::Never;
107 bool directional; 107 std::array<Pica::Regs::TevStageConfig, 6> tev_stages = {};
108 bool two_sided_diffuse; 108 u8 combiner_buffer_input = 0;
109 bool dist_atten_enabled; 109
110 } light_src[8]; 110 struct {
111 111 unsigned num = 0;
112 bool lighting_enabled; 112 bool directional = false;
113 unsigned num_lights; 113 bool two_sided_diffuse = false;
114 bool dist_atten_enabled = false;
115 GLfloat dist_atten_scale = 0.0f;
116 GLfloat dist_atten_bias = 0.0f;
117 } light_src[8];
118
119 bool lighting_enabled = false;
120 unsigned num_lights = 0;
121 };
114}; 122};
115 123
116namespace std { 124namespace std {
diff --git a/src/video_core/renderer_opengl/gl_shader_gen.cpp b/src/video_core/renderer_opengl/gl_shader_gen.cpp
index 4e02671dd..cf99cff76 100644
--- a/src/video_core/renderer_opengl/gl_shader_gen.cpp
+++ b/src/video_core/renderer_opengl/gl_shader_gen.cpp
@@ -371,12 +371,13 @@ vec4 primary_fragment_color = vec4(0.0);
371 371
372 for (unsigned light_index = 0; light_index < config.num_lights; ++light_index) { 372 for (unsigned light_index = 0; light_index < config.num_lights; ++light_index) {
373 unsigned num = config.light_src[light_index].num; 373 unsigned num = config.light_src[light_index].num;
374 std::string light_src = "light_src[" + std::to_string(num) + "]";
374 375
375 std::string light_vector; 376 std::string light_vector;
376 if (config.light_src[light_index].directional) 377 if (config.light_src[light_index].directional)
377 light_vector = "normalize(-light_src[" + std::to_string(num) + "].position)"; 378 light_vector = "normalize(-" + light_src + ".position)";
378 else 379 else
379 light_vector = "normalize(light_src[" + std::to_string(num) + "].position - fragment_position)"; 380 light_vector = "normalize(" + light_src + ".position - fragment_position)";
380 381
381 std::string dot_product; 382 std::string dot_product;
382 if (config.light_src[light_index].two_sided_diffuse) 383 if (config.light_src[light_index].two_sided_diffuse)
@@ -384,7 +385,19 @@ vec4 primary_fragment_color = vec4(0.0);
384 else 385 else
385 dot_product = "max(dot(" + light_vector + ", normal), 0.0)"; 386 dot_product = "max(dot(" + light_vector + ", normal), 0.0)";
386 387
387 out += "diffuse_sum += ((light_src[" + std::to_string(num) + "].diffuse * " + dot_product + ") + light_src[" + std::to_string(num) + "].ambient) * 1.0;\n"; 388 std::string dist_atten = "1.0";
389 if (config.light_src[light_index].dist_atten_enabled) {
390 std::string scale = std::to_string(config.light_src[light_index].dist_atten_scale);
391 std::string bias = std::to_string(config.light_src[light_index].dist_atten_bias);
392 std::string lut_index = "(" + scale + " * length(fragment_position - " + light_src + ".position) + " + bias + ")";
393 std::string clamped_lut_index = "((clamp(int(" + lut_index + " * 256.0), 0, 255)))";
394
395 unsigned lut_num = ((unsigned)Regs::LightingSampler::DistanceAttenuation + num);
396
397 dist_atten = "lighting_lut_" + std::to_string(lut_num /4) + "[" + clamped_lut_index + "][" + std::to_string(lut_num & 3) + "]";
398 }
399
400 out += "diffuse_sum += ((light_src[" + std::to_string(num) + "].diffuse * " + dot_product + ") + light_src[" + std::to_string(num) + "].ambient) * " + dist_atten + ";\n";
388 } 401 }
389 402
390 out += "diffuse_sum += lighting_global_ambient;\n"; 403 out += "diffuse_sum += lighting_global_ambient;\n";