- Notifications
You must be signed in to change notification settings - Fork45
Fast serde serializer and deserializer for Minecraft's NBT and Anvil formats
License
owengage/fastnbt
Folders and files
Name | Name | Last commit message | Last commit date | |
---|---|---|---|---|
Repository files navigation
FastNBT is aserde serializer and deserializer forMinecraft: Java Edition's NBT format, includingValue
type andnbt!
macro. Forstringified NBT (sNBT) see FastSNBT.
FastAnvil allows rendering maps of worlds, and aRegion
forusing the Region file format. Supports 1.20 down to 1.13 inclusive, and slightlyflaky support for 1.12.
An in-browser Rust-to-WASM powered Minecraft map renderer demo is below.
Demo of Hermitcraft season 8 and more atowengage.com/anvil
Theanvil
binary fromfastnbt-tools
can render your world leveraging all ofyour CPU.
A bunch of examples can be found infastnbt/examples
,fastanvil/examples
andtools/src
. Some examples are recreated below.
The following edits the world spawn to 250, 200, 250 (probably not a goodidea!). Full example in fastnbt/examples directory.
#[derive(Serialize,Deserialize)]structLevelDat{#[serde(rename ="Data")]data:Data,}#[derive(Serialize,Deserialize)]#[serde(rename_all ="PascalCase")]structData{spawn_x:i32,spawn_y:i32,spawn_z:i32,#[serde(flatten)]other:HashMap<String,Value>,}fnmain(){let args:Vec<_> = std::env::args_os().collect();let file = std::fs::File::open(&args[1]).unwrap();letmut decoder =GzDecoder::new(file);letmut bytes =vec![]; decoder.read_to_end(&mut bytes).unwrap();letmut leveldat:LevelDat = fastnbt::from_bytes(&bytes).unwrap(); leveldat.data.spawn_x =250; leveldat.data.spawn_y =200; leveldat.data.spawn_z =250;let new_bytes = fastnbt::to_bytes(&leveldat).unwrap();let outfile = std::fs::File::create("level.dat").unwrap();letmut encoder =GzEncoder::new(outfile,Compression::fast()); encoder.write_all(&new_bytes).unwrap();}
This example demonstrates printing out a players inventory and ender chest contents from theplayer datfiles found in worlds. We
- use serde's renaming attribute to have rustfmt conformant field names,
- use lifetimes to save on string allocations, and
- use the
Value
type to deserialize a field we don't specify the exactstructure of.
#[derive(Deserialize,Debug)]#[serde(rename_all ="PascalCase")]structPlayerDat<'a>{data_version:i32,#[serde(borrow)]inventory:Vec<InventorySlot<'a>>,ender_items:Vec<InventorySlot<'a>>,}#[derive(Deserialize,Debug)]structInventorySlot<'a>{id:&'astr,// We avoid allocating a string here.tag:Option<Value>,// Also get the less structured properties of the object.// We need to rename fields a lot.#[serde(rename ="Count")]count:i8,}fnmain(){let args:Vec<_> = std::env::args().skip(1).collect();let file = std::fs::File::open(args[0].clone()).unwrap();// Player dat files are compressed with GZip.letmut decoder =GzDecoder::new(file);letmut data =vec![]; decoder.read_to_end(&mut data).unwrap();let player:Result<PlayerDat> =from_bytes(data.as_slice());println!("{:#?}", player);}
For the libraries
[dependencies]fastnbt ="2"fastanvil ="0.31"
For theanvil
executable
cargo install fastnbt-tools
About
Fast serde serializer and deserializer for Minecraft's NBT and Anvil formats
Topics
Resources
License
Uh oh!
There was an error while loading.Please reload this page.