canvas实现钟表
canvas实现钟表效果,代码附在文章最后。
第一步当然是创建一个canvas画布,我这里写的是居中的画布,所以css样式需要做一下修改
然后通过js获取到canvas元素以及画笔。
我这里写的是一个函数,把所有的逻辑都写在了这个函数内,然后通过定时器,实现动画效果,函数每次进来时都会去清空画布。
重要的地方来了。既然是写钟表,那么肯定少不了获取时间对象了,毕竟想让钟表动起来的关键就在于它。
需要注意的是,时针取得不能是整数,取整数会造成时针只会在某个小时哪里保持不动。像下面图片这样,明明是3.44分,时针却一直指向3。
我们需要的效果是这样的,时针会跟随分针移动。
表盘部分
标注小时时间
画小时刻度。这里需要注意的是translate和rotate。它们分别是移动和旋转。因为我的圆心位置是在(250,250),所以想把线段移动到外圈就需要进行移动。至于旋转可以这样想,每个时针的刻度为30度,所以通过j*30*Math.PI/180得到的就是每个刻度的具体位置。
画分针刻度,这里的旋转可以理解为每个分针刻度的读数为6度
画时针
画分针
画秒针
画中心位置
现在所有的逻辑都已经走完了,我们需要的就只是一个定时器,来让我们的钟表实现动画效果
完整代码如下:
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
<style>
* {
margin: 0;
padding: 0;
}
canvas {
border: 1px solid #ccc;
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
margin: 100px auto;
}
</style>
</head>
<body>
<canvas width="500" height="500"></canvas>
<script>
var canvas = document.getElementsByTagName('canvas')[0];
var ctx = canvas.getContext('2d');
function zhongBiao() {
ctx.clearRect(0, 0, canvas.width, canvas.height)
var now = new Date();
var hour = now.getHours();
var minute = now.getMinutes();
var second = now.getSeconds();
hour = hour + minute / 60
hour = hour > 12 ? hour - 12 : hour;
ctx.beginPath();
ctx.lineWidth = '5';
ctx.arc(250, 250, 200, 0, 2 * Math.PI);
ctx.strokeStyle = 'rgba(16, 214, 204, 0.664)';
ctx.stroke();
ctx.closePath();
ctx.font = '30px 微软雅黑';
ctx.fillStyle = '#000';
ctx.fillText('12', 235, 105);
ctx.fillText('11', 160, 130);
ctx.fillText('10', 100, 180);
ctx.fillText('9', 80, 260);
ctx.fillText('8', 105, 340);
ctx.fillText('7', 170, 400);
ctx.fillText('6', 240, 420);
ctx.fillText('5', 320, 400);
ctx.fillText('4', 375, 340);
ctx.fillText('3', 400, 260);
ctx.fillText('2', 380, 180);
ctx.fillText('1', 320, 130);
for (var j = 0; j < 12; j++) {
ctx.save();
ctx.beginPath();
ctx.lineWidth = '6';
ctx.strokeStyle = 'rgba(219, 74, 16, 0.863)';
ctx.translate(250, 250);
ctx.rotate(j * 30 * Math.PI / 180);
ctx.moveTo(0, -200);
ctx.lineTo(0, -180);
ctx.stroke();
ctx.closePath();
ctx.restore();
}
for (var i = 0; i < 60; i++) {
if (i % 5 != 0) {
ctx.save();
ctx.lineWidth = 5;
ctx.strokeStyle = "crimson";
ctx.translate(250, 250);
ctx.rotate(i * 6 * Math.PI / 180);
ctx.beginPath();
ctx.moveTo(0, -200);
ctx.lineTo(0, -190);
ctx.stroke();
ctx.closePath();
ctx.restore();
}
}
ctx.save();
ctx.lineWidth = 10;
ctx.strokeStyle = "#ccc";
ctx.translate(250, 250);
ctx.rotate(hour * 30 * Math.PI / 180);
ctx.beginPath();
ctx.moveTo(0, -175);
ctx.lineTo(0, 20);
ctx.stroke();
ctx.closePath();
ctx.restore();
ctx.save();
ctx.lineWidth = 5;
ctx.strokeStyle = "red";
ctx.translate(250, 250);
ctx.rotate(minute * 6 * Math.PI / 180);
ctx.beginPath();
ctx.moveTo(0, -155);
ctx.lineTo(0, 20);
ctx.stroke();
ctx.closePath();
ctx.restore();
ctx.save();
ctx.lineWidth = 5;
ctx.strokeStyle = "pink";
ctx.translate(250, 250);
ctx.rotate(second * 6 * Math.PI / 180);
ctx.beginPath();
ctx.moveTo(0, -135);
ctx.lineTo(0, 20);
ctx.stroke();
ctx.closePath();
ctx.restore();
ctx.beginPath();
ctx.arc(250, 250, 10, 0, 2 * Math.PI);
ctx.fillStyle = 'blue'
ctx.fill();
ctx.closePath();
}
setInterval(function () {
zhongBiao()
}, 1000)
zhongBiao()
</script>
</body>
</html>