11use std:: {
2- self , collections:: VecDeque , fmt:: { self , Debug , Formatter } ,
3- hint:: unreachable_unchecked, mem, sync:: { Mutex , MutexGuard } , time:: Instant ,
2+ collections:: VecDeque , fmt:: { self , Debug , Formatter } ,
3+ hint:: unreachable_unchecked, mem,
4+ sync:: { atomic:: { AtomicBool , Ordering } , Mutex , MutexGuard } , time:: Instant ,
45} ;
56
67use cocoa:: { appkit:: NSApp , base:: nil} ;
6869
6970#[ derive( Default ) ]
7071struct Handler {
72+ ready : AtomicBool ,
7173 control_flow : Mutex < ControlFlow > ,
7274 control_flow_prev : Mutex < ControlFlow > ,
7375 start_time : Mutex < Option < Instant > > ,
@@ -88,6 +90,18 @@ impl Handler {
8890 self . waker . lock ( ) . unwrap ( )
8991 }
9092
93+ fn is_ready ( & self ) -> bool {
94+ self . ready . load ( Ordering :: Acquire )
95+ }
96+
97+ fn set_ready ( & self ) {
98+ self . ready . store ( true , Ordering :: Release ) ;
99+ }
100+
101+ fn is_control_flow_exit ( & self ) -> bool {
102+ * self . control_flow . lock ( ) . unwrap ( ) == ControlFlow :: Exit
103+ }
104+
91105 fn get_control_flow_and_update_prev ( & self ) -> ControlFlow {
92106 let control_flow = self . control_flow . lock ( ) . unwrap ( ) ;
93107 * self . control_flow_prev . lock ( ) . unwrap ( ) = * control_flow;
@@ -136,17 +150,18 @@ impl AppState {
136150 } ) ) ;
137151 }
138152
139- pub fn exit ( ) -> ! {
153+ pub fn exit ( ) {
140154 HANDLER . handle_nonuser_event ( Event :: LoopDestroyed ) ;
141- std:: process:: exit ( 0 )
142155 }
143156
144157 pub fn launched ( ) {
158+ HANDLER . set_ready ( ) ;
145159 HANDLER . waker ( ) . start ( ) ;
146160 HANDLER . handle_nonuser_event ( Event :: NewEvents ( StartCause :: Init ) ) ;
147161 }
148162
149163 pub fn wakeup ( ) {
164+ if !HANDLER . is_ready ( ) { return }
150165 let start = HANDLER . get_start_time ( ) . unwrap ( ) ;
151166 let cause = match HANDLER . get_control_flow_and_update_prev ( ) {
152167 ControlFlow :: Poll => StartCause :: Poll ,
@@ -173,29 +188,39 @@ impl AppState {
173188 }
174189
175190 pub fn queue_event ( event : Event < Never > ) {
191+ if !unsafe { msg_send ! [ class!( NSThread ) , isMainThread] } {
192+ panic ! ( "uh-oh" ) ;
193+ }
176194 HANDLER . events ( ) . push_back ( event) ;
177195 }
178196
179197 pub fn queue_events ( mut events : VecDeque < Event < Never > > ) {
198+ if !unsafe { msg_send ! [ class!( NSThread ) , isMainThread] } {
199+ panic ! ( "uh-ohs" ) ;
200+ }
180201 HANDLER . events ( ) . append ( & mut events) ;
181202 }
182203
183204 pub fn cleared ( ) {
184- HANDLER . handle_nonuser_event ( Event :: EventsCleared ) ;
205+ if !HANDLER . is_ready ( ) { return }
206+ let mut will_stop = HANDLER . is_control_flow_exit ( ) ;
185207 for event in HANDLER . take_events ( ) {
186208 HANDLER . handle_nonuser_event ( event) ;
209+ will_stop |= HANDLER . is_control_flow_exit ( ) ;
210+ }
211+ HANDLER . handle_nonuser_event ( Event :: EventsCleared ) ;
212+ will_stop |= HANDLER . is_control_flow_exit ( ) ;
213+ if will_stop {
214+ let _: ( ) = unsafe { msg_send ! [ NSApp ( ) , stop: nil] } ;
215+ return
187216 }
188217 HANDLER . update_start_time ( ) ;
189218 match HANDLER . get_old_and_new_control_flow ( ) {
190- ( ControlFlow :: Poll , ControlFlow :: Poll ) => ( ) ,
191- ( ControlFlow :: Wait , ControlFlow :: Wait ) => ( ) ,
192- ( ControlFlow :: WaitUntil ( old_instant) , ControlFlow :: WaitUntil ( new_instant) ) if old_instant == new_instant => ( ) ,
219+ ( ControlFlow :: Exit , _) | ( _, ControlFlow :: Exit ) => unreachable ! ( ) ,
220+ ( old, new) if old == new => ( ) ,
193221 ( _, ControlFlow :: Wait ) => HANDLER . waker ( ) . stop ( ) ,
194- ( _, ControlFlow :: WaitUntil ( new_instant ) ) => HANDLER . waker ( ) . start_at ( new_instant ) ,
222+ ( _, ControlFlow :: WaitUntil ( instant ) ) => HANDLER . waker ( ) . start_at ( instant ) ,
195223 ( _, ControlFlow :: Poll ) => HANDLER . waker ( ) . start ( ) ,
196- ( _, ControlFlow :: Exit ) => {
197- let _: ( ) = unsafe { msg_send ! [ NSApp ( ) , stop: nil] } ;
198- } ,
199224 }
200225 }
201226}
0 commit comments