From abbb76ab19f2d339885d85951852f3a4e07bf8b6 Mon Sep 17 00:00:00 2001 From: suprohub <125716028+suprohub@users.noreply.github.com> Date: Tue, 29 Oct 2024 10:14:57 +0300 Subject: [PATCH] Chunk optimization: remove subarray (#209) * Removed array helper * Removed array helper 2 * Add functions in ChunkBlocks * cargo fmt * clippy fix --- .../src/client/play/c_chunk_data.rs | 33 ++++++++----------- pumpkin-world/src/chunk/mod.rs | 12 +++++++ 2 files changed, 25 insertions(+), 20 deletions(-) diff --git a/pumpkin-protocol/src/client/play/c_chunk_data.rs b/pumpkin-protocol/src/client/play/c_chunk_data.rs index b1e373e01..36d4c57fe 100644 --- a/pumpkin-protocol/src/client/play/c_chunk_data.rs +++ b/pumpkin-protocol/src/client/play/c_chunk_data.rs @@ -49,7 +49,6 @@ impl<'a> ClientPacket for CChunkData<'a> { // PaletteType::Direct }; - let mut block_data_array = Vec::new(); match palette_type { PaletteType::Indirect(block_size) => { // Bits per entry @@ -62,6 +61,10 @@ impl<'a> ClientPacket for CChunkData<'a> { // Palette data_buf.put_var_int(&VarInt(id.get_id_mojang_repr())); }); + // Data array length + data_buf.put_var_int(&VarInt( + chunk.len().div_ceil(64 / block_size as usize) as i32 + )); for block_clump in chunk.chunks(64 / block_size as usize) { let mut out_long: i64 = 0; for block in block_clump.iter().rev() { @@ -70,12 +73,16 @@ impl<'a> ClientPacket for CChunkData<'a> { .expect("Its just got added, ofc it should be there"); out_long = out_long << block_size | (*index as i64); } - block_data_array.push(out_long); + data_buf.put_i64(out_long); } } PaletteType::Direct => { // Bits per entry data_buf.put_u8(DIRECT_PALETTE_BITS as u8); + // Data array length + data_buf.put_var_int(&VarInt( + chunk.len().div_ceil(64 / DIRECT_PALETTE_BITS as usize) as i32, + )); for block_clump in chunk.chunks(64 / DIRECT_PALETTE_BITS as usize) { let mut out_long: i64 = 0; let mut shift = 0; @@ -83,19 +90,11 @@ impl<'a> ClientPacket for CChunkData<'a> { out_long |= (block.get_id() as i64) << shift; shift += DIRECT_PALETTE_BITS; } - block_data_array.push(out_long); + data_buf.put_i64(out_long); } } } - // Data array length - // TODO: precompute this and omit making the `block_data_array` - data_buf.put_var_int(&VarInt(block_data_array.len() as i32)); - // Data array - for data_int in block_data_array { - data_buf.put_i64(data_int); - } - //// Biomes // TODO: make biomes work data_buf.put_u8(0); @@ -122,8 +121,7 @@ impl<'a> ClientPacket for CChunkData<'a> { // Empty Block Light Mask buf.put_bit_set(&BitSet(VarInt(1), &[0])); - let mut lighting_subchunks = Vec::new(); - + buf.put_var_int(&VarInt(self.0.blocks.subchunks_len() as i32)); self.0.blocks.iter_subchunks().for_each(|chunk| { let mut chunk_light = [0u8; 2048]; for (i, block) in chunk.iter().enumerate() { @@ -135,15 +133,10 @@ impl<'a> ClientPacket for CChunkData<'a> { chunk_light[index] |= mask; } - lighting_subchunks.push(chunk_light); + buf.put_var_int(&VarInt(chunk_light.len() as i32)); + buf.put_slice(&chunk_light); }); - buf.put_var_int(&lighting_subchunks.len().into()); - for subchunk in lighting_subchunks { - buf.put_var_int(&VarInt(subchunk.len() as i32)); - buf.put_slice(&subchunk); - } - // Block Lighting buf.put_var_int(&VarInt(0)); } diff --git a/pumpkin-world/src/chunk/mod.rs b/pumpkin-world/src/chunk/mod.rs index 1f3c5edbd..fdcf55a98 100644 --- a/pumpkin-world/src/chunk/mod.rs +++ b/pumpkin-world/src/chunk/mod.rs @@ -159,6 +159,18 @@ impl Default for ChunkBlocks { } impl ChunkBlocks { + pub const fn len(&self) -> usize { + self.blocks.len() + } + + pub const fn is_empty(&self) -> bool { + self.blocks.is_empty() + } + + pub const fn subchunks_len(&self) -> usize { + self.blocks.len().div_ceil(SUBCHUNK_VOLUME) + } + pub fn empty_with_heightmap(heightmap: ChunkHeightmaps) -> Self { Self { blocks: Box::new([BlockId::default(); CHUNK_VOLUME]),