Skip to content

Commit f5761bf

Browse files
Add node.js support for timers (#185)
* Add node.js support for timers * Bind to global scope for all platforms
1 parent f7058d5 commit f5761bf

File tree

1 file changed

+22
-70
lines changed

1 file changed

+22
-70
lines changed

crates/timers/src/callback.rs

Lines changed: 22 additions & 70 deletions
Original file line numberDiff line numberDiff line change
@@ -3,62 +3,20 @@
33
use js_sys::Function;
44
use wasm_bindgen::prelude::*;
55
use wasm_bindgen::{JsCast, JsValue};
6-
use web_sys::{Window, WorkerGlobalScope};
76

8-
thread_local! {
9-
static GLOBAL: WindowOrWorker = WindowOrWorker::new();
10-
}
11-
12-
enum WindowOrWorker {
13-
Window(Window),
14-
Worker(WorkerGlobalScope),
15-
}
16-
17-
impl WindowOrWorker {
18-
fn new() -> Self {
19-
#[wasm_bindgen]
20-
extern "C" {
21-
type Global;
22-
23-
#[wasm_bindgen(method, getter, js_name = Window)]
24-
fn window(this: &Global) -> JsValue;
25-
26-
#[wasm_bindgen(method, getter, js_name = WorkerGlobalScope)]
27-
fn worker(this: &Global) -> JsValue;
28-
}
7+
#[wasm_bindgen]
8+
extern "C" {
9+
#[wasm_bindgen(js_name = "setTimeout", catch)]
10+
fn set_timeout(handler: &Function, timeout: i32) -> Result<i32, JsValue>;
2911

30-
let global: Global = js_sys::global().unchecked_into();
12+
#[wasm_bindgen(js_name = "setInterval", catch)]
13+
fn set_interval(handler: &Function, timeout: i32) -> Result<i32, JsValue>;
3114

32-
if !global.window().is_undefined() {
33-
Self::Window(global.unchecked_into())
34-
} else if !global.worker().is_undefined() {
35-
Self::Worker(global.unchecked_into())
36-
} else {
37-
panic!("Only supported in a browser or web worker");
38-
}
39-
}
40-
}
41-
42-
macro_rules! impl_window_or_worker {
43-
($(fn $name:ident($($par_name:ident: $par_type:ty),*)$( -> $return:ty)?;)+) => {
44-
impl WindowOrWorker {
45-
$(
46-
fn $name(&self, $($par_name: $par_type),*)$( -> $return)? {
47-
match self {
48-
Self::Window(window) => window.$name($($par_name),*),
49-
Self::Worker(worker) => worker.$name($($par_name),*),
50-
}
51-
}
52-
)+
53-
}
54-
};
55-
}
15+
#[wasm_bindgen(js_name = "clearTimeout")]
16+
fn clear_timeout(handle: i32);
5617

57-
impl_window_or_worker! {
58-
fn set_timeout_with_callback_and_timeout_and_arguments_0(handler: &Function, timeout: i32) -> Result<i32, JsValue>;
59-
fn set_interval_with_callback_and_timeout_and_arguments_0(handler: &Function, timeout: i32) -> Result<i32, JsValue>;
60-
fn clear_timeout_with_handle(handle: i32);
61-
fn clear_interval_with_handle(handle: i32);
18+
#[wasm_bindgen(js_name = "clearInterval")]
19+
fn clear_interval(handle: i32);
6220
}
6321

6422
/// A scheduled timeout.
@@ -77,7 +35,7 @@ pub struct Timeout {
7735
impl Drop for Timeout {
7836
fn drop(&mut self) {
7937
if let Some(id) = self.id {
80-
GLOBAL.with(|global| global.clear_timeout_with_handle(id));
38+
clear_timeout(id);
8139
}
8240
}
8341
}
@@ -101,14 +59,11 @@ impl Timeout {
10159
{
10260
let closure = Closure::once(callback);
10361

104-
let id = GLOBAL.with(|global| {
105-
global
106-
.set_timeout_with_callback_and_timeout_and_arguments_0(
107-
closure.as_ref().unchecked_ref::<js_sys::Function>(),
108-
millis as i32,
109-
)
110-
.unwrap_throw()
111-
});
62+
let id = set_timeout(
63+
closure.as_ref().unchecked_ref::<js_sys::Function>(),
64+
millis as i32,
65+
)
66+
.unwrap_throw();
11267

11368
Timeout {
11469
id: Some(id),
@@ -180,7 +135,7 @@ pub struct Interval {
180135
impl Drop for Interval {
181136
fn drop(&mut self) {
182137
if let Some(id) = self.id {
183-
GLOBAL.with(|global| global.clear_interval_with_handle(id));
138+
clear_interval(id);
184139
}
185140
}
186141
}
@@ -203,14 +158,11 @@ impl Interval {
203158
{
204159
let closure = Closure::wrap(Box::new(callback) as Box<dyn FnMut()>);
205160

206-
let id = GLOBAL.with(|global| {
207-
global
208-
.set_interval_with_callback_and_timeout_and_arguments_0(
209-
closure.as_ref().unchecked_ref::<js_sys::Function>(),
210-
millis as i32,
211-
)
212-
.unwrap_throw()
213-
});
161+
let id = set_interval(
162+
closure.as_ref().unchecked_ref::<js_sys::Function>(),
163+
millis as i32,
164+
)
165+
.unwrap_throw();
214166

215167
Interval {
216168
id: Some(id),

0 commit comments

Comments
 (0)