trigger-rs/crates/hall-server/src/logic/ecs/event_graph.rs
traffic95 23fcde33f5 Properties calc port for 1.7beta (#7)
Reviewed-on: #7
Co-authored-by: traffic95 <traffic95@xeondev.com>
Co-committed-by: traffic95 <traffic95@xeondev.com>
2025-03-19 08:52:04 +00:00

112 lines
3.7 KiB
Rust

use bevy_derive::Deref;
use bevy_ecs::prelude::*;
use tracing::debug;
use trigger_fileconfig::main_city_script::*;
define_actions! {
ActionCreateNpcCfg,
ActionChangeInteractCfg,
ActionSetMainCityObjectState,
ActionOpenUI,
ActionSwitchSection
}
#[derive(Component)]
pub struct EventGraph {
pub interaction: String, // ENPCInteraction
pub actions: Vec<ActionInfo>,
}
pub fn sync_event_info(
interacting_units: Query<(&SceneUnitTag, &InteractContainer, &EventGraph), Changed<EventGraph>>,
mut listener: ResMut<GameStateListener>,
) {
for (unit_tag, interact_container, event_graph) in interacting_units.iter() {
listener.add(SyncEventInfoScNotify {
owner_id: interact_container.cur_interaction() as u32,
tag: **unit_tag as u32,
owner_type: EEventGraphOwnerType::SceneUnit.into(),
event_graph_uid: interact_container.cur_interaction() as u32,
npc_interaction: event_graph.interaction.clone(),
action_list: event_graph.actions.clone(),
});
}
}
pub fn advance_through_event_graph(
mut commands: Commands,
mut run_events: EventReader<RunEventGraphEvent>,
mut listener: ResMut<GameStateListener>,
mut interacting_units: Query<(Entity, &mut InteractContainer, &EventGraph)>,
) {
for event in run_events.read() {
debug!("{event:?}");
if let Some((entity_id, mut interact_container, event_graph)) = interacting_units
.iter_mut()
.find(|(_, interact_container, _)| {
interact_container.cur_interaction() == event.event_graph_uid as i32
})
{
listener.add(UpdateEventGraphScNotify {
tag: event.tag,
event_graph_owner_uid: event.owner_id,
owner_type: event.owner_type,
npc_interaction: event_graph.interaction.clone(),
is_event_success: true,
});
interact_container.finish_interaction();
commands.entity(entity_id).remove::<EventGraph>();
listener.emit_callback(GameStateCallback::ClientCmdProcessed {
ack_request_id: event.request_id,
response: Some(RunEventGraphScRsp { retcode: 0 }.into()),
});
}
}
}
macro_rules! define_actions {
($($name:ident),*) => {
paste::paste!($(
#[derive(Event, Deref)]
pub struct [<$name Event>](&'static $name);
)*);
#[derive(Event, Deref)]
pub struct GraphEvent(pub &'static ConfigEvent);
pub struct MainCityScriptPlugin;
impl bevy_app::Plugin for MainCityScriptPlugin {
fn build(&self, app: &mut bevy_app::App) {
$(paste::paste!(app.add_event::<[<$name Event>]>());)*
app.add_event::<GraphEvent>();
app.add_systems(bevy_app::PreUpdate, tick_emit_event_actions);
}
}
paste::paste! {
pub fn tick_emit_event_actions(mut events: EventReader<GraphEvent>, $(mut [<$name:snake>]: EventWriter<[<$name Event>]>),*) {
for event in events.read() {
for action in event.actions.iter() {
match action {
$(ConfigEventAction::$name(data) => { [<$name:snake>].send([<$name Event>](data)); })*
}
}
}
}}
};
}
use define_actions;
use trigger_logic::scene::EEventGraphOwnerType;
use trigger_protocol::{
ActionInfo, RunEventGraphScRsp, SyncEventInfoScNotify, UpdateEventGraphScNotify,
};
use trigger_sv::message::GameStateCallback;
use crate::logic::{GameStateListener, message::RunEventGraphEvent};
use super::scene_unit::{InteractContainer, SceneUnitTag};