Got the _good_ stencil shadows going
parent
376b06abc3
commit
e4f8d3e1b3
|
@ -10,16 +10,17 @@ varying lowp vec3 vary_color;
|
||||||
varying lowp vec3 vary_normal;
|
varying lowp vec3 vary_normal;
|
||||||
varying mediump vec2 vary_uv;
|
varying mediump vec2 vary_uv;
|
||||||
varying lowp vec3 vary_object_space_light;
|
varying lowp vec3 vary_object_space_light;
|
||||||
|
varying lowp vec3 vary_object_space_sky;
|
||||||
|
|
||||||
void main (void) {
|
void main (void) {
|
||||||
lowp vec3 normal = normalize (vary_normal);
|
lowp vec3 normal = normalize (vary_normal);
|
||||||
|
|
||||||
lowp vec3 albedo = vary_color * max (uni_min_albedo, texture2D (uni_texture, vary_uv).rgb);
|
lowp vec3 albedo = vary_color * max (uni_min_albedo, texture2D (uni_texture, vary_uv).rgb);
|
||||||
|
|
||||||
lowp vec3 sky_color = pow (vec3 (42.0, 52.0, 109.0) / vec3 (255.0), vec3 (2.0));
|
lowp vec3 sky_color = pow (vec3 (89.0, 125.0, 206.0) / vec3 (255.0), vec3 (2.0));
|
||||||
|
|
||||||
lowp float sun_factor = dot (normal, vary_object_space_light);
|
lowp float sun_factor = dot (normal, vary_object_space_light);
|
||||||
lowp float sky_factor = normal.z;
|
lowp float sky_factor = dot (normal, vary_object_space_sky);
|
||||||
|
|
||||||
lowp vec3 sun = max (sun_factor, 0.0) * (vec3 (1.0) - sky_color);
|
lowp vec3 sun = max (sun_factor, 0.0) * (vec3 (1.0) - sky_color);
|
||||||
lowp vec3 sky = (sky_factor * 0.5 + 0.5) * sky_color;
|
lowp vec3 sky = (sky_factor * 0.5 + 0.5) * sky_color;
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
#line 0
|
#line 0
|
||||||
uniform highp mat4 uni_mvp;
|
uniform highp mat4 uni_mvp;
|
||||||
uniform lowp vec3 uni_albedo;
|
uniform lowp vec3 uni_albedo;
|
||||||
|
uniform lowp vec3 uni_object_space_sky;
|
||||||
uniform lowp vec3 uni_object_space_light;
|
uniform lowp vec3 uni_object_space_light;
|
||||||
|
|
||||||
attribute highp vec4 attr_pos;
|
attribute highp vec4 attr_pos;
|
||||||
|
@ -14,6 +15,7 @@ varying lowp vec3 vary_color;
|
||||||
varying lowp vec3 vary_normal;
|
varying lowp vec3 vary_normal;
|
||||||
varying mediump vec2 vary_uv;
|
varying mediump vec2 vary_uv;
|
||||||
varying lowp vec3 vary_object_space_light;
|
varying lowp vec3 vary_object_space_light;
|
||||||
|
varying lowp vec3 vary_object_space_sky;
|
||||||
|
|
||||||
void main (void) {
|
void main (void) {
|
||||||
vary_uv = attr_uv;
|
vary_uv = attr_uv;
|
||||||
|
@ -21,6 +23,7 @@ void main (void) {
|
||||||
vary_normal = attr_normal;
|
vary_normal = attr_normal;
|
||||||
vary_color = uni_albedo * uni_albedo;
|
vary_color = uni_albedo * uni_albedo;
|
||||||
vary_object_space_light = normalize (uni_object_space_light);
|
vary_object_space_light = normalize (uni_object_space_light);
|
||||||
|
vary_object_space_sky = normalize (uni_object_space_sky);
|
||||||
|
|
||||||
gl_Position = uni_mvp * attr_pos;
|
gl_Position = uni_mvp * attr_pos;
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,18 +3,6 @@
|
||||||
#define highp
|
#define highp
|
||||||
#line 0
|
#line 0
|
||||||
|
|
||||||
uniform lowp float uni_dither_phase;
|
|
||||||
|
|
||||||
void main (void) {
|
void main (void) {
|
||||||
lowp float dither_phase = 0.0;
|
gl_FragColor = vec4 (0.0, 0.0, 0.0, 1.0);
|
||||||
dither_phase += 4.0 * mod (gl_FragCoord.y + 0.5, 4.0);
|
|
||||||
dither_phase += mod (gl_FragCoord.x + 0.5, 4.0);
|
|
||||||
dither_phase = mod (dither_phase, 16.0);
|
|
||||||
|
|
||||||
lowp float dither = 1.0;
|
|
||||||
if (dither_phase == 0.0 || dither_phase == 10.0) {
|
|
||||||
dither = 0.0;
|
|
||||||
}
|
|
||||||
|
|
||||||
gl_FragColor = vec4 (vec3 (20.0, 12.0, 28.0) / vec3 (255.0), dither);
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -104,6 +104,7 @@ use iota::iota;
|
||||||
iota! {
|
iota! {
|
||||||
pub const MVP: u32 = iota;
|
pub const MVP: u32 = iota;
|
||||||
, OBJECT_SPACE_LIGHT
|
, OBJECT_SPACE_LIGHT
|
||||||
|
, OBJECT_SPACE_SKY
|
||||||
, ALBEDO
|
, ALBEDO
|
||||||
, MIN_ALBEDO
|
, MIN_ALBEDO
|
||||||
, MIN_BRIGHT
|
, MIN_BRIGHT
|
||||||
|
@ -112,6 +113,14 @@ iota! {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn make_object_space_vec (inverse_model_mat: &Mat4, world_space_vec: &Vec3)
|
||||||
|
-> Vec3
|
||||||
|
{
|
||||||
|
let v = world_space_vec;
|
||||||
|
let v4 = *inverse_model_mat * Vec4::from ((v.x (), v.y (), v.z (), 0.0));
|
||||||
|
Vec3::from ((v4.x (), v4.y (), v4.z ()))
|
||||||
|
}
|
||||||
|
|
||||||
fn main () {
|
fn main () {
|
||||||
let sdl_context = sdl2::init ().unwrap ();
|
let sdl_context = sdl2::init ().unwrap ();
|
||||||
let video_subsystem = sdl_context.video ().unwrap ();
|
let video_subsystem = sdl_context.video ().unwrap ();
|
||||||
|
@ -159,6 +168,7 @@ fn main () {
|
||||||
vec! [
|
vec! [
|
||||||
(MVP, "mvp"),
|
(MVP, "mvp"),
|
||||||
(OBJECT_SPACE_LIGHT, "object_space_light"),
|
(OBJECT_SPACE_LIGHT, "object_space_light"),
|
||||||
|
(OBJECT_SPACE_SKY, "object_space_sky"),
|
||||||
(ALBEDO, "albedo"),
|
(ALBEDO, "albedo"),
|
||||||
(MIN_ALBEDO, "min_albedo"),
|
(MIN_ALBEDO, "min_albedo"),
|
||||||
(MIN_BRIGHT, "min_bright"),
|
(MIN_BRIGHT, "min_bright"),
|
||||||
|
@ -212,7 +222,7 @@ fn main () {
|
||||||
|
|
||||||
let renderable_sky = RenderableModel::from_iqm (&sky_model);
|
let renderable_sky = RenderableModel::from_iqm (&sky_model);
|
||||||
|
|
||||||
let (renderable_pitch, pitch_colors) = {
|
let (renderable_pitch, pitch_colors, grass_index) = {
|
||||||
let data = load_small_file ("pitch.iqm", 1024 * 1024);
|
let data = load_small_file ("pitch.iqm", 1024 * 1024);
|
||||||
let model = Model::from_slice (&data);
|
let model = Model::from_slice (&data);
|
||||||
|
|
||||||
|
@ -238,8 +248,12 @@ fn main () {
|
||||||
("Grass", (52.0, 101.0, 36.0)),
|
("Grass", (52.0, 101.0, 36.0)),
|
||||||
].into_iter ());
|
].into_iter ());
|
||||||
|
|
||||||
|
let mut grass_index = None;
|
||||||
let colors: Vec <_> = (0..model.meshes.len ()).map (|i| {
|
let colors: Vec <_> = (0..model.meshes.len ()).map (|i| {
|
||||||
let name = str::from_utf8 (model.get_mesh_name (i)).unwrap ();
|
let name = str::from_utf8 (model.get_mesh_name (i)).unwrap ();
|
||||||
|
if name == "Grass" {
|
||||||
|
grass_index = Some (i);
|
||||||
|
}
|
||||||
|
|
||||||
match color_lookup.get (name) {
|
match color_lookup.get (name) {
|
||||||
Some (t) => color_from_255 (*t),
|
Some (t) => color_from_255 (*t),
|
||||||
|
@ -247,7 +261,7 @@ fn main () {
|
||||||
}
|
}
|
||||||
}).collect ();
|
}).collect ();
|
||||||
|
|
||||||
(RenderableModel::from_iqm (&model), colors)
|
(RenderableModel::from_iqm (&model), colors, grass_index.unwrap ())
|
||||||
};
|
};
|
||||||
|
|
||||||
glezz::enable_vertex_attrib_array (attrs ["pos"]);
|
glezz::enable_vertex_attrib_array (attrs ["pos"]);
|
||||||
|
@ -306,16 +320,17 @@ fn main () {
|
||||||
let sky_mvp_mat = view_mat * Mat4::from_scale ((16.0, 16.0, 16.0).into ());
|
let sky_mvp_mat = view_mat * Mat4::from_scale ((16.0, 16.0, 16.0).into ());
|
||||||
|
|
||||||
let light = Vec3::from ((2.0, 0.0, 5.0)).normalize ();
|
let light = Vec3::from ((2.0, 0.0, 5.0)).normalize ();
|
||||||
|
//let light = Vec3::from ((0.0, 0.0, 0.0)).normalize ();
|
||||||
|
|
||||||
let orange = color_from_255 ((210.0, 125.0, 44.0));
|
let orange = color_from_255 ((210.0, 125.0, 44.0));
|
||||||
let green = color_from_255 ((52.0, 101.0, 36.0));
|
let green = color_from_255 ((52.0, 101.0, 36.0));
|
||||||
let white = color_from_255 ((255.0, 255.0, 255.0));
|
let white = color_from_255 ((255.0, 255.0, 255.0));
|
||||||
let off_white = color_from_255 ((222.0, 238.0, 214.0));
|
let _off_white = color_from_255 ((222.0, 238.0, 214.0));
|
||||||
let black = color_from_255 ((0.0, 0.0, 0.0));
|
let black = color_from_255 ((0.0, 0.0, 0.0));
|
||||||
let off_black = color_from_255 ((20.0, 12.0, 28.0));
|
let _off_black = color_from_255 ((20.0, 12.0, 28.0));
|
||||||
|
|
||||||
glezz::clear_color (1.0f32, 0.0f32, 1.0f32, 1.0f32);
|
glezz::clear_color (1.0f32, 0.0f32, 1.0f32, 1.0f32);
|
||||||
glezz::clear (gl::COLOR_BUFFER_BIT | gl::DEPTH_BUFFER_BIT);
|
glezz::clear (gl::COLOR_BUFFER_BIT | gl::DEPTH_BUFFER_BIT | gl::STENCIL_BUFFER_BIT);
|
||||||
glezz::enable (gl::CULL_FACE);
|
glezz::enable (gl::CULL_FACE);
|
||||||
|
|
||||||
let pumpkin_model_mat =
|
let pumpkin_model_mat =
|
||||||
|
@ -330,18 +345,22 @@ fn main () {
|
||||||
use uniforms::*;
|
use uniforms::*;
|
||||||
|
|
||||||
shader_program.use_program ();
|
shader_program.use_program ();
|
||||||
|
glezz::disable (gl::STENCIL_TEST);
|
||||||
glezz::front_face (gl::CW);
|
glezz::front_face (gl::CW);
|
||||||
glezz::disable (gl::BLEND);
|
|
||||||
|
|
||||||
glezz::uniform_3fv (unis [&MIN_BRIGHT], &black);
|
|
||||||
glezz::uniform_3fv (unis [&MIN_ALBEDO], &white);
|
|
||||||
|
|
||||||
let mvp = view_mat * pumpkin_model_mat;
|
let mvp = view_mat * pumpkin_model_mat;
|
||||||
glezz::uniform_matrix_4fv (unis [&MVP], &mvp);
|
glezz::uniform_matrix_4fv (unis [&MVP], &mvp);
|
||||||
|
|
||||||
let object_space_light = pumpkin_model_mat.inverse () * Vec4::from ((light.x (), light.y (), light.z (), 0.0));
|
let inverse_pumpkin = pumpkin_model_mat.inverse ();
|
||||||
let object_space_light = Vec3::from ((object_space_light.x (), object_space_light.y (), object_space_light.z ()));
|
|
||||||
|
let object_space_light = make_object_space_vec (&inverse_pumpkin, &light);
|
||||||
|
|
||||||
|
let object_space_sky = make_object_space_vec (&inverse_pumpkin, &Vec3::from ((0.0, 0.0, 1.0)));
|
||||||
|
|
||||||
|
glezz::uniform_3fv (unis [&MIN_BRIGHT], &black);
|
||||||
|
glezz::uniform_3fv (unis [&MIN_ALBEDO], &white);
|
||||||
glezz::uniform_3fv (unis [&OBJECT_SPACE_LIGHT], &object_space_light);
|
glezz::uniform_3fv (unis [&OBJECT_SPACE_LIGHT], &object_space_light);
|
||||||
|
glezz::uniform_3fv (unis [&OBJECT_SPACE_SKY], &object_space_sky);
|
||||||
|
|
||||||
{
|
{
|
||||||
glezz::uniform_3fv (unis [&ALBEDO], &orange);
|
glezz::uniform_3fv (unis [&ALBEDO], &orange);
|
||||||
|
@ -354,9 +373,10 @@ fn main () {
|
||||||
let mvp = view_mat * world_model_mat;
|
let mvp = view_mat * world_model_mat;
|
||||||
glezz::uniform_matrix_4fv (unis [&MVP], &mvp);
|
glezz::uniform_matrix_4fv (unis [&MVP], &mvp);
|
||||||
|
|
||||||
|
for (i, color) in pitch_colors.iter ().enumerate ().take (renderable_pitch.num_meshes ())
|
||||||
{
|
{
|
||||||
for i in 0..renderable_pitch.num_meshes () {
|
glezz::uniform_3fv (unis [&ALBEDO], color);
|
||||||
glezz::uniform_3fv (unis [&ALBEDO], &pitch_colors [i]);
|
if i != grass_index {
|
||||||
renderable_pitch.draw (&attrs, i);
|
renderable_pitch.draw (&attrs, i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -373,17 +393,16 @@ fn main () {
|
||||||
renderable_sky.draw (&attrs, 0);
|
renderable_sky.draw (&attrs, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
glezz::enable (gl::STENCIL_TEST);
|
||||||
|
unsafe {
|
||||||
|
gl::StencilFunc (gl::ALWAYS, 1, 1);
|
||||||
|
gl::StencilOp (gl::KEEP, gl::KEEP, gl::REPLACE);
|
||||||
|
|
||||||
|
gl::ColorMask (0, 0, 0, 0);
|
||||||
|
gl::DepthMask (0);
|
||||||
|
gl::StencilMask (1);
|
||||||
|
}
|
||||||
shadow_shader.use_program ();
|
shadow_shader.use_program ();
|
||||||
glezz::front_face (gl::CCW);
|
|
||||||
glezz::enable (gl::BLEND);
|
|
||||||
glezz::blend_func (gl::SRC_ALPHA, gl::ONE_MINUS_SRC_ALPHA);
|
|
||||||
|
|
||||||
glezz::uniform_1f (shadow_unis [&DITHER_PHASE], dither_phase as f32);
|
|
||||||
|
|
||||||
glezz::uniform_3fv (shadow_unis [&MIN_BRIGHT], &black);
|
|
||||||
glezz::uniform_3fv (shadow_unis [&MIN_ALBEDO], &white);
|
|
||||||
|
|
||||||
glezz::uniform_3fv (shadow_unis [&OBJECT_SPACE_LIGHT], &object_space_light);
|
|
||||||
|
|
||||||
let view_mat = view_mat * shadow_mat;
|
let view_mat = view_mat * shadow_mat;
|
||||||
|
|
||||||
|
@ -398,11 +417,47 @@ fn main () {
|
||||||
let mvp = view_mat * world_model_mat;
|
let mvp = view_mat * world_model_mat;
|
||||||
glezz::uniform_matrix_4fv (shadow_unis [&MVP], &mvp);
|
glezz::uniform_matrix_4fv (shadow_unis [&MVP], &mvp);
|
||||||
|
|
||||||
{
|
|
||||||
for i in 0..renderable_pitch.num_meshes () {
|
for i in 0..renderable_pitch.num_meshes () {
|
||||||
|
if i != grass_index {
|
||||||
renderable_pitch.draw (&shadow_attrs, i);
|
renderable_pitch.draw (&shadow_attrs, i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
gl::ColorMask (255, 255, 255, 255);
|
||||||
|
gl::DepthMask (1);
|
||||||
|
}
|
||||||
|
shader_program.use_program ();
|
||||||
|
glezz::front_face (gl::CW);
|
||||||
|
|
||||||
|
let inverse_pumpkin = pumpkin_model_mat.inverse ();
|
||||||
|
|
||||||
|
let object_space_light = make_object_space_vec (&inverse_pumpkin, &light);
|
||||||
|
|
||||||
|
let object_space_sky = make_object_space_vec (&inverse_pumpkin, &Vec3::from ((0.0, 0.0, 1.0)));
|
||||||
|
|
||||||
|
glezz::uniform_3fv (unis [&MIN_BRIGHT], &black);
|
||||||
|
glezz::uniform_3fv (unis [&MIN_ALBEDO], &white);
|
||||||
|
glezz::uniform_3fv (unis [&OBJECT_SPACE_SKY], &object_space_sky);
|
||||||
|
|
||||||
|
let mvp = view_mat * world_model_mat;
|
||||||
|
glezz::uniform_matrix_4fv (unis [&MVP], &mvp);
|
||||||
|
|
||||||
|
glezz::uniform_3fv (unis [&ALBEDO], &pitch_colors [grass_index]);
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
gl::StencilFunc (gl::NOTEQUAL, 0, 1);
|
||||||
|
gl::StencilOp (gl::KEEP, gl::KEEP, gl::KEEP);
|
||||||
|
}
|
||||||
|
glezz::uniform_3fv (unis [&OBJECT_SPACE_LIGHT], &Vec3::from ((0.0, 0.0, 0.0)));
|
||||||
|
renderable_pitch.draw (&attrs, grass_index);
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
gl::StencilFunc (gl::EQUAL, 0, 1);
|
||||||
|
gl::StencilOp (gl::KEEP, gl::KEEP, gl::KEEP);
|
||||||
|
}
|
||||||
|
glezz::uniform_3fv (unis [&OBJECT_SPACE_LIGHT], &object_space_light);
|
||||||
|
renderable_pitch.draw (&attrs, grass_index);
|
||||||
}
|
}
|
||||||
|
|
||||||
window.gl_swap_window ();
|
window.gl_swap_window ();
|
||||||
|
|
Loading…
Reference in New Issue