先放一张效果图:

下面是源代码:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
<style type="text/css">
div{
text-align: center;
margin-top: 150px;
}
canvas{
border: 1px solid black;
}
</style>
</head>
<body>
<div>
<canvas width="500px" height="500px" id="canvas"></canvas>
</div>
</body>
<script type="text/javascript">
var canvas = document.getElementById("canvas");
var ctx =canvas.getContext("2d");
var width = canvas.width;
var height = canvas.height;
var r = width/2;
var a = Math.floor(Math.random()*256);
var b = Math.floor(Math.random()*256);
var c = Math.floor(Math.random()*256);
function fun(){
ctx.save();
ctx.translate(r,r);
ctx.beginPath();
ctx.arc(0,0,r-5,0,Math.PI*2,false);
ctx.lineWidth = 10;
var grd = ctx.createLinearGradient(-r,0,r,0)
grd.addColorStop(0,"rgb("+a+","+b+","+c+")");
grd.addColorStop(1,"rgb("+c+","+b+","+a+")");
ctx.strokeStyle = grd;
//ctx.strokeStyle = "rgb("+a+","+b+","+c+")";
ctx.stroke();
var num = [3,4,5,6,7,8,9,10,11,12,1,2];
ctx.textAlign = "center";
ctx.textBaseline = "middle";
for(var i =0; i < num.length; i++){
var rang = Math.PI*2/12*i;
var x = Math.cos(rang)*(r-30);
var y = Math.sin(rang)*(r-30);
ctx.fillText(num[i],x,y);
ctx.closePath();
}
for(var j =0; j < 60; j++){
var rang1 = Math.PI*2/60*j;
var x1 = Math.cos(rang1)*(r-20);
var y1 = Math.sin(rang1)*(r-20);
ctx.beginPath();
ctx.arc(x1,y1,3,0,Math.PI*2);
if(j%5==0){
ctx.fillStyle = "#000000";
}
else{
ctx.fillStyle = "#cccccc";
}
ctx.fill();
ctx.closePath();
}
}
function drawHour(hour,minu){
ctx.save(); //保存当前的状态
ctx.beginPath();
ctx.lineWidth = 6;
var rad = Math.PI * 2 / 12 * hour;
var rad_minu = Math.PI * 2 / 12 / 60 * minu;
ctx.rotate(rad + rad_minu);
ctx.moveTo(0,10);
ctx.lineTo(0,-r/2);
ctx.lineCap="round";
ctx.stroke();
ctx.restore();
}
function drawMinu(minu,seco){
ctx.save();
ctx.beginPath();
ctx.lineWidth = 4;
var rad = Math.PI * 2 / 60 * minu;
var rad_seco = Math.PI * 2 / 60 / 60 * seco;
ctx.rotate(rad + rad_seco);
ctx.moveTo(0,10);
ctx.lineTo(0,-r+50);
ctx.lineCap="round";
ctx.stroke();
ctx.restore();
}
function drawSeco(seco){
ctx.save();
var rad = Math.PI * 2 / 60 * seco;
ctx.beginPath();
ctx.rotate(rad);
ctx.fillStyle = "#f00";
ctx.moveTo(-2,20);
ctx.lineTo(2,20);
ctx.lineTo(1,-r+20);
ctx.lineTo(-1,-r+20);
ctx.closePath();
ctx.fill();
ctx.restore();
}
function drawDot(){
ctx.beginPath();
ctx.fillStyle = "#fff";
ctx.arc(0,0,3,0,Math.PI*2);
ctx.closePath();
ctx.fill();
}
function draw(){
ctx.clearRect(0,0,width,height);
var datenow = new Date();
var hour = datenow.getHours();
var minu = datenow.getMinutes();
var seco = datenow.getSeconds();
fun();
drawHour(hour,minu);
drawMinu(minu,seco);
drawSeco(seco);
drawDot();
ctx.restore();
}
draw();
setInterval(draw,1000);
</script>
</html>
————
先建一个画布
<canvas width="500px" height="500px" id="canvas"></canvas>
然后在script中获取到它和它的的宽度、高度,同时定义表盘的半径
var canvas = document.getElementById("canvas"); var ctx =canvas.getContext("2d"); var width = canvas.width; var height = canvas.height; var r = width/2;
表盘的圆心在画布中央便于我们的后续操作。可是实际上画布的原点是画布的左上角,所以我们可以使用translate()方法重新映射原点坐标:
ctx.translate(r,r);
然后画一个圆,我在这加了个渐变色。(arc()中的五个参数分别是arc(圆心x坐标,圆心y坐标,半径,起始角,结束角,Boolean值))
ctx.beginPath();
ctx.arc(0,0,r-5,0,Math.PI*2,false);
ctx.lineWidth = 10;
var grd = ctx.createLinearGradient(-r,0,r,0)
grd.addColorStop(0,"rgb("+a+","+b+","+c+")");
grd.addColorStop(1,"rgb("+c+","+b+","+a+")");
ctx.strokeStyle = grd;
ctx.stroke();
定义一个数组来装表盘上的数字,然后通过循环的方式将他们打印在表盘上,这里最主要的就是要算出每个数字打印的坐标,我们可以先算出每两个数字间的弧度,然后就可以根据相应的弧度算出每个数字的位置
var num = [3,4,5,6,7,8,9,10,11,12,1,2]; ctx.textAlign = "center"; ctx.textBaseline = "middle"; for(var i =0; i < num.length; i++){ var rang = Math.PI*2/12*i; var x = Math.cos(rang)*(r-30); var y = Math.sin(rang)*(r-30); ctx.fillText(num[i],x,y); ctx.closePath(); }
然后表盘上的刻度也是同样的方法,整点的位置上的点我们可以用一点不同的颜色
for(var j =0; j < 60; j++){ var rang1 = Math.PI*2/60*j; var x1 = Math.cos(rang1)*(r-20); var y1 = Math.sin(rang1)*(r-20); ctx.beginPath(); ctx.arc(x1,y1,3,0,Math.PI*2); if(j%5==0){ ctx.fillStyle = "#000000"; } else{ ctx.fillStyle = "#cccccc"; } ctx.fill(); ctx.closePath(); }
然后是时针部分,绘制指针的时候,可以使用linecap属性给两端稍加一点弧度。(使用lineCap之后不能用closePath())
算出时针应该转动的角度,然后利用rotate()方法转动它。
function drawHour(hour,minu){ ctx.save(); ctx.beginPath(); ctx.lineWidth = 6; var rad = Math.PI * 2 / 12 * hour; var rad_minu = Math.PI * 2 / 12 / 60 * minu; ctx.rotate(rad + rad_minu); ctx.moveTo(0,10); ctx.lineTo(0,-r/2); ctx.lineCap="round"; ctx.stroke(); ctx.restore(); }
然后是分针和秒针
function drawMinu(minu,seco){ ctx.save(); ctx.beginPath(); ctx.lineWidth = 4; var rad = Math.PI * 2 / 60 * minu; var rad_seco = Math.PI * 2 / 60 / 60 * seco; ctx.rotate(rad + rad_seco); ctx.moveTo(0,10); ctx.lineTo(0,-r+50); ctx.lineCap="round"; ctx.stroke(); ctx.restore(); }
function drawSeco(seco){ ctx.save(); var rad = Math.PI * 2 / 60 * seco; ctx.beginPath(); ctx.rotate(rad); ctx.fillStyle = "#f00"; ctx.moveTo(-2,20); ctx.lineTo(2,20); ctx.lineTo(1,-r+20); ctx.lineTo(-1,-r+20); ctx.closePath(); ctx.fill(); ctx.restore(); }
为了使我们画的时钟能够使用,我们需要获取到当前的时间,并把时分秒分别赋给相应的变量后传到相应的函数中,之后用定时器每隔一秒调用一次此函数,就能达到时钟的效果
function draw(){ ctx.clearRect(0,0,width,height); var datenow = new Date(); var hour = datenow.getHours(); var minu = datenow.getMinutes(); var seco = datenow.getSeconds(); fun(); drawHour(hour,minu); drawMinu(minu,seco); drawSeco(seco); drawDot(); ctx.restore(); } draw(); setInterval(draw,1000);
浙公网安备 33010602011771号