Add cleanup code to web backend, mostly web-sys (#1715)

* web-sys: Impl. event listeners removal for canvas

* web-sys: Impl. media query listeners cleanup

* web: Emit WindowEvent::Destroyed after Window is dropped

* web-sys: Fix unload event closure being dropped early

* web: Impl. cleanup on ControlFlow::Exit

- Drops the Runner, which causes the event handler closure to be
  dropped.
- (web-sys only:) Remove event listeners from DOM.

* web: Do not remove canvas from DOM when dropping Window

The canvas was inserted by the user, so it should be up to the user
whether the canvas should be removed.

* Update changelog
This commit is contained in:
alvinhochun 2020-09-21 06:42:07 +08:00 committed by GitHub
parent 1c97a310b1
commit 47e7aa4209
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
13 changed files with 436 additions and 162 deletions

View file

@ -1,5 +1,7 @@
mod canvas;
mod event;
mod event_handle;
mod media_query_handle;
mod scaling;
mod timeout;
@ -10,7 +12,7 @@ pub use self::timeout::{AnimationFrameRequest, Timeout};
use crate::dpi::{LogicalSize, Size};
use crate::platform::web::WindowExtWebSys;
use crate::window::Window;
use wasm_bindgen::{closure::Closure, JsCast};
use wasm_bindgen::closure::Closure;
use web_sys::{window, BeforeUnloadEvent, Element, HtmlCanvasElement};
pub fn throw(msg: &str) {
@ -24,16 +26,21 @@ pub fn exit_fullscreen() {
document.exit_fullscreen();
}
pub fn on_unload(mut handler: impl FnMut() + 'static) {
pub struct UnloadEventHandle {
_listener: event_handle::EventListenerHandle<dyn FnMut(BeforeUnloadEvent)>,
}
pub fn on_unload(mut handler: impl FnMut() + 'static) -> UnloadEventHandle {
let window = web_sys::window().expect("Failed to obtain window");
let closure = Closure::wrap(
Box::new(move |_: BeforeUnloadEvent| handler()) as Box<dyn FnMut(BeforeUnloadEvent)>
);
window
.add_event_listener_with_callback("beforeunload", &closure.as_ref().unchecked_ref())
.expect("Failed to add close listener");
let listener = event_handle::EventListenerHandle::new(&window, "beforeunload", closure);
UnloadEventHandle {
_listener: listener,
}
}
impl WindowExtWebSys for Window {