首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何从WebAssembly执行Kotlin WebAssembly函数?

如何从WebAssembly执行Kotlin WebAssembly函数?
EN

Stack Overflow用户
提问于 2019-01-10 23:05:49
回答 3查看 1.5K关注 0票数 7

我的目标是编写一个Kotlin库,将它编译成WebAssembly,然后从JS调用它的函数。由于几个小时,我试着得到一个简单的你好世界的工作。有关此主题的文档要么不存在,要么隐藏得很好。

这是我的kotlin档案:

代码语言:javascript
复制
@Used
public fun hello() {
    println("Hello world!")
}

fun main(args: Array<String>) {
    println("main() function executed!")
}

当我将它编译到WebAssembly时,我会得到一个hello.wasm和hello.wasm.js文件。

首先,我尝试使用这样的方法来执行函数:

代码语言:javascript
复制
WebAssembly.instantiateStreaming(fetch('hello.wasm'), importObject)
    .then(obj => obj.instance.exports.hello());

然后,我了解到我需要在importObject参数中传递来自我的importObject文件的导入。因此,我想我需要使用hello.wasm.js文件正确地初始化我的wasm程序。

当我像下面这样加载我的wasm时,我不会收到任何错误,并且执行main()函数。

代码语言:javascript
复制
<script wasm="hello.wasm" src="hello.wasm.js"></script>

但是如何从执行函数呢?我发现的唯一kotlin示例不是调用特定的函数,而是从main()函数中呈现某些内容。

此外,任何与相关文件的链接都是非常感谢的。

更新:我成功地执行了函数,但我不认为这是正确的方法:

代码语言:javascript
复制
<script wasm="hello.wasm" src="hello.wasm.js"></script>
<script>
WebAssembly.instantiateStreaming(fetch('hello.wasm'), konan_dependencies)
        .then(obj => obj.instance.exports['kfun:hello$$ValueType']());
</script>

问题是,如果我这样做,我的wasm文件会被抓取两次。

只加载没有wasm属性的hello.wasm.js文件将得到以下错误:

代码语言:javascript
复制
Uncaught Error: Could not find the wasm attribute pointing to the WebAssembly binary.
    at Object.konan.moduleEntry (stats.wasm.js:433)
    at stats.wasm.js:532
EN

回答 3

Stack Overflow用户

发布于 2019-03-18 09:32:44

我最近对此进行了一些研究,据我所知,到目前为止,您的使用程序还没有得到真正的支持。您正在寻找的基本上是一个库,但是如果您查看Kotlin/Native的文档,它会声明:

支持以下二进制类型(请注意,并非所有的二进制类型都适用于所有本机平台): ..。 sharedLib -一个共享的本机库-除wasm32之外的所有本机目标 staticLib -静态本机库-除wasm32之外的所有本机目标

根据我的理解,困难在于使用Javascript和WebAssembly之间的数据传递,因为它只支持通过线性内存的it或相当迂回的方式。

票数 1
EN

Stack Overflow用户

发布于 2020-07-03 23:29:45

目前,我喜欢在Kotlin WASM项目上工作,(对我的研究人员来说很好),在我们的团队中没有经验。对不起,我的脑子里还有同样的问号,但已经走得很远了。

在我的例子中,我找到了很多wasm的例子,但是我觉得我无法使用它们,因为在Kotlin,事情是不同的.实际上,事实并非如此,事情只是隐藏在构建过程中,在我们的例子中,这既是一种祝福也是一种诅咒。没有多库,但是科特林为我们做了些事情!

对我来说,填补这一信息空白的最佳策略是更深入地查看生成的*wasm.js文件。它看起来可能很吓人,而且是JavaScript,但实际上很容易了解Kotlin实际上能为您做些什么。最好的方法是:如果你看了Api参考资料(https://developer.mozilla.org/en-US/docs/WebAssembly),或者你只是看了一篇教程,却无法应用你所见过的东西,你很可能会在这里找到这些代码!

谁读过这篇文章并想尝试一下:您应该准备一个构建设置,允许您将内容附加到生成的*.wasm.js文件中。在我的设置中,这方面的重要部分是:

代码语言:javascript
复制
val jsinterface by tasks.creating(Exec::class) {
    val kotlincExecutable = "${project.properties["konanHome"]}/bin/kotlinc"

    inputs.property("kotlincExecutable", kotlincExecutable)
    outputs.file(jsInterfaceKlibFileName)

    val ktFile = file(workingDir).resolve("src/wasm32Main/kotlin/js_interface/imported_js_funcs.kt")
    val jsStubFile = file(workingDir).resolve("src/wasm32Main/js/stub.js")

    executable(kotlincExecutable)
    args(
        "-include-binary", jsStubFile,
        "-produce", "library",
        "-o", jsInterfaceKlibFileName,
        "-target", "wasm32",
        ktFile
    )
}

val jsinterop by tasks.creating(Exec::class) {
    dependsOn(jsinterface) //inserts customized js functions on xxx.wasm.js
    //jsinterop -pkg kotlinx.interop.wasm.dom  -o build/klib/kotlinx.interop.wasm.dom-jsinterop.klib -target wasm32
    workingDir("./")
    executable("${project.properties["konanHome"]}/bin/jsinterop")
    args("-pkg", "kotlinx.interop.wasm.dom", "-o", jsinteropKlibFileName.toString(), "-target", "wasm32")
}

// generate jsinterop before native compile
tasks.withType(org.jetbrains.kotlin.gradle.tasks.AbstractKotlinNativeCompile::class).all {
    dependsOn(jsinterop)
}

对这个话题有多少兴趣?

票数 0
EN

Stack Overflow用户

发布于 2019-01-11 06:11:59

据我所知,您需要将函数导出到一个变量中,以便继续使用它,或者留在流的实例中。

所以我觉得应该是这样的

代码语言:javascript
复制
let helloFunc;

WebAssembly.instantiateStreaming(fetch('hello.wasm'), importObject)
.then(({instance}) => {
helloFunc = instance.exports.hello;
});

在此之后,您只需将变量作为函数使用,然后按如下方式调用:

代码语言:javascript
复制
helloFunc();

否则,如果不需要导出函数以供以后使用,只需在实例中使用它,如下所示:

代码语言:javascript
复制
WebAssembly.instantiateStreaming(fetch('hello.wasm'), importObject)
.then(({instance}) => {
instance.exports.hello();
});

如果您不想像我所用的那样使用对象解构,您可以继续使用obj.instance的正常语法。

票数 -1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/54138204

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档