Added LoD slider

This commit is contained in:
Joshua Barretto 2020-02-24 15:14:06 +00:00
parent 779c36b538
commit aab059a450
7 changed files with 102 additions and 20 deletions

View File

@ -3,7 +3,7 @@
uniform sampler2D t_map; uniform sampler2D t_map;
vec2 pos_to_uv(vec2 pos) { vec2 pos_to_uv(vec2 pos) {
vec2 uv_pos = pos / 32768.0; vec2 uv_pos = (pos + 16) / 32768.0;
return vec2(uv_pos.x, 1.0 - uv_pos.y); return vec2(uv_pos.x, 1.0 - uv_pos.y);
} }

View File

@ -196,6 +196,7 @@ pub enum Event {
ToggleZoomInvert(bool), ToggleZoomInvert(bool),
ToggleMouseYInvert(bool), ToggleMouseYInvert(bool),
AdjustViewDistance(u32), AdjustViewDistance(u32),
AdjustLodDetail(u32),
AdjustMusicVolume(f32), AdjustMusicVolume(f32),
AdjustSfxVolume(f32), AdjustSfxVolume(f32),
ChangeAudioDevice(String), ChangeAudioDevice(String),
@ -1744,6 +1745,9 @@ impl Hud {
settings_window::Event::AdjustViewDistance(view_distance) => { settings_window::Event::AdjustViewDistance(view_distance) => {
events.push(Event::AdjustViewDistance(view_distance)); events.push(Event::AdjustViewDistance(view_distance));
}, },
settings_window::Event::AdjustLodDetail(lod_detail) => {
events.push(Event::AdjustLodDetail(lod_detail));
},
settings_window::Event::CrosshairTransp(crosshair_transp) => { settings_window::Event::CrosshairTransp(crosshair_transp) => {
events.push(Event::CrosshairTransp(crosshair_transp)); events.push(Event::CrosshairTransp(crosshair_transp));
}, },

View File

@ -83,6 +83,9 @@ widget_ids! {
vd_slider, vd_slider,
vd_text, vd_text,
vd_value, vd_value,
lod_detail_slider,
lod_detail_text,
lod_detail_value,
max_fps_slider, max_fps_slider,
max_fps_text, max_fps_text,
max_fps_value, max_fps_value,
@ -202,6 +205,7 @@ pub enum Event {
ToggleMouseYInvert(bool), ToggleMouseYInvert(bool),
AdjustViewDistance(u32), AdjustViewDistance(u32),
AdjustFOV(u16), AdjustFOV(u16),
AdjustLodDetail(u32),
AdjustGamma(f32), AdjustGamma(f32),
AdjustWindowSize([u16; 2]), AdjustWindowSize([u16; 2]),
ToggleFullscreen, ToggleFullscreen,
@ -1558,9 +1562,44 @@ impl<'a> Widget for SettingsWindow<'a> {
.color(TEXT_COLOR) .color(TEXT_COLOR)
.set(state.ids.fov_value, ui); .set(state.ids.fov_value, ui);
// LoD detail
Text::new(&self.localized_strings.get("hud.settings.lod_detail"))
.down_from(state.ids.fov_slider, 10.0)
.font_size(self.fonts.cyri.scale(14))
.font_id(self.fonts.cyri.conrod_id)
.color(TEXT_COLOR)
.set(state.ids.lod_detail_text, ui);
if let Some(new_val) = ImageSlider::discrete(
self.global_state.settings.graphics.lod_detail,
100,
2000,
self.imgs.slider_indicator,
self.imgs.slider,
)
.w_h(104.0, 22.0)
.down_from(state.ids.lod_detail_text, 8.0)
.track_breadth(12.0)
.slider_length(10.0)
.pad_track((5.0, 5.0))
.set(state.ids.lod_detail_slider, ui)
{
events.push(Event::AdjustLodDetail(new_val as u32));
}
Text::new(&format!(
"{}",
self.global_state.settings.graphics.lod_detail
))
.right_from(state.ids.lod_detail_slider, 8.0)
.font_size(self.fonts.cyri.scale(14))
.font_id(self.fonts.cyri.conrod_id)
.color(TEXT_COLOR)
.set(state.ids.lod_detail_value, ui);
// Gamma // Gamma
Text::new(&self.localized_strings.get("hud.settings.gamma")) Text::new(&self.localized_strings.get("hud.settings.gamma"))
.down_from(state.ids.fov_slider, 10.0) .down_from(state.ids.lod_detail_slider, 10.0)
.font_size(self.fonts.cyri.scale(14)) .font_size(self.fonts.cyri.scale(14))
.font_id(self.fonts.cyri.conrod_id) .font_id(self.fonts.cyri.conrod_id)
.color(TEXT_COLOR) .color(TEXT_COLOR)

View File

@ -1,38 +1,61 @@
use crate::render::{ use crate::{
render::{
pipelines::lod_terrain::{Locals, Vertex}, pipelines::lod_terrain::{Locals, Vertex},
Consts, FilterMethod, Globals, LodTerrainPipeline, Mesh, Model, Quad, Renderer, Texture, Consts, FilterMethod, Globals, LodTerrainPipeline, Mesh, Model, Quad, Renderer, Texture,
},
settings::Settings,
}; };
use client::Client; use client::Client;
use common::spiral::Spiral2d; use common::spiral::Spiral2d;
use vek::*; use vek::*;
pub struct Lod { pub struct Lod {
model: Model<LodTerrainPipeline>, model: Option<(u32, Model<LodTerrainPipeline>)>,
locals: Consts<Locals>, locals: Consts<Locals>,
map: Texture, map: Texture,
tgt_detail: u32,
} }
impl Lod { impl Lod {
pub fn new(renderer: &mut Renderer, client: &Client) -> Self { pub fn new(renderer: &mut Renderer, client: &Client, settings: &Settings) -> Self {
Self { Self {
model: renderer model: None,
.create_model(&create_lod_terrain_mesh(500))
.unwrap(),
locals: renderer.create_consts(&[Locals::default()]).unwrap(), locals: renderer.create_consts(&[Locals::default()]).unwrap(),
map: renderer map: renderer
.create_texture(&client.world_map.0, Some(FilterMethod::Trilinear), None) .create_texture(&client.world_map.0, Some(FilterMethod::Trilinear), None)
.expect("Failed to generate map texture"), .expect("Failed to generate map texture"),
tgt_detail: settings.graphics.lod_detail,
}
}
pub fn set_detail(&mut self, detail: u32) { self.tgt_detail = detail.max(100).min(2000); }
pub fn maintain(&mut self, renderer: &mut Renderer) {
if self
.model
.as_ref()
.map(|(detail, _)| *detail != self.tgt_detail)
.unwrap_or(true)
{
self.model = Some((
self.tgt_detail,
renderer
.create_model(&create_lod_terrain_mesh(self.tgt_detail))
.unwrap(),
));
} }
} }
pub fn render(&self, renderer: &mut Renderer, globals: &Consts<Globals>) { pub fn render(&self, renderer: &mut Renderer, globals: &Consts<Globals>) {
renderer.render_lod_terrain(&self.model, globals, &self.locals, &self.map); if let Some((_, model)) = self.model.as_ref() {
renderer.render_lod_terrain(&model, globals, &self.locals, &self.map);
}
} }
} }
fn create_lod_terrain_mesh(detail: usize) -> Mesh<LodTerrainPipeline> { fn create_lod_terrain_mesh(detail: u32) -> Mesh<LodTerrainPipeline> {
Spiral2d::new() Spiral2d::new()
.take(detail * detail) .take((detail * detail) as usize)
.map(|pos| { .map(|pos| {
let x = pos.x + detail as i32 / 2; let x = pos.x + detail as i32 / 2;
let y = pos.y + detail as i32 / 2; let y = pos.y + detail as i32 / 2;

View File

@ -17,6 +17,7 @@ use crate::{
create_pp_mesh, create_skybox_mesh, Consts, Globals, Light, Model, PostProcessLocals, create_pp_mesh, create_skybox_mesh, Consts, Globals, Light, Model, PostProcessLocals,
PostProcessPipeline, Renderer, Shadow, SkyboxLocals, SkyboxPipeline, PostProcessPipeline, Renderer, Shadow, SkyboxLocals, SkyboxPipeline,
}, },
settings::Settings,
window::Event, window::Event,
}; };
use client::Client; use client::Client;
@ -56,7 +57,7 @@ pub struct Scene {
skybox: Skybox, skybox: Skybox,
postprocess: PostProcess, postprocess: PostProcess,
terrain: Terrain<TerrainChunk>, terrain: Terrain<TerrainChunk>,
lod: Lod, pub lod: Lod,
loaded_distance: f32, loaded_distance: f32,
select_pos: Option<Vec3<i32>>, select_pos: Option<Vec3<i32>>,
@ -67,7 +68,7 @@ pub struct Scene {
impl Scene { impl Scene {
/// Create a new `Scene` with default parameters. /// Create a new `Scene` with default parameters.
pub fn new(renderer: &mut Renderer, client: &Client) -> Self { pub fn new(renderer: &mut Renderer, client: &Client, settings: &Settings) -> Self {
let resolution = renderer.get_resolution().map(|e| e as f32); let resolution = renderer.get_resolution().map(|e| e as f32);
Self { Self {
@ -91,7 +92,7 @@ impl Scene {
.unwrap(), .unwrap(),
}, },
terrain: Terrain::new(renderer), terrain: Terrain::new(renderer),
lod: Lod::new(renderer, client), lod: Lod::new(renderer, client, settings),
loaded_distance: 0.0, loaded_distance: 0.0,
select_pos: None, select_pos: None,
@ -153,7 +154,7 @@ impl Scene {
renderer: &mut Renderer, renderer: &mut Renderer,
audio: &mut AudioFrontend, audio: &mut AudioFrontend,
client: &Client, client: &Client,
gamma: f32, settings: &Settings,
) { ) {
// Get player position. // Get player position.
let player_pos = client let player_pos = client
@ -301,10 +302,13 @@ impl Scene {
.map(|b| b.kind()) .map(|b| b.kind())
.unwrap_or(BlockKind::Air), .unwrap_or(BlockKind::Air),
self.select_pos, self.select_pos,
gamma, settings.graphics.gamma,
)]) )])
.expect("Failed to update global constants"); .expect("Failed to update global constants");
// Maintain LoD.
self.lod.maintain(renderer);
// Maintain the terrain. // Maintain the terrain.
self.terrain.maintain( self.terrain.maintain(
renderer, renderer,

View File

@ -39,7 +39,11 @@ impl SessionState {
pub fn new(global_state: &mut GlobalState, client: Rc<RefCell<Client>>) -> Self { pub fn new(global_state: &mut GlobalState, client: Rc<RefCell<Client>>) -> Self {
// Create a scene for this session. The scene handles visible elements of the // Create a scene for this session. The scene handles visible elements of the
// game world. // game world.
let mut scene = Scene::new(global_state.window.renderer_mut(), &*client.borrow()); let mut scene = Scene::new(
global_state.window.renderer_mut(),
&*client.borrow(),
&global_state.settings,
);
scene scene
.camera_mut() .camera_mut()
.set_fov_deg(global_state.settings.graphics.fov); .set_fov_deg(global_state.settings.graphics.fov);
@ -484,6 +488,12 @@ impl PlayState for SessionState {
global_state.settings.graphics.view_distance = view_distance; global_state.settings.graphics.view_distance = view_distance;
global_state.settings.save_to_file_warn(); global_state.settings.save_to_file_warn();
}, },
HudEvent::AdjustLodDetail(lod_detail) => {
self.scene.lod.set_detail(lod_detail);
global_state.settings.graphics.lod_detail = lod_detail;
global_state.settings.save_to_file_warn();
},
HudEvent::CrosshairTransp(crosshair_transp) => { HudEvent::CrosshairTransp(crosshair_transp) => {
global_state.settings.gameplay.crosshair_transp = crosshair_transp; global_state.settings.gameplay.crosshair_transp = crosshair_transp;
global_state.settings.save_to_file_warn(); global_state.settings.save_to_file_warn();
@ -614,7 +624,7 @@ impl PlayState for SessionState {
global_state.window.renderer_mut(), global_state.window.renderer_mut(),
&mut global_state.audio, &mut global_state.audio,
&self.client.borrow(), &self.client.borrow(),
global_state.settings.graphics.gamma, &global_state.settings,
); );
// Render the session. // Render the session.

View File

@ -197,6 +197,7 @@ pub struct GraphicsSettings {
pub fluid_mode: FluidMode, pub fluid_mode: FluidMode,
pub window_size: [u16; 2], pub window_size: [u16; 2],
pub fullscreen: bool, pub fullscreen: bool,
pub lod_detail: u32,
} }
impl Default for GraphicsSettings { impl Default for GraphicsSettings {
@ -211,6 +212,7 @@ impl Default for GraphicsSettings {
fluid_mode: FluidMode::Shiny, fluid_mode: FluidMode::Shiny,
window_size: [1920, 1080], window_size: [1920, 1080],
fullscreen: false, fullscreen: false,
lod_detail: 500,
} }
} }
} }