use std::time::Duration;
use serde::{Deserialize, Serialize};
use crate::{
comp::{CharacterState, StateUpdate},
event::RegrowHeadEvent,
states::utils::{end_ability, tick_attack_or_default},
};
use super::{
behavior::CharacterBehavior,
utils::{AbilityInfo, StageSection},
};
#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize)]
pub enum FrontendSpecifier {
Hydra,
}
#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
pub struct StaticData {
pub buildup_duration: Duration,
pub recover_duration: Duration,
pub energy_cost: f32,
pub ability_info: AbilityInfo,
pub specifier: Option<FrontendSpecifier>,
}
#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
pub struct Data {
pub static_data: StaticData,
pub timer: Duration,
pub stage_section: StageSection,
}
impl CharacterBehavior for Data {
fn behavior(
&self,
data: &super::behavior::JoinData,
output_events: &mut crate::comp::character_state::OutputEvents,
) -> crate::comp::StateUpdate {
let mut update = StateUpdate::from(data);
match self.stage_section {
StageSection::Buildup => {
if self.timer < self.static_data.buildup_duration {
update.character = CharacterState::RegrowHead(Data {
static_data: self.static_data.clone(),
timer: tick_attack_or_default(data, self.timer, None),
..*self
});
} else {
output_events.emit_server(RegrowHeadEvent {
entity: data.entity,
});
update.character = CharacterState::RegrowHead(Data {
static_data: self.static_data.clone(),
timer: Duration::default(),
stage_section: StageSection::Recover,
});
}
},
StageSection::Recover => {
if self.timer < self.static_data.recover_duration {
update.character = CharacterState::RegrowHead(Data {
static_data: self.static_data.clone(),
timer: tick_attack_or_default(
data,
self.timer,
Some(data.stats.recovery_speed_modifier),
),
..*self
});
} else {
end_ability(data, &mut update);
}
},
_ => {
end_ability(data, &mut update);
},
}
update
}
}