Version
fabricjs 2.0.0-beta.6 node-canvas 1.6.6 nodejs 6.11.0
Steps to reproduce
fabricjs on nodejs, 1.7.16 works fine with image filter, when update to 2.0.0, can't get it work
var jsonStr = '{"objects":[{"type":"circle","originX":"left","originY":"top","left":119,"top":64,"width":100,"height":100,"fill":"#6dcdd0","stroke":null,"strokeWidth":1,"strokeDashArray":null,"strokeLineCap":"butt","strokeLineJoin":"miter","strokeMiterLimit":10,"scaleX":1,"scaleY":1,"angle":0,"flipX":false,"flipY":false,"opacity":0.8,"shadow":null,"visible":true,"clipTo":null,"backgroundColor":"","fillRule":"nonzero","globalCompositeOperation":"source-over","transformMatrix":null,"skewX":0,"skewY":0,"radius":50,"startAngle":0,"endAngle":6.283185307179586}]}';
var canvas = fabric.createCanvasForNode(600, 600);
canvas.loadFromJSON(jsonStr, function() {
canvas.renderAll();
var dataUrl = canvas.toDataURL();
fabric.Image.fromURL(dataUrl, function(img) {
var filter = new fabric.Image.filters.Sepia();
img.filters.push(filter);
img.applyFilters();
canvas.add(img);
var dataUrl = canvas.toDataURL();
});
Expected Behavior
canvas.toDataURL()
returns dataurl
Actual Behavior
"TypeError: Image or Canvas expected", " at TypeError (native)", " at klass._render (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:18699:28)", " at klass.drawObject (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:12527:12)", " at klass.render (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:12475:14)", " at klass._renderObjects (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:6949:34)", " at klass.renderCanvas (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:6927:12)", " at klass.renderAll (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:8862:12)", " at klass.__toDataURLWithMultiplier (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:11226:14)", " at klass.toDataURL (/data/web/websites/adamlv/node_workspace/monet/node_modules/fabric/dist/fabric.js:11198:19)", " at Command.callback (/data/web/websites/adamlv/node_workspace/monet/api/canvas_converter.js:249:58)", " at normal_reply (/data/web/websites/adamlv/node_workspace/monet/node_modules/redis/index.js:721:21)", " at RedisClient.return_reply (/data/web/websites/adamlv/node_workspace/monet/node_modules/redis/index.js:819:9)", " at JavascriptRedisParser.returnReply (/data/web/websites/adamlv/node_workspace/monet/node_modules/redis/index.js:192:18)", " at JavascriptRedisParser.execute (/data/web/websites/adamlv/node_workspace/monet/node_modules/redis-parser/lib/parser.js:553:10)", " at Socket. (/data/web/websites/adamlv/node_workspace/monet/node_modules/redis/index.js:274:27)", " at emitOne (events.js:96:13)"
While this is not a solving answer, it explains you what is going on. A solution is being worked on.
The JSDOM package is taking care of creating canvases with node-canvas integration for fabricjs.
writing
document.createElement('canvas')
should provide a fake canvas element in node, backed and wrapped with node-canvas.Somehow this is not working correctly in fabric where one of the canvases is not wrapped in JSDOM. When drawImage is called from a context of a JSDOM canvas, the received first argument is unwrapped and the node-canvas is used instead of the html shimmer. It looks like this is not working as of now since the
createCanvasForNode
function is not exposing the correct context/canvas.If you do not use it and just do: var fabric = require('fabric').fabric;
you will notice the script is working without the nodeCanvas but using plain browser code. Filtering is still broken.