将画布集成到jsdom中

时间:2017-10-02 15:48:23

标签: express canvas html2canvas jsdom

通过检查jsdom的文档,似乎支持canvas。然而,唯一的解释是:

  

jsdom支持使用canvas或canvas-prebuilt包来使用canvas API扩展任何元素。为了使这项工作,您需要将canvas作为依赖项包含在项目中,作为jsdom的同行。如果jsdom可以找到canvas包,它会使用它,但是如果它不存在,那么元素将表现得像s。

这对我没有任何帮助。我通过 npm 安装了 canvas-prebuilt ,并在jsdom之前导入了canvas-prebuilt

import canvas from 'canvas-prebuilt';
import jsdom from 'jsdom';

接下来我想创建一个html片段的dom对象,然后将html插入到 html2canvas 的画布中:

const dom = new JSDOM(html);
let domcanvas = await html2canvas(dom, {
  dpi: dpi,
  useCORS: true,
  timeout: 20000
});

执行代码时会抛出错误说:

No canvas support

我认为jsdom没有找到画布。

因此我的问题是如何将canvas整合到jsdom中?

修改

因此,在深入研究JSDom代码后,我发现JSDom实际上是在找画布。我通过修改 node_modules / jsdom / lib / jsdom / utils.js 中的代码来解决这个问题,方法是添加一些控制台日志以验证是否找到了画布:

exports.Canvas = null;
["canvas", "canvas-prebuilt"].some(moduleName => {
  try {
    exports.Canvas = require(moduleName);
    if (typeof exports.Canvas !== "function") {
      console.log(moduleName+' is not a function');
      // In browserify, the require will succeed but return an empty object
      exports.Canvas = null;
    }
    console.log('Successfully found ' + moduleName);
  } catch (e) {
    console.log('Cannot find ' + moduleName);
    exports.Canvas = null;
  }
  return exports.Canvas !== null;
});

在我的情况下,输出是:

  

找不到画布

     

成功找到canvas-prebuilt

因此,我的初始问题得到了回答。 抛出的错误来自html2canvas,因为windowdocument等对象不是全局的。解决方法是使用

使其全局化
global.window   = dom.window;
global.document = dom.window.document;
global.Image    = window.Image;
global.Node     = window.Node;

然而,@ niklas提到的html2canvas和jsdom还有几个问题,因为它们超出了这个问题的范围,所以这里不再进一步讨论。

希望这个问题对某些人有用。

1 个答案:

答案 0 :(得分:1)

我复制了我的编辑,将其贴在我的问题的答案上:

因此,在深入研究JSDom代码后,我发现JSDom实际上是在找画布。我通过修改 node_modules / jsdom / lib / jsdom / utils.js 中的代码来解决这个问题,方法是添加一些控制台日志以验证是否找到了画布:

exports.Canvas = null;
["canvas", "canvas-prebuilt"].some(moduleName => {
  try {
    exports.Canvas = require(moduleName);
    if (typeof exports.Canvas !== "function") {
      console.log(moduleName+' is not a function');
      // In browserify, the require will succeed but return an empty object
      exports.Canvas = null;
    }
    console.log('Successfully found ' + moduleName);
  } catch (e) {
    console.log('Cannot find ' + moduleName);
    exports.Canvas = null;
  }
  return exports.Canvas !== null;
});

在我的情况下,输出是:

  

找不到画布

     

成功找到canvas-prebuilt

因此,我的初始问题得到了回答。 抛出的错误来自html2canvas,因为windowdocument等对象不是全局的。解决方法是使用

使其全局化
global.window   = dom.window;
global.document = dom.window.document;
global.Image    = window.Image;
global.Node     = window.Node;

然而,@ niklas提到的html2canvas和jsdom还有几个问题,因为它们超出了这个问题的范围,所以不会在这里进一步讨论。

希望这个问题对某些人有用。