@@ -22,6 +22,7 @@ use std::time::{Duration, Instant};
22
22
use std:: rc:: Rc ;
23
23
use std:: cell:: RefCell ;
24
24
use std:: collections:: VecDeque ;
25
+ use std:: marker:: PhantomData ;
25
26
use parking_lot:: Mutex ;
26
27
27
28
use winapi:: ctypes:: c_int;
@@ -43,7 +44,7 @@ use winapi::um::winnt::{LONG, LPCSTR, SHORT};
43
44
44
45
use window:: WindowId as RootWindowId ;
45
46
use monitor:: MonitorHandle ;
46
- use event_loop:: { ControlFlow , EventLoop as RootEventLoop , EventLoopClosed } ;
47
+ use event_loop:: { ControlFlow , EventLoopWindowTarget as RootELW , EventLoopClosed } ;
47
48
use dpi:: { LogicalPosition , LogicalSize , PhysicalSize } ;
48
49
use event:: { DeviceEvent , Touch , TouchPhase , StartCause , KeyboardInput , Event , WindowEvent } ;
49
50
use platform_impl:: platform:: { event, Cursor , WindowId , DEVICE_ID , wrap_device_id, util} ;
@@ -138,11 +139,15 @@ impl<T> ThreadMsgTargetSubclassInput<T> {
138
139
}
139
140
}
140
141
141
- pub struct EventLoop < T > {
142
+ pub struct EventLoop < T : ' static > {
142
143
// Id of the background thread from the Win32 API.
143
- thread_id : DWORD ,
144
144
thread_msg_target : HWND ,
145
145
thread_msg_sender : Sender < T > ,
146
+ window_target : RootELW < T >
147
+ }
148
+
149
+ pub struct EventLoopWindowTarget < T > {
150
+ thread_id : DWORD ,
146
151
trigger_newevents_on_redraw : Arc < AtomicBool > ,
147
152
pub ( crate ) runner_shared : EventLoopRunnerShared < T > ,
148
153
}
@@ -152,6 +157,10 @@ impl<T: 'static> EventLoop<T> {
152
157
Self :: with_dpi_awareness ( true )
153
158
}
154
159
160
+ pub fn window_target ( & self ) -> & RootELW < T > {
161
+ & self . window_target
162
+ }
163
+
155
164
pub fn with_dpi_awareness ( dpi_aware : bool ) -> EventLoop < T > {
156
165
become_dpi_aware ( dpi_aware) ;
157
166
@@ -163,37 +172,40 @@ impl<T: 'static> EventLoop<T> {
163
172
let ( thread_msg_target, thread_msg_sender) = thread_event_target_window ( runner_shared. clone ( ) ) ;
164
173
165
174
EventLoop {
166
- thread_id,
167
175
thread_msg_target, thread_msg_sender,
168
- trigger_newevents_on_redraw : Arc :: new ( AtomicBool :: new ( true ) ) ,
169
- runner_shared
176
+ window_target : RootELW {
177
+ p : EventLoopWindowTarget {
178
+ thread_id,
179
+ trigger_newevents_on_redraw : Arc :: new ( AtomicBool :: new ( true ) ) ,
180
+ runner_shared
181
+ } ,
182
+ _marker : PhantomData
183
+ }
170
184
}
171
185
}
172
186
173
187
pub fn run < F > ( mut self , event_handler : F ) -> !
174
- where F : ' static + FnMut ( Event < T > , & RootEventLoop < T > , & mut ControlFlow )
188
+ where F : ' static + FnMut ( Event < T > , & RootELW < T > , & mut ControlFlow )
175
189
{
176
190
self . run_return ( event_handler) ;
177
191
:: std:: process:: exit ( 0 ) ;
178
192
}
179
193
180
194
pub fn run_return < F > ( & mut self , mut event_handler : F )
181
- where F : FnMut ( Event < T > , & RootEventLoop < T > , & mut ControlFlow )
195
+ where F : FnMut ( Event < T > , & RootELW < T > , & mut ControlFlow )
182
196
{
183
197
unsafe { winuser:: IsGUIThread ( 1 ) ; }
184
198
185
- assert_eq ! ( mem:: size_of:: <RootEventLoop <T >>( ) , mem:: size_of:: <EventLoop <T >>( ) ) ;
186
- let self_ptr = self as * const EventLoop < T > ;
199
+ let event_loop_windows_ref = & self . window_target ;
187
200
188
201
let mut runner = unsafe { EventLoopRunner :: new (
189
202
self ,
190
203
move |event, control_flow| {
191
- let event_loop_ref = & * ( self_ptr as * const RootEventLoop < T > ) ;
192
- event_handler ( event, event_loop_ref, control_flow)
204
+ event_handler ( event, event_loop_windows_ref, control_flow)
193
205
}
194
206
) } ;
195
207
{
196
- let runner_shared = self . runner_shared . clone ( ) ;
208
+ let runner_shared = self . window_target . p . runner_shared . clone ( ) ;
197
209
let mut runner_ref = runner_shared. runner . borrow_mut ( ) ;
198
210
loop {
199
211
let event = runner_shared. buffer . borrow_mut ( ) . pop_front ( ) ;
@@ -206,7 +218,7 @@ impl<T: 'static> EventLoop<T> {
206
218
}
207
219
208
220
macro_rules! runner {
209
- ( ) => { { self . runner_shared. runner. borrow_mut( ) . as_mut( ) . unwrap( ) } } ;
221
+ ( ) => { { self . window_target . p . runner_shared. runner. borrow_mut( ) . as_mut( ) . unwrap( ) } } ;
210
222
}
211
223
212
224
unsafe {
@@ -244,7 +256,7 @@ impl<T: 'static> EventLoop<T> {
244
256
}
245
257
246
258
runner ! ( ) . call_event_handler ( Event :: LoopDestroyed ) ;
247
- * self . runner_shared . runner . borrow_mut ( ) = None ;
259
+ * self . window_target . p . runner_shared . runner . borrow_mut ( ) = None ;
248
260
}
249
261
250
262
pub fn create_proxy ( & self ) -> EventLoopProxy < T > {
@@ -253,7 +265,9 @@ impl<T: 'static> EventLoop<T> {
253
265
event_send : self . thread_msg_sender . clone ( )
254
266
}
255
267
}
268
+ }
256
269
270
+ impl < T > EventLoopWindowTarget < T > {
257
271
#[ inline( always) ]
258
272
pub ( crate ) fn create_thread_executor ( & self ) -> EventLoopThreadExecutor {
259
273
EventLoopThreadExecutor {
@@ -309,7 +323,7 @@ impl<T> EventLoopRunner<T> {
309
323
where F : FnMut ( Event < T > , & mut ControlFlow )
310
324
{
311
325
EventLoopRunner {
312
- trigger_newevents_on_redraw : event_loop. trigger_newevents_on_redraw . clone ( ) ,
326
+ trigger_newevents_on_redraw : event_loop. window_target . p . trigger_newevents_on_redraw . clone ( ) ,
313
327
control_flow : ControlFlow :: default ( ) ,
314
328
runner_state : RunnerState :: New ,
315
329
in_modal_loop : false ,
@@ -545,8 +559,6 @@ impl<T> Drop for EventLoop<T> {
545
559
fn drop ( & mut self ) {
546
560
unsafe {
547
561
winuser:: DestroyWindow ( self . thread_msg_target ) ;
548
- // Posting `WM_QUIT` will cause `GetMessage` to stop.
549
- winuser:: PostThreadMessageA ( self . thread_id , winuser:: WM_QUIT , 0 , 0 ) ;
550
562
}
551
563
}
552
564
}
0 commit comments