一次从脚本读取大用户提供的文件,一次读取块

问题描述 投票:0回答:1

我正在寻找一个API,该API可让我一次读取通过(或允许从浏览器访问用户文件的任何其他方法)块提供的文件。我正在读取大文件,所以我不想将整个文件加载到内存中。

我的用例是,我正在使用用emcc编译的ffmpeg库,因此我不会用它来处理多媒体文件。我可以实现自己的AVIOContext,但要做到这一点,我需要等效于C函数fread和fseek。

[我当时正在查看具有WORKERFS文件系统类型的FS API,但是我不清楚我是否可以使用来自DOM的File对象从辅助线程中安装它。

file-io emscripten webassembly html5-filesystem
1个回答
0
投票

我能够从工作线程使用WORKERFS挂载文件。

最小示例:

main.html:

<html>
<head>
<script>
    const worker = new Worker("worker.js");
    function onClick() {
        const f = document.getElementById("in-file").files[0];
        worker.postMessage([ f ]);
    }
</script>
</head>
<body>
    <input type="file" id="in-file" />
    <input type="button" onClick="onClick()" value="ok" />
</body>
</html>

worker.js

onmessage = function(e) {
    const f = e.data[0];

    FS.mkdir('/work');
    FS.mount(WORKERFS, { files: [f] }, '/work');

    console.log(Module.read_file('/work/' + f.name));
}

self.importScripts('hello.js');

hello.js使用以下命令编译hello.cpp(emcc --bind -lworkerfs.js -o hello.js hello.cpp -s WASM=1):

#include <cstdio>
#include <string>
#include <iostream>
#include <fstream>
#include <emscripten/bind.h>
using namespace emscripten;

std::string read_file(const std::string &fn)
{
    std::ifstream f(fn);
    std::string line;
    std::getline(f, line);
    return line;
}

EMSCRIPTEN_BINDINGS(hello) {
    function("read_file", &read_file);
}
© www.soinside.com 2019 - 2024. All rights reserved.