stdweb::web::html_element::CanvasElement from document().que



我正在Rust中构建一个紫杉web应用程序,并试图从CSS选择器中获得一个CanvasRenderingContext2d。我遇到的问题是如何将stdweb::web::Element转换为stdweb::web::html_element::CanvasElement

我的当前代码是:

use stdweb::web::{CanvasRenderingContext2d, document, Element, IParentNode};
use stdweb::web::html_element::CanvasElement;
fn get_canvas_context(selector: &str) -> CanvasRenderingContext2d {
let element: Element = document().query_selector(selector)
.expect(format!("query_selector({selector}) not found").as_str())
.unwrap()
;
// BUG: the trait `From<stdweb::web::Element>` is not implemented for `CanvasElement`
let canvas_element: CanvasElement = element
.try_into()
.expect(format!("query_selector({selector}) not CanvasElement").as_str())
;
let context: CanvasRenderingContext2d = canvas_element.get_context()
.expect(format!("query_selector({selector}) failed to get_context()").as_str())
;
context
}

cargo check报告以下错误

error[E0277]: the trait bound `CanvasElement: From<stdweb::web::Element>` is not satisfied
--> src/utils.rs:12:10
|
12 |         .try_into()
|          ^^^^^^^^ the trait `From<stdweb::web::Element>` is not implemented for `CanvasElement`
|
= note: required because of the requirements on the impl of `Into<CanvasElement>` for `stdweb::web::Element`
= note: required because of the requirements on the impl of `std::convert::TryFrom<stdweb::web::Element>` for `CanvasElement`
= note: required because of the requirements on the impl of `std::convert::TryInto<CanvasElement>` for `stdweb::web::Element`

我的最终目标是返回一个我认为需要canvas_element.get_context()CanvasRenderingContext2d

正确的做法是什么?

试试dyn_into:

let canvas = document
.get_element_by_id("my-canvas")
.unwrap()
.dyn_into::<web_sys::HtmlCanvasElement>()?;

更多信息见JsCast文档。

感谢@ben用你上面的答案激励了我。

该代码在实践中实现比您的代码片段所建议的要复杂一些。然而,你的提示使用.dyn_into()从JsCast允许我搜索github更多的代码示例。

经过几天的努力,我终于能够编译和呈现以下代码片段:

  • 灵感:https://github.com/jessaimaya/rust_wasm/blob/89cea2a7aea240f6bd3ec8722e539aca35cee73c/src/browser.rs
  • 来源:https://github.com/JamesMcGuigan/fractals/blob/1c5d8bbf5cee6f02536205cd9036f71597f523f1/src/html/canvas_context.rs
use anyhow::{anyhow, Result};
use wasm_bindgen::JsCast;
use web_sys::{CanvasRenderingContext2d, Document, HtmlCanvasElement, Window};
#[allow(dead_code)]
// DOCS: https://developer.mozilla.org/en-US/docs/Web/API/Window
pub fn window() -> Result<Window> {
web_sys::window()
.ok_or_else(|| anyhow!("No Window Found"))
}
#[allow(dead_code)]
// DOCS: https://developer.mozilla.org/en-US/docs/Web/API/Document
pub fn document() -> Result<Document> {
window()?
.document()
.ok_or_else(|| anyhow!("No Document Found"))
}
#[allow(dead_code)]
// DOCS: https://developer.mozilla.org/en-US/docs/Web/API/HtmlCanvasElement
pub fn canvas(id_selector: &str) -> Result<HtmlCanvasElement> {
document()?
.get_element_by_id(id_selector)
.ok_or_else(|| anyhow!("No Canvas Element found with ID 'canvas'"))?
.dyn_into::<web_sys::HtmlCanvasElement>()
.map_err(|element| anyhow!("Error converting {:#?} to HtmlCanvasElement", element))
}
#[allow(dead_code)]
// DOCS: https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2d
pub fn canvas_context_2d(id_selector: &str) -> Result<CanvasRenderingContext2d> {
canvas(id_selector)?
.get_context("2d")
.map_err(|js_value| anyhow!("Error getting 2d context {:#?}", js_value))?
.ok_or_else(|| anyhow!("No 2d context found"))?
.dyn_into::<web_sys::CanvasRenderingContext2d>()
.map_err(|element| {
anyhow!(
"Error converting {:#?} to CanvasRenderingContext2d",
element
)
})
}

最新更新