• 突袭HTML5之Canvas 2D入门4 直接操作像素


      前面的例子都是使用图片或者图形来绘图,这是相对高级的API,而且所有的操作和变换都是针对“网格坐标系”的。除此之外,canvas还支持直接操作每个像素(全部的,或者部分的);毋庸置疑,这些操作是针对“像素坐标系”中的像素的,这些操作完全不受变换矩阵、阴影效果、全局透明度设置、裁剪路径、组合效果的影响,因为这些所有的效果都是针对“网格坐标系”的。操作完以后再放回canvas中,可以实现一些有趣的效果。
    下面是常见的方法:
    imagedata = context.createImageData(sw, sh)
    返回指定维度的ImageData对象。
    imagedata = context.createImageData(imagedata)
    返回与指定对象相同维度的ImageData对象。
    imagedata = context.getImageData(sx, sy, sw, sh)
    返回指定起点与维度的ImageData对象。
    imagedata.width
    imagedata.height
    返回ImageData的维度值(每行/列的像素数目)。
    imagedata.data
    按照每个像素的RGBA的顺序返回一维的像素数组(按照从左向右,从上到下的顺序,从左上角的像素开始,依次把每个像素的RGBA分量放到这个数组中,所以数组的长度是像素数目的4倍),这个数组的元素全是整数,范围是0~255。
    context.putImageData(imagedata, dx, dy [, dirtyX, dirtyY, dirtyWidth, dirtyHeight ])
    把像素写回到指定的canvas区域,如果指定了dirty矩形的范围,则只有这个范围的像素会被写回。所有针对“网格坐标系”的样式操作都会被覆盖掉。

    看一个简单的例子:

    var data = c.createImageData(300,200);
    for(var x=0; x<data.width; x++) {
        for(var y=0; y<data.height; y++) {
            
            var val = 0;
            var horz = (Math.floor(x/4) % 2 == 0); //loop every 4 pixels
            var vert = (Math.floor(y/4) % 2 == 0); // loop every 4 pixels
            if( (horz && !vert) || (!horz && vert)) {
                val = 255;
            } else {
                val = 0;
            }
            
            var index = (y*data.width+x)*4;  //calculate index
            data.data[index] = val;   // red
            data.data[index+1] = val; // green
            data.data[index+2] = val; // blue
            data.data[index+3] = 255; // force alpha to 100%
        }
    }
    //set the data back
    c.putImageData(data,0,0);

    这个相当简单,就是把每个像素的颜色分量设置相应的值。

      此外,操作像素也可以直接修改图像的效果,这个道理也很简单,就是获取canvas中图像区域的像素,编辑完放回去就可以了。
    看反转图像的一个例子(FireFox中可以看到效果,目前Chrome看不到效果):

    function testPixel()
    {
     var canvas = document.getElementById('lesson01');
     var c = canvas.getContext('2d');  
     
     var img = new Image();
     
    img.onload = function() {
        //draw the image to the canvas
        c.drawImage(img,0,0);
        //get the canvas data
        var data = c.getImageData(0,0,canvas.width,canvas.height);
        //invert each pixel
        for(n=0; n<data.width*data.height; n++) {
            var index = n*4; 
            data.data[index]   = 255-data.data[index];
            data.data[index+1] = 255-data.data[index];
            data.data[index+2] = 255-data.data[index];
            //don't touch the alpha
        }
        
        //set the data back
        c.putImageData(data,0,0);
    }
     img.src = "Penguins.png";
    }


     

  • 相关阅读:
    理解二进制操作
    web前端代码重构
    Tomcat是一个Servlet容器?
    对于python命令行参数使用,你应该这么做才专业
    利用深度学习识别滑动验证码缺口位置
    机器学习笔记(十)---- KNN(K Nearst Neighbor)
    基于NB-IoT的智慧路灯监控系统(项目简介)
    【读一本书】《昇腾AI处理器架构与编程》--神经网络基础知识(2)
    高性能Web动画和渲染原理系列(4)“Compositor-Pipeline演讲PPT”学习摘要【华为云技术分享】
    华为云数据库亮相下一代数据技术发展论坛,助力“数字一带一路”
  • 原文地址:https://www.cnblogs.com/dxy1982/p/2376753.html
Copyright © 2020-2023  润新知