Automattic / node-canvas

Node canvas is a Cairo backed Canvas implementation for NodeJS.
9.98k stars 1.15k forks source link

Use standard Canvas `ctx.filter` API (blur/grayscale/saturate/contrast) #1063

Open paramaggarwal opened 6 years ago

paramaggarwal commented 6 years ago

HTML5 Canvas recently introduced support for filters like ctx.filter = "blur(5px)"; in the browser, for example to blur, saturate, grayscale and modify contrast.

Issue or Feature

API support for HTML5 Canvas ctx.filter from from MDN web docs

Steps to Reproduce

var Canvas = require('canvas');
var canvas = Canvas.createCanvas(200, 200);
var ctx = canvas.getContext('2d');
ctx.filter = "blur(5px)";
ctx.drawImage(img,0,0);

Your Environment

asturur commented 6 years ago

This api is actually much new also for browsers ( chrome 49+ )

paramaggarwal commented 6 years ago

Ah, right. Closing issue for now.

asturur commented 6 years ago

I did not mean to make you close it. Just can be expected that is not implemented in node-canvas since it became a standard non experimental api not long ago.

paramaggarwal commented 6 years ago

No, no - I previously thought that this is a bug, but actually it is a feature request. Hence closed it. 😄

zbjornson commented 6 years ago

Feature requests are valid issues :-)

ghost commented 4 years ago

Same problem. I make a canvas with nodejs and use ctx.filter = 'blur(4px)'; to blur canvas then I convert it to png. image It doesn't work !! My code: const canvas = createCanvas(900, 900) const ctx = canvas.getContext('2d') ctx.filter = 'blur(400px)'; ctx.font = '48px serif'; ctx.fillText('Hello world', 50, 100); fs.writeFileSync('layer-1.png', canvas.toBuffer());

asturur commented 4 years ago

i would like to work on this, i wonder if we have the exact specs of the filters. Would be ok to implement those with normal loops over the pixels?

zbjornson commented 4 years ago

Reopening because we still don't have this feature.

@asturur I think the full list is here: https://drafts.fxtf.org/filter-effects/#supported-filter-functions.

Would be ok to implement those with normal loops over the pixels?

It's better to use Cairo APIs if possible because Cairo and pixman use SIMD extensions. However, the Cairo cookbook recipe for Gaussian blur (https://www.cairographics.org/cookbook/blur.c/) is indeed a loop. (Skia on the other hand has quite a few filters built in, were we to switch to that.)

paramaggarwal commented 4 years ago

Oh ok, I was going through all my open issues across GitHub and closing old ones. Thanks for reopening.

asturur commented 4 years ago

I have a dumb question, since so long and i never made it just because i was worried it was too dumb.

To get a great node-canvas compatibility, what does stop someone to take the full firefox canvas implementation from the source code and make it for node?

Wouldn't it an accurate node-canvas at that point?

mifi commented 3 years ago

Hm, I found this: https://github.com/Automattic/node-canvas/blob/master/src/CanvasRenderingContext2d.cc#L615 Looks like an implementation of the filters 😮

HoseinDanesh commented 3 years ago

issue in 2017 awful Doesn't want provide this feature ? whatever its experimental or not

saberjsd commented 3 years ago

I had the same problem........

PainOchoco commented 3 years ago

Any update on that? It would be really cool!

PainOchoco commented 3 years ago

In the meantime I will use skia-canvas which supports filters, it's a great alternative.

dawidjaniga commented 2 years ago

Hi, do you plan to implement filter?

zmnv commented 2 years ago

we really need a blur filter please < 3

paramaggarwal commented 2 years ago

To support filters we will need to migrate to Skia graphics engine from the Cairo engine. Such a rewrite would effectively be like starting an entirely new project and should not be in the scope of this project (which should continue to be a great canvas API wrapper on top of Cairo engine) - hence closing this.

See discussion here: https://github.com/Automattic/node-canvas/issues/1652#issuecomment-691535373

Pomax commented 1 year ago

Another option is to implement filters "the old way" (i.e. write the filters in JS and composite to a new, same-sized pixel matrix, then replace the original with the updated one) and tell folks that while things will technically work, it will be slow. For most applications that would probably be an acceptable tradeoff: I'd much rather wait a little longer for image generation to finish if it means the result looks (near) identical between node-canvas and the browser =)