22// SPDX-License-Identifier: Apache-2.0
33// SPDX-License-Identifier: MIT
44
5- use super :: { Event , EventId } ;
5+ use crate :: { Runtime , Window } ;
6+
7+ use super :: { EmitArgs , Event , EventId } ;
68
79use std:: {
810 boxed:: Box ,
@@ -15,33 +17,33 @@ use std::{
1517} ;
1618
1719/// What to do with the pending handler when resolving it?
18- enum Pending {
20+ enum Pending < R : Runtime > {
1921 Unlisten ( EventId ) ,
20- Listen ( EventId , String , Handler ) ,
21- Trigger ( String , Option < String > , Option < String > ) ,
22+ Listen ( EventId , String , Handler < R > ) ,
23+ Emit ( EmitArgs ) ,
2224}
2325
2426/// Stored in [`Listeners`] to be called upon when the event that stored it is triggered.
25- struct Handler {
26- window : Option < String > ,
27+ struct Handler < R : Runtime > {
28+ window : Option < Window < R > > ,
2729 callback : Box < dyn Fn ( Event ) + Send > ,
2830}
2931
3032/// Holds event handlers and pending event handlers, along with the salts associating them.
31- struct InnerListeners {
32- handlers : Mutex < HashMap < String , HashMap < EventId , Handler > > > ,
33- pending : Mutex < Vec < Pending > > ,
33+ struct InnerListeners < R : Runtime > {
34+ handlers : Mutex < HashMap < String , HashMap < EventId , Handler < R > > > > ,
35+ pending : Mutex < Vec < Pending < R > > > ,
3436 function_name : & ' static str ,
3537 listeners_object_name : & ' static str ,
3638 next_event_id : Arc < AtomicU32 > ,
3739}
3840
3941/// A self-contained event manager.
40- pub struct Listeners {
41- inner : Arc < InnerListeners > ,
42+ pub struct Listeners < R : Runtime > {
43+ inner : Arc < InnerListeners < R > > ,
4244}
4345
44- impl Default for Listeners {
46+ impl < R : Runtime > Default for Listeners < R > {
4547 fn default ( ) -> Self {
4648 Self {
4749 inner : Arc :: new ( InnerListeners {
@@ -55,15 +57,15 @@ impl Default for Listeners {
5557 }
5658}
5759
58- impl Clone for Listeners {
60+ impl < R : Runtime > Clone for Listeners < R > {
5961 fn clone ( & self ) -> Self {
6062 Self {
6163 inner : self . inner . clone ( ) ,
6264 }
6365 }
6466}
6567
66- impl Listeners {
68+ impl < R : Runtime > Listeners < R > {
6769 pub ( crate ) fn next_event_id ( & self ) -> EventId {
6870 self . inner . next_event_id . fetch_add ( 1 , Ordering :: Relaxed )
6971 }
@@ -79,7 +81,7 @@ impl Listeners {
7981 }
8082
8183 /// Insert a pending event action to the queue.
82- fn insert_pending ( & self , action : Pending ) {
84+ fn insert_pending ( & self , action : Pending < R > ) {
8385 self
8486 . inner
8587 . pending
@@ -89,7 +91,7 @@ impl Listeners {
8991 }
9092
9193 /// Finish all pending event actions.
92- fn flush_pending ( & self ) {
94+ fn flush_pending ( & self ) -> crate :: Result < ( ) > {
9395 let pending = {
9496 let mut lock = self
9597 . inner
@@ -102,13 +104,17 @@ impl Listeners {
102104 for action in pending {
103105 match action {
104106 Pending :: Unlisten ( id) => self . unlisten ( id) ,
105- Pending :: Listen ( id, event, handler) => self . listen_ ( id, event, handler) ,
106- Pending :: Trigger ( ref event, window, payload) => self . trigger ( event, window, payload) ,
107+ Pending :: Listen ( id, event, handler) => self . listen_with_id ( id, event, handler) ,
108+ Pending :: Emit ( args) => {
109+ self . emit ( & args) ?;
110+ }
107111 }
108112 }
113+
114+ Ok ( ( ) )
109115 }
110116
111- fn listen_ ( & self , id : EventId , event : String , handler : Handler ) {
117+ fn listen_with_id ( & self , id : EventId , event : String , handler : Handler < R > ) {
112118 match self . inner . handlers . try_lock ( ) {
113119 Err ( _) => self . insert_pending ( Pending :: Listen ( id, event, handler) ) ,
114120 Ok ( mut lock) => {
@@ -117,11 +123,11 @@ impl Listeners {
117123 }
118124 }
119125
120- /// Adds an event listener for JS events .
126+ /// Adds an event listener.
121127 pub ( crate ) fn listen < F : Fn ( Event ) + Send + ' static > (
122128 & self ,
123129 event : String ,
124- window : Option < String > ,
130+ window : Option < Window < R > > ,
125131 handler : F ,
126132 ) -> EventId {
127133 let id = self . next_event_id ( ) ;
@@ -130,16 +136,16 @@ impl Listeners {
130136 callback : Box :: new ( handler) ,
131137 } ;
132138
133- self . listen_ ( id, event, handler) ;
139+ self . listen_with_id ( id, event, handler) ;
134140
135141 id
136142 }
137143
138- /// Listen to a JS event and immediately unlisten.
144+ /// Listen to an event and immediately unlisten.
139145 pub ( crate ) fn once < F : FnOnce ( Event ) + Send + ' static > (
140146 & self ,
141147 event : String ,
142- window : Option < String > ,
148+ window : Option < Window < R > > ,
143149 handler : F ,
144150 ) {
145151 let self_ = self . clone ( ) ;
@@ -164,19 +170,42 @@ impl Listeners {
164170 }
165171 }
166172
167- /// Triggers the given global event with its payload.
168- pub ( crate ) fn trigger ( & self , event : & str , window : Option < String > , payload : Option < String > ) {
173+ /// Emits the given event with its payload based on a filter.
174+ pub ( crate ) fn emit_filter < F > ( & self , emit_args : & EmitArgs , filter : Option < F > ) -> crate :: Result < ( ) >
175+ where
176+ F : Fn ( & Window < R > ) -> bool ,
177+ {
169178 let mut maybe_pending = false ;
170179 match self . inner . handlers . try_lock ( ) {
171- Err ( _) => self . insert_pending ( Pending :: Trigger ( event . to_owned ( ) , window , payload ) ) ,
180+ Err ( _) => self . insert_pending ( Pending :: Emit ( emit_args . clone ( ) ) ) ,
172181 Ok ( lock) => {
173- if let Some ( handlers) = lock. get ( event) {
174- for ( & id, handler) in handlers {
175- if handler. window . is_none ( ) || window == handler. window {
182+ if let Some ( handlers) = lock. get ( & emit_args. event_name ) {
183+ let handlers = if let Some ( filter) = filter {
184+ handlers
185+ . iter ( )
186+ . filter ( |h| {
187+ h. 1
188+ . window
189+ . as_ref ( )
190+ . map ( |w| {
191+ // clippy sees this as redundant closure but
192+ // fixing it will result in a compiler error
193+ #[ allow( clippy:: redundant_closure) ]
194+ filter ( w)
195+ } )
196+ . unwrap_or ( false )
197+ } )
198+ . collect :: < Vec < _ > > ( )
199+ } else {
200+ handlers. iter ( ) . collect :: < Vec < _ > > ( )
201+ } ;
202+
203+ if !handlers. is_empty ( ) {
204+ for ( & id, handler) in handlers {
176205 maybe_pending = true ;
177206 ( handler. callback ) ( self :: Event {
178207 id,
179- data : payload. clone ( ) ,
208+ data : emit_args . payload . clone ( ) ,
180209 } )
181210 }
182211 }
@@ -185,14 +214,22 @@ impl Listeners {
185214 }
186215
187216 if maybe_pending {
188- self . flush_pending ( ) ;
217+ self . flush_pending ( ) ? ;
189218 }
219+
220+ Ok ( ( ) )
221+ }
222+
223+ /// Emits the given event with its payload.
224+ pub ( crate ) fn emit ( & self , emit_args : & EmitArgs ) -> crate :: Result < ( ) > {
225+ self . emit_filter ( emit_args, None :: < & dyn Fn ( & Window < R > ) -> bool > )
190226 }
191227}
192228
193229#[ cfg( test) ]
194230mod test {
195231 use super :: * ;
232+ use crate :: test:: MockRuntime ;
196233 use proptest:: prelude:: * ;
197234
198235 // dummy event handler function
@@ -206,7 +243,7 @@ mod test {
206243 // check to see if listen() is properly passing keys into the LISTENERS map
207244 #[ test]
208245 fn listeners_check_key( e in "[a-z]+" ) {
209- let listeners: Listeners = Default :: default ( ) ;
246+ let listeners: Listeners < MockRuntime > = Default :: default ( ) ;
210247 // clone e as the key
211248 let key = e. clone( ) ;
212249 // pass e and an dummy func into listen
@@ -222,7 +259,7 @@ mod test {
222259 // check to see if listen inputs a handler function properly into the LISTENERS map.
223260 #[ test]
224261 fn listeners_check_fn( e in "[a-z]+" ) {
225- let listeners: Listeners = Default :: default ( ) ;
262+ let listeners: Listeners < MockRuntime > = Default :: default ( ) ;
226263 // clone e as the key
227264 let key = e. clone( ) ;
228265 // pass e and an dummy func into listen
@@ -248,11 +285,11 @@ mod test {
248285 // check to see if on_event properly grabs the stored function from listen.
249286 #[ test]
250287 fn check_on_event( key in "[a-z]+" , d in "[a-z]+" ) {
251- let listeners: Listeners = Default :: default ( ) ;
252- // call listen with e and the event_fn dummy func
288+ let listeners: Listeners < MockRuntime > = Default :: default ( ) ;
289+ // call listen with key and the event_fn dummy func
253290 listeners. listen( key. clone( ) , None , event_fn) ;
254- // call on event with e and d.
255- listeners. trigger ( & key, None , Some ( d ) ) ;
291+ // call on event with key and d.
292+ listeners. emit ( & EmitArgs { event_name : key. clone ( ) , event : serde_json :: to_string ( & key ) . unwrap ( ) , source_window_label : "null" . into ( ) , payload : serde_json :: to_string ( & d ) . unwrap ( ) } ) ? ;
256293
257294 // lock the mutex
258295 let l = listeners. inner. handlers. lock( ) . unwrap( ) ;
0 commit comments