Use new world generator

This commit is contained in:
Jarrod Doyle 2023-05-09 17:33:46 +01:00
parent 8a3b0ed4ea
commit 7e6746a8cd
Signed by: Jayrude
GPG Key ID: 38B57B16E7C0ADF7
3 changed files with 58 additions and 62 deletions

View File

@ -68,6 +68,14 @@ impl App {
0.25, 0.25,
); );
let mut world = voxel::world::WorldManager::new(voxel::world::GenerationSettings {
seed: 0,
frequency: 0.04,
octaves: 3,
gain: 0.5,
lacunarity: 2.0,
});
let mut renderer = voxel::VoxelRenderer::new(&self.render_ctx, &camera_controller); let mut renderer = voxel::VoxelRenderer::new(&self.render_ctx, &camera_controller);
let mut cumulative_dt = 0.0; let mut cumulative_dt = 0.0;
@ -95,6 +103,7 @@ impl App {
camera_controller.update_buffer(&self.render_ctx); camera_controller.update_buffer(&self.render_ctx);
renderer.render(&self.render_ctx); renderer.render(&self.render_ctx);
renderer.update(&dt, &self.render_ctx); renderer.update(&dt, &self.render_ctx);
renderer.update_brickmap(&self.render_ctx, &mut world);
// Simple framerate tracking // Simple framerate tracking
cumulative_dt += dt.as_secs_f32(); cumulative_dt += dt.as_secs_f32();

View File

@ -36,7 +36,6 @@ pub struct BrickmapManager {
// - GPU side unpack buffer rather than uploading each changed brickmap part // - GPU side unpack buffer rather than uploading each changed brickmap part
// - Cyclic brickmap cache with unloading // - Cyclic brickmap cache with unloading
// - Brickworld system // - Brickworld system
// - Move terrain generation to it's own system
impl BrickmapManager { impl BrickmapManager {
pub fn new(context: &render::Context) -> Self { pub fn new(context: &render::Context) -> Self {
let mut state_uniform = WorldState::default(); let mut state_uniform = WorldState::default();
@ -132,7 +131,11 @@ impl BrickmapManager {
&self.feedback_result_buffer &self.feedback_result_buffer
} }
pub fn process_feedback_buffer(&mut self, context: &render::Context) { pub fn process_feedback_buffer(
&mut self,
context: &render::Context,
world: &mut super::world::WorldManager,
) {
// Get request count // Get request count
let mut slice = self.feedback_result_buffer.slice(0..16); let mut slice = self.feedback_result_buffer.slice(0..16);
slice.map_async(wgpu::MapMode::Read, |_| {}); slice.map_async(wgpu::MapMode::Read, |_| {});
@ -154,47 +157,15 @@ impl BrickmapManager {
// Generate a sphere of voxels // Generate a sphere of voxels
let world_dims = self.state_uniform.brickmap_cache_dims; let world_dims = self.state_uniform.brickmap_cache_dims;
let sphere_center = glam::vec3(3.5, 3.5, 3.5);
let sphere_r2 = u32::pow(4, 2) as f32;
for i in 0..request_count { for i in 0..request_count {
let chunk_x = data[i * 4]; let chunk_x = data[i * 4];
let chunk_y = data[i * 4 + 1]; let chunk_y = data[i * 4 + 1];
let chunk_z = data[i * 4 + 2]; let chunk_z = data[i * 4 + 2];
let noise_vals = simdnoise::NoiseBuilder::fbm_3d_offset( let chunk_pos = glam::ivec3(0, 0, 0);
chunk_x as f32 * 8.0, let block_pos = glam::uvec3(chunk_x, chunk_y, chunk_z);
8, let block = world.get_block(chunk_pos, block_pos);
chunk_y as f32 * 8.0, assert_eq!(block.len(), 512);
8,
chunk_z as f32 * 8.0,
8,
)
.with_seed(0)
.with_freq(0.005)
.with_octaves(3)
.with_gain(0.5)
.with_lacunarity(2.0)
.generate();
// Generate full data
let mut chunk = [(false, 0u32); 512];
for z in 0..8 {
for y in 0..8 {
for x in 0..8 {
let idx = (x + y * 8 + z * 8 * 8) as usize;
let val = noise_vals.0[idx];
if val > 0.0 {
let mut albedo = 0u32;
albedo += ((x + 1) * 32 - 1) << 24;
albedo += ((y + 1) * 32 - 1) << 16;
albedo += ((z + 1) * 32 - 1) << 8;
albedo += 255;
chunk[idx] = (true, albedo);
}
}
}
}
// Cull interior voxels // Cull interior voxels
let mut bitmask_data = [0xFFFFFFFF as u32; 16]; let mut bitmask_data = [0xFFFFFFFF as u32; 16];
@ -206,30 +177,37 @@ impl BrickmapManager {
for x in 0..8 { for x in 0..8 {
// Ignore non-solids // Ignore non-solids
let idx = x + y * 8 + z * 8 * 8; let idx = x + y * 8 + z * 8 * 8;
if !chunk[idx].0 { let empty_voxel = super::world::Voxel::Empty;
continue;
}
// A voxel is on the surface if at least one of it's match block[idx] {
// cardinal neighbours is non-solid. Also for simplicity if super::world::Voxel::Empty => continue,
// it's on the edge of the chunk super::world::Voxel::Color(r, g, b) => {
let surface_voxel: bool; // A voxel is on the surface if at least one of it's
if x == 0 || x == 7 || y == 0 || y == 7 || z == 0 || z == 7 { // cardinal neighbours is non-solid. Also for simplicity
surface_voxel = true; // if it's on the edge of the chunk
} else { let surface_voxel: bool;
surface_voxel = !(chunk[idx + 1].0 if x == 0 || x == 7 || y == 0 || y == 7 || z == 0 || z == 7 {
&& chunk[idx - 1].0 surface_voxel = true;
&& chunk[idx + 8].0 } else {
&& chunk[idx - 8].0 surface_voxel = !(block[idx + 1] == empty_voxel
&& chunk[idx + 64].0 && block[idx - 1] == empty_voxel
&& chunk[idx - 64].0); && block[idx + 8] == empty_voxel
} && block[idx - 8] == empty_voxel
&& block[idx + 64] == empty_voxel
&& block[idx - 64] == empty_voxel);
}
// Set the appropriate bit in the z entry and add the shading // Set the appropriate bit in the z entry and add the
// data // shading data
if surface_voxel { if surface_voxel {
entry += 1 << (x + y * 8); entry += 1 << (x + y * 8);
albedo_data.push(chunk[idx].1); let albedo = ((r as u32) << 24)
+ ((g as u32) << 16)
+ ((b as u32) << 8)
+ 255u32;
albedo_data.push(albedo);
}
}
} }
} }
} }

View File

@ -215,7 +215,16 @@ impl render::Renderer for VoxelRenderer {
frame.present(); frame.present();
} }
fn update(&mut self, dt: &Duration, context: &render::Context) { fn update(&mut self, _dt: &Duration, _context: &render::Context) {}
self.brickmap_manager.process_feedback_buffer(context); }
impl VoxelRenderer {
pub fn update_brickmap(
&mut self,
context: &render::Context,
world: &mut super::world::WorldManager,
) {
self.brickmap_manager
.process_feedback_buffer(context, world);
} }
} }