简体   繁体   中英

Javascript canvas.getImageData IE vs Chrome

I have a canvas object from which i want to get the color of a position with canvas.getImageData. When i paint a gradient on it and try to get the color from point (0,0) chrome behaves as expected and returns the color value 255,255,255 whereas IE returns 254,253,253.

I have here a plunker which shows what i mean :

http://plnkr.co/edit/BWSn2J2N2A6poaH4WR6a?p=preview

You can just execute this in IE and in Chrome and you'll see the difference. I use the IE v11 and the Chrome v40.

Maybe the error is during my creation of the canvas.

var RepaintGradient = function(gradient)
{           
    _gradientContext.fillStyle = 'rgb(255,0,0)';
    _gradientContext.fillRect(0,0,width,height);

    var gradientWTT = _gradientContext.createLinearGradient(0, 0, width, 0);
    gradientWTT.addColorStop(0, "white");
    gradientWTT.addColorStop(1, gradient);
    _gradientContext.fillStyle = gradientWTT;
    _gradientContext.fillRect(0, 0, width, height);

    var gradientBTT = _gradientContext.createLinearGradient(0, width, 0, 0);
    gradientBTT.addColorStop(0, "black");
    gradientBTT.addColorStop(1, "transparent");
    _gradientContext.fillStyle = gradientBTT;
    _gradientContext.fillRect(0, 0, width, height);
    var color = _gradientContext.getImageData(0, 0, 1, 1).data;
    alert(color[0]+' '+color[1]+' '+color[2]);
};

Is this a normal behavior and IE and Chrome have this difference or is it something that i missed during the creation of the canvas ?

This is due to rounding errors during blending and composition when sub-pixeling is used - different browsers gain different result based on their approach (IE and FireFox gives the same result, webkit browsers a different result).

It's not much we can do with the inner working, but we can adjust for sub-pixeling so it won't happen by simply translating the canvas half pixel.

Add this line to the top of the gradient function:

  _gradientContext.setTransform(1,0,0,1, 0.5,0.5); // offset 0.5 pixel

and it should work

The reason being that pixels are initially rendered from the pixel's center, meaning 0.5 of the pixel is interpolated both ways. Translating 0.5 pixel will match the center to the pixel grid.

Update (from comments):

Another approach using coordinates to calculate color value (HSL) instead of picking a pixel (this approach will also allow you to set a point in the picker based on input values):

It's normal...

Different browsers are allowed to impliment slightly different renderings of canvas gradients.

Even one image will be rendered slightly differently on each browser.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM