aboutsummaryrefslogtreecommitdiff
path: root/src/types.rs
diff options
context:
space:
mode:
authorJoey Sacchini <joey@sacchini.net>2020-10-09 18:42:32 -0400
committerJoey Sacchini <joey@sacchini.net>2020-10-09 18:42:32 -0400
commitfafe72ac2d97bd5c94ad55bd55526c2dcba9b8ff (patch)
treede32700329d34bb811ca47170e4e41aeedeb68c0 /src/types.rs
parentbda2a204d8a44d94a76ac94f4dd33682ac1b05d3 (diff)
downloadmcproto-rs-fafe72ac2d97bd5c94ad55bd55526c2dcba9b8ff.tar.gz
mcproto-rs-fafe72ac2d97bd5c94ad55bd55526c2dcba9b8ff.tar.bz2
mcproto-rs-fafe72ac2d97bd5c94ad55bd55526c2dcba9b8ff.zip
fix broken lighting data and totally rewrite chat engine
Diffstat (limited to 'src/types.rs')
-rw-r--r--src/types.rs314
1 files changed, 2 insertions, 312 deletions
diff --git a/src/types.rs b/src/types.rs
index 2082b56..cda622a 100644
--- a/src/types.rs
+++ b/src/types.rs
@@ -4,6 +4,8 @@ use crate::utils::*;
use crate::uuid::UUID4;
use crate::*;
+pub use super::chat::*;
+
#[cfg(test)]
use crate::protocol::TestRandom;
@@ -611,318 +613,6 @@ impl TestRandom for FixedInt {
}
}
-// chat
-#[derive(serde::Serialize, serde::Deserialize, Debug, PartialEq, Clone)]
-pub struct Chat {
- pub text: String,
- #[serde(skip_serializing_if = "Option::is_none")]
- pub bold: Option<bool>,
- #[serde(skip_serializing_if = "Option::is_none")]
- pub italic: Option<bool>,
- #[serde(skip_serializing_if = "Option::is_none")]
- pub underlined: Option<bool>,
- #[serde(skip_serializing_if = "Option::is_none")]
- pub strikethrough: Option<bool>,
- #[serde(skip_serializing_if = "Option::is_none")]
- pub obfuscated: Option<bool>,
- #[serde(skip_serializing_if = "Option::is_none")]
- pub color: Option<String>,
- #[serde(skip_serializing_if = "Option::is_none")]
- pub extra: Option<Vec<Chat>>,
-}
-
-impl ToString for Chat {
- fn to_string(&self) -> String {
- self.extra
- .as_ref()
- .into_iter()
- .flat_map(|v| v.into_iter())
- .map(|item| item.to_string())
- .fold(self.text.clone(), |acc, v| acc + v.as_str())
- }
-}
-
-const SECTION_SYMBOL: char = 'ยง';
-
-#[derive(PartialOrd, PartialEq, Debug, Copy, Clone)]
-pub enum ColorCode {
- Black,
- DarkBlue,
- DarkGreen,
- DarkAqua,
- DarkRed,
- DarkPurple,
- Gold,
- Gray,
- DarkGray,
- Blue,
- Green,
- Aqua,
- Red,
- LightPurple,
- Yellow,
- White,
-}
-
-impl ColorCode {
- pub fn from_code(i: &char) -> Option<Self> {
- match i {
- '0' => Some(ColorCode::Black),
- '1' => Some(ColorCode::DarkBlue),
- '2' => Some(ColorCode::DarkGreen),
- '3' => Some(ColorCode::DarkAqua),
- '4' => Some(ColorCode::DarkRed),
- '5' => Some(ColorCode::DarkPurple),
- '6' => Some(ColorCode::Gold),
- '7' => Some(ColorCode::Gray),
- '8' => Some(ColorCode::DarkGray),
- '9' => Some(ColorCode::Blue),
- 'a' => Some(ColorCode::Green),
- 'b' => Some(ColorCode::Aqua),
- 'c' => Some(ColorCode::Red),
- 'd' => Some(ColorCode::LightPurple),
- 'e' => Some(ColorCode::Yellow),
- 'f' => Some(ColorCode::White),
- _ => None,
- }
- }
-
- pub fn to_code(&self) -> char {
- match self {
- ColorCode::Black => '0',
- ColorCode::DarkBlue => '1',
- ColorCode::DarkGreen => '2',
- ColorCode::DarkAqua => '3',
- ColorCode::DarkRed => '4',
- ColorCode::DarkPurple => '5',
- ColorCode::Gold => '6',
- ColorCode::Gray => '7',
- ColorCode::DarkGray => '8',
- ColorCode::Blue => '9',
- ColorCode::Green => 'a',
- ColorCode::Aqua => 'b',
- ColorCode::Red => 'c',
- ColorCode::LightPurple => 'd',
- ColorCode::Yellow => 'e',
- ColorCode::White => 'f',
- }
- }
-
- pub fn from_name(name: &str) -> Option<Self> {
- match name.to_ascii_lowercase().as_str() {
- "black" => Some(ColorCode::Black),
- "dark_blue" => Some(ColorCode::DarkBlue),
- "dark_green" => Some(ColorCode::DarkGreen),
- "dark_aqua" => Some(ColorCode::DarkAqua),
- "dark_red" => Some(ColorCode::DarkRed),
- "dark_purple" => Some(ColorCode::DarkPurple),
- "gold" => Some(ColorCode::Gold),
- "gray" => Some(ColorCode::Gray),
- "dark_gray" => Some(ColorCode::DarkGray),
- "blue" => Some(ColorCode::Blue),
- "green" => Some(ColorCode::Green),
- "aqua" => Some(ColorCode::Aqua),
- "red" => Some(ColorCode::Red),
- "light_purple" => Some(ColorCode::LightPurple),
- "yellow" => Some(ColorCode::Yellow),
- "white" => Some(ColorCode::White),
- _ => None,
- }
- }
-
- pub fn name(&self) -> &str {
- match self {
- ColorCode::Black => "black",
- ColorCode::DarkBlue => "dark_blue",
- ColorCode::DarkGreen => "dark_green",
- ColorCode::DarkAqua => "dark_aqua",
- ColorCode::DarkRed => "dark_red",
- ColorCode::DarkPurple => "dark_purple",
- ColorCode::Gold => "gold",
- ColorCode::Gray => "gray",
- ColorCode::DarkGray => "dark_gray",
- ColorCode::Blue => "blue",
- ColorCode::Green => "green",
- ColorCode::Aqua => "aqua",
- ColorCode::Red => "red",
- ColorCode::LightPurple => "light_purple",
- ColorCode::Yellow => "yellow",
- ColorCode::White => "white",
- }
- }
-}
-
-#[derive(PartialOrd, PartialEq, Debug, Copy, Clone)]
-pub enum Formatter {
- Color(ColorCode),
- Obfuscated,
- Bold,
- Strikethrough,
- Underline,
- Italic,
- Reset,
-}
-
-impl Formatter {
- pub fn from_code(i: &char) -> Option<Self> {
- match i.to_ascii_lowercase() {
- 'k' => Some(Formatter::Obfuscated),
- 'l' => Some(Formatter::Bold),
- 'm' => Some(Formatter::Strikethrough),
- 'n' => Some(Formatter::Underline),
- 'o' => Some(Formatter::Italic),
- 'r' => Some(Formatter::Reset),
- _ => ColorCode::from_code(i).map(Formatter::Color),
- }
- }
-
- pub fn code(&self) -> char {
- match self {
- Formatter::Color(c) => c.to_code(),
- Formatter::Obfuscated => 'k',
- Formatter::Bold => 'l',
- Formatter::Strikethrough => 'm',
- Formatter::Underline => 'n',
- Formatter::Italic => 'o',
- Formatter::Reset => 'r',
- }
- }
-
- pub fn from_name(name: &str) -> Option<Self> {
- match name.to_ascii_lowercase().as_str() {
- "obfuscated" => Some(Formatter::Obfuscated),
- "bold" => Some(Formatter::Bold),
- "strikethrough" => Some(Formatter::Strikethrough),
- "underline" => Some(Formatter::Underline),
- "italic" => Some(Formatter::Italic),
- "reset" => Some(Formatter::Reset),
- _ => ColorCode::from_name(name).map(Formatter::Color),
- }
- }
-
- pub fn name(&self) -> &str {
- match self {
- Formatter::Obfuscated => "obfuscated",
- Formatter::Bold => "bold",
- Formatter::Strikethrough => "strikethrough",
- Formatter::Underline => "underline",
- Formatter::Italic => "italic",
- Formatter::Reset => "reset",
- Formatter::Color(c) => c.name(),
- }
- }
-}
-
-impl ToString for Formatter {
- fn to_string(&self) -> String {
- vec![SECTION_SYMBOL, self.code()].into_iter().collect()
- }
-}
-
-impl Chat {
- pub fn to_traditional(&self) -> String {
- self.to_traditional_parts(Vec::<Formatter>::new().as_ref(), None)
- }
-
- fn to_traditional_parts(
- &self,
- formatters: &Vec<Formatter>,
- color: Option<ColorCode>,
- ) -> String {
- let mut own_formatters = formatters.clone();
- Self::update_formatter(&mut own_formatters, Formatter::Bold, &self.bold);
- Self::update_formatter(&mut own_formatters, Formatter::Italic, &self.italic);
- Self::update_formatter(&mut own_formatters, Formatter::Underline, &self.underlined);
- Self::update_formatter(
- &mut own_formatters,
- Formatter::Strikethrough,
- &self.strikethrough,
- );
- Self::update_formatter(&mut own_formatters, Formatter::Obfuscated, &self.obfuscated);
-
- let own_color_option = self
- .color
- .as_ref()
- .map(String::as_str)
- .and_then(ColorCode::from_name)
- .or(color);
-
- let own_color = own_color_option
- .map(Formatter::Color)
- .map(|f| f.to_string());
-
- let own_formatter = own_formatters
- .clone()
- .into_iter()
- .map(|f| f.to_string())
- .fold(String::new(), |acc, v| acc + v.as_str());
-
- let own_color_str = match own_color {
- Some(v) => v,
- None => String::new(),
- };
-
- let own_out = own_formatter + own_color_str.as_str() + self.text.as_str();
-
- self.extra
- .as_ref()
- .into_iter()
- .flat_map(|v| v.into_iter())
- .map(|child| child.to_traditional_parts(&own_formatters, own_color_option))
- .fold(own_out, |acc, next| acc + next.as_str())
- }
-
- fn update_formatter(to: &mut Vec<Formatter>, formatter: Formatter, v: &Option<bool>) {
- if !to.contains(&formatter) && v.unwrap_or(false) {
- to.push(formatter)
- }
- }
-
- pub fn from_text(text: &str) -> Chat {
- Chat {
- text: text.to_owned(),
- bold: None,
- italic: None,
- underlined: None,
- strikethrough: None,
- obfuscated: None,
- color: None,
- extra: None,
- }
- }
-}
-
-impl Serialize for Chat {
- fn mc_serialize<S: Serializer>(&self, to: &mut S) -> SerializeResult {
- serde_json::to_string(self)
- .map_err(move |err| {
- SerializeErr::FailedJsonEncode(format!("failed to serialize chat {:?}", err))
- })?
- .mc_serialize(to)
- }
-}
-
-impl Deserialize for Chat {
- fn mc_deserialize(data: &[u8]) -> DeserializeResult<'_, Self> {
- String::mc_deserialize(data)?.try_map(move |str| {
- serde_json::from_str(str.as_str()).map_err(move |err| {
- DeserializeErr::FailedJsonDeserialize(format!(
- "failed to deserialize chat {:?}",
- err
- ))
- })
- })
- }
-}
-
-#[cfg(test)]
-impl TestRandom for Chat {
- fn test_gen_random() -> Self {
- let str = String::test_gen_random();
- Chat::from_text(str.as_str())
- }
-}
-
#[derive(Default)]
pub struct BytesSerializer {
data: Vec<u8>,