Skip to content

Commit

Permalink
Dynamic chunk loading
Browse files Browse the repository at this point in the history
  • Loading branch information
Snowiiii committed Sep 1, 2024
1 parent 2085307 commit 5c0dffb
Show file tree
Hide file tree
Showing 33 changed files with 367 additions and 181 deletions.
2 changes: 2 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions pumpkin-core/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
pub mod gamemode;
pub mod math;
pub mod random;
pub mod text;

Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
use pumpkin_protocol::position::WorldPosition;
use pumpkin_world::vector3::Vector3;
use super::{position::WorldPosition, vector3::Vector3};

pub struct BoundingBox {
pub min_x: f64,
Expand Down Expand Up @@ -38,6 +37,6 @@ impl BoundingBox {
let d = f64::max(f64::max(self.min_x - pos.x, pos.x - self.max_x), 0.0);
let e = f64::max(f64::max(self.min_y - pos.y, pos.y - self.max_y), 0.0);
let f = f64::max(f64::max(self.min_z - pos.z, pos.z - self.max_z), 0.0);
super::math::squared_magnitude(d, e, f)
super::squared_magnitude(d, e, f)
}
}
11 changes: 11 additions & 0 deletions pumpkin/src/util/math.rs → pumpkin-core/src/math/mod.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
pub mod boundingbox;
pub mod position;
pub mod vector2;
pub mod vector3;

pub fn wrap_degrees(var: f32) -> f32 {
let mut var1 = var % 360.0;
if var1 >= 180.0 {
Expand All @@ -14,3 +19,9 @@ pub fn wrap_degrees(var: f32) -> f32 {
pub fn squared_magnitude(a: f64, b: f64, c: f64) -> f64 {
a * a + b * b + c * c
}

/// Converts a world coordinate to the corresponding chunk-section coordinate.
// TODO: This proberbly should place not here
pub fn get_section_cord(coord: i32) -> i32 {
coord >> 4
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
use pumpkin_world::vector3::Vector3;
use serde::{Deserialize, Serialize};

use super::vector3::Vector3;

/// Aka Block Position
pub struct WorldPosition(pub Vector3<i32>);

impl Serialize for WorldPosition {
Expand Down
File renamed without changes.
File renamed without changes.
2 changes: 2 additions & 0 deletions pumpkin-entity/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,7 @@ version.workspace = true
edition.workspace = true

[dependencies]
pumpkin-core = { path = "../pumpkin-core"}

num-traits = "0.2"
num-derive = "0.4"
43 changes: 31 additions & 12 deletions pumpkin-entity/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
use entity_type::EntityType;
use pose::EntityPose;
use pumpkin_core::math::{
get_section_cord, position::WorldPosition, vector2::Vector2, vector3::Vector3,
};

pub mod entity_type;
pub mod pose;
Expand All @@ -9,12 +12,10 @@ pub type EntityId = i32;
pub struct Entity {
pub entity_id: EntityId,
pub entity_type: EntityType,
pub x: f64,
pub y: f64,
pub z: f64,
pub lastx: f64,
pub lasty: f64,
pub lastz: f64,
pub pos: Vector3<f64>,
pub block_pos: WorldPosition,
pub chunk_pos: Vector2<i32>,

pub yaw: f32,
pub head_yaw: f32,
pub pitch: f32,
Expand All @@ -28,17 +29,35 @@ impl Entity {
Self {
entity_id,
entity_type,
x: 0.0,
y: 0.0,
z: 0.0,
lastx: 0.0,
lasty: 0.0,
lastz: 0.0,
pos: Vector3::new(0.0, 0.0, 0.0),
block_pos: WorldPosition(Vector3::new(0, 0, 0)),
chunk_pos: Vector2::new(0, 0),
yaw: 0.0,
head_yaw: 0.0,
pitch: 0.0,
standing_eye_height,
pose: EntityPose::Standing,
}
}

pub fn set_pos(&mut self, x: f64, y: f64, z: f64) {
if self.pos.x != x || self.pos.y != y || self.pos.z != z {
self.pos = Vector3::new(x, y, z);
let i = x.floor() as i32;
let j = y.floor() as i32;
let k = z.floor() as i32;

let block_pos = self.block_pos.0;
if i != block_pos.x || j != block_pos.y || k != block_pos.z {
self.block_pos = WorldPosition(Vector3::new(i, j, k));

if get_section_cord(i) != self.chunk_pos.x
|| get_section_cord(k) != self.chunk_pos.z
{
self.chunk_pos =
Vector2::new(get_section_cord(block_pos.x), get_section_cord(block_pos.z));
}
}
}
}
}
22 changes: 10 additions & 12 deletions pumpkin-protocol/src/bytebuf/packet_id.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
use bytes::BufMut;
use serde::{
de::{self, DeserializeOwned, SeqAccess, Visitor},
Deserialize, Deserializer, Serialize, Serializer,
Expand All @@ -22,19 +23,16 @@ impl Serialize for VarInt {
where
S: Serializer,
{
let mut val = self.0;
let mut buf: Vec<u8> = Vec::new();
for _ in 0..5 {
let mut b: u8 = val as u8 & 0b01111111;
val >>= 7;
if val != 0 {
b |= 0b10000000;
}
buf.push(b);
if val == 0 {
break;
}
let mut value = self.0 as u32;
let mut buf = Vec::new();

while value > 0x7F {
buf.put_u8(value as u8 | 0x80);
value >>= 7;
}

buf.put_u8(value as u8);

serializer.serialize_bytes(&buf)
}
}
Expand Down
3 changes: 2 additions & 1 deletion pumpkin-protocol/src/client/play/c_block_destroy_stage.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
use pumpkin_core::math::position::WorldPosition;
use pumpkin_macros::packet;
use serde::Serialize;

use crate::{position::WorldPosition, VarInt};
use crate::VarInt;

#[derive(Serialize)]
#[packet(0x06)]
Expand Down
3 changes: 2 additions & 1 deletion pumpkin-protocol/src/client/play/c_block_update.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
use pumpkin_core::math::position::WorldPosition;
use pumpkin_macros::packet;
use serde::Serialize;

use crate::{position::WorldPosition, VarInt};
use crate::VarInt;

#[derive(Serialize)]
#[packet(0x09)]
Expand Down
3 changes: 2 additions & 1 deletion pumpkin-protocol/src/client/play/c_login.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
use pumpkin_core::math::position::WorldPosition;
use pumpkin_macros::packet;
use serde::Serialize;

use crate::{position::WorldPosition, VarInt};
use crate::VarInt;

#[derive(Serialize)]
#[packet(0x2B)]
Expand Down
3 changes: 1 addition & 2 deletions pumpkin-protocol/src/client/play/c_worldevent.rs
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
use pumpkin_core::math::position::WorldPosition;
use pumpkin_macros::packet;
use serde::Serialize;

use crate::position::WorldPosition;

#[derive(Serialize)]
#[packet(0x28)]
pub struct CWorldEvent<'a> {
Expand Down
1 change: 0 additions & 1 deletion pumpkin-protocol/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@ pub mod bytebuf;
pub mod client;
pub mod packet_decoder;
pub mod packet_encoder;
pub mod position;
pub mod server;
pub mod slot;
pub mod uuid;
Expand Down
3 changes: 2 additions & 1 deletion pumpkin-protocol/src/server/play/s_player_action.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
use num_derive::FromPrimitive;
use pumpkin_core::math::position::WorldPosition;
use pumpkin_macros::packet;

use crate::{position::WorldPosition, VarInt};
use crate::VarInt;

#[derive(serde::Deserialize)]
#[packet(0x24)]
Expand Down
3 changes: 2 additions & 1 deletion pumpkin-protocol/src/server/play/s_use_item_on.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
use pumpkin_core::math::position::WorldPosition;
use pumpkin_macros::packet;
use serde::Deserialize;

use crate::{position::WorldPosition, VarInt};
use crate::VarInt;

#[derive(Deserialize)]
#[packet(0x38)]
Expand Down
4 changes: 3 additions & 1 deletion pumpkin-world/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,9 @@ version.workspace = true
edition.workspace = true

[dependencies]
# fastanvil = "0.31"
pumpkin-core = { path = "../pumpkin-core"}


fastnbt = { git = "https://github.com/owengage/fastnbt.git" }
fastsnbt = "0.2"
tokio.workspace = true
Expand Down
2 changes: 1 addition & 1 deletion pumpkin-world/src/block/mod.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
use crate::vector3::Vector3;
use num_derive::FromPrimitive;

pub mod block_id;
mod block_registry;

pub use block_id::BlockId;
use pumpkin_core::math::vector3::Vector3;

#[derive(FromPrimitive)]
pub enum BlockFace {
Expand Down
2 changes: 1 addition & 1 deletion pumpkin-world/src/chunk.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@ use std::collections::HashMap;
use std::ops::Index;

use fastnbt::LongArray;
use pumpkin_core::math::vector2::Vector2;
use serde::{Deserialize, Serialize};

use crate::{
block::BlockId,
coordinates::{ChunkRelativeBlockCoordinates, Height},
level::{ChunkNotGeneratedError, WorldError},
vector2::Vector2,
WORLD_HEIGHT,
};

Expand Down
3 changes: 2 additions & 1 deletion pumpkin-world/src/coordinates.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,10 @@ use std::ops::Deref;

use derive_more::derive::{AsMut, AsRef, Display, Into};
use num_traits::{PrimInt, Signed, Unsigned};
use pumpkin_core::math::vector2::Vector2;
use serde::{Deserialize, Serialize};

use crate::{vector2::Vector2, WORLD_LOWEST_Y, WORLD_MAX_Y};
use crate::{WORLD_LOWEST_Y, WORLD_MAX_Y};

#[derive(
Serialize, Deserialize, Debug, Clone, Copy, PartialEq, Eq, AsRef, AsMut, Into, Display,
Expand Down
83 changes: 83 additions & 0 deletions pumpkin-world/src/cylindrical_chunk_iterator.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
use pumpkin_core::math::vector2::Vector2;

#[derive(Debug, PartialEq)]
pub struct Cylindrical {
pub center: Vector2<i32>,
pub view_distance: i32,
}

impl Cylindrical {
pub fn new(center: Vector2<i32>, view_distance: i32) -> Self {
Self {
center,
view_distance,
}
}

#[allow(unused_variables)]
pub fn for_each_changed_chunk(
old_cylindrical: Cylindrical,
new_cylindrical: Cylindrical,
mut newly_included: impl FnMut(Vector2<i32>),
just_removed: impl FnMut(Vector2<i32>),
ignore: bool,
) {
let min_x = old_cylindrical.get_left().min(new_cylindrical.get_left());
let max_x = old_cylindrical.get_right().max(new_cylindrical.get_right());
let min_z = old_cylindrical
.get_bottom()
.min(new_cylindrical.get_bottom());
let max_z = old_cylindrical.get_top().max(new_cylindrical.get_top());

for x in min_x..=max_x {
for z in min_z..=max_z {
// TODO
// let old_is_within = if ignore {
// false
// } else {
// old_cylindrical.is_within_distance(x, z)
// };
// let new_is_within = if ignore {
// true
// } else {
// new_cylindrical.is_within_distance(x, z)
// };

// if old_is_within != new_is_within {
// if new_is_within {
newly_included(Vector2::new(x, z));
// } else {
// dbg!("aa");
// just_removed(Vector2::new(x, z));
// }
// }
}
}
}

fn get_left(&self) -> i32 {
self.center.x - self.view_distance - 1
}

fn get_bottom(&self) -> i32 {
self.center.z - self.view_distance - 1
}

fn get_right(&self) -> i32 {
self.center.x + self.view_distance + 1
}

fn get_top(&self) -> i32 {
self.center.z + self.view_distance + 1
}

#[allow(dead_code)]
fn is_within_distance(&self, x: i32, z: i32) -> bool {
let max_dist_squared = self.view_distance * self.view_distance;
let max_dist = self.view_distance as i64;
let dist_x = (x - self.center.x).abs().max(0) - (1);
let dist_z = (z - self.center.z).abs().max(0) - (1);
let dist_squared = dist_x.pow(2) + (max_dist.min(dist_z as i64) as i32).pow(2);
dist_squared < max_dist_squared
}
}
2 changes: 1 addition & 1 deletion pumpkin-world/src/level.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,13 @@ use std::{

use flate2::{bufread::ZlibDecoder, read::GzDecoder};
use itertools::Itertools;
use pumpkin_core::math::vector2::Vector2;
use rayon::prelude::*;
use thiserror::Error;
use tokio::sync::mpsc;

use crate::{
chunk::ChunkData,
vector2::Vector2,
world_gen::{get_world_gen, Seed, WorldGenerator},
};

Expand Down
Loading

0 comments on commit 5c0dffb

Please sign in to comment.