diff --git a/macro_convert/Cargo.toml b/macro_convert/Cargo.toml index f7f6c336..05ddda0d 100644 --- a/macro_convert/Cargo.toml +++ b/macro_convert/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "macro_convert" -version = "0.2.0" +version = "0.3.0" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/macro_convert/src/lib.rs b/macro_convert/src/lib.rs index 3c3cac7e..7c22a4a5 100644 --- a/macro_convert/src/lib.rs +++ b/macro_convert/src/lib.rs @@ -26,7 +26,6 @@ fn handle_enum(name: &Ident, data: &DataEnum) -> TokenStream2 { let default: Ident = get_default(data); return quote! { - use std::fmt; #[automatically_derived] impl #name { @@ -36,8 +35,8 @@ fn handle_enum(name: &Ident, data: &DataEnum) -> TokenStream2 { } #[automatically_derived] - impl fmt::Display for #name { - fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + impl std::fmt::Display for #name { + fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { write!(f, "{:?}", self) } } diff --git a/macro_core/Cargo.toml b/macro_core/Cargo.toml index 432e5ae7..7fca3dfd 100644 --- a/macro_core/Cargo.toml +++ b/macro_core/Cargo.toml @@ -1,4 +1,4 @@ [package] name = "macro_core" -version = "0.2.0" +version = "0.3.0" edition = "2021" diff --git a/macro_ui/Cargo.toml b/macro_ui/Cargo.toml index 866e9a29..292a582e 100644 --- a/macro_ui/Cargo.toml +++ b/macro_ui/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "macro_ui" -version = "0.2.0" +version = "0.3.0" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/macro_ui/src/lib.rs b/macro_ui/src/lib.rs index bfe63185..c71ac865 100644 --- a/macro_ui/src/lib.rs +++ b/macro_ui/src/lib.rs @@ -39,8 +39,8 @@ fn handle_enum(name: &Ident, data: &DataEnum) -> TokenStream2 { if is_simple_enum(data) { return quote! { #[automatically_derived] - impl UI for #name { - fn visit(visitor: &mut dyn UiVisitor, spaces: &str, _in_tuple: bool) { + impl macro_core::visitor::UI for #name { + fn visit(visitor: &mut dyn macro_core::visitor::UiVisitor, spaces: &str, _in_tuple: bool) { println!("{}Add simple enum {} with path '{}'!", spaces, stringify!(#name), visitor.get_path()); visitor.add_simple_enum(&[#(stringify!(#variants).to_string()),*]); } @@ -48,9 +48,9 @@ fn handle_enum(name: &Ident, data: &DataEnum) -> TokenStream2 { #[automatically_derived] impl #name { - pub fn parse<'a>(parser: &'a dyn UiParser<'a>, path: &str, spaces: &str) -> #name { + pub fn parse<'a>(parser: &'a dyn macro_core::parser::UiParser<'a>, path: &str, spaces: &str) -> #name { println!("{}Parse simple enum {} with path '{}'", spaces, stringify!(#name), path); - get_enum(parser, path) + macro_core::parser::get_enum(parser, path) } } }; @@ -61,8 +61,8 @@ fn handle_enum(name: &Ident, data: &DataEnum) -> TokenStream2 { quote! { #[automatically_derived] - impl UI for #name { - fn visit(visitor: &mut dyn UiVisitor, spaces: &str, _in_tuple: bool) { + impl macro_core::visitor::UI for #name { + fn visit(visitor: &mut dyn macro_core::visitor::UiVisitor, spaces: &str, _in_tuple: bool) { println!("{}Create Viewer for enum {} with path '{}'!", spaces, stringify!(#name), visitor.get_path()); visitor.enter_enum(&[#(stringify!(#variants).to_string()),*]); let inner_spaces = format!(" {}", spaces); @@ -74,7 +74,7 @@ fn handle_enum(name: &Ident, data: &DataEnum) -> TokenStream2 { #[automatically_derived] impl #name { - pub fn parse<'a>(parser: &'a dyn UiParser<'a>, path: &str, spaces: &str) -> #name { + pub fn parse<'a>(parser: &'a dyn macro_core::parser::UiParser<'a>, path: &str, spaces: &str) -> #name { println!("{}Parse complex enum {} with path '{}'", spaces, stringify!(#name), path); let t = parser.get_str(&format!("{}.type", path)).unwrap_or(""); println!("{}type '{}'", spaces, t); @@ -96,8 +96,8 @@ fn handle_struct(name: &Ident, fields: &FieldsNamed) -> TokenStream2 { quote! { #[automatically_derived] - impl UI for #name { - fn visit(visitor: &mut dyn UiVisitor, spaces: &str, in_tuple: bool) { + impl macro_core::visitor::UI for #name { + fn visit(visitor: &mut dyn macro_core::visitor::UiVisitor, spaces: &str, in_tuple: bool) { println!("{}Create Viewer for struct {} with path '{}' & in_tuple={}!", spaces, stringify!(#name), visitor.get_path(), in_tuple); visitor.enter_struct(in_tuple); let inner_spaces = format!(" {}", spaces); @@ -109,7 +109,7 @@ fn handle_struct(name: &Ident, fields: &FieldsNamed) -> TokenStream2 { #[automatically_derived] impl #name { - pub fn parse<'a>(parser: &'a dyn UiParser<'a>, path: &str, spaces: &str) -> #name { + pub fn parse<'a>(parser: &'a dyn macro_core::parser::UiParser<'a>, path: &str, spaces: &str) -> #name { println!("{}Parse struct {} with path '{}'", spaces, stringify!(#name), path); Self { #parsed_fields diff --git a/macro_ui/tests/parse_test.rs b/macro_ui/tests/parse_test.rs index e22180fd..72dbc6ba 100644 --- a/macro_ui/tests/parse_test.rs +++ b/macro_ui/tests/parse_test.rs @@ -1,7 +1,5 @@ use macro_convert::Convert; -use macro_core::parser::get_enum; -use macro_core::parser::{MockParser, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; +use macro_core::parser::MockParser; use macro_ui::ui; use std::collections::HashMap; diff --git a/resources/characters/characters.yaml b/resources/characters/characters.yaml index 118e3c5e..0db48347 100644 --- a/resources/characters/characters.yaml +++ b/resources/characters/characters.yaml @@ -9,6 +9,11 @@ skin: type: NormalSkin color: Fair + clothing: + type: Simple + pants: + style: Regular + color: Blue head: ears: type: Normal @@ -66,6 +71,8 @@ skin: type: Scales color: Red + clothing: + type: None head: ears: type: Normal @@ -152,6 +159,11 @@ skin: type: ExoticSkin color: White + clothing: + type: Simple + pants: + style: Balloon + color: Red head: ears: type: Normal @@ -206,6 +218,11 @@ skin: type: ExoticSkin color: Green + clothing: + type: Simple + pants: + style: Regular + color: Purple head: ears: type: None @@ -248,6 +265,11 @@ skin: type: NormalSkin color: Light + clothing: + type: Simple + pants: + style: Regular + color: Gray head: ears: type: Normal diff --git a/resources/templates/appearance_edit.html.tera b/resources/templates/appearance_edit.html.tera index b925fea0..00f7aef6 100644 --- a/resources/templates/appearance_edit.html.tera +++ b/resources/templates/appearance_edit.html.tera @@ -437,6 +437,25 @@ {% endif %} +
  • + Clothing: {{ macros::add_select(name="appearance.body.clothing.type", options=[ "None","Simple" ], selected=appearance.body.clothing.type, update=true) }} + +
  • diff --git a/resources/templates/character.html.tera b/resources/templates/character.html.tera index c2d69a4e..4f5888e1 100644 --- a/resources/templates/character.html.tera +++ b/resources/templates/character.html.tera @@ -438,6 +438,25 @@ {% endif %}
  • +
  • + Clothing: {{ appearance.body.clothing.type }} + +
  • diff --git a/rpg_tools_core/Cargo.toml b/rpg_tools_core/Cargo.toml index 72a3d5bb..57c52130 100644 --- a/rpg_tools_core/Cargo.toml +++ b/rpg_tools_core/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "rpg_tools_core" -version = "0.2.0" +version = "0.3.0" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/rpg_tools_core/src/model/character/appearance/beard/full.rs b/rpg_tools_core/src/model/character/appearance/beard/full.rs index 0359227f..26b2da50 100644 --- a/rpg_tools_core/src/model/character/appearance/beard/full.rs +++ b/rpg_tools_core/src/model/character/appearance/beard/full.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/beard/goatee.rs b/rpg_tools_core/src/model/character/appearance/beard/goatee.rs index 99c2e21c..36648e40 100644 --- a/rpg_tools_core/src/model/character/appearance/beard/goatee.rs +++ b/rpg_tools_core/src/model/character/appearance/beard/goatee.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/beard/mod.rs b/rpg_tools_core/src/model/character/appearance/beard/mod.rs index c3f259b7..c790bed8 100644 --- a/rpg_tools_core/src/model/character/appearance/beard/mod.rs +++ b/rpg_tools_core/src/model/character/appearance/beard/mod.rs @@ -3,8 +3,6 @@ use crate::model::character::appearance::beard::goatee::GoateeStyle; use crate::model::character::appearance::beard::moustache::MoustacheStyle; use crate::model::color::Color; use crate::model::length::Length; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/beard/moustache.rs b/rpg_tools_core/src/model/character/appearance/beard/moustache.rs index 0de5ae6a..6c445754 100644 --- a/rpg_tools_core/src/model/character/appearance/beard/moustache.rs +++ b/rpg_tools_core/src/model/character/appearance/beard/moustache.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/body.rs b/rpg_tools_core/src/model/character/appearance/body.rs index c0dcdee2..8c3e41b5 100644 --- a/rpg_tools_core/src/model/character/appearance/body.rs +++ b/rpg_tools_core/src/model/character/appearance/body.rs @@ -1,8 +1,7 @@ use crate::model::character::appearance::skin::Skin; +use crate::model::equipment::appearance::Clothing; use crate::model::width::Width; use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; @@ -13,6 +12,7 @@ pub struct Body { /// How wide is the body? pub width: Width, pub skin: Skin, + pub clothing: Clothing, } impl Default for Body { @@ -27,6 +27,7 @@ impl Body { shape: BodyShape::Rectangle, width: Width::Average, skin, + clothing: Clothing::None, } } } diff --git a/rpg_tools_core/src/model/character/appearance/ear/mod.rs b/rpg_tools_core/src/model/character/appearance/ear/mod.rs index 53204e47..09567485 100644 --- a/rpg_tools_core/src/model/character/appearance/ear/mod.rs +++ b/rpg_tools_core/src/model/character/appearance/ear/mod.rs @@ -1,7 +1,5 @@ use crate::model::character::appearance::ear::shape::EarShape; use crate::model::size::Size; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/ear/shape.rs b/rpg_tools_core/src/model/character/appearance/ear/shape.rs index e9980a75..36caf07a 100644 --- a/rpg_tools_core/src/model/character/appearance/ear/shape.rs +++ b/rpg_tools_core/src/model/character/appearance/ear/shape.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/eye/brow/mod.rs b/rpg_tools_core/src/model/character/appearance/eye/brow/mod.rs index 25be3f5b..75e6c08e 100644 --- a/rpg_tools_core/src/model/character/appearance/eye/brow/mod.rs +++ b/rpg_tools_core/src/model/character/appearance/eye/brow/mod.rs @@ -2,8 +2,6 @@ use crate::model::character::appearance::eye::brow::shape::EyebrowShape; use crate::model::character::appearance::eye::brow::style::EyebrowStyle; use crate::model::color::Color; use crate::model::width::Width; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/eye/brow/shape.rs b/rpg_tools_core/src/model/character/appearance/eye/brow/shape.rs index 4a8b5964..ce39a52d 100644 --- a/rpg_tools_core/src/model/character/appearance/eye/brow/shape.rs +++ b/rpg_tools_core/src/model/character/appearance/eye/brow/shape.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/eye/brow/style.rs b/rpg_tools_core/src/model/character/appearance/eye/brow/style.rs index e507455b..419c5717 100644 --- a/rpg_tools_core/src/model/character/appearance/eye/brow/style.rs +++ b/rpg_tools_core/src/model/character/appearance/eye/brow/style.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/eye/mod.rs b/rpg_tools_core/src/model/character/appearance/eye/mod.rs index 22d81352..8581b48b 100644 --- a/rpg_tools_core/src/model/character/appearance/eye/mod.rs +++ b/rpg_tools_core/src/model/character/appearance/eye/mod.rs @@ -3,8 +3,6 @@ use crate::model::character::appearance::eye::pupil::PupilShape; use crate::model::character::appearance::eye::shape::EyeShape; use crate::model::color::Color; use crate::model::size::Size; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/eye/pupil.rs b/rpg_tools_core/src/model/character/appearance/eye/pupil.rs index 6524c676..88fb5325 100644 --- a/rpg_tools_core/src/model/character/appearance/eye/pupil.rs +++ b/rpg_tools_core/src/model/character/appearance/eye/pupil.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/eye/shape.rs b/rpg_tools_core/src/model/character/appearance/eye/shape.rs index 4c328f2e..66cb0ed1 100644 --- a/rpg_tools_core/src/model/character/appearance/eye/shape.rs +++ b/rpg_tools_core/src/model/character/appearance/eye/shape.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/bun.rs b/rpg_tools_core/src/model/character/appearance/hair/bun.rs index 872979fa..e511259b 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/bun.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/bun.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/hairline.rs b/rpg_tools_core/src/model/character/appearance/hair/hairline.rs index f2c1ecd0..213ece3e 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/hairline.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/hairline.rs @@ -1,8 +1,5 @@ use crate::model::size::Size; use macro_convert::Convert; -use macro_core::parser::get_enum; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/long.rs b/rpg_tools_core/src/model/character/appearance/hair/long.rs index a05d3817..c32716a6 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/long.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/long.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/mod.rs b/rpg_tools_core/src/model/character/appearance/hair/mod.rs index 8419a53a..68e059da 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/mod.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/mod.rs @@ -6,8 +6,6 @@ use crate::model::character::appearance::hair::short::ShortHair; use crate::model::color::Color; use crate::model::length::Length; use crate::model::size::Size; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/ponytail/mod.rs b/rpg_tools_core/src/model/character/appearance/hair/ponytail/mod.rs index 2aaf5501..9ee498b3 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/ponytail/mod.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/ponytail/mod.rs @@ -3,8 +3,6 @@ use crate::model::character::appearance::hair::ponytail::position::PonytailPosit use crate::model::character::appearance::hair::ponytail::style::PonytailStyle; use crate::model::color::Color; use crate::model::length::Length; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/ponytail/position.rs b/rpg_tools_core/src/model/character/appearance/hair/ponytail/position.rs index a00d7629..a70ff845 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/ponytail/position.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/ponytail/position.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/ponytail/style.rs b/rpg_tools_core/src/model/character/appearance/hair/ponytail/style.rs index 427fe801..e62fd330 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/ponytail/style.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/ponytail/style.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/hair/short.rs b/rpg_tools_core/src/model/character/appearance/hair/short.rs index 3dda5939..4cf51f9d 100644 --- a/rpg_tools_core/src/model/character/appearance/hair/short.rs +++ b/rpg_tools_core/src/model/character/appearance/hair/short.rs @@ -1,7 +1,5 @@ use crate::model::side::Side; use crate::model::size::Size; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/head.rs b/rpg_tools_core/src/model/character/appearance/head.rs index be627a38..bfd422d7 100644 --- a/rpg_tools_core/src/model/character/appearance/head.rs +++ b/rpg_tools_core/src/model/character/appearance/head.rs @@ -4,8 +4,6 @@ use crate::model::character::appearance::hair::Hair; use crate::model::character::appearance::mouth::Mouth; use crate::model::character::appearance::skin::Skin; use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/mod.rs b/rpg_tools_core/src/model/character/appearance/mod.rs index 56713ff4..373cb313 100644 --- a/rpg_tools_core/src/model/character/appearance/mod.rs +++ b/rpg_tools_core/src/model/character/appearance/mod.rs @@ -1,8 +1,6 @@ use crate::model::character::appearance::body::Body; use crate::model::character::appearance::head::Head; use crate::model::length::Length; -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/mouth.rs b/rpg_tools_core/src/model/character/appearance/mouth.rs index 4b36a340..6f9ec0fb 100644 --- a/rpg_tools_core/src/model/character/appearance/mouth.rs +++ b/rpg_tools_core/src/model/character/appearance/mouth.rs @@ -2,8 +2,6 @@ use crate::model::character::appearance::beard::Beard; use crate::model::color::Color; use crate::model::size::Size; use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/character/appearance/skin.rs b/rpg_tools_core/src/model/character/appearance/skin.rs index 7d8cd314..ca39f0ff 100644 --- a/rpg_tools_core/src/model/character/appearance/skin.rs +++ b/rpg_tools_core/src/model/character/appearance/skin.rs @@ -1,7 +1,5 @@ use crate::model::color::Color; use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; @@ -16,7 +14,7 @@ pub enum Skin { impl Default for Skin { fn default() -> Self { - Self::ExoticSkin { color: Color::Aqua } + Skin::normal(SkinColor::default()) } } diff --git a/rpg_tools_core/src/model/color.rs b/rpg_tools_core/src/model/color.rs index c8f8ec19..aba030d0 100644 --- a/rpg_tools_core/src/model/color.rs +++ b/rpg_tools_core/src/model/color.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/equipment/appearance/mod.rs b/rpg_tools_core/src/model/equipment/appearance/mod.rs new file mode 100644 index 00000000..03c3a92f --- /dev/null +++ b/rpg_tools_core/src/model/equipment/appearance/mod.rs @@ -0,0 +1,15 @@ +use crate::model::equipment::appearance::pants::Pants; +use macro_ui::ui; +use serde::{Deserialize, Serialize}; + +pub mod pants; + +#[derive(ui, Clone, Copy, Debug, Default, PartialEq, Eq, Serialize, Deserialize)] +#[serde(tag = "type")] +pub enum Clothing { + #[default] + None, + Simple { + pants: Pants, + }, +} diff --git a/rpg_tools_core/src/model/equipment/appearance/pants.rs b/rpg_tools_core/src/model/equipment/appearance/pants.rs new file mode 100644 index 00000000..599776b3 --- /dev/null +++ b/rpg_tools_core/src/model/equipment/appearance/pants.rs @@ -0,0 +1,22 @@ +use crate::model::color::Color; +use macro_convert::Convert; +use macro_ui::ui; +use serde::{Deserialize, Serialize}; + +/// Clothing for the lower body. +#[derive(ui, Clone, Copy, Debug, Default, PartialEq, Eq, Serialize, Deserialize)] +pub struct Pants { + pub style: PantsStyle, + pub color: Color, +} + +/// What style of pants? +#[derive(Convert, ui, Clone, Copy, Debug, Default, PartialEq, Eq, Serialize, Deserialize)] +pub enum PantsStyle { + Balloon, + Bermuda, + HotPants, + #[default] + Regular, + Shorts, +} diff --git a/rpg_tools_core/src/model/equipment/mod.rs b/rpg_tools_core/src/model/equipment/mod.rs new file mode 100644 index 00000000..2126bcfa --- /dev/null +++ b/rpg_tools_core/src/model/equipment/mod.rs @@ -0,0 +1 @@ +pub mod appearance; diff --git a/rpg_tools_core/src/model/length.rs b/rpg_tools_core/src/model/length.rs index 6ec476e8..a1c61ec2 100644 --- a/rpg_tools_core/src/model/length.rs +++ b/rpg_tools_core/src/model/length.rs @@ -1,5 +1,3 @@ -use macro_core::parser::UiParser; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/mod.rs b/rpg_tools_core/src/model/mod.rs index 5911d2fa..9e56bab2 100644 --- a/rpg_tools_core/src/model/mod.rs +++ b/rpg_tools_core/src/model/mod.rs @@ -1,5 +1,6 @@ pub mod character; pub mod color; +pub mod equipment; pub mod length; pub mod side; pub mod size; diff --git a/rpg_tools_core/src/model/side.rs b/rpg_tools_core/src/model/side.rs index a878d645..508777af 100644 --- a/rpg_tools_core/src/model/side.rs +++ b/rpg_tools_core/src/model/side.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/size.rs b/rpg_tools_core/src/model/size.rs index fcd44b0d..070c1840 100644 --- a/rpg_tools_core/src/model/size.rs +++ b/rpg_tools_core/src/model/size.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_core/src/model/width.rs b/rpg_tools_core/src/model/width.rs index 9674b6c1..a1b3fecd 100644 --- a/rpg_tools_core/src/model/width.rs +++ b/rpg_tools_core/src/model/width.rs @@ -1,6 +1,4 @@ use macro_convert::Convert; -use macro_core::parser::{get_enum, UiParser}; -use macro_core::visitor::{UiVisitor, UI}; use macro_ui::ui; use serde::{Deserialize, Serialize}; diff --git a/rpg_tools_editor/Cargo.toml b/rpg_tools_editor/Cargo.toml index 2e97ad03..a9daf3ed 100644 --- a/rpg_tools_editor/Cargo.toml +++ b/rpg_tools_editor/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "rpg_tools_editor" -version = "0.2.0" +version = "0.3.0" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/rpg_tools_rendering/Cargo.toml b/rpg_tools_rendering/Cargo.toml index 4eb9d473..b181e9e0 100644 --- a/rpg_tools_rendering/Cargo.toml +++ b/rpg_tools_rendering/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "rpg_tools_rendering" -version = "0.2.0" +version = "0.3.0" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/rpg_tools_rendering/examples/beards_full.rs b/rpg_tools_rendering/examples/beards_full.rs index f54306ef..c1db5235 100644 --- a/rpg_tools_rendering/examples/beards_full.rs +++ b/rpg_tools_rendering/examples/beards_full.rs @@ -18,6 +18,7 @@ use rpg_tools_core::model::character::appearance::mouth::{Mouth, SpecialTeeth, T use rpg_tools_core::model::character::appearance::skin::{Skin, SkinColor}; use rpg_tools_core::model::character::appearance::Appearance; use rpg_tools_core::model::color::Color; +use rpg_tools_core::model::equipment::appearance::Clothing; use rpg_tools_core::model::length::Length; use rpg_tools_core::model::size::Size::Medium; use rpg_tools_core::model::width::Width; @@ -56,6 +57,7 @@ fn create_appearance(height: Length, beard: &Beard, face: &HeadShape) -> Appeara shape: BodyShape::Rectangle, width: Width::Average, skin: Skin::normal(SkinColor::Light), + clothing: Clothing::None, }, Head { ears: Ears::Normal { diff --git a/rpg_tools_rendering/examples/body.rs b/rpg_tools_rendering/examples/body.rs index 8d5e6831..99b394e4 100644 --- a/rpg_tools_rendering/examples/body.rs +++ b/rpg_tools_rendering/examples/body.rs @@ -2,44 +2,30 @@ extern crate rpg_tools_core; extern crate rpg_tools_rendering; use crate::utils::render::render_2_sets; -use rpg_tools_core::model::character::appearance::body::BodyShape::*; use rpg_tools_core::model::character::appearance::body::{Body, BodyShape}; -use rpg_tools_core::model::character::appearance::ear::Ears; -use rpg_tools_core::model::character::appearance::eye::Eyes; -use rpg_tools_core::model::character::appearance::hair::Hair; -use rpg_tools_core::model::character::appearance::head::{Head, HeadShape}; -use rpg_tools_core::model::character::appearance::mouth::Mouth; -use rpg_tools_core::model::character::appearance::skin::{Skin, SkinColor}; +use rpg_tools_core::model::character::appearance::head::Head; use rpg_tools_core::model::character::appearance::Appearance; use rpg_tools_core::model::length::Length; use rpg_tools_core::model::width::Width; -use rpg_tools_core::model::width::Width::*; pub mod utils; fn main() { - let rows = vec![Thin, Average, Wide]; - let columns = vec![Fat, Hourglass, Muscular, Rectangle]; + let rows = Width::get_all(); + let columns = BodyShape::get_all(); render_2_sets("bodies.svg", rows, columns, create_appearance, false); } fn create_appearance(height: Length, width: &Width, shape: &BodyShape) -> Appearance { - let skin = Skin::normal(SkinColor::Light); Appearance::humanoid( Body { shape: *shape, width: *width, - skin, - }, - Head { - ears: Ears::None, - eyes: Eyes::None, - hair: Hair::None, - mouth: Mouth::None, - shape: HeadShape::Oval, - skin, + skin: Default::default(), + clothing: Default::default(), }, + Head::default(), height, ) } diff --git a/rpg_tools_rendering/examples/eyebrows.rs b/rpg_tools_rendering/examples/eyebrows.rs index b75f97a3..29ea7e40 100644 --- a/rpg_tools_rendering/examples/eyebrows.rs +++ b/rpg_tools_rendering/examples/eyebrows.rs @@ -22,17 +22,16 @@ use rpg_tools_core::model::color::Color; use rpg_tools_core::model::length::Length; use rpg_tools_core::model::size::Size::Medium; use rpg_tools_core::model::width::Width; -use std::vec; pub mod utils; fn main() { let mut options = Vec::new(); - for is_unibrow in vec![false, true] { + for is_unibrow in &[false, true] { for style in EyebrowStyle::get_all() { for width in Width::get_all() { - options.push((is_unibrow, style, width)); + options.push((*is_unibrow, style, width)); } } } diff --git a/rpg_tools_rendering/examples/eyes.rs b/rpg_tools_rendering/examples/eyes.rs index c25d51d8..320ace95 100644 --- a/rpg_tools_rendering/examples/eyes.rs +++ b/rpg_tools_rendering/examples/eyes.rs @@ -52,7 +52,7 @@ fn create_appearance(height: Length, eyes: &Eyes, face: &HeadShape) -> Appearanc Appearance::head( Head { ears: Ears::None, - eyes: eyes.clone(), + eyes: *eyes, hair: Hair::None, mouth: Mouth::None, shape: *face, diff --git a/rpg_tools_rendering/examples/pants.rs b/rpg_tools_rendering/examples/pants.rs new file mode 100644 index 00000000..a4756a2a --- /dev/null +++ b/rpg_tools_rendering/examples/pants.rs @@ -0,0 +1,50 @@ +extern crate rpg_tools_core; +extern crate rpg_tools_rendering; + +use crate::utils::render::render_2_sets; +use rpg_tools_core::model::character::appearance::body::{Body, BodyShape}; +use rpg_tools_core::model::character::appearance::head::Head; +use rpg_tools_core::model::character::appearance::Appearance; +use rpg_tools_core::model::color::Color; +use rpg_tools_core::model::equipment::appearance::pants::{Pants, PantsStyle}; +use rpg_tools_core::model::equipment::appearance::Clothing; +use rpg_tools_core::model::length::Length; +use rpg_tools_core::model::width::Width; + +pub mod utils; + +fn main() { + let mut pants = vec![]; + + for style in PantsStyle::get_all() { + pants.push(create(style)) + } + + render_2_sets( + "pants.svg", + pants, + BodyShape::get_all(), + create_appearance, + false, + ); +} + +fn create(style: PantsStyle) -> Pants { + Pants { + style, + color: Color::Blue, + } +} + +fn create_appearance(height: Length, pants: &Pants, shape: &BodyShape) -> Appearance { + Appearance::humanoid( + Body { + shape: *shape, + width: Width::default(), + skin: Default::default(), + clothing: Clothing::Simple { pants: *pants }, + }, + Head::default(), + height, + ) +} diff --git a/rpg_tools_rendering/src/rendering/body/torso.rs b/rpg_tools_rendering/src/rendering/body/torso.rs index 82da57fe..0b7ac964 100644 --- a/rpg_tools_rendering/src/rendering/body/torso.rs +++ b/rpg_tools_rendering/src/rendering/body/torso.rs @@ -4,7 +4,7 @@ use crate::renderer::{RenderOptions, Renderer}; use crate::rendering::config::body::torso::TorsoConfig; use crate::rendering::config::body::BodyConfig; use crate::rendering::config::RenderConfig; -use rpg_tools_core::model::character::appearance::body::{Body, BodyShape}; +use rpg_tools_core::model::character::appearance::body::Body; pub fn render_torso( renderer: &mut dyn Renderer, @@ -14,12 +14,11 @@ pub fn render_torso( options: &RenderOptions, ) { let torso_aabb = config.body.get_torso_aabb(body, aabb); - let polygon = match body.shape { - BodyShape::Fat => create_torso(&torso_aabb, &config.body, &config.body.fat), - BodyShape::Hourglass => create_torso(&torso_aabb, &config.body, &config.body.hourglass), - BodyShape::Muscular => create_torso(&torso_aabb, &config.body, &config.body.muscular), - BodyShape::Rectangle => create_torso(&torso_aabb, &config.body, &config.body.rectangle), - }; + let polygon = create_torso( + &torso_aabb, + &config.body, + config.body.get_torso_config(body.shape), + ); renderer.render_rounded_polygon(&polygon, options); } diff --git a/rpg_tools_rendering/src/rendering/character.rs b/rpg_tools_rendering/src/rendering/character.rs index 6a0b843b..5bd885f3 100644 --- a/rpg_tools_rendering/src/rendering/character.rs +++ b/rpg_tools_rendering/src/rendering/character.rs @@ -4,6 +4,7 @@ use crate::renderer::Renderer; use crate::rendering::body::{calculate_head_aabb, render_body}; use crate::rendering::config::RenderConfig; use crate::rendering::ear::render_ears; +use crate::rendering::equipment::render_clothing; use crate::rendering::eye::render_eyes; use crate::rendering::hair::{ render_hair_back, render_hair_before_head_from_front, render_hair_behind_head_from_front, @@ -38,6 +39,7 @@ pub fn render_character_from_front( let head_aabb = calculate_head_aabb(config, &inner); render_head_behind_body_from_front(renderer, config, head, &head_aabb); render_body(renderer, config, &inner, body); + render_clothing(renderer, config, &inner, body); render_head_before_body_from_front(renderer, config, head, &head_aabb); } } @@ -57,6 +59,7 @@ pub fn render_character_from_back( } Appearance::Humanoid { body, head, .. } => { render_body(renderer, config, &inner, &body); + render_clothing(renderer, config, &inner, &body); let head_aabb = calculate_head_aabb(config, &inner); render_head_from_back(renderer, config, &head, &head_aabb); } diff --git a/rpg_tools_rendering/src/rendering/config/body/mod.rs b/rpg_tools_rendering/src/rendering/config/body/mod.rs index 16f28be7..8f8ba2b7 100644 --- a/rpg_tools_rendering/src/rendering/config/body/mod.rs +++ b/rpg_tools_rendering/src/rendering/config/body/mod.rs @@ -35,7 +35,7 @@ impl BodyConfig { } pub fn get_leg_width(&self, body: &Body) -> f32 { - self.width_leg * self.get_width_factor(body) + self.width_leg * self.get_width_factor(body) * self.get_torso_config(body.shape).legs_width } pub fn get_width_factor(&self, body: &Body) -> f32 { @@ -54,6 +54,7 @@ impl BodyConfig { /// The aabb of both legs is limited to the smaller width of shoulders or hip to match *Fat* & *Muscular* [`body shapes`](BodyShape). pub fn get_legs_width(&self, body: &Body) -> f32 { self.get_shoulder_width(body).min(self.get_hip_width(body)) + * self.get_torso_config(body.shape).legs_width } pub fn get_shoulder_width(&self, body: &Body) -> f32 { @@ -78,12 +79,16 @@ impl BodyConfig { self.get_shoulder_width(body).max(self.get_hip_width(body)) } + pub fn get_torso_bottom(&self) -> f32 { + self.y_torso + self.height_torso + } + pub fn get_arm_y(&self) -> f32 { self.y_torso + 0.05 } pub fn get_leg_y(&self) -> f32 { - self.y_torso + self.height_torso - 0.05 + self.get_torso_bottom() - 0.05 } pub fn get_fat_offset_factor(&self, body: &Body) -> f32 { @@ -99,6 +104,21 @@ impl BodyConfig { } pub fn get_foot_radius(&self, body: &Body, aabb: &AABB) -> u32 { - aabb.convert_to_height(self.foot_factor * self.get_width_factor(body)) + aabb.convert_to_height(self.get_foot_radius_factor(body)) + } + + pub fn get_foot_radius_factor(&self, body: &Body) -> f32 { + self.foot_factor + * self.get_width_factor(body) + * self.get_torso_config(body.shape).legs_width + } + + pub fn get_torso_config(&self, shape: BodyShape) -> &TorsoConfig { + match shape { + BodyShape::Fat => &self.fat, + BodyShape::Hourglass => &self.hourglass, + BodyShape::Muscular => &self.muscular, + BodyShape::Rectangle => &self.rectangle, + } } } diff --git a/rpg_tools_rendering/src/rendering/config/body/torso.rs b/rpg_tools_rendering/src/rendering/config/body/torso.rs index 17a1a1a9..ed08fb70 100644 --- a/rpg_tools_rendering/src/rendering/config/body/torso.rs +++ b/rpg_tools_rendering/src/rendering/config/body/torso.rs @@ -4,4 +4,5 @@ pub struct TorsoConfig { pub shoulder_width: f32, pub waist_width: f32, pub hip_width: f32, + pub legs_width: f32, } diff --git a/rpg_tools_rendering/src/rendering/config/equipment/mod.rs b/rpg_tools_rendering/src/rendering/config/equipment/mod.rs new file mode 100644 index 00000000..9cb84244 --- /dev/null +++ b/rpg_tools_rendering/src/rendering/config/equipment/mod.rs @@ -0,0 +1 @@ +pub mod pants; diff --git a/rpg_tools_rendering/src/rendering/config/equipment/pants.rs b/rpg_tools_rendering/src/rendering/config/equipment/pants.rs new file mode 100644 index 00000000..c53b0b49 --- /dev/null +++ b/rpg_tools_rendering/src/rendering/config/equipment/pants.rs @@ -0,0 +1,35 @@ +use crate::rendering::config::body::BodyConfig; +use rpg_tools_core::model::character::appearance::body::Body; + +/// The rendering config of the [`pants`](Pants). +#[derive(Debug, PartialEq)] +pub struct PantsConfig { + pub height_bermuda: f32, + pub height_shorts: f32, + pub offset_center: f32, + pub offset_bottom: f32, + pub width_padding: f32, + pub balloon_padding: f32, +} + +impl PantsConfig { + /// Returns the width of pants and the space between the individuals pants. + pub fn get_widths(&self, config: &BodyConfig, body: &Body) -> (f32, f32) { + let legs_width = config.get_legs_width(body); + let padding = legs_width * self.width_padding; + let pants_width = legs_width + padding; + let pant_width = config.get_leg_width(body) + padding; + let inner_width = pants_width - 2.0 * pant_width; + + (pants_width, inner_width) + } + + pub fn get_hip_width(&self, config: &BodyConfig, body: &Body) -> f32 { + let torso = config.get_torso_config(body.shape); + torso.hip_width * (1.0 + self.width_padding) + } + + pub fn get_bottom_y(&self, config: &BodyConfig, body: &Body) -> f32 { + 1.0 - config.get_foot_radius_factor(body) - self.offset_bottom + } +} diff --git a/rpg_tools_rendering/src/rendering/config/example.rs b/rpg_tools_rendering/src/rendering/config/example.rs index 2709d1b3..4f51fd2a 100644 --- a/rpg_tools_rendering/src/rendering/config/example.rs +++ b/rpg_tools_rendering/src/rendering/config/example.rs @@ -5,6 +5,7 @@ use crate::renderer::RenderOptions; use crate::rendering::config::body::torso::TorsoConfig; use crate::rendering::config::body::BodyConfig; use crate::rendering::config::ear::EarConfig; +use crate::rendering::config::equipment::pants::PantsConfig; use crate::rendering::config::eye::eyebrow::EyebrowConfig; use crate::rendering::config::eye::EyeConfig; use crate::rendering::config::hair::hairline::HairlineConfig; @@ -50,21 +51,25 @@ pub fn create_config() -> RenderConfig { shoulder_width: 0.64, waist_width: 0.82, hip_width: 1.0, + legs_width: 1.0, }, hourglass: TorsoConfig { shoulder_width: 1.0, waist_width: 0.7, hip_width: 1.0, + legs_width: 0.85, }, muscular: TorsoConfig { shoulder_width: 1.0, waist_width: 0.82, hip_width: 0.64, + legs_width: 1.0, }, rectangle: TorsoConfig { shoulder_width: 1.0, waist_width: 1.0, hip_width: 1.0, + legs_width: 0.9, }, width_arm: 0.1, width_leg: 0.14, @@ -114,6 +119,14 @@ pub fn create_config() -> RenderConfig { ear: create_ear_config(), eye: create_eye_config(), mouth: create_mouth_config(), + pants: PantsConfig { + height_bermuda: 0.5, + height_shorts: 0.3, + offset_center: 0.03, + offset_bottom: 0.01, + width_padding: 0.05, + balloon_padding: 0.2, + }, } } diff --git a/rpg_tools_rendering/src/rendering/config/mod.rs b/rpg_tools_rendering/src/rendering/config/mod.rs index 2ff63f37..b04bbf93 100644 --- a/rpg_tools_rendering/src/rendering/config/mod.rs +++ b/rpg_tools_rendering/src/rendering/config/mod.rs @@ -2,6 +2,7 @@ use crate::renderer::color::WebColor; use crate::renderer::RenderOptions; use crate::rendering::config::body::BodyConfig; use crate::rendering::config::ear::EarConfig; +use crate::rendering::config::equipment::pants::PantsConfig; use crate::rendering::config::eye::EyeConfig; use crate::rendering::config::hair::HairConfig; use crate::rendering::config::head::HeadConfig; @@ -12,6 +13,7 @@ use rpg_tools_core::model::color::Color; pub mod body; pub mod ear; +pub mod equipment; pub mod example; pub mod eye; pub mod hair; @@ -27,11 +29,12 @@ pub struct RenderConfig { pub line_width: u32, pub thin_line_width: u32, pub body: BodyConfig, - pub hair: HairConfig, - pub head: HeadConfig, pub ear: EarConfig, pub eye: EyeConfig, + pub hair: HairConfig, + pub head: HeadConfig, pub mouth: MouthConfig, + pub pants: PantsConfig, } impl RenderConfig { diff --git a/rpg_tools_rendering/src/rendering/equipment/mod.rs b/rpg_tools_rendering/src/rendering/equipment/mod.rs new file mode 100644 index 00000000..86545cba --- /dev/null +++ b/rpg_tools_rendering/src/rendering/equipment/mod.rs @@ -0,0 +1,19 @@ +use crate::math::aabb2d::AABB; +use crate::renderer::Renderer; +use crate::rendering::config::RenderConfig; +use crate::rendering::equipment::pants::render_pants; +use rpg_tools_core::model::character::appearance::body::Body; +use rpg_tools_core::model::equipment::appearance::Clothing; + +pub mod pants; + +pub fn render_clothing( + renderer: &mut dyn Renderer, + config: &RenderConfig, + aabb: &AABB, + body: &Body, +) { + if let Clothing::Simple { pants } = &body.clothing { + render_pants(renderer, config, aabb, body, pants) + } +} diff --git a/rpg_tools_rendering/src/rendering/equipment/pants.rs b/rpg_tools_rendering/src/rendering/equipment/pants.rs new file mode 100644 index 00000000..e18fb44e --- /dev/null +++ b/rpg_tools_rendering/src/rendering/equipment/pants.rs @@ -0,0 +1,104 @@ +use crate::math::aabb2d::AABB; +use crate::math::polygon2d::builder::Polygon2dBuilder; +use crate::math::polygon2d::Polygon2d; +use crate::renderer::Renderer; +use crate::rendering::config::RenderConfig; +use rpg_tools_core::model::character::appearance::body::Body; +use rpg_tools_core::model::equipment::appearance::pants::{Pants, PantsStyle}; + +pub fn render_pants( + renderer: &mut dyn Renderer, + config: &RenderConfig, + aabb: &AABB, + body: &Body, + pants: &Pants, +) { + let options = config.get_options(pants.color); + let polygon = match pants.style { + PantsStyle::Balloon => get_balloon(config, aabb, body), + PantsStyle::Bermuda => get_bermuda(config, aabb, body), + PantsStyle::HotPants => get_hot_pants(config, aabb, body), + PantsStyle::Regular => get_regular_pants(config, aabb, body), + PantsStyle::Shorts => get_shorts(config, aabb, body), + }; + + renderer.render_rounded_polygon(&polygon, &options); +} + +fn get_balloon(config: &RenderConfig, aabb: &AABB, body: &Body) -> Polygon2d { + let bottom_y = config.pants.get_bottom_y(&config.body, body); + get_pants(config, aabb, body, bottom_y, true) +} + +fn get_bermuda(config: &RenderConfig, aabb: &AABB, body: &Body) -> Polygon2d { + get_shorter_pants(config, aabb, body, config.pants.height_bermuda) +} + +fn get_hot_pants(config: &RenderConfig, aabb: &AABB, body: &Body) -> Polygon2d { + get_base(config, aabb, body).build() +} + +fn get_regular_pants(config: &RenderConfig, aabb: &AABB, body: &Body) -> Polygon2d { + let bottom_y = config.pants.get_bottom_y(&config.body, body); + get_pants(config, aabb, body, bottom_y, false) +} + +fn get_shorts(config: &RenderConfig, aabb: &AABB, body: &Body) -> Polygon2d { + get_shorter_pants(config, aabb, body, config.pants.height_shorts) +} + +fn get_shorter_pants(config: &RenderConfig, aabb: &AABB, body: &Body, factor: f32) -> Polygon2d { + let top_y = config.body.get_torso_bottom(); + let full_bottom_y = config.pants.get_bottom_y(&config.body, body); + let bottom_y = interpolate(top_y, full_bottom_y, factor); + get_pants(config, aabb, body, bottom_y, false) +} + +fn get_pants( + config: &RenderConfig, + aabb: &AABB, + body: &Body, + bottom_y: f32, + is_balloon: bool, +) -> Polygon2d { + let mut builder = get_base(config, aabb, body); + let (pants_width, inner_width) = config.pants.get_widths(&config.body, body); + let top_y = config.body.get_torso_bottom(); + let mid_y = (top_y + bottom_y) * 0.5; + + builder.add_mirrored_points(aabb, pants_width, mid_y, false); + + if is_balloon { + let balloon_extra = pants_width * config.pants.balloon_padding; + builder.add_mirrored_points(aabb, pants_width + balloon_extra, bottom_y, false); + builder.add_mirrored_points(aabb, inner_width - balloon_extra, bottom_y, false); + } else { + builder.add_mirrored_points(aabb, pants_width, bottom_y, true); + builder.add_mirrored_points(aabb, inner_width, bottom_y, true); + } + + builder.add_mirrored_points(aabb, inner_width, mid_y, false); + builder.add_point(aabb.get_point(0.5, top_y), false); + + builder.build() +} + +fn get_base(config: &RenderConfig, aabb: &AABB, body: &Body) -> Polygon2dBuilder { + let torso_aabb = config.body.get_torso_aabb(body, aabb); + let hip_width = config.pants.get_hip_width(&config.body, body); + let top_y = config.body.y_lower; + let center_y = top_y + config.pants.offset_center; + let mut builder = Polygon2dBuilder::new(); + + // center curves downwards + builder.add_point(torso_aabb.get_point(0.5, center_y), false); + // rectangle forming the base of the pants + builder.add_mirrored_points(&torso_aabb, hip_width, top_y, true); + builder.add_mirrored_points(&torso_aabb, hip_width, 1.0, false); + + builder +} + +fn interpolate(start: f32, end: f32, factor: f32) -> f32 { + start * (1.0 - factor) + end * factor +} diff --git a/rpg_tools_rendering/src/rendering/mod.rs b/rpg_tools_rendering/src/rendering/mod.rs index c7b65de8..8a0073fa 100644 --- a/rpg_tools_rendering/src/rendering/mod.rs +++ b/rpg_tools_rendering/src/rendering/mod.rs @@ -8,6 +8,7 @@ pub mod body; pub mod character; pub mod config; pub mod ear; +pub mod equipment; pub mod eye; pub mod hair; pub mod head;