# HG changeset patch # User Emmanuel Gil Peyrot # Date 1360868843 -3600 # Node ID 3ce4065840e93563aea0380613195854a2aef978 # Parent 7aa70f0def38538abc6454eceaf7914186a45929 Calculate the fog per-fragment and remove the fixed-pipeline glFog* functions; now both vertex shaders are the same. diff --git a/pytouhou/ui/gamerenderer.py b/pytouhou/ui/gamerenderer.py --- a/pytouhou/ui/gamerenderer.py +++ b/pytouhou/ui/gamerenderer.py @@ -71,27 +71,37 @@ class GameRenderer(Renderer): dx, dy, dz = back.position2_interpolator.values fog_b, fog_g, fog_r, fog_start, fog_end = back.fog_interpolator.values + # Those two lines may come from the difference between Direct3D and + # OpenGL’s distance handling. The first one seem to calculate fog + # from the eye, while the second does that starting from the near + # plane. + #TODO: investigate, and use a variable to keep the near plane + # distance at a single place. + fog_start -= 101010101./2010101. + fog_end -= 101010101./2010101. + model = Matrix() model.data[3] = [-x, -y, -z, 1] view = self.setup_camera(dx, dy, dz) - - glFogi(GL_FOG_MODE, GL_LINEAR) - glFogf(GL_FOG_START, fog_start) - glFogf(GL_FOG_END, fog_end) - glFogfv(GL_FOG_COLOR, (GLfloat * 4)(fog_r / 255., fog_g / 255., fog_b / 255., 1.)) + model_view_projection = model * view * self.proj + mvp = model_view_projection.get_c_data() if self.use_fixed_pipeline: - glEnable(GL_FOG) + glMatrixMode(GL_MODELVIEW) + glLoadMatrixf(mvp) - model_view_projection = model * view * self.proj - glMatrixMode(GL_MODELVIEW) - glLoadMatrixf(model_view_projection.get_c_data()) + glEnable(GL_FOG) + glFogi(GL_FOG_MODE, GL_LINEAR) + glFogf(GL_FOG_START, fog_start) + glFogf(GL_FOG_END, fog_end) + glFogfv(GL_FOG_COLOR, (GLfloat * 4)(fog_r / 255., fog_g / 255., fog_b / 255., 1.)) else: self.background_shader.bind() + self.background_shader.uniform_matrixf('mvp', mvp) - model_view = model * view - self.background_shader.uniform_matrixf('model_view', model_view.get_c_data()) - self.background_shader.uniform_matrixf('projection', self.proj.get_c_data()) + self.background_shader.uniformf('fog_scale', 1. / (fog_end - fog_start)) + self.background_shader.uniformf('fog_end', fog_end) + self.background_shader.uniformf('fog_color', fog_r / 255., fog_g / 255., fog_b / 255., 1.) self.render_background() else: diff --git a/pytouhou/ui/shaders/eosd.py b/pytouhou/ui/shaders/eosd.py --- a/pytouhou/ui/shaders/eosd.py +++ b/pytouhou/ui/shaders/eosd.py @@ -60,37 +60,33 @@ class BackgroundShader(Shader): attribute vec2 in_texcoord; attribute vec4 in_color; - uniform mat4 model_view; - uniform mat4 projection; + uniform mat4 mvp; varying vec2 texcoord; varying vec4 color; - varying float fog_density; void main() { - vec4 position = model_view * vec4(in_position, 1.0); + gl_Position = mvp * vec4(in_position, 1.0); texcoord = in_texcoord; color = in_color; - - float fog_position = -position.z / position.w; - fog_density = clamp((gl_Fog.end - fog_position) * gl_Fog.scale, 0.0f, 1.0f); - - gl_Position = projection * position; } '''], [''' #version 120 varying vec2 texcoord; varying vec4 color; - varying float fog_density; uniform sampler2D color_map; + uniform float fog_scale; + uniform float fog_end; + uniform vec4 fog_color; void main() { vec4 temp_color = texture2D(color_map, texcoord) * color; - gl_FragColor = mix(gl_Fog.color, temp_color, fog_density); - gl_FragColor.a = temp_color.a; + float depth = gl_FragCoord.z / gl_FragCoord.w; + float fog_density = clamp((fog_end - depth) * fog_scale, 0.0f, 1.0f); + gl_FragColor = vec4(mix(fog_color, temp_color, fog_density).rgb, temp_color.a); } '''])