@@ -184,7 +184,7 @@ impl EventLoop {
184
184
}
185
185
186
186
impl EventLoop {
187
- /// Run the application with the event loop on the calling thread.
187
+ /// Run the event loop with the given application on the calling thread.
188
188
///
189
189
/// ## Event loop flow
190
190
///
@@ -237,34 +237,70 @@ impl EventLoop {
237
237
/// [`ControlFlow::WaitUntil`] and life-cycle methods like [`ApplicationHandler::resumed`], but
238
238
/// it should give you an idea of how things fit together.
239
239
///
240
- /// ## Platform-specific
240
+ /// ## Returns
241
+ ///
242
+ /// The semantics of this function can be a bit confusing, because the way different platforms
243
+ /// control their event loop varies significantly.
244
+ ///
245
+ /// On most platforms (Android, X11, Wayland, Windows, macOS), this blocks the caller, runs the
246
+ /// event loop internally, and then returns once [`ActiveEventLoop::exit`] is called.
247
+ ///
248
+ /// On iOS, this will register the application handler, and then call [`UIApplicationMain`]
249
+ /// (which is the only way to run the system event loop), which never returns to the caller
250
+ /// (the process instead exits after the handler has been dropped).
251
+ ///
252
+ /// On the web, this works by registering the application handler, and then immediately
253
+ /// returning to the caller. This is necessary because WebAssembly (and JavaScript) is always
254
+ /// executed in the context of the browser's own (internal) event loop, and thus we need to
255
+ /// return to avoid blocking that and allow events to later be delivered asynchronously.
256
+ ///
257
+ /// If you call this function inside `fn main`, you usually do not need to think about these
258
+ /// details.
259
+ ///
260
+ /// [`UIApplicationMain`]: https://developer.apple.com/documentation/uikit/uiapplicationmain(_:_:_:_:)-1yub7?language=objc
241
261
///
242
- /// - **iOS:** Will never return to the caller and so values not passed to this function will
243
- /// *not* be dropped before the process exits.
244
- /// - **Web:** Will _act_ as if it never returns to the caller by throwing a Javascript
245
- /// exception (that Rust doesn't see) that will also mean that the rest of the function is
246
- /// never executed and any values not passed to this function will *not* be dropped.
262
+ /// ## Static
247
263
///
248
- /// Web applications are recommended to use
264
+ /// To alleviate the issues noted above, this function requires that you pass in a `'static`
265
+ /// handler, to ensure that any state your application uses will be alive as long as the
266
+ /// application is running.
267
+ ///
268
+ /// To be clear, you should avoid doing e.g. `event_loop.run_app(&mut app)?`, and prefer
269
+ /// `event_loop.run_app(app)?` instead.
270
+ ///
271
+ /// If this requirement is prohibitive for you, consider using
249
272
#[ cfg_attr(
250
- web_platform,
251
- doc = " [`EventLoopExtWeb::spawn_app()`][crate::platform::web::EventLoopExtWeb::spawn_app()]"
273
+ any(
274
+ windows_platform,
275
+ macos_platform,
276
+ android_platform,
277
+ x11_platform,
278
+ wayland_platform,
279
+ docsrs,
280
+ ) ,
281
+ doc = "[`EventLoopExtRunOnDemand::run_app_on_demand`](crate::platform::run_on_demand::EventLoopExtRunOnDemand::run_app_on_demand)"
252
282
) ]
253
- #[ cfg_attr( not( web_platform) , doc = " `EventLoopExtWeb::spawn_app()`" ) ]
254
- /// [^1] instead of [`run_app()`] to avoid the need for the Javascript exception trick, and to
255
- /// make it clearer that the event loop runs asynchronously (via the browser's own,
256
- /// internal, event loop) and doesn't block the current thread of execution like it does
257
- /// on other platforms.
258
- ///
259
- /// This function won't be available with `target_feature = "exception-handling"`.
283
+ #[ cfg_attr(
284
+ not( any(
285
+ windows_platform,
286
+ macos_platform,
287
+ android_platform,
288
+ x11_platform,
289
+ wayland_platform,
290
+ docsrs,
291
+ ) ) ,
292
+ doc = "`EventLoopExtRunOnDemand::run_app_on_demand`"
293
+ ) ]
294
+ /// instead (though note that this is not available on iOS and web).
260
295
///
261
- /// [^1]: `spawn_app()` is only available on the Web platform.
296
+ /// ## Platform-specific
262
297
///
263
- /// [`set_control_flow()`]: ActiveEventLoop::set_control_flow()
264
- /// [`run_app()`]: Self::run_app()
298
+ /// - **Web** Once your handler has been dropped, it's possible to reinitialize another event
299
+ /// loop by calling this function again. This can be useful if you want to recreate the event
300
+ /// loop while the WebAssembly module is still loaded. For example, this can be used to
301
+ /// recreate the event loop when switching between tabs on a single page application.
265
302
#[ inline]
266
- #[ cfg( not( all( web_platform, target_feature = "exception-handling" ) ) ) ]
267
- pub fn run_app < A : ApplicationHandler > ( self , app : A ) -> Result < ( ) , EventLoopError > {
303
+ pub fn run_app < A : ApplicationHandler + ' static > ( self , app : A ) -> Result < ( ) , EventLoopError > {
268
304
self . event_loop . run_app ( app)
269
305
}
270
306
0 commit comments