zoukankan      html  css  js  c++  java
  • [Rust] Pass a JavaScript Function to WebAssembly and Invoke it from Rust

    In some cases it’s useful to be able to invoke a JavaScript function inside Rust. This session showcases how this can be done, by passing along our JavaScript functions to the WebAssembly module instantiation.

    First let's create a function in js:

          const appendNumberToBody = (number) => {
            const text = document.createTextNode(number);
            document.body.appendChild(text);
          }

    Wrap this function into a single object which contains 'env':

          const importObject = {
            env: {
              appendNumberToBody: appendNumberToBody
            }
          };

    When we load wasm, we can pass in the object:

    WebAssembly.instantiateStreaming(fetch("utils.gc.wasm"), importObject)

    It return a promise, we can run the exported function return by wasm inside the promise.

    Now we are going to create a function in Rust:

    extern {
        fn appendNumberToBody(x: u32);
    }
    
    #[no_mangle]
    pub extern fn run() {
        unsafe { // we need to wrap with unsafe if getting the passed in value from third party
            appendNumberToBody(42);
        }
    }

    We exprot 'run' function, then we can invoke it inside promise:

          WebAssembly.instantiateStreaming(fetch("utils.gc.wasm"), importObject)
          .then(wasmModule => {
              wasmModule.instance.exports.run();
            });

    ---------

    Full code: Github

    index.html:

    <!DOCTYPE html>
    <html>
      <head>
        <script> 
    
          // pass the data from Js to Rust
          const appendNumberToBody = (number) => {
            const text = document.createTextNode(number);
            document.body.appendChild(text);
          }
    
          const importObject = {
            env: {
              appendNumberToBody: appendNumberToBody,
              alert: alert
            }
          };
    
          WebAssembly.instantiateStreaming(fetch("utils.gc.wasm"), importObject)
          .then(wasmModule => {
              wasmModule.instance.exports.run();
            });
        </script>
      <head>
      <body></body>
    <html>

    lib.rs:

    extern {
        fn appendNumberToBody(x: u32);
        fn alert(x: u32);
    }
    
    #[no_mangle]
    pub extern fn run() {
        unsafe {
            appendNumberToBody(42);
            alert(33)
        }
    }
  • 相关阅读:
    new和malloc的区别
    C++中的数据类型强制转换方法
    C++中pair和make_pair的区别
    PlantUML 图绘制类库--VSCODE插件
    Exception: HOUR_OF_DAY: 0 -> 1的问题
    Fiddler手机抓包工具如何设置过滤域名
    MySQL 正则表达式 REGEXP
    ASP.NET Web API 2 中的属性路由
    windows服务搭建(VS2019创建Windows服务不显示安装组件)
    JWT的验证(转载)
  • 原文地址:https://www.cnblogs.com/Answer1215/p/9823954.html
Copyright © 2011-2022 走看看