Skip to content

Commit

Permalink
上下文共享结构大改
Browse files Browse the repository at this point in the history
支持单次伤害trigger
  • Loading branch information
eigeen committed Mar 27, 2024
1 parent 2016642 commit 9acc942
Show file tree
Hide file tree
Showing 15 changed files with 280 additions and 240 deletions.
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
/target
mas-config.toml
*.lib
*.lib

/.vscode
14 changes: 10 additions & 4 deletions mas-config.example.toml
Original file line number Diff line number Diff line change
Expand Up @@ -166,7 +166,7 @@ action_mode = "random"

[[trigger.action]]
cmd = "SendChatMessage"
param = "绿灯"
param = "黄灯"


# ========== 虫棍三灯 ==========
Expand Down Expand Up @@ -273,17 +273,23 @@ action_mode = "sequential_all"
param = "使用了回避衣装"


# ========== 造成伤害 ==========
# ========== 真蓄造成伤害 ==========
[[trigger]]
name = "造成伤害"
action_mode = "sequential_all"

[trigger.trigger_on.damage]
value = { gt = 200 }

[[trigger.check]]
weapon_type.value = 0

[[trigger.check]]
fsm.value = { target = 3, id = 137 }

[[trigger.action]]
cmd = "SendChatMessage"
param = "造成了200以上伤害"
param = "强击真三蓄!造成了{{damage}}伤害"


# 开发中/计划开发

Expand Down
83 changes: 44 additions & 39 deletions src/conditions/charge_blade.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,67 +3,72 @@ use log::error;
use crate::{
configs::{NewOldValueCmp, TriggerCondition, ValueCmp},
event::{Event, EventType},
triggers::AsTriggerCondition,
triggers::{AsTriggerCondition, SharedContext},
};

use super::TriggerFn;

pub struct ChargeBladeCondition {
trigger_fn: TriggerFn,
shared_ctx: SharedContext,
sword_charge_timer: Option<NewOldValueCmp>,
shield_charge_timer: Option<NewOldValueCmp>,
power_axe_timer: Option<NewOldValueCmp>,
phials: Option<NewOldValueCmp>,
sword_power: Option<NewOldValueCmp>,
}

impl ChargeBladeCondition {
pub fn new_trigger(cond: &TriggerCondition) -> Self {
pub fn new_trigger(cond: &TriggerCondition, shared_ctx: SharedContext) -> Self {
let cond = cond.clone();
let trigger_fn: TriggerFn = if let TriggerCondition::ChargeBlade {
if let TriggerCondition::ChargeBlade {
sword_charge_timer,
shield_charge_timer,
power_axe_timer,
phials,
sword_power,
} = cond
{
Box::new(move |event| {
if let Event::ChargeBlade { ctx } = event {
let phials = parse_cfg_phials_special(&phials, ctx.charge_blade.max_phials);
let power_axe_timer = parse_cfg_power_axe_timer_special(&power_axe_timer);
// 计算总电锯时长
let new_total_power_axe_timer = ctx.charge_blade.phials as f32 * ctx.charge_blade.power_axe_timer;
let old_total_power_axe_timer = ctx.last_ctx.as_ref().unwrap().charge_blade.phials as f32
* ctx.last_ctx.as_ref().unwrap().charge_blade.power_axe_timer;
compare_cfg_ctx_f32(
&sword_charge_timer,
ctx.charge_blade.sword_charge_timer,
ctx.last_ctx.as_ref().unwrap().charge_blade.sword_charge_timer,
) && compare_cfg_ctx_f32(
&shield_charge_timer,
ctx.charge_blade.shield_charge_timer,
ctx.last_ctx.as_ref().unwrap().charge_blade.shield_charge_timer,
) && compare_cfg_ctx(
&phials,
ctx.charge_blade.phials,
ctx.last_ctx.as_ref().unwrap().charge_blade.phials,
) && compare_cfg_ctx_f32(
&sword_power,
ctx.charge_blade.sword_power,
ctx.last_ctx.as_ref().unwrap().charge_blade.sword_power,
) && compare_cfg_ctx_f32(&power_axe_timer, new_total_power_axe_timer, old_total_power_axe_timer)
} else {
false
}
})
return ChargeBladeCondition {
shared_ctx,
sword_charge_timer,
shield_charge_timer,
power_axe_timer,
phials,
sword_power,
};
} else {
error!("internal: InsectGlaiveCondition cmp_fn 参数不正确");
Box::new(|_| false)
panic!("internal: InsectGlaiveCondition cmp_fn 参数不正确");
};

ChargeBladeCondition { trigger_fn }
}
}

impl AsTriggerCondition for ChargeBladeCondition {
fn check(&self, event: &Event) -> bool {
(self.trigger_fn)(event)
let ctx = self.shared_ctx.read().unwrap();
if let Event::ChargeBlade = event {
let phials = parse_cfg_phials_special(&self.phials, ctx.charge_blade.max_phials);
let power_axe_timer = parse_cfg_power_axe_timer_special(&self.power_axe_timer);
// 计算总电锯时长
let new_total_power_axe_timer = ctx.charge_blade.phials as f32 * ctx.charge_blade.power_axe_timer;
let old_total_power_axe_timer = ctx.last_ctx.as_ref().unwrap().charge_blade.phials as f32
* ctx.last_ctx.as_ref().unwrap().charge_blade.power_axe_timer;
compare_cfg_ctx_f32(
&self.sword_charge_timer,
ctx.charge_blade.sword_charge_timer,
ctx.last_ctx.as_ref().unwrap().charge_blade.sword_charge_timer,
) && compare_cfg_ctx_f32(
&self.shield_charge_timer,
ctx.charge_blade.shield_charge_timer,
ctx.last_ctx.as_ref().unwrap().charge_blade.shield_charge_timer,
) && compare_cfg_ctx(&phials, ctx.charge_blade.phials, ctx.last_ctx.as_ref().unwrap().charge_blade.phials)
&& compare_cfg_ctx_f32(
&self.sword_power,
ctx.charge_blade.sword_power,
ctx.last_ctx.as_ref().unwrap().charge_blade.sword_power,
)
&& compare_cfg_ctx_f32(&power_axe_timer, new_total_power_axe_timer, old_total_power_axe_timer)
} else {
false
}
}

fn event_type(&self) -> EventType {
Expand Down
48 changes: 31 additions & 17 deletions src/conditions/damage.rs
Original file line number Diff line number Diff line change
@@ -1,43 +1,57 @@
use std::{collections::HashMap, sync::Mutex};

use log::error;

use super::TriggerFn;
use crate::{
configs::TriggerCondition,
configs::{TriggerCondition, ValueCmp},
event::{Event, EventType},
triggers::AsTriggerCondition,
triggers::{ActionContext, AsTriggerCondition},
};

pub struct DamageCondition {
trigger_fn: TriggerFn,
trigger_value: ValueCmp,
action_ctx: Mutex<ActionContext>,
}

impl DamageCondition {
pub fn new_trigger(cond: &TriggerCondition) -> Self {
let mut instance = DamageCondition {
trigger_value: ValueCmp::EqInt(0),
action_ctx: Mutex::new(None),
};

let cond = cond.clone();
let trigger_fn: TriggerFn = if let TriggerCondition::Damage { value } = cond {
Box::new(move |event| {
if let Event::Damage { damage } = event {
log::debug!("Event::Damage damage = {damage}");
&value == damage
} else {
false
}
})
if let TriggerCondition::Damage { value } = cond {
instance.trigger_value = value;
} else {
error!("internal: DamageCondition cmp_fn 参数不正确");
Box::new(|_| false)
};
}

DamageCondition { trigger_fn }
instance
}
}

impl AsTriggerCondition for DamageCondition {
fn check(&self, event: &Event) -> bool {
(self.trigger_fn)(event)
if let Event::Damage { damage, .. } = event {
if &self.trigger_value == damage {
let mut context = HashMap::new();
context.insert("damage".to_string(), damage.to_string());
self.action_ctx.lock().unwrap().replace(context);
true
} else {
false
}
} else {
false
}
}

fn event_type(&self) -> EventType {
EventType::Damage
}

fn get_action_context(&self) -> ActionContext {
self.action_ctx.lock().unwrap().clone()
}
}
14 changes: 8 additions & 6 deletions src/conditions/fsm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,19 +3,19 @@ use log::error;
use crate::{
configs::{CheckCondition, TriggerCondition},
event::{Event, EventType},
game_context::Context,
triggers::{AsCheckCondition, AsTriggerCondition},
triggers::{AsCheckCondition, AsTriggerCondition, SharedContext},
};

use super::{CheckFn, TriggerFn};

pub struct FsmCondition {
trigger_fn: TriggerFn,
check_fn: CheckFn,
shared_ctx: SharedContext,
}

impl FsmCondition {
pub fn new_trigger(cond: &TriggerCondition) -> Self {
pub fn new_trigger(cond: &TriggerCondition, shared_ctx: SharedContext) -> Self {
let cond = cond.clone();
let trigger_fn: TriggerFn = if let TriggerCondition::Fsm { new, old } = cond {
Box::new(move |event| {
Expand Down Expand Up @@ -46,10 +46,11 @@ impl FsmCondition {
FsmCondition {
trigger_fn,
check_fn: Box::new(|_| false),
shared_ctx,
}
}

pub fn new_check(cond: &CheckCondition) -> Self {
pub fn new_check(cond: &CheckCondition, shared_ctx: SharedContext) -> Self {
let cond = cond.clone();
let check_fn: CheckFn = if let CheckCondition::Fsm { value } = cond {
Box::new(move |ctx| value == ctx.fsm)
Expand All @@ -61,6 +62,7 @@ impl FsmCondition {
FsmCondition {
trigger_fn: Box::new(|_| false),
check_fn,
shared_ctx,
}
}
}
Expand All @@ -76,7 +78,7 @@ impl AsTriggerCondition for FsmCondition {
}

impl AsCheckCondition for FsmCondition {
fn check(&self, ctx: &Context) -> bool {
(self.check_fn)(ctx)
fn check(&self) -> bool {
(self.check_fn)(&self.shared_ctx.read().unwrap())
}
}
65 changes: 34 additions & 31 deletions src/conditions/insect_glaive.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,50 +3,53 @@ use log::error;
use crate::{
configs::{NewOldValueCmp, TriggerCondition},
event::{Event, EventType},
triggers::AsTriggerCondition,
triggers::{AsTriggerCondition, SharedContext},
};

use super::TriggerFn;

pub struct InsectGlaiveCondition {
trigger_fn: TriggerFn,
shared_ctx: SharedContext,
cond_red: Option<NewOldValueCmp>,
cond_white: Option<NewOldValueCmp>,
cond_yellow: Option<NewOldValueCmp>,
}

impl InsectGlaiveCondition {
pub fn new_trigger(cond: &TriggerCondition) -> Self {
pub fn new_trigger(cond: &TriggerCondition, shared_ctx: SharedContext) -> Self {
let cond = cond.clone();
let trigger_fn: TriggerFn = if let TriggerCondition::InsectGlaiveLight { red, white, yellow } = cond {
Box::new(move |event| {
if let Event::InsectGlaive { ctx } = event {
compare_cfg_ctx(
&red,
ctx.insect_glaive.attack_timer,
ctx.last_ctx.as_ref().unwrap().insect_glaive.attack_timer,
) && compare_cfg_ctx(
&white,
ctx.insect_glaive.speed_timer,
ctx.last_ctx.as_ref().unwrap().insect_glaive.speed_timer,
) && compare_cfg_ctx(
&yellow,
ctx.insect_glaive.defense_timer,
ctx.last_ctx.as_ref().unwrap().insect_glaive.defense_timer,
)
} else {
false
}
})
if let TriggerCondition::InsectGlaiveLight { red, white, yellow } = cond {
InsectGlaiveCondition {
shared_ctx,
cond_red: red,
cond_white: white,
cond_yellow: yellow,
}
} else {
error!("internal: InsectGlaiveCondition cmp_fn 参数不正确");
Box::new(|_| false)
};

InsectGlaiveCondition { trigger_fn }
error!("internal: InsectGlaiveCondition: invalid cond {:?}", cond);
panic!("Invalid cond")
}
}
}

impl AsTriggerCondition for InsectGlaiveCondition {
fn check(&self, event: &Event) -> bool {
(self.trigger_fn)(event)
let ctx = self.shared_ctx.read().unwrap();
if let Event::InsectGlaive = event {
compare_cfg_ctx(
&self.cond_red,
ctx.insect_glaive.attack_timer,
ctx.last_ctx.as_ref().unwrap().insect_glaive.attack_timer,
) && compare_cfg_ctx(
&self.cond_white,
ctx.insect_glaive.speed_timer,
ctx.last_ctx.as_ref().unwrap().insect_glaive.speed_timer,
) && compare_cfg_ctx(
&self.cond_yellow,
ctx.insect_glaive.defense_timer,
ctx.last_ctx.as_ref().unwrap().insect_glaive.defense_timer,
)
} else {
false
}
}

fn event_type(&self) -> EventType {
Expand Down
Loading

0 comments on commit 9acc942

Please sign in to comment.