mirror of
https://github.com/mat-1/azalea.git
synced 2025-08-02 06:16:04 +00:00
fix edge case with reading FormattedText as nbt
This commit is contained in:
parent
f919fb65d6
commit
0ddad8bd9c
2 changed files with 95 additions and 57 deletions
|
@ -308,65 +308,89 @@ impl simdnbt::FromNbtTag for FormattedText {
|
|||
} else if let Some(translate) = compound.get("translate") {
|
||||
let translate = translate.string()?.into();
|
||||
if let Some(with) = compound.get("with") {
|
||||
let with = with.list()?.compounds()?;
|
||||
let mut with_array = Vec::with_capacity(with.len());
|
||||
for item in with {
|
||||
// if it's a string component with no styling and no siblings, just add
|
||||
// a string to with_array otherwise add the
|
||||
// component to the array
|
||||
if let Some(primitive) = item.get("") {
|
||||
// minecraft does this sometimes, for example
|
||||
// for the /give system messages
|
||||
match primitive {
|
||||
simdnbt::borrow::NbtTag::Byte(b) => {
|
||||
// interpreted as boolean
|
||||
with_array.push(StringOrComponent::String(
|
||||
if *b != 0 { "true" } else { "false" }.to_string(),
|
||||
let mut with_array = Vec::new();
|
||||
match with.list()? {
|
||||
simdnbt::borrow::NbtList::Empty => {}
|
||||
simdnbt::borrow::NbtList::String(with) => {
|
||||
for item in with {
|
||||
with_array.push(StringOrComponent::String(item.to_string()));
|
||||
}
|
||||
}
|
||||
simdnbt::borrow::NbtList::Compound(with) => {
|
||||
for item in with {
|
||||
// if it's a string component with no styling and no siblings,
|
||||
// just add a string to
|
||||
// with_array otherwise add the
|
||||
// component to the array
|
||||
if let Some(primitive) = item.get("") {
|
||||
// minecraft does this sometimes, for example
|
||||
// for the /give system messages
|
||||
match primitive {
|
||||
simdnbt::borrow::NbtTag::Byte(b) => {
|
||||
// interpreted as boolean
|
||||
with_array.push(StringOrComponent::String(
|
||||
if *b != 0 { "true" } else { "false" }
|
||||
.to_string(),
|
||||
));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Short(s) => {
|
||||
with_array
|
||||
.push(StringOrComponent::String(s.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Int(i) => {
|
||||
with_array
|
||||
.push(StringOrComponent::String(i.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Long(l) => {
|
||||
with_array
|
||||
.push(StringOrComponent::String(l.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Float(f) => {
|
||||
with_array
|
||||
.push(StringOrComponent::String(f.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Double(d) => {
|
||||
with_array
|
||||
.push(StringOrComponent::String(d.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::String(s) => {
|
||||
with_array
|
||||
.push(StringOrComponent::String(s.to_string()));
|
||||
}
|
||||
_ => {
|
||||
warn!("couldn't parse {item:?} as FormattedText because it has a disallowed primitive");
|
||||
with_array.push(StringOrComponent::String(
|
||||
"?".to_string(),
|
||||
));
|
||||
}
|
||||
}
|
||||
} else if let Some(c) = FormattedText::from_nbt_tag(
|
||||
&simdnbt::borrow::NbtTag::Compound(item.clone()),
|
||||
) {
|
||||
if let FormattedText::Text(text_component) = c {
|
||||
if text_component.base.siblings.is_empty()
|
||||
&& text_component.base.style.is_empty()
|
||||
{
|
||||
with_array.push(StringOrComponent::String(
|
||||
text_component.text,
|
||||
));
|
||||
continue;
|
||||
}
|
||||
}
|
||||
with_array.push(StringOrComponent::FormattedText(
|
||||
FormattedText::from_nbt_tag(
|
||||
&simdnbt::borrow::NbtTag::Compound(item.clone()),
|
||||
)?,
|
||||
));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Short(s) => {
|
||||
with_array.push(StringOrComponent::String(s.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Int(i) => {
|
||||
with_array.push(StringOrComponent::String(i.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Long(l) => {
|
||||
with_array.push(StringOrComponent::String(l.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Float(f) => {
|
||||
with_array.push(StringOrComponent::String(f.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::Double(d) => {
|
||||
with_array.push(StringOrComponent::String(d.to_string()));
|
||||
}
|
||||
simdnbt::borrow::NbtTag::String(s) => {
|
||||
with_array.push(StringOrComponent::String(s.to_string()));
|
||||
}
|
||||
_ => {
|
||||
warn!("couldn't parse {item:?} as FormattedText because it has a disallowed primitive");
|
||||
} else {
|
||||
warn!("couldn't parse {item:?} as FormattedText");
|
||||
with_array.push(StringOrComponent::String("?".to_string()));
|
||||
}
|
||||
}
|
||||
} else if let Some(c) = FormattedText::from_nbt_tag(
|
||||
&simdnbt::borrow::NbtTag::Compound(item.clone()),
|
||||
) {
|
||||
if let FormattedText::Text(text_component) = c {
|
||||
if text_component.base.siblings.is_empty()
|
||||
&& text_component.base.style.is_empty()
|
||||
{
|
||||
with_array
|
||||
.push(StringOrComponent::String(text_component.text));
|
||||
continue;
|
||||
}
|
||||
}
|
||||
with_array.push(StringOrComponent::FormattedText(
|
||||
FormattedText::from_nbt_tag(
|
||||
&simdnbt::borrow::NbtTag::Compound(item.clone()),
|
||||
)?,
|
||||
));
|
||||
} else {
|
||||
warn!("couldn't parse {item:?} as FormattedText");
|
||||
with_array.push(StringOrComponent::String("?".to_string()));
|
||||
}
|
||||
_ => {
|
||||
warn!("couldn't parse {with:?} as FormattedText because it's not a list of compounds");
|
||||
return None;
|
||||
}
|
||||
}
|
||||
component = FormattedText::Translatable(TranslatableComponent::new(
|
||||
|
@ -448,8 +472,9 @@ impl McBufReadable for FormattedText {
|
|||
fn read_from(buf: &mut std::io::Cursor<&[u8]>) -> Result<Self, BufReadError> {
|
||||
let nbt = simdnbt::borrow::NbtTag::read_optional(buf)?;
|
||||
if let Some(nbt) = nbt {
|
||||
FormattedText::from_nbt_tag(&nbt)
|
||||
.ok_or(BufReadError::Custom("couldn't read nbt".to_owned()))
|
||||
FormattedText::from_nbt_tag(&nbt).ok_or(BufReadError::Custom(
|
||||
"couldn't convert nbt to chat message".to_owned(),
|
||||
))
|
||||
} else {
|
||||
Ok(FormattedText::default())
|
||||
}
|
||||
|
|
|
@ -29,4 +29,17 @@ mod tests {
|
|||
"[py5: Gave 1 [Diamond Pickaxe] to py5]".to_string()
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_translate_with_string_array_clientbound_system_chat_packet() {
|
||||
#[rustfmt::skip]
|
||||
let bytes = [
|
||||
10, 9, 0, 4, 119, 105, 116, 104, 8, 0, 0, 0, 1, 0, 14, 109, 105, 110, 101, 99, 114, 97, 102, 116, 58, 100, 117, 115, 116, 8, 0, 9, 116, 114, 97, 110, 115, 108, 97, 116, 101, 0, 25, 99, 111, 109, 109, 97, 110, 100, 115, 46, 112, 97, 114, 116, 105, 99, 108, 101, 46, 115, 117, 99, 99, 101, 115, 115, 0, 0
|
||||
];
|
||||
let packet = ClientboundSystemChatPacket::read_from(&mut Cursor::new(&bytes)).unwrap();
|
||||
assert_eq!(
|
||||
packet.content.to_string(),
|
||||
"Displaying particle minecraft:dust".to_string()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue