fix packet errors

This commit is contained in:
Snowiiii 2024-07-31 22:17:51 +02:00
parent 2479019443
commit 87b537ccc9
16 changed files with 213 additions and 146 deletions

30
Cargo.lock generated
View File

@ -211,6 +211,19 @@ dependencies = [
"serde_bytes", "serde_bytes",
] ]
[[package]]
name = "fastsnbt"
version = "0.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "51b48b5b742a5441eb6dac3dfe2c2bd048e91fd8e98abf266b4d9f89972aa8ec"
dependencies = [
"byteorder",
"itoa",
"nom",
"ryu",
"serde",
]
[[package]] [[package]]
name = "fdeflate" name = "fdeflate"
version = "0.3.4" version = "0.3.4"
@ -333,6 +346,12 @@ version = "2.7.4"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "78ca9ab1a0babb1e7d5695e3530886289c18cf2f87ec19a575a0abdce112e3a3" checksum = "78ca9ab1a0babb1e7d5695e3530886289c18cf2f87ec19a575a0abdce112e3a3"
[[package]]
name = "minimal-lexical"
version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a"
[[package]] [[package]]
name = "miniz_oxide" name = "miniz_oxide"
version = "0.7.4" version = "0.7.4"
@ -356,6 +375,16 @@ dependencies = [
"windows-sys 0.52.0", "windows-sys 0.52.0",
] ]
[[package]]
name = "nom"
version = "7.1.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d273983c5a657a70a3e8f2a01329822f3b8c8172b73826411a55751e404a0a4a"
dependencies = [
"memchr",
"minimal-lexical",
]
[[package]] [[package]]
name = "num-bigint" name = "num-bigint"
version = "0.4.6" version = "0.4.6"
@ -506,6 +535,7 @@ dependencies = [
"cfb8", "cfb8",
"crossbeam-channel", "crossbeam-channel",
"fastnbt", "fastnbt",
"fastsnbt",
"flate2", "flate2",
"image", "image",
"log", "log",

View File

@ -30,4 +30,6 @@ crossbeam-channel = "0.5.13"
uuid = "1.10" uuid = "1.10"
toml = "0.8.17" toml = "0.8.17"
fastnbt = "2.5.0" fastnbt = "2.5.0"
fastsnbt = "0.2"

View File

@ -1,7 +1,7 @@
use crate::{ use crate::{
protocol::{ protocol::{
client::{ client::{
config::{CFinishConfig, CKnownPacks, CPluginMessage, CRegistryData, Entry}, config::{CFinishConfig, CKnownPacks, CRegistryData, Entry},
login::{CEncryptionRequest, CLoginSuccess}, login::{CEncryptionRequest, CLoginSuccess},
status::{CPingResponse, CStatusResponse}, status::{CPingResponse, CStatusResponse},
}, },
@ -83,10 +83,8 @@ impl ClientPacketProcessor for Client {
let verify_token: [u8; 4] = rand::random(); let verify_token: [u8; 4] = rand::random();
let public_key_der = &server.public_key_der; let public_key_der = &server.public_key_der;
let packet = CEncryptionRequest::new( let packet = CEncryptionRequest::new(
"".into(), "",
public_key_der.len() as i32,
public_key_der, public_key_der,
verify_token.len() as i32,
&verify_token, &verify_token,
false, // TODO false, // TODO
); );
@ -101,7 +99,7 @@ impl ClientPacketProcessor for Client {
dbg!("encryption response"); dbg!("encryption response");
// should be impossible // should be impossible
if self.uuid.is_none() || self.name.is_none() { if self.uuid.is_none() || self.name.is_none() {
self.kick("UUID or Name is none".into()); self.kick("UUID or Name is none");
return; return;
} }
self.enable_encryption(server, encryption_response.shared_secret) self.enable_encryption(server, encryption_response.shared_secret)
@ -126,14 +124,11 @@ impl ClientPacketProcessor for Client {
self.connection_state = ConnectionState::Config; self.connection_state = ConnectionState::Config;
Server::send_brand(self); Server::send_brand(self);
// known data packs // known data packs
self.send_packet(CKnownPacks::new( self.send_packet(CKnownPacks::new(&[KnownPack {
1, namespace: "minecraft",
&[KnownPack { id: "core",
namespace: "minecraft".to_string(), version: "1.21",
id: "core".to_string(), }]));
version: "1.21".to_string(),
}],
));
dbg!("login achnowlaged"); dbg!("login achnowlaged");
} }
fn handle_client_information( fn handle_client_information(
@ -155,11 +150,10 @@ impl ClientPacketProcessor for Client {
fn handle_known_packs(&mut self, server: &mut Server, config_acknowledged: SKnownPacks) { fn handle_known_packs(&mut self, server: &mut Server, config_acknowledged: SKnownPacks) {
self.send_packet(CRegistryData::new( self.send_packet(CRegistryData::new(
"0".into(), "dimension_type",
1, &[
vec![
Entry { Entry {
entry_id: "minecraft:dimension_type".into(), entry_id: "minecraft:dimension_type",
has_data: true, has_data: true,
}, },
/* Entry { /* Entry {

View File

@ -222,7 +222,7 @@ impl Client {
Ok(self.closed) Ok(self.closed)
} }
pub fn kick(&mut self, reason: String) { pub fn kick(&mut self, reason: &str) {
// Todo // Todo
match self.connection_state { match self.connection_state {
ConnectionState::Login => { ConnectionState::Login => {

View File

@ -56,7 +56,7 @@ impl PacketDecoder {
Ok(Some(RawPacket { Ok(Some(RawPacket {
len: packet_len, len: packet_len,
id: packet_id, id: packet_id,
bytebuf: ByteBuffer::new(BytesMut::from(data)), bytebuf: ByteBuffer::new(data),
})) }))
} }

View File

@ -1,5 +1,5 @@
use core::str; use core::str;
use std::io::{self, Error, ErrorKind, Read, Write}; use std::io::{self, Error, ErrorKind};
use bytes::{Buf, BufMut, BytesMut}; use bytes::{Buf, BufMut, BytesMut};
@ -180,17 +180,17 @@ impl ByteBuffer {
self.put_list(v, |p, &v| p.put_var_int(v)) self.put_list(v, |p, &v| p.put_var_int(v))
} }
/* pub fn get_nbt(&mut self) -> Option<crab_nbt::NbtTag> { /* pub fn get_nbt(&mut self) -> Option<fastnbt::value::Value> {
match crab_nbt::NbtTag::deserialize(self.buf()) { match crab_nbt::NbtTag::deserialize(self.buf()) {
Ok(v) => Some(v), Ok(v) => Some(v),
Err(err) => None, Err(err) => None,
} }
} }
pub fn put_nbt(&mut self, nbt: NbtTag) { pub fn put_nbt(&mut self, nbt: N) {
self.buffer.put_slice(&nbt.serialize()); self.buffer.put_slice(&nbt.serialize());
} */ }
*/
pub fn buf(&mut self) -> &mut BytesMut { pub fn buf(&mut self) -> &mut BytesMut {
&mut self.buffer &mut self.buffer
} }

View File

@ -26,25 +26,25 @@ impl<'a> ClientPacket for CPluginMessage<'a> {
fn write(&self, bytebuf: &mut ByteBuffer) { fn write(&self, bytebuf: &mut ByteBuffer) {
bytebuf.put_string(&self.channel); bytebuf.put_string(&self.channel);
bytebuf.put_slice(&self.data); bytebuf.put_slice(self.data);
} }
} }
pub struct CConfigDisconnect { pub struct CConfigDisconnect<'a> {
reason: String, reason: &'a str,
} }
impl CConfigDisconnect { impl<'a> CConfigDisconnect<'a> {
pub fn new(reason: String) -> Self { pub fn new(reason: &'a str) -> Self {
Self { reason } Self { reason }
} }
} }
impl ClientPacket for CConfigDisconnect { impl<'a> ClientPacket for CConfigDisconnect<'a> {
const PACKET_ID: crate::protocol::VarInt = 0x02; const PACKET_ID: crate::protocol::VarInt = 0x02;
fn write(&self, bytebuf: &mut ByteBuffer) { fn write(&self, bytebuf: &mut ByteBuffer) {
bytebuf.put_string(&self.reason); bytebuf.put_string(self.reason);
} }
} }
@ -69,13 +69,12 @@ impl ClientPacket for CFinishConfig {
} }
pub struct CKnownPacks<'a> { pub struct CKnownPacks<'a> {
count: VarInt, known_packs: &'a [KnownPack<'a>],
known_packs: &'a [KnownPack],
} }
impl<'a> CKnownPacks<'a> { impl<'a> CKnownPacks<'a> {
pub fn new(count: VarInt, known_packs: &'a [KnownPack]) -> Self { pub fn new(known_packs: &'a [KnownPack]) -> Self {
Self { count, known_packs } Self { known_packs }
} }
} }
@ -83,47 +82,43 @@ impl<'a> ClientPacket for CKnownPacks<'a> {
const PACKET_ID: VarInt = 0x0E; const PACKET_ID: VarInt = 0x0E;
fn write(&self, bytebuf: &mut ByteBuffer) { fn write(&self, bytebuf: &mut ByteBuffer) {
// bytebuf.write_var_int(self.count); bytebuf.put_list::<KnownPack>(self.known_packs, |p, v| {
bytebuf.put_list::<KnownPack>(&self.known_packs, |p, v| { p.put_string(v.namespace);
p.put_string(&v.namespace); p.put_string(v.id);
p.put_string(&v.id); p.put_string(v.version);
p.put_string(&v.version);
}); });
} }
} }
pub struct CRegistryData { pub struct CRegistryData<'a> {
registry_id: String, registry_id: &'a str,
entry_count: VarInt, entries: &'a [Entry<'a>],
entries: Vec<Entry>,
} }
impl CRegistryData { impl<'a> CRegistryData<'a> {
pub fn new(registry_id: String, entry_count: VarInt, entries: Vec<Entry>) -> Self { pub fn new(registry_id: &'a str, entries: &'a [Entry]) -> Self {
Self { Self {
registry_id, registry_id,
entry_count,
entries, entries,
} }
} }
} }
pub struct Entry { pub struct Entry<'a> {
pub entry_id: String, pub entry_id: &'a str,
pub has_data: bool, pub has_data: bool,
// data provided by registry::write_codec // data provided by registry::write_codec
} }
impl ClientPacket for CRegistryData { impl<'a> ClientPacket for CRegistryData<'a> {
const PACKET_ID: VarInt = 0x07; const PACKET_ID: VarInt = 0x07;
fn write(&self, bytebuf: &mut ByteBuffer) { fn write(&self, bytebuf: &mut ByteBuffer) {
bytebuf.put_string(&self.registry_id); bytebuf.put_string(self.registry_id);
bytebuf.put_var_int(self.entry_count); bytebuf.put_list::<Entry>(self.entries, |p, v| {
bytebuf.put_list::<Entry>(&self.entries, |p, v| { p.put_string(v.entry_id);
p.put_string(&v.entry_id);
p.put_bool(v.has_data); p.put_bool(v.has_data);
registry::write_single_dimension(p, -64, 320); registry::write_codec(p, -64, 384);
}); });
} }
} }

View File

@ -1,16 +1,16 @@
use crate::protocol::{bytebuf::ByteBuffer, ClientPacket, VarInt}; use crate::protocol::{bytebuf::ByteBuffer, ClientPacket, VarInt};
pub struct CLoginDisconnect { pub struct CLoginDisconnect<'a> {
reason: String, reason: &'a str,
} }
impl CLoginDisconnect { impl<'a> CLoginDisconnect<'a> {
pub fn new(reason: String) -> Self { pub fn new(reason: &'a str) -> Self {
Self { reason } Self { reason }
} }
} }
impl ClientPacket for CLoginDisconnect { impl<'a> ClientPacket for CLoginDisconnect<'a> {
const PACKET_ID: VarInt = 0x00; const PACKET_ID: VarInt = 0x00;
fn write(&self, bytebuf: &mut ByteBuffer) { fn write(&self, bytebuf: &mut ByteBuffer) {
@ -19,28 +19,22 @@ impl ClientPacket for CLoginDisconnect {
} }
pub struct CEncryptionRequest<'a> { pub struct CEncryptionRequest<'a> {
server_id: String, // 20 server_id: &'a str, // 20
public_key_length: VarInt,
public_key: &'a [u8], public_key: &'a [u8],
verify_token_length: VarInt,
verify_token: &'a [u8], verify_token: &'a [u8],
should_authenticate: bool, should_authenticate: bool,
} }
impl<'a> CEncryptionRequest<'a> { impl<'a> CEncryptionRequest<'a> {
pub fn new( pub fn new(
server_id: String, server_id: &'a str,
public_key_length: VarInt,
public_key: &'a [u8], public_key: &'a [u8],
verify_token_length: VarInt,
verify_token: &'a [u8], verify_token: &'a [u8],
should_authenticate: bool, should_authenticate: bool,
) -> Self { ) -> Self {
Self { Self {
server_id, server_id,
public_key_length,
public_key, public_key,
verify_token_length,
verify_token, verify_token,
should_authenticate, should_authenticate,
} }
@ -51,10 +45,10 @@ impl<'a> ClientPacket for CEncryptionRequest<'a> {
const PACKET_ID: VarInt = 0x01; const PACKET_ID: VarInt = 0x01;
fn write(&self, bytebuf: &mut ByteBuffer) { fn write(&self, bytebuf: &mut ByteBuffer) {
bytebuf.put_string(self.server_id.as_str()); bytebuf.put_string(self.server_id);
bytebuf.put_var_int(self.public_key_length); bytebuf.put_var_int(self.public_key.len() as VarInt);
bytebuf.put_slice(self.public_key); bytebuf.put_slice(self.public_key);
bytebuf.put_var_int(self.verify_token_length); bytebuf.put_var_int(self.verify_token.len() as VarInt);
bytebuf.put_slice(self.verify_token); bytebuf.put_slice(self.verify_token);
bytebuf.put_bool(self.should_authenticate); bytebuf.put_bool(self.should_authenticate);
} }

View File

@ -124,7 +124,7 @@ pub trait ClientPacket {
fn write(&self, bytebuf: &mut ByteBuffer); fn write(&self, bytebuf: &mut ByteBuffer);
} }
#[derive(Serialize, Deserialize)] #[derive(Serialize)]
pub struct StatusResponse { pub struct StatusResponse {
pub version: Version, pub version: Version,
pub players: Players, pub players: Players,
@ -132,27 +132,27 @@ pub struct StatusResponse {
pub favicon: String, // data:image/png;base64,<data> pub favicon: String, // data:image/png;base64,<data>
// Players, favicon ... // Players, favicon ...
} }
#[derive(Serialize, Deserialize)] #[derive(Serialize)]
pub struct Version { pub struct Version {
pub name: String, pub name: String,
pub protocol: u32, pub protocol: u32,
} }
#[derive(Serialize, Deserialize)] #[derive(Serialize)]
pub struct Players { pub struct Players {
pub max: u32, pub max: u32,
pub online: u32, pub online: u32,
pub sample: Vec<Sample>, pub sample: Vec<Sample>,
} }
#[derive(Serialize, Deserialize)] #[derive(Serialize)]
pub struct Sample { pub struct Sample {
pub name: String, pub name: String,
pub id: String, // uuid pub id: String, // uuid
} }
pub struct KnownPack { pub struct KnownPack<'a> {
pub namespace: String, pub namespace: &'a str,
pub id: String, pub id: &'a str,
pub version: String, pub version: &'a str,
} }

View File

@ -1,6 +1,6 @@
use crate::protocol::VarInt; use crate::protocol::VarInt;
use super::CodecItem; use super::RegistryValue;
use serde::Serialize; use serde::Serialize;
#[derive(Debug, Clone, Serialize)] #[derive(Debug, Clone, Serialize)]
@ -72,7 +72,7 @@ struct Music {
} }
// 1.20.6 default https://gist.github.com/WinX64/ab8c7a8df797c273b32d3a3b66522906 // 1.20.6 default https://gist.github.com/WinX64/ab8c7a8df797c273b32d3a3b66522906
pub(super) fn all() -> Vec<CodecItem<Biome>> { pub(super) fn all() -> Vec<RegistryValue<Biome>> {
let biome = Biome { let biome = Biome {
has_precipitation: false, has_precipitation: false,
temperature: 1.0, temperature: 1.0,
@ -99,7 +99,7 @@ pub(super) fn all() -> Vec<CodecItem<Biome>> {
}, },
}; };
vec![CodecItem { vec![RegistryValue {
name: "minecraft:plains".into(), name: "minecraft:plains".into(),
id: 0, id: 0,
element: biome, element: biome,

View File

@ -1,4 +1,4 @@
use super::CodecItem; use super::RegistryValue;
use serde::Serialize; use serde::Serialize;
#[derive(Debug, Clone, Serialize)] #[derive(Debug, Clone, Serialize)]
@ -13,8 +13,8 @@ struct Decoration {
parameters: Vec<String>, parameters: Vec<String>,
} }
pub(super) fn all() -> Vec<CodecItem<ChatType>> { pub(super) fn all() -> Vec<RegistryValue<ChatType>> {
vec![CodecItem { vec![RegistryValue {
name: "minecraft:chat".into(), name: "minecraft:chat".into(),
id: 0, id: 0,
element: ChatType { element: ChatType {

View File

@ -1,6 +1,7 @@
use super::CodecItem;
use serde::Serialize; use serde::Serialize;
use super::RegistryValue;
#[derive(Debug, Clone, Serialize)] #[derive(Debug, Clone, Serialize)]
pub struct DamageType { pub struct DamageType {
message_id: String, message_id: String,
@ -60,10 +61,10 @@ const NAMES: &[&str] = &[
"wither_skull", "wither_skull",
]; ];
pub(super) fn all() -> Vec<CodecItem<DamageType>> { pub(super) fn all() -> Vec<RegistryValue<DamageType>> {
let mut items: Vec<_> = NAMES let mut items: Vec<_> = NAMES
.iter() .iter()
.map(|name| CodecItem { .map(|name| RegistryValue {
name: (*name).into(), name: (*name).into(),
id: 0, id: 0,
element: DamageType { element: DamageType {

View File

@ -1,48 +1,83 @@
use serde::Serialize; use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Serialize)] #[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Dimension { pub struct Dimension {
#[serde(skip_serializing_if = "Option::is_none")] pub ambient_light: f32,
fixed_time: Option<f64>,
has_skylight: bool,
has_ceiling: bool,
ultrawarm: bool,
natural: bool,
coordinate_scale: f64,
bed_works: bool, bed_works: bool,
respawn_anchor_works: bool, coordinate_scale: f64,
min_y: i32, effects: DimensionEffects,
height: i32, #[serde(skip_serializing_if = "Option::is_none")]
logical_height: i32, fixed_time: Option<i32>,
infiniburn: String, has_ceiling: bool,
effects: String,
ambient_light: f32,
piglin_safe: bool,
has_raids: bool, has_raids: bool,
monster_spawn_light_level: i32, has_skylight: bool,
height: i32,
infiniburn: String,
logical_height: i32,
min_y: i32,
monster_spawn_block_light_limit: i32, monster_spawn_block_light_limit: i32,
monster_spawn_light_level: MonsterSpawnLightLevel,
natural: bool,
piglin_safe: bool,
respawn_anchor_works: bool,
ultrawarm: bool,
} }
pub fn overworld(world_min_y: i32, world_height: u32) -> Dimension { #[derive(Serialize, Deserialize, Clone, Copy, PartialEq, Eq, Default, Debug)]
Dimension { pub enum DimensionEffects {
piglin_safe: false, #[serde(rename = "minecraft:overworld")]
natural: true, #[default]
ambient_light: 0.0, Overworld,
fixed_time: Some(6000.0), #[serde(rename = "minecraft:the_nether")]
infiniburn: "#minecraft:infiniburn_overworld".into(), TheNether,
respawn_anchor_works: false, #[serde(rename = "minecraft:the_end")]
has_skylight: true, TheEnd,
bed_works: true, }
effects: "minecraft:overworld".into(),
has_raids: false,
logical_height: 384,
coordinate_scale: 1.0,
ultrawarm: false,
has_ceiling: false,
min_y: world_min_y,
height: (world_height as i32 + 15) / 16 * 16,
monster_spawn_light_level: 7, impl Default for Dimension {
monster_spawn_block_light_limit: 7, fn default() -> Self {
Self {
ambient_light: 0.0,
bed_works: true,
coordinate_scale: 1.0,
effects: DimensionEffects::default(),
fixed_time: None,
has_ceiling: false,
has_raids: true,
has_skylight: true,
height: 384,
infiniburn: "#minecraft:infiniburn_overworld".into(),
logical_height: 384,
min_y: -64,
monster_spawn_block_light_limit: 0,
monster_spawn_light_level: MonsterSpawnLightLevel::Int(7),
natural: true,
piglin_safe: false,
respawn_anchor_works: false,
ultrawarm: false,
}
}
}
#[derive(Copy, Clone, PartialEq, Debug, Serialize, Deserialize)]
#[serde(untagged)]
pub enum MonsterSpawnLightLevel {
Int(i32),
Tagged(MonsterSpawnLightLevelTagged),
}
#[derive(Copy, Clone, PartialEq, Debug, Serialize, Deserialize)]
#[serde(tag = "type", content = "value")]
pub enum MonsterSpawnLightLevelTagged {
#[serde(rename = "minecraft:uniform")]
Uniform {
min_inclusive: i32,
max_inclusive: i32,
},
}
impl From<i32> for MonsterSpawnLightLevel {
fn from(value: i32) -> Self {
Self::Int(value)
} }
} }

View File

@ -1,3 +1,4 @@
use dimensions::Dimension;
use serde::Serialize; use serde::Serialize;
use super::bytebuf::ByteBuffer; use super::bytebuf::ByteBuffer;
@ -11,45 +12,55 @@ mod dimensions;
struct LoginInfo { struct LoginInfo {
#[serde(rename = "minecraft:dimension_type")] #[serde(rename = "minecraft:dimension_type")]
dimensions: Codec<dimensions::Dimension>, dimensions: Codec<dimensions::Dimension>,
#[serde(rename = "minecraft:worldgen/biome")] /* #[serde(rename = "minecraft:worldgen/biome")]
biomes: Codec<biomes::Biome>, biomes: Codec<biomes::Biome>,
#[serde(rename = "minecraft:chat_type")] #[serde(rename = "minecraft:chat_type")]
chat: Codec<chat_type::ChatType>, chat: Codec<chat_type::ChatType>,
#[serde(rename = "minecraft:damage_type")] #[serde(rename = "minecraft:damage_type")]
damage: Codec<damage_type::DamageType>, damage: Codec<damage_type::DamageType>, */
} }
#[derive(Debug, Clone, Serialize)] #[derive(Debug, Clone, Serialize)]
struct Codec<T> { struct Codec<T> {
#[serde(rename = "type")] #[serde(rename = "type")]
ty: String, ty: String,
value: Vec<CodecItem<T>>, value: Vec<RegistryValue<T>>,
} }
#[derive(Debug, Clone, Serialize)] #[derive(Debug, Clone, Serialize)]
struct CodecItem<T> { struct RegistryValue<T> {
name: String, name: String,
id: i32, id: i32,
element: T, element: T,
} }
pub fn write_single_dimension(out: &mut ByteBuffer, world_min_y: i32, world_height: u32) { pub fn write_single_dimension(out: &mut ByteBuffer, world_min_y: i32, world_height: u32) {
let dimension = dimensions::overworld(world_min_y, world_height); let dimension = Dimension::default();
// out.put_nbt(nbt!(dimension)) let nbt = Codec {
ty: "minecraft:dimension_type".into(),
value: vec![RegistryValue {
name: "minecraft:overworld".into(),
id: 0,
element: dimension,
}],
};
let val = &fastsnbt::to_string(&nbt).unwrap();
dbg!(val);
out.put_string(val);
} }
pub fn write_codec(out: &mut ByteBuffer, world_min_y: i32, world_height: u32) { pub fn write_codec(out: &mut ByteBuffer, world_min_y: i32, world_height: u32) {
let dimension = dimensions::overworld(world_min_y, world_height); let dimension = Dimension::default();
let info = LoginInfo { let info = LoginInfo {
dimensions: Codec { dimensions: Codec {
ty: "minecraft:dimension_type".into(), ty: "minecraft:dimension_type".into(),
value: vec![CodecItem { value: vec![RegistryValue {
name: "minecraft:overworld".into(), name: "minecraft:overworld".into(),
id: 0, id: 0,
element: dimension, element: dimension,
}], }],
}, },
biomes: Codec { /* biomes: Codec {
ty: "minecraft:worldgen/biome".into(), ty: "minecraft:worldgen/biome".into(),
value: biomes::all(), value: biomes::all(),
}, },
@ -60,11 +71,13 @@ pub fn write_codec(out: &mut ByteBuffer, world_min_y: i32, world_height: u32) {
damage: Codec { damage: Codec {
ty: "minecraft:damage_type".into(), ty: "minecraft:damage_type".into(),
value: damage_type::all(), value: damage_type::all(),
}, }, */
}; };
let val = &fastsnbt::to_string(&info).unwrap();
dbg!(val);
// Dimension codec // Dimension codec
// out.put_slice(&nbt::to_nbt("", &info).unwrap().serialize()); out.put_string(val);
// Current dimension type (key in dimension codec) // Current dimension type (key in dimension codec)
out.put_string("minecraft:overworld"); out.put_string("minecraft:overworld");
// Current world // Current world

View File

@ -16,10 +16,7 @@ use crate::{
Entity, EntityId, Entity, EntityId,
}, },
protocol::{ protocol::{
client::{ client::{config::CPluginMessage, play::CLogin},
config::{CFinishConfig, CKnownPacks, CPluginMessage, CRegistryData, Entry},
play::CLogin,
},
Players, Sample, StatusResponse, VarInt, VarInt32, Version, Players, Sample, StatusResponse, VarInt, VarInt32, Version,
}, },
world::World, world::World,

View File

@ -4,6 +4,12 @@ pub struct World {
pub players: Vec<Player>, pub players: Vec<Player>,
} }
impl Default for World {
fn default() -> Self {
Self::new()
}
}
impl World { impl World {
pub fn new() -> Self { pub fn new() -> Self {
Self { Self {