mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Directional baked lights for figures
This commit is contained in:
parent
c7e82aea26
commit
100cafa91b
@ -50,6 +50,7 @@ uniform u_locals {
|
||||
mat4 model_mat;
|
||||
vec4 highlight_col;
|
||||
vec4 model_light;
|
||||
vec4 model_glow;
|
||||
ivec4 atlas_offs;
|
||||
vec3 model_pos;
|
||||
// bit 0 - is player
|
||||
@ -181,7 +182,7 @@ void main() {
|
||||
|
||||
float ao = f_ao * sqrt(f_ao);//0.25 + f_ao * 0.75; ///*pow(f_ao, 0.5)*/f_ao * 0.85 + 0.15;
|
||||
|
||||
vec3 glow = pow(model_light.y, 3) * 4 * GLOW_COLOR;
|
||||
vec3 glow = pow(pow(model_glow.w, 2.0) * (max(dot(f_norm, normalize(model_glow.xyz)), 0.0) * 1.0 + max(1.0 - length(model_glow.xyz), 0.0)), 1) * 4 * GLOW_COLOR;
|
||||
emitted_light += glow;
|
||||
|
||||
reflected_light *= ao;
|
||||
|
@ -28,6 +28,7 @@ uniform u_locals {
|
||||
mat4 model_mat;
|
||||
vec4 highlight_col;
|
||||
vec4 model_light;
|
||||
vec4 model_glow;
|
||||
ivec4 atlas_offs;
|
||||
vec3 model_pos;
|
||||
// bit 0 - is player
|
||||
|
@ -40,6 +40,7 @@ uniform u_locals {
|
||||
mat4 model_mat;
|
||||
vec4 highlight_col;
|
||||
vec4 model_light;
|
||||
vec4 model_glow;
|
||||
ivec4 atlas_offs;
|
||||
vec3 model_pos;
|
||||
// bit 0 - is player
|
||||
|
@ -26,6 +26,7 @@ uniform u_locals {
|
||||
mat4 model_mat;
|
||||
vec4 highlight_col;
|
||||
vec4 model_light;
|
||||
vec4 model_glow;
|
||||
ivec4 atlas_offs;
|
||||
vec3 model_pos;
|
||||
int flags;
|
||||
|
@ -266,7 +266,7 @@ void main() {
|
||||
max_light *= f_light;
|
||||
|
||||
// TODO: Apply AO after this
|
||||
vec3 glow = GLOW_COLOR * (pow(f_glow, 6) * 8 + pow(f_glow, 2) * 0.5);
|
||||
vec3 glow = GLOW_COLOR * (pow(f_glow, 6) * 8 + pow(f_glow, 1.5) * 1.0);
|
||||
emitted_light += glow;
|
||||
reflected_light += glow;
|
||||
|
||||
|
@ -30,8 +30,8 @@ enum FaceKind {
|
||||
Fluid,
|
||||
}
|
||||
|
||||
const SUNLIGHT: u8 = 24;
|
||||
const MAX_LIGHT_DIST: i32 = SUNLIGHT as i32;
|
||||
pub const SUNLIGHT: u8 = 24;
|
||||
pub const MAX_LIGHT_DIST: i32 = SUNLIGHT as i32;
|
||||
|
||||
fn calc_light<V: RectRasterableVol<Vox = Block> + ReadVol + Debug>(
|
||||
is_sunlight: bool,
|
||||
|
@ -14,6 +14,7 @@ gfx_defines! {
|
||||
model_mat: [[f32; 4]; 4] = "model_mat",
|
||||
highlight_col: [f32; 4] = "highlight_col",
|
||||
model_light: [f32; 4] = "model_light",
|
||||
model_glow: [f32; 4] = "model_glow",
|
||||
atlas_offs: [i32; 4] = "atlas_offs",
|
||||
model_pos: [f32; 3] = "model_pos",
|
||||
flags: u32 = "flags",
|
||||
@ -60,7 +61,7 @@ impl Locals {
|
||||
atlas_offs: Vec2<i32>,
|
||||
is_player: bool,
|
||||
light: f32,
|
||||
glow: f32,
|
||||
glow: (Vec3<f32>, f32),
|
||||
) -> Self {
|
||||
let mut flags = 0;
|
||||
flags |= is_player as u32;
|
||||
@ -70,7 +71,8 @@ impl Locals {
|
||||
highlight_col: [col.r, col.g, col.b, 1.0],
|
||||
model_pos: pos.into_array(),
|
||||
atlas_offs: Vec4::from(atlas_offs).into_array(),
|
||||
model_light: [light, glow, 1.0, 1.0],
|
||||
model_light: [light, 1.0, 1.0, 1.0],
|
||||
model_glow: [glow.0.x, glow.0.y, glow.0.z, glow.1],
|
||||
flags,
|
||||
}
|
||||
}
|
||||
@ -85,7 +87,7 @@ impl Default for Locals {
|
||||
Vec2::default(),
|
||||
false,
|
||||
1.0,
|
||||
0.0,
|
||||
(Vec3::zero(), 0.0),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -4602,7 +4602,7 @@ pub struct FigureStateMeta {
|
||||
last_pos: Option<anim::vek::Vec3<f32>>,
|
||||
avg_vel: anim::vek::Vec3<f32>,
|
||||
last_light: f32,
|
||||
last_glow: f32,
|
||||
last_glow: (Vec3<f32>, f32),
|
||||
acc_vel: f32,
|
||||
}
|
||||
|
||||
@ -4649,7 +4649,7 @@ impl<S: Skeleton> FigureState<S> {
|
||||
last_pos: None,
|
||||
avg_vel: anim::vek::Vec3::zero(),
|
||||
last_light: 1.0,
|
||||
last_glow: 0.0,
|
||||
last_glow: (Vec3::zero(), 0.0),
|
||||
acc_vel: 0.0,
|
||||
},
|
||||
skeleton,
|
||||
@ -4743,14 +4743,15 @@ impl<S: Skeleton> FigureState<S> {
|
||||
let s = Lerp::lerp(s_10, s_11, (wpos.x.fract() - 0.5).abs() * 2.0);
|
||||
*/
|
||||
|
||||
Vec2::new(t.light_at_wpos(wposi), t.glow_at_wpos(wposi)).into_tuple()
|
||||
(t.light_at_wpos(wposi), t.glow_normal_at_wpos(wpos))
|
||||
})
|
||||
.unwrap_or((1.0, 0.0));
|
||||
.unwrap_or((1.0, (Vec3::zero(), 0.0)));
|
||||
// Fade between light and glow levels
|
||||
// TODO: Making this temporal rather than spatial is a bit dumb but it's a very
|
||||
// subtle difference
|
||||
self.last_light = vek::Lerp::lerp(self.last_light, light, 16.0 * dt);
|
||||
self.last_glow = vek::Lerp::lerp(self.last_glow, glow, 16.0 * dt);
|
||||
self.last_glow.0 = vek::Lerp::lerp(self.last_glow.0, glow.0, 16.0 * dt);
|
||||
self.last_glow.1 = vek::Lerp::lerp(self.last_glow.1, glow.1, 16.0 * dt);
|
||||
|
||||
let locals = FigureLocals::new(
|
||||
mat,
|
||||
|
@ -3,7 +3,7 @@ mod watcher;
|
||||
pub use self::watcher::BlocksOfInterest;
|
||||
|
||||
use crate::{
|
||||
mesh::{greedy::GreedyMesh, Meshable},
|
||||
mesh::{greedy::GreedyMesh, Meshable, terrain::SUNLIGHT},
|
||||
render::{
|
||||
ColLightFmt, ColLightInfo, Consts, FluidPipeline, GlobalModel, Instances, Mesh, Model,
|
||||
RenderError, Renderer, ShadowPipeline, SpriteInstance, SpriteLocals, SpritePipeline,
|
||||
@ -508,6 +508,38 @@ impl<V: RectRasterableVol> Terrain<V> {
|
||||
.unwrap_or(0.0)
|
||||
}
|
||||
|
||||
pub fn glow_normal_at_wpos(&self, wpos: Vec3<f32>) -> (Vec3<f32>, f32) {
|
||||
let wpos_chunk = wpos.xy().map2(TerrainChunk::RECT_SIZE, |e: f32, sz| {
|
||||
(e as i32).div_euclid(sz as i32)
|
||||
});
|
||||
|
||||
const AMBIANCE: f32 = 0.2; // 0-1, the proportion of light that should illuminate the rear of an object
|
||||
|
||||
let (bias, total, max) = Spiral2d::new()
|
||||
.take(9)
|
||||
.map(|rpos| {
|
||||
let chunk_pos = wpos_chunk + rpos;
|
||||
self.chunks
|
||||
.get(&chunk_pos)
|
||||
.map(|c| c.blocks_of_interest.lights.iter())
|
||||
.into_iter()
|
||||
.flatten()
|
||||
.map(move |(lpos, level)| (Vec3::<i32>::from(chunk_pos * TerrainChunk::RECT_SIZE.map(|e| e as i32)) + *lpos, level))
|
||||
})
|
||||
.flatten()
|
||||
.fold((Vec3::broadcast(0.001), 0.0, 0.0f32), |(bias, total, max), (lpos, level)| {
|
||||
let rpos = lpos.map(|e| e as f32 + 0.5) - wpos;
|
||||
let level = (*level as f32 - rpos.magnitude()).max(0.0) / SUNLIGHT as f32;
|
||||
(
|
||||
bias + rpos.try_normalized().unwrap_or_else(Vec3::zero) * level * (1.0 - AMBIANCE),
|
||||
total + level,
|
||||
max.max(level),
|
||||
)
|
||||
});
|
||||
|
||||
(bias.try_normalized().unwrap_or_else(Vec3::zero) / total.max(0.001), self.glow_at_wpos(wpos.map(|e| e.floor() as i32)))
|
||||
}
|
||||
|
||||
/// Maintain terrain data. To be called once per tick.
|
||||
#[allow(clippy::for_loops_over_fallibles)] // TODO: Pending review in #587
|
||||
#[allow(clippy::len_zero)] // TODO: Pending review in #587
|
||||
|
Loading…
Reference in New Issue
Block a user