javascript - 将 Emscripten webGL Canvas 保存为 JS 中的图像

标签 javascript canvas webgl emscripten

我有一个 Emscripten 驱动的 webGL Canvas ,我需要将其保存为来自 Javascript 处理程序的图像。假设有一个简单的 JS“保存”按钮。

<script type="text/javascript">
var Exporter = {
    preRun: [],
    postRun: [],
    save: function() {
    var c=Module.canvas;
    var d=c.toDataURL("image/png");
    var w=window.open('about:blank','image from canvas');
    w.document.write("<img src='"+d+"' alt='from canvas'/>");
    }
};
</script>
<input type="button" value="Save" onclick="Exporter.save()" />

默认情况下,webGL 上下文将 preserveDrawingBuffer 设置为 false,因此生成的图像是空白的。

为了让图像显示渲染的 webGL 场景,我需要添加 preserveDrawingBuffer: true到我编译的 Empscripten 代码中的 getContext 调用中传递的属性。我可以通过手动编辑编译的 empscripten js 代码来做到这一点;然后生成的图像是正确的,但我想避免这种黑客攻击 - 我必须在每次重新编译后都这样做。

有没有更简单、更干净的方法来添加 preserveDrawingBufferwebGLContextAttributes从外面?即作为 emcc 的编译选项,C 代码中的一些 SDL 参数还是来自托管页面中的 Javascript?

更新
解决方法见下文;我遇到的无关问题是保存的图像的位深度较低,抗锯齿线看起来很糟糕。使用 c.toDataURL( "image/jpeg" )解决了这个问题。

最佳答案

嗯,首先,所有的 emscripten 和它的所有库都是开源的,所以你可以去改变它们。

特别复制library_gl.js到您的项目文件夹,然后删除 -lGL并添加 --js-library library_gl.js到你的构建脚本,然后你可以破解你的本地library_gl.js做任何你想做的事。

否则我根本不了解 SDL,但您可以在调用 emscripten 代码之前自己获取上下文。如果您调用 getContext,则 Canvas 只能有一个上下文。再次对于相同类型的上下文,您将获得相同的上下文。换句话说,如果您的 JavaScript 首先创建上下文,则 emscripten 代码将获得相同的上下文

所以这应该有效

 theCanvasElement.getContext("webgl", {preserveDrawingBuffer: true});

 ... now execute emscripten and have it use `theCanvasElement`

如果你甚至不能这样做,你可以覆盖 getContext
HTMLCanvasElement.prototype.getContext = (function(oldGetContextFn) {
  return function(type, attrs) {
    attrs = attrs || {};
    if (type === "webgl") {
      attrs.preserveDrawingBuffer = true;
    }
    return oldGetContextFn.call(this, type, attrs);
  };
}(HTMLCanvasElement.prototype.getContext));

关于javascript - 将 Emscripten webGL Canvas 保存为 JS 中的图像,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43976975/

相关文章:

javascript - 使用 pre3d 的嵌套长方体

javascript - 无论我放入其中的数据如何,纹理都是黑色的

structure - 从 WebGl 中的代码访问顶点着色器中的结构

javascript - 如何使我的所有路由都具有 https 并强制从 http 到 https?

javascript - 使用正则表达式 replace() 方法一步删除定界符并将第一个字母大写

javascript - 添加本地存储以保存 Canvas 绘图

html - 安全错误 : DOM Exception 18 ONLY IN Safari

javascript - 如何: callback function that takes ajax get array as a parameter

javascript - 日历问题和识别空闲槽

javascript - Python toDataUrl 等效项