fabric.js: Export single objects as PNG
This allows you to export single objects on a fabric canvas as PNG image. Works for all types of objects.
by Arjan Haverkamp
HTML
<script src="https://code.jquery.com/jquery-3.6.3.slim.min.js"></script>
<div id="canvasContainer">
<canvas id="c" width="450" height="450"></canvas>
</div><br>
<button type="button" onclick="obj2png()">obj2png</button>
CSS
#canvasContainer {
background-image: url(data:image/gif;base64,R0lGODlhCgAKAIAAAOLi4v///yH5BAAHAP8ALAAAAAAKAAoAAAIRhB2ZhxoM3GMSykqd1VltzxQAOw==);
border: 2px solid #ccc;
display: inline-block;
}
JavaScript
fabric.Object.prototype.exportPNG = function() {
function trimCanvas(canvas)
{
var ctx = canvas.getContext('2d'),
w = canvas.width,
h = canvas.height,
pix = {x:[], y:[]}, n,
imageData = ctx.getImageData(0,0,w,h),
fn = function(a,b) { return a-b };
for (var y = 0; y < h; y++) {
for (var x = 0; x < w; x++) {
if (imageData.data[((y * w + x) * 4)+3] > 0) {
pix.x.push(x);
pix.y.push(y);
}
}
}
pix.x.sort(fn);
pix.y.sort(fn);
n = pix.x.length-1;
w = pix.x[n] - pix.x[0];
h = pix.y[n] - pix.y[0];
var cut = ctx.getImageData(pix.x[0], pix.y[0], w, h);
canvas.width = w;
canvas.height = h;
ctx.putImageData(cut, 0, 0);
};
var bound = this.getBoundingRect(),
json = JSON.stringify(this),
canvas = fabric.util.createCanvasElement();
canvas.width = bound.width;
canvas.height = bound.height;
var fcanvas = new fabric.Canvas(canvas, {enableRetinaScaling:false});
fabric.util.enlivenObjects([JSON.parse(json)], function(objects) {
objects.forEach(function(o) {
o.top -= bound.top;
o.left -= bound.left;
fcanvas.add(o);
});
fcanvas.renderAll();
var canvas = fcanvas.getElement();
trimCanvas(canvas);
/*
var url = canvas.toDataURL('image/png'),
img = new Image();
img.width = canvas.width;
img.height = canvas.height;
img.src = url;
document.body.appendChild(img);
*/
canvas.toBlob(function(blob) {
$('<a>', {href:URL.createObjectURL(blob), download:'element.png'})[0].click();
}, 'image/png');
});
};
function obj2png() {
var obj = fcanvas.getActiveObject();
if (!obj) { return; }
obj.exportPNG();
}
// Create fabric canvas
var fcanvas = new fabric.Canvas('c');
// Add some objects
fcanvas.add(new fabric.Circle({
radius: 100, fill: 'green', left: 10, top: 10
}));
fcanvas.add(new fabric.Triangle({
width: 130, height: 130, fill: 'blue', left: 220, top: 250, angle: -30
}));