提问人:Athan Clark 提问时间:7/13/2022 更新时间:7/13/2022 访问量:689
使用 Yew 回调作为wasm_bindgen闭包
Using a Yew Callback as a wasm_bindgen Closure
问:
此问题是为 Yew v0.19 编写的
异步外部 JavaScript 函数可以在 Rust 中使用到 Closures,作为传入的函数:
#[wasm_bindgen]
extern "C" {
fn setInterval(closure: &Closure<dyn FnMut()>, time: u32) -> i32;
}
// ...
let cb = Closure::new(|| {
log("interval elapsed!");
});
let interval_id = setInterval(&cb, 1_000);
这对于一个迂腐的例子来说很好,但有一个关键的要求——应用的函数需要有生命周期。同样,对于 Yew 应用程序,自发响应的完美机制是枚举,并让它 .但是,(发出消息)中的机制没有静态生存期。Closure
'static
Message
update()
Model
link()
Context
在理想情况下,提交给闭包的值可以作为 Yew 组件消息应用:
struct Model {
thing: Option<JsValue>,
}
enum Msg {
GotThing(JsValue),
}
#[wasm_bindgen]
extern "C" {
fn createThing(closure: &Closure<dyn FnMut(JsValue) -> ());
}
impl Component for Model {
type Message = Msg;
type Properties = ();
fn create(_ctx: &Context<Self>) -> Self {
Model {
thing: None, // initial value
}
}
fn update(&mut self, _ctx: &Context<Self>, msg: Self::Message) -> bool {
match msg {
Msg::GotThing(x) => { // handle the message
self.thing = Some(x);
true
},
}
}
fn rendered(&mut self, ctx: &Context<Self>, first_render: bool) {
if first_render {
let cb: Box<dyn FnMut(JsValue) -> ()> = Box::new(|x| {
// try and issue the message
ctx.link().send_message(Msg::GotThing(x));
// ^ doesn't have a `'static` lifetime! Won't compile
});
createThing(Closure::wrap(&cb));
}
}
// fn view() ... omitted, not relevant
}
我想知道是否有办法将 a 转换为 ,或者是否有更好、更规范的方法可以做到这一点,请纠正我。Callback
Closure
我的另一个想法是使用某种静态定义的队列(这并不安全,因为它是一个可变的静态变量),但它可以用作传递给之间的中间数据类型,并且可以在组件内调度消息。Closure
createThing
也许有一种与我忽略的 Yew 组件交互的外部方式?我不确定如何解决这个问题。实现这一目标的最正确方法是什么?
答: 暂无答案
评论