canvas实现简单的画布
利用canvas可以做出很多有意思的东西,比如各种动画效果等,之前在岑安大神的博客中看到一个特别炫的demo,在这里。加入了很多运动学的东西在里面,本来想去研究一下怎么实现的,但是想到之前也过一个很水的画布的效果,就决定先把画布的功能重新写一下,一方面对canvas的基本用法再熟悉一下,另一方面也是练习一下js,而且这两个练习也确实加深了我对js的理解,很明显的就是this的使用,因为在代码的实现过程中,我们的作用域很可能会发生变化,因此就要先将this值赋给一个变量,通过闭包的形式来访问,还有由于在实现过程中没有用到第三方库,对原生js的使用也更熟练了一些,总之收获还是很大的。先看下demo~
附上代码:
1 <!DOCTYPE html> 2 <html> 3 <head lang="en"> 4 <meta charset="UTF-8"> 5 <title>canvas绘图</title> 6 <style type="text/css"> 7 /** 8 * canvas样式表 9 * author hualuyao 10 * date 2015/6/5 11 */ 12 13 body { 14 padding: 0; 15 margin: 0; 16 padding-top: 20px; 17 } 18 19 * { 20 box-sizing: border-box; 21 } 22 23 h1 { 24 text-align: center; 25 } 26 27 .container { 28 width: 800px; 29 margin: 0 auto; 30 } 31 32 .container p { 33 padding: 0; 34 margin: 0; 35 line-height: 22px; 36 font-size: 14px; 37 font-family: "楷体"; 38 color: #000; 39 } 40 41 .btn { 42 margin-top: 5px; 43 margin-bottom: 5px; 44 padding: 3px 6px; 45 background: #99f; 46 border: none; 47 border-bottom: 2px solid #77f; 48 border-radius: 2px; 49 -webkit-border-radius: 2px; 50 color: #333; 51 cursor: pointer; 52 } 53 .color { 54 display: inline-block; 55 width: 20px; 56 height: 20px; 57 border-radius: 2px; 58 -webkit-border-radius:2px; 59 cursor: pointer; 60 } 61 62 .checked { 63 border: 2px solid #000; 64 } 65 66 .red { 67 background: #f00; 68 } 69 70 .green { 71 background: #0f0; 72 } 73 74 .blue { 75 background: #00f; 76 } 77 78 .line { 79 display: inline-block; 80 width: 20px; 81 height: 20px; 82 cursor: pointer; 83 } 84 85 .line-3 { 86 border-bottom: 3px solid #ccc; 87 } 88 89 .line-5 { 90 border-bottom: 5px solid #ccc; 91 } 92 93 .line-7 { 94 border-bottom: 7px solid #ccc; 95 } 96 97 .canvas-container { 98 width: 800px; 99 margin: 0 auto; 100 } 101 102 .canvas-container > canvas { 103 background: #efefef; 104 } 105 </style> 106 </head> 107 <body> 108 <h1>画布实例^_^</h1> 109 <div class="container"> 110 <div> 111 <p>请选择画笔颜色:</p> 112 <p id="color"> 113 红色:<span class="color red"></span> 114 绿色:<span class="color green"></span> 115 蓝色:<span class="color blue"></span> 116 </p> 117 </div> 118 <div> 119 <p>请选择画笔宽度:</p> 120 <p id="lineWidth"> 121 3px: <span class="line line-3"></span> 122 5px: <span class="line line-5"></span> 123 7px: <span class="line line-7"></span> 124 </p> 125 </div> 126 <button id="clear" class="btn">清除画布</button> 127 </div> 128 <div class="canvas-container"> 129 <canvas id="myCanvas" width="800" height="400"></canvas> 130 </div> 131 </body> 132 <script type="text/javascript"> 133 var paint = function() { 134 var $ = function(id) { 135 return document.getElementById(id); 136 } 137 138 var addListener = function(obj, e, fn) { 139 if(obj.addEventListener) { 140 obj.addEventListener(e, fn, false); 141 } 142 else { 143 obj.attachEvent('on' + e, function() {fn.call(obj)}); 144 } 145 } 146 147 var cvs = $('myCanvas'); 148 var lineColor = $('color'); 149 var lineWidth = $('lineWidth'); 150 var clearCanvas = $('clear'); 151 152 var init = function() { 153 this.cvs = cvs; 154 this.ctx = this.cvs.getContext('2d'); 155 this.lineColor = lineColor; 156 this.lineWidth = lineWidth; 157 this.clearCanvas = clearCanvas; 158 this.x = new Array(); 159 this.y = new Array(); 160 this.lock = true; 161 this.bindBody(); 162 this.bindSettings(); 163 } 164 165 init.prototype = { 166 167 constructor: init, 168 169 bindBody: function() { 170 var _this = this; 171 var body = document.body; 172 var ctx = _this.ctx; 173 174 addListener(body, 'mousedown', function(e) { 175 e = e || window.event; 176 var target = e.target || e.srcElement; 177 if(target === _this.cvs) { 178 _this.lock = false; 179 var _x = e.clientX - target.parentElement.offsetLeft; 180 var _y = e.clientY + document.body.scrollTop - target.parentElement.offsetTop; 181 _this.x.push(_x); 182 _this.y.push(_y); 183 } 184 }); 185 186 addListener(body, 'mousemove', function(e) { 187 e = e || window.event; 188 var target = e.target || e.srcElement; 189 if(target === _this.cvs && !_this.lock) { 190 var _x = e.clientX - target.parentElement.offsetLeft; 191 var _y = e.clientY + document.body.scrollTop - target.parentElement.offsetTop; 192 _this.x.push(_x); 193 _this.y.push(_y); 194 var length = _this.x.length; 195 ctx.beginPath(); 196 ctx.moveTo(_this.x[length-2], _this.y[length-2]); 197 ctx.lineTo(_this.x[length-1], _this.y[length-1]); 198 ctx.stroke(); 199 ctx.closePath(); 200 } 201 }); 202 203 addListener(body, 'mouseup', function(e) { 204 _this.lock = true; 205 _this.x = []; 206 _this.y = []; 207 }); 208 }, 209 210 bindSettings: function() { 211 var lineColor = this.lineColor; 212 var lineWidth = this.lineWidth; 213 var clearCanvas = this.clearCanvas; 214 var ctx = this.ctx; 215 var _this = this; 216 217 addListener(lineColor, 'click', function(e) { 218 e = e || window.event; 219 var target = e.target || e.srcElement; 220 221 if (target instanceof HTMLSpanElement) { 222 var className = target.className; 223 var color = className.substr(6); 224 225 var siblings = target.parentNode.children; 226 227 for(var i=0,len=siblings.length;i<len;i++) { 228 if(siblings[i].className.indexOf("checked") != -1) { 229 var l = siblings[i].className.length; 230 siblings[i].className = siblings[i].className.substr(0, l-8); 231 console.log(siblings[i].className); 232 } 233 } 234 235 target.className += " " + "checked"; 236 237 switch(color) { 238 case 'red': 239 ctx.strokeStyle = "red"; 240 break; 241 case 'green': 242 ctx.strokeStyle = "green"; 243 break; 244 case 'blue': 245 ctx.strokeStyle = "blue"; 246 break; 247 } 248 } 249 }); 250 251 addListener(lineWidth, 'click', function(e) { 252 e = e || window.event; 253 var target = e.target || e.srcElement; 254 255 if (target instanceof HTMLSpanElement) { 256 var className = target.className; 257 var l_width = className.substr(5); 258 259 var siblings = target.parentNode.children; 260 261 for(var i=0,len=siblings.length;i<len;i++) { 262 if(siblings[i].className.indexOf("checked") != -1) { 263 var l = siblings[i].className.length; 264 siblings[i].className = siblings[i].className.substr(0, l-8); 265 console.log(siblings[i].className); 266 } 267 } 268 269 target.className += " " + "checked"; 270 271 switch(l_width) { 272 case 'line-3': 273 ctx.lineWidth = 3; 274 break; 275 case 'line-5': 276 ctx.lineWidth = 5; 277 break; 278 case 'line-7': 279 ctx.lineWidth = 7; 280 } 281 } 282 }); 283 284 addListener(clearCanvas, 'click', function() { 285 _this.clearCvs(); 286 }) 287 }, 288 289 clearCvs: function() { 290 var ctx = this.ctx; 291 ctx.clearRect(0,0,800,400); 292 } 293 } 294 return init; 295 }(); 296 </script> 297 <script type="text/javascript"> 298 new paint(); 299 </script> 300 </html>