使用canvas进行图像编辑的实例

前面的话

本文将分为几个小功能的形式来详细介绍canvas图像编辑

缩放

下面是一张分析图,假设默认情况下,图片和canvas宽高相同。图片的缩放(scale)范围为0.5到3,缩放时改变的是图片的大小和图片的坐标位置

W(宽) = canvas.width * scale
H(高) = canvas.height * scale
x坐标 = (W - canvas.width)/2;
y坐标 = (H - canvas.height)/2;

因此,代码如下

<canvas id="drawing" >
  <p>The canvas element is not supported!</p>
</canvas>
<br>
<input id="scale-range" min="0.5" max="1.5" step="0.01" type="range" >
<script>
var drawing = document.getElementById('drawing');
if(drawing.getContext){
 var context = drawing.getContext('2d');
 var slider = document.getElementById('scale-range');
 var W = 400;
 var H = 290;
 drawing.width = W;
 drawing.height = H;
 var image = new Image();
 image.src="http://sandbox.runjs.cn/uploads/rs/26/ddzmgynp/chunfen.jpg";
 image.onload = function(){
  drawImgByScale(slider.value);
  slider.onmousemove = function(){
   drawImgByScale(slider.value);
  }
 }
 function drawImgByScale(scale){
  var imgW = W * scale;
  var imgH = H * scale;
  var dx =(W - imgW)/2;
  var dy =(H - imgH)/2;
  context.clearRect(0,0,W,H);
  context.drawImage(image,dx,dy,imgW,imgH);
 }
}
</script>

水印

利用canvas可以实现向图片添加水印的功能,先通过file控件的reader选择图片,然后使用canvas添加图片及水印,并且使用toDataURL()和a标签实现添加水印后的图片的下载功能

<canvas id="drawing" >
  <p>The canvas element is not supported!</p>
</canvas>
<div>
 <span>
  <input type="file" id="addImgHelper" >
  <button id="addImg">选择图片</button>
 </span>
 <span>
  <button id="addWaterMark" disabled>添加水印</button>
  <span>水印文字为</span>
  <input id="waterMarkWords" type="text" value="小火柴的蓝色理想">
 </span>
 <span>
  <button id="downloadImg" disabled>下载图片</button>
  <a id="downloadImgHelper" href="#" rel="external nofollow" download="带水印图片" ></a>
 </span>
</div>
<script>
if(drawing.getContext){
 var cxt = drawing.getContext('2d');
 var W,H;
 addImg.onclick = function(){
  addImgHelper.click();
 }
 addImgHelper.onchange = function(){
  addWaterMark.disabled = true;
  downloadImg.disabled = true;
  var file = addImgHelper.files[0];
  if(file && /image/.test(file.type)){
   var reader = new FileReader();
   reader.readAsDataURL(file);
   reader.onload = function(){
    var img = new Image();
    img.src= reader.result;
    img.onload = function(){
     addWaterMark.disabled = false;
     drawing.width = W = img.width;
     drawing.height = H = img.height;
     cxt.drawImage(img,0,0);
     addWaterMark.onclick = function(){
       downloadImg.disabled = false;
       cxt.clearRect(0,0,W,H);
       cxt.drawImage(img,0,0);
       var str = waterMarkWords.value;
       cxt.font = "bold 50px Arial";
       cxt.lineWidth = '1';
       cxt.fillStyle = 'rgba(255,255,255,0.5)';
       cxt.textBaseline = "bottom";
       cxt.textAlign = 'end';
       cxt.fillText(str,W-10,H-10,W/2);
       downloadImg.onclick = function(){
        downloadImgHelper.href = drawing.toDataURL('image/png');
        downloadImgHelper.click();
       }
     }
    }
   }
  }
 }
}
</script>

放大镜

下面来实现一个放大镜的效果,鼠标按下并移动时,显示当前图片区域的放大效果,抬起后效果消失。放大镜效果主要使用离屏canvas的技术,离屏canvas放置的是图片的放大版,而普通canvas则放置图片的正常版

<canvas id="drawing" >
  <p>The canvas element is not supported!</p>
</canvas>
<canvas id="drawingOff" >
  <p>The canvas element is not supported!</p>
</canvas>
<script>
if(drawing.getContext){
 var cxt = drawing.getContext('2d');
 var cxtOff = drawingOff.getContext('2d');
 var W,H;
 var scale = 1.5;
 var img = new Image();
 img.src="http://sandbox.runjs.cn/uploads/rs/26/ddzmgynp/chunfen.jpg";
 img.onload = function(){
  W = img.width;
  H = img.height;
  drawing.width = W/scale;
  drawing.height = H/scale;
  drawingOff.width = W;
  drawingOff.height = H;
  cxt.drawImage(img,0,0,W/scale,H/scale);
  cxtOff.drawImage(img,0,0);
  drawing.onmousedown = function(e){
   e = e || event;
   var x0 = this.offsetLeft;
   var y0 = this.offsetTop;
   drawMagnifier(e);
   drawing.onmousemove = function(e){
    drawMagnifier(e);
   }
   document.onmouseup = function(e){
    cxt.clearRect(0,0,W/scale,H/scale);
    cxt.drawImage(img,0,0,W/scale,H/scale);
    drawing.onmousemove = null;
   }
   function drawMagnifier(e){
    cxt.clearRect(0,0,W/scale,H/scale);
    cxt.drawImage(img,0,0,W/scale,H/scale);
    var x = (e.clientX-x0);
    var y = (e.clientY-y0);
    var r = 40;
    var dx = x - r;
    var dy = y - r;
    var sx = x*scale - r;
    var sy = y*scale - r;
    cxt.save();
    cxt.beginPath();
    cxt.arc(x,y,r,0,Math.PI*2);
    cxt.lineWidth = 4;
    cxt.strokeStyle = '#069';
    cxt.stroke();
    cxt.clip();
    cxt.drawImage(drawingOff,sx,sy,2*r,2*r,dx,dy,2*r,2*r);
    cxt.restore();
   }
  }
 }
}
</script>

滤镜

下面利用canvas的getImageData()方法,获取原始图像数据,通过对图像数据进行修改,然后输出修改后的图像数据

<canvas id="drawing1" >
  <p>The canvas element is not supported!</p>
</canvas>
<canvas id="drawing2" >
  <p>The canvas element is not supported!</p>
</canvas>
<br>
<button id="noGreen">无绿色</button>
<button id="noBlue">无蓝色</button>
<button id="toGrey">灰度</button>
<button id="toBlackWhite">黑白</button>
<button id="reverse">反色</button>
<script>
if(drawing1.getContext){
 var cxt1 = drawing1.getContext('2d');
 var cxt2 = drawing2.getContext('2d');
 var img = new Image();
 img.src="chunfen.jpg";
 img.onload = function(){
  cxt1.drawImage(img,0,0);
  function filter(fn){
   var imageData = cxt1.getImageData(0,0,img.width,img.height);
   cxt2.clearRect(0,0,drawing2.width,drawing2.height);
   var data = imageData.data;
   for(var i = 0, len = data.length; i < len; i+=4){
    fn(data,i)
   }
   imageData.data = data;
   cxt2.putImageData(imageData,0,0);
  }
  function fnNoGreen(data,i){
   data[i+1] = 0;
  }
  function fnNoBlue(data,i){
   data[i+2] = 0;
  }
  function fnReverse(data,i){
   var red = data[i];
   var green = data[i+1];
   var blue = data[i+2];
   var alpha = data[i+3];
   data[i] = 255 - red;
   data[i+1] = 255 - green;
   data[i+2] = 255 - blue;
  }
  function fnToGrey(data,i){
   var red = data[i];
   var green = data[i+1];
   var blue = data[i+2];
   var alpha = data[i+3];
   var average = Math.floor((red+green+blue)/3);
   data[i] = data[i+1] = data[i+2] = average;
  }
  function fnToBlackWhite(data,i){
   var red = data[i];
   var green = data[i+1];
   var blue = data[i+2];
   var alpha = data[i+3];
   var average = Math.floor((red+green+blue)/3);
   if(average > 255/2){
    var result = 255;
   }else{
    var result = 0;
   }
   data[i] = data[i+1] = data[i+2] = result;
  }
  toGrey.onclick = function(){
   filter(fnToGrey);
  }
  noGreen.onclick = function(){
   filter(fnNoGreen);
  }
  noBlue.onclick = function(){
   filter(fnNoBlue);
  }
  toBlackWhite.onclick = function(){
   filter(fnToBlackWhite);
  }
  reverse.onclick = function(){
   filter(fnReverse);
  }
 }
}
</script>

马赛克效果

【普通模糊效果】

普通模糊效果不仅需要使用当前像素点,还需要使用周围的像素点,并把这些像素点都赋予平均值

function fnToBlur(n){
   cxt2.clearRect(0,0,drawing2.width,drawing2.height);
   var imageData = cxt1.getImageData(0,0,drawing2.width,drawing2.height);
   var tempImageData = imageData;
   var data = imageData.data;
   var tempData = tempImageData.data;
   var blurR = n;
   var totalnum = (2*blurR + 1)*(2*blurR + 1);
   for(var i = blurR; i < drawing2.height - blurR; i++){
    for(var j = blurR; j < drawing2.width - blurR; j++){
     var totalr = 0, totalg = 0, totalb = 0;
     for(var dx = -blurR; dx <= blurR; dx++){
      for(var dy = -blurR; dy <= blurR; dy++){
       var x = i + dx;
       var y = j + dy;
       var p = x*drawing2.width + y;
       totalr += tempData[p*4+0];
       totalg += tempData[p*4+1];
       totalb += tempData[p*4+2];
      }
     }
     var p = i*drawing2.width + j;
     data[p*4+0] = totalr / totalnum;
     data[p*4+1] = totalg / totalnum;
     data[p*4+2] = totalb / totalnum;
    }
   }
   imageData.data = data;
   cxt2.putImageData(imageData,0,0);
  }

【马赛克效果】

马赛克效果则是把一块区域的值,全部都赋予平均值

function fnToMosaic(n){
   cxt2.clearRect(0,0,drawing2.width,drawing2.height);
   var imageData = cxt1.getImageData(0,0,drawing2.width,drawing2.height);
   var tempImageData = imageData;
   var data = imageData.data;
   var tempData = tempImageData.data;
   var size = n;
   var totalnum = size*size;
   for(var i = 0; i < drawing2.height; i+=size){
    for(var j = 0; j < drawing2.width; j+=size){
     var totalr = 0, totalg = 0, totalb = 0;
     for(var dx = 0; dx < size; dx++){
      for(var dy = 0; dy < size; dy++){
       var x = i + dx;
       var y = j + dy;
       var p = x*drawing2.width + y;
       totalr += tempData[p*4+0];
       totalg += tempData[p*4+1];
       totalb += tempData[p*4+2];
      }
     }
     var p = i*drawing2.width + j;
     var resr = totalr / totalnum;
     var resg = totalg / totalnum;
     var resb = totalb / totalnum;
     for(var dx = 0; dx < size; dx++){
      for(var dy = 0; dy < size; dy++){
       var x = i + dx;
       var y = j + dy;
       var p = x*drawing2.width + y;
       data[p*4+0]= resr;
       data[p*4+1]= resg;
       data[p*4+2]= resb;
      }
     }
    }
   }
   imageData.data = data;
   cxt2.putImageData(imageData,0,0);
  }

下面是一个实例

<canvas id="drawing1" >
  <p>The canvas element is not supported!</p>
</canvas>
<canvas id="drawing2" >
  <p>The canvas element is not supported!</p>
</canvas>
<br>
<button id="toLightBlur">轻度模糊</button>
<button id="toHeavyBlur">重度模糊</button>
<button id="toLightMosaic">轻度马赛克</button>
<button id="toHeavyMosaic">重度马赛克</button>
<script>
if(drawing1.getContext){
 var cxt1 = drawing1.getContext('2d');
 var cxt2 = drawing2.getContext('2d');
 var img = new Image();
 img.src="chunfen.jpg";
 img.onload = function(){
  cxt1.drawImage(img,0,0);
  toLightBlur.onclick = function(){
   fnToBlur(1);
  }
  toHeavyBlur.onclick = function(){
   fnToBlur(3);
  }
  toLightMosaic.onclick = function(){
   fnToMosaic(4);
  }
  toHeavyMosaic.onclick = function(){
   fnToMosaic(9);
  }
  function fnToBlur(n){
   cxt2.clearRect(0,0,drawing2.width,drawing2.height);
   var imageData = cxt1.getImageData(0,0,drawing2.width,drawing2.height);
   var tempImageData = imageData;
   var data = imageData.data;
   var tempData = tempImageData.data;
   var blurR = n;
   var totalnum = (2*blurR + 1)*(2*blurR + 1);
   for(var i = blurR; i < drawing2.height - blurR; i++){
    for(var j = blurR; j < drawing2.width - blurR; j++){
     var totalr = 0, totalg = 0, totalb = 0;
     for(var dx = -blurR; dx <= blurR; dx++){
      for(var dy = -blurR; dy <= blurR; dy++){
       var x = i + dx;
       var y = j + dy;
       var p = x*drawing2.width + y;
       totalr += tempData[p*4+0];
       totalg += tempData[p*4+1];
       totalb += tempData[p*4+2];
      }
     }
     var p = i*drawing2.width + j;
     data[p*4+0] = totalr / totalnum;
     data[p*4+1] = totalg / totalnum;
     data[p*4+2] = totalb / totalnum;
    }
   }
   imageData.data = data;
   cxt2.putImageData(imageData,0,0);
  }
  function fnToMosaic(n){
   cxt2.clearRect(0,0,drawing2.width,drawing2.height);
   var imageData = cxt1.getImageData(0,0,drawing2.width,drawing2.height);
   var tempImageData = imageData;
   var data = imageData.data;
   var tempData = tempImageData.data;
   var size = n;
   var totalnum = size*size;
   for(var i = 0; i < drawing2.height; i+=size){
    for(var j = 0; j < drawing2.width; j+=size){
     var totalr = 0, totalg = 0, totalb = 0;
     for(var dx = 0; dx < size; dx++){
      for(var dy = 0; dy < size; dy++){
       var x = i + dx;
       var y = j + dy;
       var p = x*drawing2.width + y;
       totalr += tempData[p*4+0];
       totalg += tempData[p*4+1];
       totalb += tempData[p*4+2];
      }
     }
     var p = i*drawing2.width + j;
     var resr = totalr / totalnum;
     var resg = totalg / totalnum;
     var resb = totalb / totalnum;
     for(var dx = 0; dx < size; dx++){
      for(var dy = 0; dy < size; dy++){
       var x = i + dx;
       var y = j + dy;
       var p = x*drawing2.width + y;
       data[p*4+0]= resr;
       data[p*4+1]= resg;
       data[p*4+2]= resb;
      }
     }
    }
   }
   imageData.data = data;
   cxt2.putImageData(imageData,0,0);
  }
 }
}
</script>

以上这篇使用canvas进行图像编辑的实例就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持我们。

(0)

相关推荐

  • canvas实现图像放大镜

    本文实例为大家分享了canvas实现图像放大镜的具体代码,供大家参考,具体内容如下 <!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <title>canvas-放大镜</title> <style> body{ padding: 0px; margin: 0px; } #canvas{ border: 1p

  • js canvas实现简单的图像扩散效果

    本文实例为大家分享了canvas实现简单图像扩散的代码,供大家参考,具体内容如下 <!DOCTYPE HTML> <html> <body> <canvas id="myCanvas" width="800" height="800" style="border:1px solid #c3c3c3;"> Your browser does not support the canv

  • canvas实现图像截取功能

    本文实例为大家分享了canvas图像截取的具体代码,供大家参考,具体内容如下 <!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <title>canvas-图像截取</title> <style> canvas{ border: 1px dashed red; float: left; position: r

  • Android开发之图形图像与动画(一)Paint和Canvas类学习

    Paint类 *Paint类代表画笔,用来描述图形的颜色和风格,如线宽,颜色,透明度和填充效果等信息. *使用Paint类时,需要先创建该类的对象,可以通过该类的构造函数实现.通常情况的实现代码是: *Paintpaint=newPaint(); *创建完Paint对象后,可以通过该对象提供的方法对画笔的默认设置进行改变 Canvas *Canvas类代表画布,通过该类提供的构造方法,可以绘制各种图形. *通常情况下,要在Android中绘图,需要先创建一个继承自View类的视图,并且在该类中重

  • PHP实现将HTML5中Canvas图像保存到服务器的方法

    本文实例讲述了PHP实现将HTML5中Canvas图像保存到服务器的方法.分享给大家供大家参考.具体实现方法如下: 一.问题: 在几年前HTML5还没有流行的时候,我们的项目经理曾经向我提出这样一个需求:让项目评审专家们在评审结束时用笔在平板电脑上进行电子签名.这需要我们评审软件里提供这样一个功能:打开浏览器,登录,进入评审意见页,页面最下部有个方块区域,用户在这里用触摸笔进行签名,然后这个签名将会保持的服务器上. 这样的一个需求在当时是让我大费周折,但如今想起来,如果用html5的canvas

  • canvas实现图像布局填充功能

    本文实例为大家分享了canvas图像布局填充的具体代码,供大家参考,具体内容如下 <!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <title>canvas-图像布局填充</title> <style> #canvas{ border: 1px solid palevioletred; } </sty

  • 使用canvas进行图像编辑的实例

    前面的话 本文将分为几个小功能的形式来详细介绍canvas图像编辑 缩放 下面是一张分析图,假设默认情况下,图片和canvas宽高相同.图片的缩放(scale)范围为0.5到3,缩放时改变的是图片的大小和图片的坐标位置 W(宽) = canvas.width * scale H(高) = canvas.height * scale x坐标 = (W - canvas.width)/2; y坐标 = (H - canvas.height)/2; 因此,代码如下 <canvas id="dra

  • 基于vue+canvas的excel-like组件实例详解

    a vue component,基于vue的表格组件,主要解决大数据量的表格渲染性能问题,使用canvas绘制表格,同时支持类似excel的批量选中,复制黏贴删除,实时编辑等功能. vue-grid-canvas Install NPM / Yarn Install the package: npm install vue-canvas-grid --save Then import it in your project import Vue from 'vue' import Grid fro

  • JavaScript+canvas实现七色板效果实例

    本文实例讲述了JavaScript+canvas实现七色板效果.分享给大家供大家参考,具体如下: 效果图如下: html: <canvas id="canvas" class="canvas" width="600" height="600"></canvas> css: html,body{margin: 0;padding: 0} .canvas{display: block; margin-lef

  • JS+canvas画一个圆锥实例代码

    以下是我们给大家分享是实例代码: <html> <head> <title>我的第一个 HTML 页面</title> </head> <body> <canvas id='cvs' width='1000' height="800"> </canvas> <script> const cvs =document.getElementById('cvs'); // 计算画布的宽度

  • jquery canvas绘制图片验证码实例

    本文实例为大家分享了jquery canvas绘制图片验证码的具体代码,供大家参考,具体内容如下 CSS .identify-code{ position: absolute; right: 6px; top: 50%; width: 118px; height: 40px; margin: -21px 0 0 0; } HTML <span id="code" class="identify-code"> <canvas class="

  • 原生JS+Canvas实现五子棋游戏实例

    一.功能模块 先看下现在做完的效果: 线上体验:https://wj704.github.io/five_game.html 主要功能模块为: 1.人机对战功能 2.悔棋功能 3.撤销悔棋功能 二.代码详解 2.1 人机对战功能实现 从效果图可以看到,棋盘的横竖可以放的位置为15*15,通过canvas画棋盘: //绘画棋盘 var drawChessBoard = function(){ for(var i = 0; i < 15; i++){ context.moveTo(15 + i *

  • html5 canvas js(数字时钟)实例代码

    复制代码 代码如下: <!doctype html><html>    <head>        <title>canvas dClock</title>    </head>    <body>        <canvas id = "clock" width = "500px" height = "200px">            您的浏览

  • HTML5 canvas 9绘制图片实例详解

    绘制图片 Var image=new Image(); image.src=" http://img4.duitang.com/uploads/item/201406/25/20140625182321_4MTau.thumb.700_0.jpeg"; image.onload=function(){} Context.drawImage(image,x,y); Context.drawImage(image,x,y,w,h); Context.drawIamge(image,sx,s

  • 微信小程序 使用canvas制作K线实例详解

    微信小程序 使用canvas制作K线 实现效果图: 前言: 我们目的是想要一条平滑的曲线来表示均线等,而不是一条转折点明显的折线.因此还得继续探索api.我们发现,在canvas API中,能够画出曲线的有2个 beZierCurveTo(num1, num2, num3, num4, x, y) quadraticCurveTo(num1, num2, x, y) 这两个api都是通过贝塞尔曲线来绘制路径.好在学习PS的时候,对贝塞尔曲线的具体表现也是有一定的熟练程度的,因此知道要确定一条由多

  • canvas 弹幕效果(实例分享)

    话不多说,请看代码 <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Document</title> </head> <body> <canvas style="width: 1280px;height: 720px;background-color: rgba(0

随机推荐