From eaf5959f2bcd3128062f678a233e90ae81d208af Mon Sep 17 00:00:00 2001 From: Alexander Medvedev Date: Mon, 28 Jul 2025 12:18:54 +0200 Subject: [PATCH] Minor Chunk gen speed gains --- README.md | 2 +- pumpkin-world/src/chunk/mod.rs | 27 +++++++------ pumpkin-world/src/chunk/palette.rs | 15 +++++--- .../src/generation/implementation/mod.rs | 38 ++++++++++++------- pumpkin-world/src/level.rs | 16 ++------ pumpkin/src/world/mod.rs | 22 +++-------- 6 files changed, 60 insertions(+), 60 deletions(-) diff --git a/README.md b/README.md index 38af598be..f46650c36 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,7 @@ ![CI](https://github.com/Snowiiii/Pumpkin/actions/workflows/rust.yml/badge.svg) [![Discord](https://img.shields.io/discord/1268592337445978193.svg?label=&logo=discord&logoColor=ffffff&color=7389D8&labelColor=6A7EC2)](https://discord.gg/wT8XjrjKkf) [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT) -![Current version)](https://img.shields.io/badge/current_version-1.21.7-blue) +![Current version)](https://img.shields.io/badge/current_version-1.21.8-blue) diff --git a/pumpkin-world/src/chunk/mod.rs b/pumpkin-world/src/chunk/mod.rs index c6f4c0a0a..2389665b8 100644 --- a/pumpkin-world/src/chunk/mod.rs +++ b/pumpkin-world/src/chunk/mod.rs @@ -94,7 +94,7 @@ pub struct ChunkEntityData { #[derive(Debug, Clone)] pub struct ChunkSections { pub sections: Box<[SubChunk]>, - min_y: i32, + pub min_y: i32, } impl ChunkSections { @@ -179,18 +179,19 @@ impl ChunkSections { } } + /// Returns the replaced block state ID pub fn set_block_absolute_y( &mut self, relative_x: usize, y: i32, relative_z: usize, block_state: BlockStateId, - ) { + ) -> BlockStateId { let y = y - self.min_y; debug_assert!(y >= 0); let relative_y = y as usize; - self.set_relative_block(relative_x, relative_y, relative_z, block_state); + self.set_relative_block(relative_x, relative_y, relative_z, block_state) } /// Gets the given block in the chunk @@ -210,7 +211,7 @@ impl ChunkSections { .map(|section| section.block_states.get(relative_x, relative_y, relative_z)) } - /// Sets the given block in the chunk, returning the old block + /// Sets the given block in the chunk, returning the old block state ID #[inline] pub fn set_relative_block( &mut self, @@ -218,9 +219,9 @@ impl ChunkSections { relative_y: usize, relative_z: usize, block_state_id: BlockStateId, - ) { + ) -> BlockStateId { // TODO @LUK_ESC? update the heightmap - self.set_block_no_heightmap_update(relative_x, relative_y, relative_z, block_state_id); + self.set_block_no_heightmap_update(relative_x, relative_y, relative_z, block_state_id) } /// Sets the given block in the chunk, returning the old block @@ -234,20 +235,20 @@ impl ChunkSections { relative_y: usize, relative_z: usize, block_state_id: BlockStateId, - ) { + ) -> BlockStateId { debug_assert!(relative_x < BlockPalette::SIZE); debug_assert!(relative_z < BlockPalette::SIZE); let section_index = relative_y / BlockPalette::SIZE; let relative_y = relative_y % BlockPalette::SIZE; if let Some(section) = self.sections.get_mut(section_index) { - section + return section .block_states .set(relative_x, relative_y, relative_z, block_state_id); } + 0 } - /// Sets the given block in the chunk, returning the old block pub fn set_relative_biome( &mut self, relative_x: usize, @@ -260,9 +261,11 @@ impl ChunkSections { let section_index = relative_y / BiomePalette::SIZE; let relative_y = relative_y % BiomePalette::SIZE; - self.sections[section_index] - .biomes - .set(relative_x, relative_y, relative_z, biome_id); + if let Some(section) = self.sections.get_mut(section_index) { + section + .biomes + .set(relative_x, relative_y, relative_z, biome_id); + } } } diff --git a/pumpkin-world/src/chunk/palette.rs b/pumpkin-world/src/chunk/palette.rs index dcf421571..ca904daee 100644 --- a/pumpkin-world/src/chunk/palette.rs +++ b/pumpkin-world/src/chunk/palette.rs @@ -29,7 +29,8 @@ impl HeterogeneousPaletteData { self.cube[y][z][x] } - fn set(&mut self, x: usize, y: usize, z: usize, value: V) { + /// Returns the Original + fn set(&mut self, x: usize, y: usize, z: usize, value: V) -> V { debug_assert!(x < DIM); debug_assert!(y < DIM); debug_assert!(z < DIM); @@ -48,6 +49,7 @@ impl HeterogeneousPaletteData { .entry(value) .and_modify(|count| *count += 1) .or_insert(1); + original } } @@ -191,24 +193,27 @@ impl PalettedContainer } } - pub fn set(&mut self, x: usize, y: usize, z: usize, value: V) { + pub fn set(&mut self, x: usize, y: usize, z: usize, value: V) -> V { debug_assert!(x < Self::SIZE); debug_assert!(y < Self::SIZE); debug_assert!(z < Self::SIZE); match self { Self::Homogeneous(original) => { - if value != *original { - let mut cube = Box::new([[[*original; DIM]; DIM]; DIM]); + let original = *original; + if value != original { + let mut cube = Box::new([[[original; DIM]; DIM]; DIM]); cube[y][z][x] = value; *self = Self::from_cube(cube); } + original } Self::Heterogeneous(data) => { - data.set(x, y, z, value); + let original = data.set(x, y, z, value); if data.counts.len() == 1 { *self = Self::Homogeneous(*data.counts.keys().next().unwrap()); } + original } } } diff --git a/pumpkin-world/src/generation/implementation/mod.rs b/pumpkin-world/src/generation/implementation/mod.rs index e3c5b428e..1c9977e3f 100644 --- a/pumpkin-world/src/generation/implementation/mod.rs +++ b/pumpkin-world/src/generation/implementation/mod.rs @@ -90,24 +90,34 @@ impl WorldGenerator for VanillaGenerator { proto_chunk.generate_features(level, block_registry); for y in 0..biome_coords::from_block(generation_settings.shape.height) { - for z in 0..BiomePalette::SIZE { - for x in 0..BiomePalette::SIZE { - let absolute_y = - biome_coords::from_block(generation_settings.shape.min_y as i32) + y as i32; - let biome = - proto_chunk.get_biome(&Vector3::new(x as i32, absolute_y, z as i32)); - sections.set_relative_biome(x, y as usize, z, biome.id); + let relative_y = y as usize; + let section_index = relative_y / BiomePalette::SIZE; + let relative_y = relative_y % BiomePalette::SIZE; + if let Some(section) = sections.sections.get_mut(section_index) { + for z in 0..BiomePalette::SIZE { + for x in 0..BiomePalette::SIZE { + let absolute_y = + biome_coords::from_block(generation_settings.shape.min_y as i32) + + y as i32; + let biome = + proto_chunk.get_biome(&Vector3::new(x as i32, absolute_y, z as i32)); + section.biomes.set(x, relative_y, z, biome.id); + } } } } - for y in 0..generation_settings.shape.height { - for z in 0..BlockPalette::SIZE { - for x in 0..BlockPalette::SIZE { - let absolute_y = generation_settings.shape.min_y as i32 + y as i32; - let block = - proto_chunk.get_block_state(&Vector3::new(x as i32, absolute_y, z as i32)); - sections.set_relative_block(x, y as usize, z, block.0); + let relative_y = (y as i32 - sections.min_y) as usize; + let section_index = relative_y / BlockPalette::SIZE; + let relative_y = relative_y % BlockPalette::SIZE; + if let Some(section) = sections.sections.get_mut(section_index) { + for z in 0..BlockPalette::SIZE { + for x in 0..BlockPalette::SIZE { + let absolute_y = generation_settings.shape.min_y as i32 + y as i32; + let block = proto_chunk + .get_block_state(&Vector3::new(x as i32, absolute_y, z as i32)); + section.block_states.set(x, relative_y, z, block.0); + } } } } diff --git a/pumpkin-world/src/level.rs b/pumpkin-world/src/level.rs index ea354aa68..8156423f7 100644 --- a/pumpkin-world/src/level.rs +++ b/pumpkin-world/src/level.rs @@ -621,23 +621,15 @@ impl Level { let chunk = self.get_chunk(chunk_coordinate).await; let mut chunk = chunk.write().await; - let replaced_block_state_id = chunk - .section - .get_block_absolute_y(relative.x as usize, relative.y, relative.z as usize) - .unwrap(); - - if replaced_block_state_id == block_state_id { - return block_state_id; - } - - chunk.mark_dirty(true); - - chunk.section.set_block_absolute_y( + let replaced_block_state_id = chunk.section.set_block_absolute_y( relative.x as usize, relative.y, relative.z as usize, block_state_id, ); + if replaced_block_state_id != block_state_id { + chunk.mark_dirty(true); + } replaced_block_state_id } diff --git a/pumpkin/src/world/mod.rs b/pumpkin/src/world/mod.rs index 676c3d3fa..4d673a66f 100644 --- a/pumpkin/src/world/mod.rs +++ b/pumpkin/src/world/mod.rs @@ -1836,7 +1836,6 @@ impl World { } /// Sets a block and returns the old block id - #[expect(clippy::too_many_lines)] pub async fn set_block_state( self: &Arc, position: &BlockPos, @@ -1850,26 +1849,17 @@ impl World { else { panic!("Timed out while waiting to acquire chunk write lock") }; - let Some(replaced_block_state_id) = chunk.section.get_block_absolute_y( - relative.x as usize, - relative.y, - relative.z as usize, - ) else { - return block_state_id; - }; - - if replaced_block_state_id == block_state_id { - return block_state_id; - } - - chunk.mark_dirty(true); - - chunk.section.set_block_absolute_y( + let replaced_block_state_id = chunk.section.set_block_absolute_y( relative.x as usize, relative.y, relative.z as usize, block_state_id, ); + if replaced_block_state_id == block_state_id { + return block_state_id; + } + chunk.mark_dirty(true); + self.unsent_block_changes .lock() .await