diff --git a/nap_gameserver/src/commands/avatar.rs b/nap_gameserver/src/commands/avatar.rs index 6c33a56..027c162 100644 --- a/nap_gameserver/src/commands/avatar.rs +++ b/nap_gameserver/src/commands/avatar.rs @@ -1,4 +1,4 @@ -use data::tables::AvatarBaseID; +use data::tables::{self, AvatarBaseID}; use proto::{AddAvatarPerformType, AddAvatarScNotify, PlayerSyncScNotify}; use crate::ServerState; @@ -55,3 +55,62 @@ pub async fn add( "successfully added avatar {avatar_id} to player {uid}" )) } + +pub async fn add_all( + args: ArgSlice<'_>, + state: &ServerState, +) -> Result> { + const USAGE: &str = "Usage: avatar add_all [player_uid]"; + + if args.len() != 1 { + return Ok(USAGE.to_string()); + } + + let uid = args[0].parse::()?; + + let Some(player_lock) = state.player_mgr.get_player(uid).await else { + return Ok(String::from("player not found")); + }; + + let (session_id, avatar_sync, avatar_id_list) = { + let mut player = player_lock.lock().await; + + let avatar_id_list = tables::avatar_base_template_tb::iter() + .filter(|tmpl| tmpl.id.value() < 2000 && !player.role_model.has_avatar(tmpl.id)) + .map(|tmpl| tmpl.id) + .collect::>(); + + avatar_id_list + .iter() + .for_each(|id| player.role_model.add_avatar(*id)); + + ( + player.current_session_id(), + player.role_model.avatar_sync(), + avatar_id_list, + ) + }; + + if let Some(session) = session_id.map(|id| state.session_mgr.get(id)).flatten() { + for id in avatar_id_list { + session + .notify(AddAvatarScNotify { + avatar_id: id.value(), + perform_type: AddAvatarPerformType::ShowPopup.into(), + ..Default::default() + }) + .await?; + } + + session + .notify(PlayerSyncScNotify { + avatar: Some(avatar_sync), + ..Default::default() + }) + .await?; + } else { + state.player_mgr.save_and_remove(uid).await; + } + + Ok(format!("successfully added all avatars to player {uid}")) +} diff --git a/nap_gameserver/src/commands/mod.rs b/nap_gameserver/src/commands/mod.rs index 86b1fb7..9e9e926 100644 --- a/nap_gameserver/src/commands/mod.rs +++ b/nap_gameserver/src/commands/mod.rs @@ -86,9 +86,10 @@ impl CommandManager { player::avatar "[player_uid] [avatar_id]" "changes player avatar for main city"; player::nickname "[player_uid] [nickname]" "changes player nickname"; player::procedure "[player_uid] [procedure_id]" "changes current beginner procedure id, parameter -1 can be used for skipping it"; - avatar::add "[player_uid] [avatar_id]" "gives avatar with specified id to player"; - item::add_weapon "[player_uid] [weapon_id]" "gives weapon with specified id to player"; player::kick "[player_uid] [reason]" "kick the specified player (reason is optional)"; + avatar::add "[player_uid] [avatar_id]" "gives avatar with specified id to player"; + avatar::add_all "[player_uid]" "gives all avatars to player"; + item::add_weapon "[player_uid] [weapon_id]" "gives weapon with specified id to player"; gacha::up "[player_uid]" "start a gacha UP setting guide (available for Bangboo pool)"; } } diff --git a/nap_gameserver/src/logic/role/role_model.rs b/nap_gameserver/src/logic/role/role_model.rs index 7f93dfe..99cb09c 100644 --- a/nap_gameserver/src/logic/role/role_model.rs +++ b/nap_gameserver/src/logic/role/role_model.rs @@ -22,15 +22,17 @@ impl RoleModel { const DEFAULT_AVATARS: [u32; 2] = [1011, 1081]; pub fn add_avatar(&mut self, template_id: AvatarBaseID) { - if !self - .avatar_list - .iter() - .any(|a| a.template_id == template_id) - { + if !self.has_avatar(template_id) { self.avatar_list.push(Avatar::new(template_id)); } } + pub fn has_avatar(&self, template_id: AvatarBaseID) -> bool { + self.avatar_list + .iter() + .any(|a| a.template_id == template_id) + } + pub fn avatar_sync(&self) -> AvatarSync { AvatarSync { avatar_list: self.avatar_list.iter().map(Avatar::to_client).collect(),