1
1
use std:: cell:: { Cell , RefCell } ;
2
+ use std:: collections:: VecDeque ;
2
3
use std:: ffi:: c_void;
3
4
use std:: ptr;
4
5
use std:: rc:: Rc ;
@@ -267,6 +268,7 @@ impl<'a> Window<'a> {
267
268
keyboard_state : KeyboardState :: new ( ) ,
268
269
frame_timer : Cell :: new ( None ) ,
269
270
window_info : Cell :: new ( window_info) ,
271
+ deferred_events : RefCell :: default ( ) ,
270
272
} ) ;
271
273
272
274
let window_state_ptr = Rc :: into_raw ( Rc :: clone ( & window_state) ) ;
@@ -360,6 +362,9 @@ pub(super) struct WindowState {
360
362
frame_timer : Cell < Option < CFRunLoopTimer > > ,
361
363
/// The last known window info for this window.
362
364
pub window_info : Cell < WindowInfo > ,
365
+
366
+ /// Events that will be triggered at the end of `window_handler`'s borrow.
367
+ deferred_events : RefCell < VecDeque < Event > > ,
363
368
}
364
369
365
370
impl WindowState {
@@ -378,14 +383,34 @@ impl WindowState {
378
383
state
379
384
}
380
385
386
+ /// Trigger the event immediately and return the event status.
387
+ /// Will panic if `window_handler` is already borrowed (see `trigger_deferrable_event`).
381
388
pub ( super ) fn trigger_event ( & self , event : Event ) -> EventStatus {
382
389
let mut window = crate :: Window :: new ( Window { inner : & self . window_inner } ) ;
383
- self . window_handler . borrow_mut ( ) . on_event ( & mut window, event)
390
+ let mut window_handler = self . window_handler . borrow_mut ( ) ;
391
+ let status = window_handler. on_event ( & mut window, event) ;
392
+ self . send_deferred_events ( window_handler. as_mut ( ) ) ;
393
+ status
394
+ }
395
+
396
+ /// Trigger the event immediately if `window_handler` can be borrowed mutably,
397
+ /// otherwise add the event to a queue that will be cleared once `window_handler`'s mutable borrow ends.
398
+ /// As this method might result in the event triggering asynchronously, it can't reliably return the event status.
399
+ pub ( super ) fn trigger_deferrable_event ( & self , event : Event ) {
400
+ if let Ok ( mut window_handler) = self . window_handler . try_borrow_mut ( ) {
401
+ let mut window = crate :: Window :: new ( Window { inner : & self . window_inner } ) ;
402
+ window_handler. on_event ( & mut window, event) ;
403
+ self . send_deferred_events ( window_handler. as_mut ( ) ) ;
404
+ } else {
405
+ self . deferred_events . borrow_mut ( ) . push_back ( event) ;
406
+ }
384
407
}
385
408
386
409
pub ( super ) fn trigger_frame ( & self ) {
387
410
let mut window = crate :: Window :: new ( Window { inner : & self . window_inner } ) ;
388
- self . window_handler . borrow_mut ( ) . on_frame ( & mut window) ;
411
+ let mut window_handler = self . window_handler . borrow_mut ( ) ;
412
+ window_handler. on_frame ( & mut window) ;
413
+ self . send_deferred_events ( window_handler. as_mut ( ) ) ;
389
414
}
390
415
391
416
pub ( super ) fn keyboard_state ( & self ) -> & KeyboardState {
@@ -419,6 +444,18 @@ impl WindowState {
419
444
420
445
( * window_state_ptr) . frame_timer . set ( Some ( timer) ) ;
421
446
}
447
+
448
+ fn send_deferred_events ( & self , window_handler : & mut dyn WindowHandler ) {
449
+ let mut window = crate :: Window :: new ( Window { inner : & self . window_inner } ) ;
450
+ loop {
451
+ let next_event = self . deferred_events . borrow_mut ( ) . pop_front ( ) ;
452
+ if let Some ( event) = next_event {
453
+ window_handler. on_event ( & mut window, event) ;
454
+ } else {
455
+ break ;
456
+ }
457
+ }
458
+ }
422
459
}
423
460
424
461
unsafe impl < ' a > HasRawWindowHandle for Window < ' a > {
0 commit comments