无法使用画布将图像转换为其他格式

时间:2018-06-20 16:11:17

标签: javascript node.js canvas

问题

我正在尝试使用画布将图像转换为另一种格式,然后(使用Node.js)将图像保存到磁盘,我不确定为什么它不起作用。

我真的不需要画布本身,我只是用它来转换图像。我是否应该将画布附加到HTML元素中以使其起作用?

代码

convertImage () {
    var image = new Image(); 
    image.src = 'C:/test/test.png';

    // Converts image to canvas
    var canvas = document.createElement("canvas");
    canvas.width = image.width;
    canvas.height = image.height;
    // Do I even need to draw it?
    canvas.getContext("2d").drawImage(image, 0, 0);

    // Converts canvas to a data url
    var imageOut = new Image();
    let base64data = canvas.toDataURL("image/png");
    imageOut.src = base64data;

    var data = base64data.replace(/^data:image\/\w+;base64,/, "");
    var buffer = new Buffer(data, 'base64');
    fs.writeFile('C:/test/converted.jpg', buffer);
}

2 个答案:

答案 0 :(得分:2)

将canvas与nodejs一起使用可能不是最好的方法,因为它依赖于浏览器。即使铬应该能够处理它。过去,我依靠jimp库

  

完全用JavaScript编写的Node图像处理库,原生依赖项为零

https://github.com/oliver-moran/jimp

这是它的外观(未经测试)

var Jimp = require("jimp");

convertImage (img, imgName) {
  Jimp.read(img, function (err, myImage) {
      if (err) throw err;
      myImage.quality(60)  // set JPEG quality
        .write(imgName);   // save
  });
}

convertImage('C:/test/test.png', 'C:/test/converted.jpg')

答案 1 :(得分:1)

您的代码有两个问题:

  1. 图像在浏览器中异步加载,因此您需要等待它们加载后再处理它们(即使使用Electron时也是如此)。在您的情况下,当您尝试在画布上渲染图像时尚未加载该图像,那么结果是一个空的.png

  2. writeFile在Node中也是异步的,并且不使用回调。您可以使用fs.writeFileSync

使用jimp的建议答案效果很好,可以将其发布给您和其他人,他们想知道如何在不提取库的情况下执行相同的操作。

convertImage () {
    var image = new Image(); 
    image.onload = function() {
         // Converts image to canvas
         var canvas = document.createElement("canvas");
         canvas.width = image.width;
         canvas.height = image.height;
         // Yes, you need to draw the canvas before creating an image from it
         canvas.getContext("2d").drawImage(image, 0, 0);

         // Converts canvas to a data url
         var imageOut = new Image();
         let base64data = canvas.toDataURL("image/png");
         imageOut.src = base64data;

         var data = base64data.replace(/^data:image\/\w+;base64,/, "");
         var buffer = new Buffer(data, 'base64');
         // use writeFileSync instead
         fs.writeFileSync('C:/test/converted.jpg', buffer);
    }
    image.src = 'C:/test/test.png';
}