画布/照片 - getImageData无效

时间:2016-05-01 18:48:17

标签: javascript html canvas html5-canvas

我正在将照片加载到画布中;我drawImage(),将getImageData()存储到变量中进行操作。我希望能够多次操作数据,例如:添加/删除各种过滤器。如何存储数据,以便每次使用putImageData()绘制图片时都会更新数据?

基本上,我认为我误解了getImageData的使用或错误地使用它。我的想法是,对图片进行的任何操作,我都可以运行getImageData并更新包含信息的变量,并使用它来“重绘”图片。

实施例: 在下面的片段中让我说我运行一个将图片变为黑白的功能。我有另一个功能,可以在单击时调整图片大小。 当我调整图片大小时,黑白滤镜会消失。保留图片信息我做错了什么?

//Read in picture
var reader = new FileReader();
                reader.onload = function leDraw(e){
                    imgObj = new Image();
                    picWidth = canvas.width/2;
                    picHeight = canvas.height/2;
                    imgObj.src = e.target.result;
                    newX = 0;
                    newY = 0;
                    ctx.drawImage(imgObj,0,0, picWidth, picHeight);
                    imageData = ctx.getImageData(newX,newY, canvas.width, canvas.height);
                    originalCopy = ctx.getImageData(newX,newY, picWidth, picHeight);
                    data = imageData.data;

function resize(val){ Resizes picture

        userPicHeight = document.getElementById("cSelect").value;
        userPicWidth = document.getElementById("cSelect").value;
        ctx.clearRect(0,0, canvas.width, canvas.height);
        ctx.drawImage(imgObj, newX, newY, userPicWidth, userPicHeight);
        window['imageData'] = ctx.getImageData(newX,newY, userPicWidth, userPicHeight);
        ctx.putImageData(imageData, newX, newY);
    };

1 个答案:

答案 0 :(得分:1)

imageData是画布像素数据的快照。在你的情况下,它是整个画布(彩色 - 而不是B& W)像素数据。

因此,当您执行.putImageData(imageData...)时,画布上会再次显示未更改的快照。

如果您要重新调整图片的B& W版本:

  1. 在使用var memCanvas = document.createElement创建的新画布上绘制彩色图像。将画布调整为图像大小。画布可以留在内存中 - 无需appendChild进入DOM。

  2. 将过滤器应用于getImageData的新画布,修改像素数据putImageData。现在你有了一个“图像画布”,你可以在以后使用它来调整大小等等。

  3. 将图像画布绘制到可见画布上:context.drawImage(memCanvas,0,0)。是的,memCanvas可以是drawImage的图像源。

  4. 要缩放图像的B& W版本,只需清除画布,使用context.scale&缩放画布。然后用drawImage(memCanvas,0,0)

  5. 绘制缩放的B& W图像

    如果您以后想重新调整B& W图像的尺寸,可以再次执行步骤#4。

    示例代码和使用灰度滤镜的演示:

    var canvas=document.getElementById("canvas");
    var ctx=canvas.getContext("2d");
    var cw=canvas.width;
    var ch=canvas.height;
    
    var img=new Image
    img.crossOrigin='anonymous';
    img.onload=start;
    img.src="https://dl.dropboxusercontent.com/u/139992952/multple/kingcard.png";
    function start(){
    
        // create a grayscale image-canvas
        var grayImg=makeFilteredImageCanvas(img,grayscaleFilter);
        
        // scale the visible canvas
        ctx.scale(1.25,1.25);
        
        // draw the grayscale imag-canvas on the canvas
        // (the result will be scaled)
        ctx.drawImage(grayImg,0,0);
    
    }
    
    function makeFilteredImageCanvas(img,filter){
        var c=document.createElement('canvas');
        var cctx=c.getContext('2d');
        iw=c.width=img.width;
        ih=c.height=img.height;
        cctx.drawImage(img,0,0);
        filter(cctx);
        return(c);
    }
    
    function grayscaleFilter(context){
        var canvas=context.canvas;
        var w=canvas.width;
        var h=canvas.height;
        var imageData=context.getImageData(0,0,w,h);
        var data=imageData.data;
        for(var i=0;i<data.length;i+=4){
              var gray=data[i]*0.33+data[i+1]*0.5+data[i+2]*0.16;
              data[i]=data[i+1]=data[i+2]=gray;
        }
        context.putImageData(imageData,0,0);
    }
    body{ background-color: ivory; }
    #canvas{border:1px solid red; margin:0 auto; }
    <h4>Grayscale image scaled up by 25%</h4>
    <canvas id="canvas" width=300 height=300></canvas>
    <h4>Original Image:</h4>
    <img src='https://dl.dropboxusercontent.com/u/139992952/multple/kingcard.png' crossOrigin='anonymous'>