Glow Effect on HTML Canvas, Potentially Using Convolute Kernel / Matrix
Asked Answered
R

1

6

I am drawing a PNG image to an HTML canvas and I have implemented a filter system to allow convolute filters to be executed against the image data before it is blitted to the canvas.

Does anyone have an idea how to create a glow effect using either a convolute kernel / matrix (I'm not sure what the terminology is but I'm talking about these: http://www.html5rocks.com/en/tutorials/canvas/imagefilters/) or by other means such as using the globalCompositeOperation (https://developer.mozilla.org/samples/canvas-tutorial/6_1_canvas_composite.html)?

I am aware that you can start with a low opacity and a scaled image then increase opacity while scaling the image down a bit. This works to create a sort-of glow effect but only around the edge of an image.

In an ideal world it would be great to be able to designate areas of the image that have glow using a secondary glow texture. Any ideas on either scenario? :)

Rugby answered 13/11, 2012 at 10:35 Comment(1)
Do you have a visual example, a before/after example, of what such an effect would look like?Peppard
P
23

Hope the following is along the lines of what you were looking to do, I think it turned out pretty well. So I used the filter library code from the article, and just created a new glow filter for the library, since his code was done pretty well to begin with. Here is a Live Demo showing the glow effect in action.

This is the filter code that you need to add to the library

Filters.glow = function(pixels, passes, image, glowPasses){
        for(var i=0; i < passes; i++){  
            pixels = Filters.convolute(pixels, 
                [1/9,  1/9,  1/9,
                1/9,  1/9,  1/9,
                1/9,  1/9,  1/9 ]);
        }
        
        var tempCanvas = document.createElement("canvas"),
            glowCanvas = document.createElement("canvas"),
            tCtx = tempCanvas.getContext("2d"),
            gCtx = glowCanvas.getContext("2d");
        
        tempCanvas.width = glowCanvas.width = pixels.width;
        tempCanvas.height = tempCanvas.height = pixels.height;
        
        tCtx.putImageData(pixels, 0, 0);
        gCtx.drawImage(image, 0, 0);

        gCtx.globalCompositeOperation = "lighter";

        for(i = 0; i < glowPasses; i++){
            gCtx.drawImage(tempCanvas,0,0);
        }
        
        return Filters.getPixels(glowCanvas);
    }

And this is how you would use the above filter.

var glowImage = document.images[1],
    glowMask = document.images[0],
    c = document.getElementById("canvas"),
    ctx = c.getContext("2d");

window.onload = function() {
    var pData = Filters.filterImage(Filters.glow, glowImage, 5, glowMask, 2);
    c.width = pData.width;
    c.height = pData.height;
    ctx.putImageData(pData, 0, 0);
}

You need to provide it with 2 images. The first is the image you want the glow to appear on, and the second is the actual glow mask that is applied to the image. You can then specify how many blur passes to perform, which makes the glow more prominent, and how many glow passes to perform, which add the glow to the image. I use the lighter global composition for the canvas which alpha blends it.

This article is a pretty great resource on creating a glow effect, its also where I got the graphics in order to test my results against theirs.

Probationer answered 16/11, 2012 at 20:16 Comment(3)
That is EXACTLY, like PRECISELY, laser-perfectly targeted what I was looking for. I think that is probably the first answer I have ever had on SO where the person answering actually read my question fully. Serious thanks. I cannot award the bounty for 11 hours apparently but will do once I'm allowed to. Cheers buddy.Rugby
@RobEvans awesome glad it helped you :) it was pretty fun to work on I love the way glow effects look, and you did most of the work finding that great library for canvas filters.Probationer
I'm giving +1 just because Rob was so happy with the outcome of this question. Everybody wins.Underarm

© 2022 - 2024 — McMap. All rights reserved.