pub use self::event_handlers::*;
pub use self::event_name::EventName;
#[cfg(feature = "web")]
pub(crate) use self::virtual_events::set_events_id;
#[cfg(feature = "web")]
pub use self::virtual_events::VirtualEventsWebSys;
pub use self::virtual_events::{
ElementEventsId, VirtualEventElement, VirtualEventNode, VirtualEvents, ELEMENT_EVENTS_ID_PROP,
};
#[cfg(feature = "web")]
pub use self::web::{insert_non_delegated_event, EventAttribFn};
use std::cell::RefCell;
use std::collections::hash_map::Drain;
use std::collections::HashMap;
use std::fmt;
use std::ops::{Deref, DerefMut};
use std::rc::Rc;
mod event_handlers;
mod event_name;
mod virtual_events;
#[cfg(feature = "web")]
mod web;
pub struct Events<Dom: RealDom> {
events: HashMap<EventName, EventHandler<Dom>>,
}
impl<Dom: RealDom> PartialEq for Events<Dom> {
fn eq(&self, other: &Self) -> bool {
let Events { events: lhs_events } = self;
let Events { events: rhs_events } = other;
lhs_events == rhs_events
}
}
impl<Dom: RealDom> Events<Dom> {
pub fn has_events(&self) -> bool {
!self.events.is_empty()
}
pub fn events(&self) -> &HashMap<EventName, EventHandler<Dom>> {
&self.events
}
pub fn insert_no_args(&mut self, event_name: EventName, event: Rc<RefCell<dyn FnMut()>>) {
self.events
.insert(event_name, EventHandler::<Dom>::NoArgs(event));
}
#[doc(hidden)]
pub fn __insert_unsupported_signature(
&mut self,
event_name: EventName,
event: Dom::EventCallback,
) {
self.events.insert(event_name, EventHandler::Custom(event));
}
pub fn insert_mouse_event(
&mut self,
event_name: EventName,
event: Rc<RefCell<dyn FnMut(Dom::MouseEvent)>>,
) {
self.events
.insert(event_name, EventHandler::MouseEvent(event));
}
pub fn take_events(&mut self) -> Drain<'_, EventName, EventHandler<Dom>> {
self.events.drain()
}
pub fn convert_all<New: RealDom>(
mut self,
convert: impl Fn(EventHandler<Dom>) -> EventHandler<New>,
) -> Events<New> {
let mut new_events = HashMap::with_capacity(self.events.len());
for (event_name, before) in self.events.drain() {
let after = convert(before);
new_events.insert(event_name, after);
}
Events { events: new_events }
}
}
impl<Dom: RealDom> Events<Dom> {
pub fn new() -> Self {
Events {
events: HashMap::new(),
}
}
}
pub trait RealDom {
type Event;
type MouseEvent;
type EventCallback: Clone;
}
#[cfg(feature = "web")]
impl RealDom for web_sys::Window {
type Event = web_sys::Event;
type MouseEvent = crate::event::MouseEventWebSys;
type EventCallback = Rc<dyn AsRef<wasm_bindgen::JsValue>>;
}
impl RealDom for () {
type Event = ();
type MouseEvent = ();
type EventCallback = ();
}
#[cfg(feature = "web")]
impl EventAttribFn {
#[doc(hidden)]
pub fn new_noop() -> EventAttribFn {
use wasm_bindgen::JsValue;
let noop = Rc::new(JsValue::NULL);
EventAttribFn::new(noop)
}
}
impl<Dom: RealDom> fmt::Debug for Events<Dom> {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let events: String = self
.events
.keys()
.map(|key| " ".to_string() + key.with_on_prefix())
.collect();
write!(f, "{}", events)
}
}
impl<Dom: RealDom> Deref for Events<Dom> {
type Target = HashMap<EventName, EventHandler<Dom>>;
fn deref(&self) -> &Self::Target {
&self.events
}
}
impl<Dom: RealDom> DerefMut for Events<Dom> {
fn deref_mut(&mut self) -> &mut Self::Target {
&mut self.events
}
}