1、首先编写canvas的相关格式:
动态获取canvas的宽高以便修改处理,运用.translate();将画布中心点从默认左上角移到中心点方便后面的操作和换算。
<canvas width="800px" height="800px" id="canvas"></canvas> <script> var canvas=document.getElementById("canvas"); var gj=canvas.getContext("2d"); var width=canvas.width; var height=canvas.height; var r=width/2 gj.translate(r,r);
2、绘制外表盘、数字及静态的对象:
绘制外表盘:(这里我运用了渐变色使得表盘更加好看)
var grd=gj.createLinearGradient(-r,-r,r,r); grd.addColorStop(0,"cornflowerblue"); grd.addColorStop(1,"red"); gj.clearRect(-r,-r,r*2,r*2); gj.beginPath(); gj.arc(0,0,r-5,0,2*Math.PI,false); gj.closePath(); gj.strokeStyle=grd; gj.lineWidth=10 gj.stroke();
绘制表盘数字:(运用循环添加,运用三角函数辅助定位)
var sz=[3,4,5,6,7,8,9,10,11,12,1,2]; for (var i=0;i<sz.length;i++) { var rad=Math.PI*2/12*i; var x=Math.cos(rad)*(r-50); var y=Math.sin(rad)*(r-50); if (sz[i]%3==0) { gj.font="28px 微软雅黑"; }else{ gj.font="20px 微软雅黑"; } gj.fillStyle="goldenrod"; gj.textAlign="center"; gj.textBaseline="middle"; gj.fillText(sz[i],x,y); } for (var j=0;j<60;j++) { var rad=2*Math.PI/60*j var x=Math.cos(rad)*(r-30); var y=Math.sin(rad)*(r-30); gj.beginPath(); gj.closePath(); if (j%5==0) { gj.arc(x,y,4,0,2*Math.PI); gj.fillStyle="#000"; } else{ gj.arc(x,y,2,0,2*Math.PI); gj.fillStyle="#ccc"; } gj.fill(); }
3、绘制动态指针:
绘制时针:根据获取的时间换算成角度,通过.rotate();将指针旋转至想要的位置,由于canvas里上面的样式会影响到下面的样式,这里的旋转会影响下面时针分针的旋转,所以这里我们加上.gave();用来保存当前的状态,再在函数的末尾加上.restore();用来返回到之前保存的状态,这样就不会对后面的样式产生影响。
function drawhour(hour,min){ gj.save(); var rad = 2*Math.PI/12*hour; var radmin = 2*Math.PI/12/60*min; gj.rotate(rad+radmin); gj.beginPath(); gj.moveTo(-2,10); gj.lineTo(2,10); gj.lineTo(0,-r/2); gj.lineTo(-2,10); gj.closePath(); gj.fillStyle="brown" gj.fill(); gj.restore();
分针、秒针的绘制如同时针的绘制,只是在样式上有所改变。值得注意的是,时钟上分针的位置会相应影响时针的位置,秒针的位置也会相应影响分针的位置。这里我们给时针、分针函数相应添加了两个参数,经过换算得到双重影响下时针分针应该停留的位置。
// 绘制分针 function drawmin(min,sec){ gj.save(); var rad = 2*Math.PI/60*min; var radsec = 2*Math.PI/60/60*sec; gj.rotate(rad+radsec); gj.beginPath(); gj.moveTo(-2,10); gj.lineTo(2,10); gj.lineTo(0,-2*r/3); gj.lineTo(-2,10); gj.closePath(); gj.fillStyle="burlywood" gj.fill(); gj.restore(); } // 绘制秒针 function drawsec(sec){ gj.save(); var rad = 2*Math.PI/60*sec; gj.rotate(rad); gj.beginPath(); gj.moveTo(-2,10); gj.lineTo(2,10); gj.lineTo(0,-5*r/6); gj.lineTo(-2,10); gj.closePath(); gj.fillStyle="coral" gj.fill(); gj.restore(); }
随后设置定时器并完善函数调用:用new Date();来得到当前时间然后逐步获取相应的时、分、秒,然后调用之前所写函数,将得到的时、分、秒已参数的形式传给函数,然后得到我们想要的结果。值得注意的是,定时器每一次执行都得先清除画布,消除上一秒会出的时分秒针,而且将原点设置到中心点的操作记得写在函数外面或者用保存返回的方式使它回到初始状态,否则每一次执行都会以已经定义好的原点在重新定义原点。
function time(){ var t=new Date(); var hour=t.getHours(); var min=t.getMinutes(); var sec=t.getSeconds();
drawhour(hour,min);
drawmin(min,sec);
drawsec(sec);
最后完成时钟的制作,如果想使自己画出的时钟更好看,不妨发挥想象力尝试各种样式来修饰它。