Use Closure::new in examples (#2991)

There isn't much of a reason to use `Closure::wrap` over `Closure::new` anymore, so this changes `wasm-bindgen`'s examples to use `Closure::new` as the recommended method of creating closures.
This commit is contained in:
Liam Murphy 2022-07-13 23:55:44 +10:00 committed by GitHub
parent 9a7732f7a7
commit e322e6fb8b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
13 changed files with 66 additions and 77 deletions

View File

@ -78,7 +78,7 @@ impl Queue {
// This closure will only be called on the next microtask event
// tick
Closure::wrap(Box::new(move |_| state.run_all()))
Closure::new(move |_| state.run_all())
},
state,

View File

@ -97,7 +97,7 @@ impl Task {
let closure = {
let this = Rc::clone(&this);
Closure::wrap(Box::new(move |_| this.run()) as Box<dyn FnMut(JsValue)>)
Closure::new(move |_| this.run())
};
*this.inner.borrow_mut() = Some(Inner { future, closure });

View File

@ -63,7 +63,7 @@ fn setup_clock(window: &Window, document: &Document) -> Result<(), JsValue> {
.get_element_by_id("current-time")
.expect("should have #current-time on the page");
update_time(&current_time);
let a = Closure::wrap(Box::new(move || update_time(&current_time)) as Box<dyn Fn()>);
let a = Closure::<dyn Fn()>::new(move || update_time(&current_time));
window
.set_interval_with_callback_and_timeout_and_arguments_0(a.as_ref().unchecked_ref(), 1000)?;
fn update_time(current_time: &Element) {
@ -96,10 +96,10 @@ fn setup_clicker(document: &Document) {
.get_element_by_id("num-clicks")
.expect("should have #num-clicks on the page");
let mut clicks = 0;
let a = Closure::wrap(Box::new(move || {
let a = Closure::<dyn FnMut()>::new(move || {
clicks += 1;
num_clicks.set_inner_html(&clicks.to_string());
}) as Box<dyn FnMut()>);
});
document
.get_element_by_id("green-square")
.expect("should have #green-square on the page")

View File

@ -22,36 +22,36 @@ pub fn start() -> Result<(), JsValue> {
{
let context = context.clone();
let pressed = pressed.clone();
let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| {
let closure = Closure::<dyn FnMut(_)>::new(move |event: web_sys::MouseEvent| {
context.begin_path();
context.move_to(event.offset_x() as f64, event.offset_y() as f64);
pressed.set(true);
}) as Box<dyn FnMut(_)>);
});
canvas.add_event_listener_with_callback("mousedown", closure.as_ref().unchecked_ref())?;
closure.forget();
}
{
let context = context.clone();
let pressed = pressed.clone();
let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| {
let closure = Closure::<dyn FnMut(_)>::new(move |event: web_sys::MouseEvent| {
if pressed.get() {
context.line_to(event.offset_x() as f64, event.offset_y() as f64);
context.stroke();
context.begin_path();
context.move_to(event.offset_x() as f64, event.offset_y() as f64);
}
}) as Box<dyn FnMut(_)>);
});
canvas.add_event_listener_with_callback("mousemove", closure.as_ref().unchecked_ref())?;
closure.forget();
}
{
let context = context.clone();
let pressed = pressed.clone();
let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| {
let closure = Closure::<dyn FnMut(_)>::new(move |event: web_sys::MouseEvent| {
pressed.set(false);
context.line_to(event.offset_x() as f64, event.offset_y() as f64);
context.stroke();
}) as Box<dyn FnMut(_)>);
});
canvas.add_event_listener_with_callback("mouseup", closure.as_ref().unchecked_ref())?;
closure.forget();
}

View File

@ -43,10 +43,10 @@ impl WorkerPool {
let pool = WorkerPool {
state: Rc::new(PoolState {
workers: RefCell::new(Vec::with_capacity(initial)),
callback: Closure::wrap(Box::new(|event: Event| {
callback: Closure::new(|event: Event| {
console_log!("unhandled event: {}", event.type_());
crate::logv(&event);
}) as Box<dyn FnMut(Event)>),
}),
}),
};
for _ in 0..initial {
@ -145,7 +145,7 @@ impl WorkerPool {
let worker2 = worker.clone();
let reclaim_slot = Rc::new(RefCell::new(None));
let slot2 = reclaim_slot.clone();
let reclaim = Closure::wrap(Box::new(move |event: Event| {
let reclaim = Closure::<dyn FnMut(_)>::new(move |event: Event| {
if let Some(error) = event.dyn_ref::<ErrorEvent>() {
console_log!("error in worker: {}", error.message());
// TODO: this probably leaks memory somehow? It's sort of
@ -166,7 +166,7 @@ impl WorkerPool {
console_log!("unhandled event: {}", event.type_());
crate::logv(&event);
// TODO: like above, maybe a memory leak here?
}) as Box<dyn FnMut(Event)>);
});
worker.set_onmessage(Some(reclaim.as_ref().unchecked_ref()));
*reclaim_slot.borrow_mut() = Some(reclaim);
}

View File

@ -43,7 +43,7 @@ pub fn run() -> Result<(), JsValue> {
let g = f.clone();
let mut i = 0;
*g.borrow_mut() = Some(Closure::wrap(Box::new(move || {
*g.borrow_mut() = Some(Closure::new(move || {
if i > 300 {
body().set_text_content(Some("All done!"));
@ -61,7 +61,7 @@ pub fn run() -> Result<(), JsValue> {
// Schedule ourself for another requestAnimationFrame callback.
request_animation_frame(f.borrow().as_ref().unwrap());
}) as Box<dyn FnMut()>));
}));
request_animation_frame(g.borrow().as_ref().unwrap());
Ok(())

View File

@ -61,7 +61,7 @@ impl Element {
where
T: 'static + FnMut(web_sys::Event),
{
let cb = Closure::wrap(Box::new(handler) as Box<dyn FnMut(_)>);
let cb = Closure::new(handler);
if let Some(el) = self.el.take() {
let el_et: EventTarget = el.into();
el_et
@ -94,7 +94,7 @@ impl Element {
// TODO document selector to the target element
let tg_el = document;
let cb = Closure::wrap(Box::new(move |event: web_sys::Event| {
let cb = Closure::new(move |event: web_sys::Event| {
if let Some(target_element) = event.target() {
let dyn_target_el: Option<&web_sys::Node> =
wasm_bindgen::JsCast::dyn_ref(&target_element);
@ -116,7 +116,7 @@ impl Element {
}
}
}
}) as Box<dyn FnMut(_)>);
});
dyn_el
.add_event_listener_with_callback_and_bool(

View File

@ -86,7 +86,7 @@ impl View {
None => return,
};
let sched = self.sched.clone();
let set_page = Closure::wrap(Box::new(move || {
let set_page = Closure::<dyn FnMut()>::new(move || {
if let Some(location) = document.location() {
if let Ok(hash) = location.hash() {
if let Ok(sched) = &(sched.try_borrow_mut()) {
@ -94,7 +94,7 @@ impl View {
}
}
}
}) as Box<dyn FnMut()>);
});
let window_et: web_sys::EventTarget = window.into();
window_et

View File

@ -68,7 +68,7 @@ fn setup_input_oninput_callback(worker: Rc<RefCell<web_sys::Worker>>) {
#[allow(unused_assignments)]
let mut persistent_callback_handle = get_on_msg_callback();
let callback = Closure::wrap(Box::new(move || {
let callback = Closure::new(move || {
console::log_1(&"oninput callback triggered".into());
let document = web_sys::window().unwrap().document().unwrap();
@ -103,7 +103,7 @@ fn setup_input_oninput_callback(worker: Rc<RefCell<web_sys::Worker>>) {
.set_inner_text("");
}
}
}) as Box<dyn FnMut()>);
});
// Attach the closure as `oninput` callback to the input field.
document
@ -119,7 +119,7 @@ fn setup_input_oninput_callback(worker: Rc<RefCell<web_sys::Worker>>) {
/// Create a closure to act on the message returned by the worker
fn get_on_msg_callback() -> Closure<dyn FnMut(MessageEvent)> {
let callback = Closure::wrap(Box::new(move |event: MessageEvent| {
let callback = Closure::new(move |event: MessageEvent| {
console::log_2(&"Received response: ".into(), &event.data().into());
let result = match event.data().as_bool().unwrap() {
@ -134,7 +134,7 @@ fn get_on_msg_callback() -> Closure<dyn FnMut(MessageEvent)> {
.dyn_ref::<HtmlElement>()
.expect("#resultField should be a HtmlInputElement")
.set_inner_text(result);
}) as Box<dyn FnMut(_)>);
});
callback
}

View File

@ -44,15 +44,13 @@ pub async fn start() -> Result<(), JsValue> {
let dc1_clone = dc1.clone();
let onmessage_callback =
Closure::wrap(
Box::new(move |ev: MessageEvent| match ev.data().as_string() {
Some(message) => {
console_warn!("{:?}", message);
dc1_clone.send_with_str("Pong from pc1.dc!").unwrap();
}
None => {}
}) as Box<dyn FnMut(MessageEvent)>,
);
Closure::<dyn FnMut(_)>::new(move |ev: MessageEvent| match ev.data().as_string() {
Some(message) => {
console_warn!("{:?}", message);
dc1_clone.send_with_str("Pong from pc1.dc!").unwrap();
}
None => {}
});
dc1.set_onmessage(Some(onmessage_callback.as_ref().unchecked_ref()));
onmessage_callback.forget();
@ -60,27 +58,25 @@ pub async fn start() -> Result<(), JsValue> {
* If negotiation has done, this closure will be called
*
*/
let ondatachannel_callback = Closure::wrap(Box::new(move |ev: RtcDataChannelEvent| {
let ondatachannel_callback = Closure::<dyn FnMut(_)>::new(move |ev: RtcDataChannelEvent| {
let dc2 = ev.channel();
console_log!("pc2.ondatachannel!: {:?}", dc2.label());
let onmessage_callback =
Closure::wrap(
Box::new(move |ev: MessageEvent| match ev.data().as_string() {
Some(message) => console_warn!("{:?}", message),
None => {}
}) as Box<dyn FnMut(MessageEvent)>,
);
Closure::<dyn FnMut(_)>::new(move |ev: MessageEvent| match ev.data().as_string() {
Some(message) => console_warn!("{:?}", message),
None => {}
});
dc2.set_onmessage(Some(onmessage_callback.as_ref().unchecked_ref()));
onmessage_callback.forget();
let dc2_clone = dc2.clone();
let onopen_callback = Closure::wrap(Box::new(move || {
let onopen_callback = Closure::<dyn FnMut()>::new(move || {
dc2_clone.send_with_str("Ping from pc2.dc!").unwrap();
}) as Box<dyn FnMut()>);
});
dc2.set_onopen(Some(onopen_callback.as_ref().unchecked_ref()));
onopen_callback.forget();
}) as Box<dyn FnMut(RtcDataChannelEvent)>);
});
pc2.set_ondatachannel(Some(ondatachannel_callback.as_ref().unchecked_ref()));
ondatachannel_callback.forget();
@ -90,31 +86,25 @@ pub async fn start() -> Result<(), JsValue> {
*/
let pc2_clone = pc2.clone();
let onicecandidate_callback1 =
Closure::wrap(
Box::new(move |ev: RtcPeerConnectionIceEvent| match ev.candidate() {
Some(candidate) => {
console_log!("pc1.onicecandidate: {:#?}", candidate.candidate());
let _ =
pc2_clone.add_ice_candidate_with_opt_rtc_ice_candidate(Some(&candidate));
}
None => {}
}) as Box<dyn FnMut(RtcPeerConnectionIceEvent)>,
);
Closure::<dyn FnMut(_)>::new(move |ev: RtcPeerConnectionIceEvent| match ev.candidate() {
Some(candidate) => {
console_log!("pc1.onicecandidate: {:#?}", candidate.candidate());
let _ = pc2_clone.add_ice_candidate_with_opt_rtc_ice_candidate(Some(&candidate));
}
None => {}
});
pc1.set_onicecandidate(Some(onicecandidate_callback1.as_ref().unchecked_ref()));
onicecandidate_callback1.forget();
let pc1_clone = pc1.clone();
let onicecandidate_callback2 =
Closure::wrap(
Box::new(move |ev: RtcPeerConnectionIceEvent| match ev.candidate() {
Some(candidate) => {
console_log!("pc2.onicecandidate: {:#?}", candidate.candidate());
let _ =
pc1_clone.add_ice_candidate_with_opt_rtc_ice_candidate(Some(&candidate));
}
None => {}
}) as Box<dyn FnMut(RtcPeerConnectionIceEvent)>,
);
Closure::<dyn FnMut(_)>::new(move |ev: RtcPeerConnectionIceEvent| match ev.candidate() {
Some(candidate) => {
console_log!("pc2.onicecandidate: {:#?}", candidate.candidate());
let _ = pc1_clone.add_ice_candidate_with_opt_rtc_ice_candidate(Some(&candidate));
}
None => {}
});
pc2.set_onicecandidate(Some(onicecandidate_callback2.as_ref().unchecked_ref()));
onicecandidate_callback2.forget();

View File

@ -20,7 +20,7 @@ pub fn start_websocket() -> Result<(), JsValue> {
ws.set_binary_type(web_sys::BinaryType::Arraybuffer);
// create callback
let cloned_ws = ws.clone();
let onmessage_callback = Closure::wrap(Box::new(move |e: MessageEvent| {
let onmessage_callback = Closure::<dyn FnMut(_)>::new(move |e: MessageEvent| {
// Handle difference Text/Binary,...
if let Ok(abuf) = e.data().dyn_into::<js_sys::ArrayBuffer>() {
console_log!("message event, received arraybuffer: {:?}", abuf);
@ -40,13 +40,12 @@ pub fn start_websocket() -> Result<(), JsValue> {
let fr = web_sys::FileReader::new().unwrap();
let fr_c = fr.clone();
// create onLoadEnd callback
let onloadend_cb = Closure::wrap(Box::new(move |_e: web_sys::ProgressEvent| {
let onloadend_cb = Closure::<dyn FnMut(_)>::new(move |_e: web_sys::ProgressEvent| {
let array = js_sys::Uint8Array::new(&fr_c.result().unwrap());
let len = array.byte_length() as usize;
console_log!("Blob received {}bytes: {:?}", len, array.to_vec());
// here you can for example use the received image/png data
})
as Box<dyn FnMut(web_sys::ProgressEvent)>);
});
fr.set_onloadend(Some(onloadend_cb.as_ref().unchecked_ref()));
fr.read_as_array_buffer(&blob).expect("blob not readable");
onloadend_cb.forget();
@ -55,20 +54,20 @@ pub fn start_websocket() -> Result<(), JsValue> {
} else {
console_log!("message event, received Unknown: {:?}", e.data());
}
}) as Box<dyn FnMut(MessageEvent)>);
});
// set message event handler on WebSocket
ws.set_onmessage(Some(onmessage_callback.as_ref().unchecked_ref()));
// forget the callback to keep it alive
onmessage_callback.forget();
let onerror_callback = Closure::wrap(Box::new(move |e: ErrorEvent| {
let onerror_callback = Closure::<dyn FnMut(_)>::new(move |e: ErrorEvent| {
console_log!("error event: {:?}", e);
}) as Box<dyn FnMut(ErrorEvent)>);
});
ws.set_onerror(Some(onerror_callback.as_ref().unchecked_ref()));
onerror_callback.forget();
let cloned_ws = ws.clone();
let onopen_callback = Closure::wrap(Box::new(move |_| {
let onopen_callback = Closure::<dyn FnMut()>::new(move || {
console_log!("socket opened");
match cloned_ws.send_with_str("ping") {
Ok(_) => console_log!("message successfully sent"),
@ -79,7 +78,7 @@ pub fn start_websocket() -> Result<(), JsValue> {
Ok(_) => console_log!("binary message successfully sent"),
Err(err) => console_log!("error sending message: {:?}", err),
}
}) as Box<dyn FnMut(JsValue)>);
});
ws.set_onopen(Some(onopen_callback.as_ref().unchecked_ref()));
onopen_callback.forget();

View File

@ -121,7 +121,7 @@ impl XrApp {
let g = f.clone();
let mut i = 0;
*g.borrow_mut() = Some(Closure::wrap(Box::new(move |time: f64, frame: XrFrame| {
*g.borrow_mut() = Some(Closure::new(move |time: f64, frame: XrFrame| {
log!("Frame rendering...");
if i > 2 {
log!("All done!");
@ -138,7 +138,7 @@ impl XrApp {
// Schedule ourself for another requestAnimationFrame callback.
// TODO: WebXR Samples call this at top of request_animation_frame - should this be moved?
request_animation_frame(&sess, f.borrow().as_ref().unwrap());
}) as Box<dyn FnMut(f64, XrFrame)>));
}));
let session: &Option<XrSession> = &self.session.borrow();
let sess: &XrSession = if let Some(sess) = session {

View File

@ -65,7 +65,7 @@ use crate::UnwrapThrowExt;
///
/// #[wasm_bindgen]
/// pub fn run() -> IntervalHandle {
/// // First up we use `Closure::wrap` to wrap up a Rust closure and create
/// // First up we use `Closure::new` to wrap up a Rust closure and create
/// // a JS closure.
/// let cb = Closure::new(|| {
/// log("interval elapsed!");