use libpso::character::character; use crate::common::leveltable::CharacterStats; use crate::entity::character::Character; use crate::ship::items::Inventory; // TODO: exp pub struct CharacterBytesBuilder<'a> { character: Option<&'a Character>, stats: Option<&'a CharacterStats>, level: Option, } impl<'a> CharacterBytesBuilder<'a> { pub fn new() -> CharacterBytesBuilder<'a> { CharacterBytesBuilder { character: None, stats: None, level: None, } } pub fn character(self, character: &'a Character) -> CharacterBytesBuilder<'a> { CharacterBytesBuilder { character: Some(character), ..self } } pub fn stats(self, stats: &'a CharacterStats) -> CharacterBytesBuilder<'a> { CharacterBytesBuilder { stats: Some(stats), ..self } } pub fn level(self, level: u32) -> CharacterBytesBuilder<'a> { CharacterBytesBuilder { level: Some(level), ..self } } pub fn build(self) -> character::Character { let character = self.character.unwrap(); let stats = self.stats.unwrap(); let level = self.level.unwrap(); character::Character { name: libpso::utf8_to_utf16_array!(character.name, 16), hp: stats.hp, atp: stats.atp, mst: stats.mst, evp: stats.evp, dfp: stats.dfp, ata: stats.ata, lck: stats.lck, level: level, section_id: character.section_id.into(), ch_class: character.char_class.into(), costume: character.appearance.costume, skin: character.appearance.skin, face: character.appearance.face, head: character.appearance.head, hair: character.appearance.hair, hair_r: character.appearance.hair_r, hair_g: character.appearance.hair_g, hair_b: character.appearance.hair_b, prop_x: character.appearance.prop_x, prop_y: character.appearance.prop_y, config: character.config.as_bytes(), techniques: character.techs.as_bytes(), ..character::Character::default() } } } pub struct FullCharacterBytesBuilder<'a> { character: Option<&'a Character>, stats: Option<&'a CharacterStats>, level: Option, inventory: Option<&'a Inventory>, key_config: Option<&'a [u8; 0x16C]>, joystick_config: Option<&'a [u8; 0x38]>, } impl<'a> FullCharacterBytesBuilder<'a> { pub fn new() -> FullCharacterBytesBuilder<'a> { FullCharacterBytesBuilder { character: None, stats: None, level: None, inventory: None, key_config: None, joystick_config: None, } } pub fn character(self, character: &'a Character) -> FullCharacterBytesBuilder<'a> { FullCharacterBytesBuilder { character: Some(character), ..self } } pub fn stats(self, stats: &'a CharacterStats) -> FullCharacterBytesBuilder<'a> { FullCharacterBytesBuilder { stats: Some(stats), ..self } } pub fn level(self, level: u32) -> FullCharacterBytesBuilder<'a> { FullCharacterBytesBuilder { level: Some(level), ..self } } pub fn inventory(self, inventory: &'a Inventory) -> FullCharacterBytesBuilder<'a> { FullCharacterBytesBuilder { inventory: Some(inventory), ..self } } pub fn key_config(self, key_config: &'a [u8; 0x16C]) -> FullCharacterBytesBuilder<'a> { FullCharacterBytesBuilder { key_config: Some(key_config), ..self } } pub fn joystick_config(self, joystick_config: &'a [u8; 0x38]) -> FullCharacterBytesBuilder<'a> { FullCharacterBytesBuilder { joystick_config: Some(joystick_config), ..self } } pub fn build(self) -> character::FullCharacter { let character = self.character.unwrap(); let stats = self.stats.unwrap(); let level = self.level.unwrap(); let inventory = self.inventory.unwrap(); let key_config = self.key_config.unwrap(); let joystick_config = self.joystick_config.unwrap(); character::FullCharacter { character: CharacterBytesBuilder::new() .character(&character) .stats(&stats) .level(level - 1) .build(), inventory: character::Inventory { item_count: inventory.count() as u8, items: inventory.as_client_inventory_items(), ..character::Inventory::default() }, key_team_config: character::KeyTeamConfig { key_config: *key_config, joystick_config: *joystick_config, ..character::KeyTeamConfig::default() }, info_board: character.info_board.as_bytes(), ..character::FullCharacter::default() } } }