use bevy::ecs::component::ComponentId;
use bevy::ecs::event::{Trigger, trigger_entity_internal};
use bevy::ecs::observer::{CachedObservers, TriggerContext};
use bevy::ecs::world::DeferredWorld;
use bevy::prelude::*;
use bevy::ptr::PtrMut;
pub struct EntityComponentTrigger {
pub component: ComponentId,
}
unsafe impl<'a, E: EntityEvent + Event<Trigger<'a> = EntityComponentTrigger>> Trigger<E>
for EntityComponentTrigger
{
unsafe fn trigger(
&mut self,
world: DeferredWorld,
observers: &CachedObservers,
trigger_context: &TriggerContext,
event: &mut E,
) {
let entity = event.event_target();
unsafe {
self.trigger_internal(world, observers, event.into(), entity, trigger_context);
}
}
}
impl EntityComponentTrigger {
#[inline(never)]
unsafe fn trigger_internal(
&mut self,
mut world: DeferredWorld,
observers: &CachedObservers,
mut event: PtrMut,
entity: Entity,
trigger_context: &TriggerContext,
) {
unsafe {
trigger_entity_internal(
world.reborrow(),
observers,
event.reborrow(),
self.into(),
entity,
trigger_context,
);
}
if let Some(component_observers) = observers.component_observers().get(&self.component) {
for (observer, runner) in component_observers.global_observers() {
unsafe {
(runner)(
world.reborrow(),
*observer,
trigger_context,
event.reborrow(),
self.into(),
);
}
}
if let Some(map) = component_observers
.entity_component_observers()
.get(&entity)
{
for (observer, runner) in map {
unsafe {
(runner)(
world.reborrow(),
*observer,
trigger_context,
event.reborrow(),
self.into(),
);
}
}
}
}
}
}