概述

基于Canvas实现的仪表盘及效果。通过配置参数,可以任意修改仪表盘颜色,刻度,动画过渡时间等,满足不同场景下的使用。同时使用原生的Canvas,也是学习Canvas的很好的例子。

详细

一、演示效果

仪表盘效果如下:

二、项目结构截图

gauge.js文件是canvas仪表盘的主逻辑,demo.html中是使用的方法。

注:本例子只有2个文件,如上图所示。

三、使用方法

在html中,加入一个canvas的元素,设置宽高为510。

<canvas width=510 height=510 id="gauge"></canvas>
<script src="./gauge.js"></script> //然后配置仪表盘
var my_canvas_obj= document.getElementById("gauge");
var gauge2 = new Gauge({
"tick_length": 12,
"large_tick_length": 22,
"tick_thickness": 1,
"tick_group_length": 9,
"ticks_groups_begin": 0,
"total_degrees": 250,
"total_tick": 101,
"tick_color": "#666",
"num_font_size": 18,
"percent": 0,
"center_font_size": 172,
tick_on_color: '#f1594e',
cur_score_circle_color: '#ff5e52',
center_font_color: '#ff5e52',
center_text_unit: '%',
animation_duration: 1000,
"canvas": my_canvas_obj2
}) // 绘制初始仪表盘初始值0%
gauge.render()
setTimeout(function(){ //绘制目标值,90%
gauge.updatePercent(90)
}, 1000)

仪表盘通过一系列的配置参数来实现各种颜色,动画时间,刻度多少等的自定义

* 配置参数
* 颜色配置
tick_color: "#555962", // 未达到的刻度颜色
tick_on_color: "#527d98", // 已达到的刻度颜色
on_color_gradient: // 已达到的刻度颜色,渐变效果,详细参考demo中,guage1。值为Array
例如:
on_color_gradient: [
{
color: "#50B517",
percent: 0 // 最开始,0%
},
{
color: "#000000",
percent: 100 // 结束,100%
},
]
on_color_gradient 设置之后,tick_on_color则不会生效 center_font_color: '#555962', //中间数字颜色 设置为#fff-#000时,表示从左往右渐变
bg_color: // cavans的背景色 * 尺寸配置:
tick_length: 80, // 短刻度长度
large_tick_length: 110, // 长刻度长度
tick_thickness: 6, //刻度条宽度
tick_group_length: 9, //每组内的短刻度个数
ticks_groups_begin: 0, //起始点
total_degrees: 240, // 刻度的总角度
animation_duration: 550, //达到目标值的动画时间
total_tick: 101, // 刻度总个数
show_num: true, // 是否展示长刻度下的数字
show_center_num: true, // 是否显示中间大的数字
center_font_size: 200, //中间数字font-size
center_num_font_family: ,//中间数字font-family
num_gap: 1, // 每个刻度之间的间隔值,计算显示数字时需要
num_begin: 0, // 起始刻度值
num_font_size: 24, // 刻度值字体大小
num_font_family: 'HanHei SC,PingFang SC,Helvetica Neue Thin, Helvetica, STHeitiSC-Light, Arial, sans-serif' // 刻度数字font-family * 不建议随意修改的参数
tickmask_offset: 10 // 刻度值距离刻度的间隔, 单位px,
center_offset: {
x: 0,
y: 0
}, // 中间数字上下位置的偏移
circle_radius: 5, // 刻度指示圆形的半径
circle_offset: 0 // 刻度指示距离刻度的空隙
gauge_scale: 1, // 缩放比例

四、代码实现过程

下面介绍canvas仪表盘的实现过程,代码逻辑位于gauge.js文件中

1.初始化

首先properties中放置了所有配置的默认值。

然后将传入的配置值和默认的配置值就行合并。合并完之后进行一下初始化值的设置。

初始化时,设置一下每一个刻度需要旋转的角度:

总的刻度角度 / (刻度条的个数 - 1) * Math.PI / 180

2.绘制每一帧

    // 计算一下最初始的角度,也就开始的刻度线相对于水平线的角度
var starting_deg = (180 - this.total_degrees) / 2;
// 然后将整个画布旋转到初始角度。从左下角可是绘制
context.rotate(starting_deg * PIDEG);
// 首先绘制刻度盘上指示刻度的小圆点
this._drawScoreTipCircle(this._halfCanvasWidth - this.circle_radius, this.circle_radius, 0); // 绘制刻度线,num_ticks 为总刻度线的条数。
for(var i = 1; i <= num_ticks; i++) {
//判断是刻度线是应该亮起来还是暗的
var is_on = (((i - 1) / num_ticks) * 100 < this._percent);
//判断是长刻度线还是短刻度线
var _isLargeTick = this._isLargeTick(i)
var tick_length = _isLargeTick ? this.large_tick_length : this.tick_length; //获取不同刻度线的颜色
var color = this._getTickColor(is_on, i);
//设置填充色
context.fillStyle = color;
// 绘制刻度线,即一个长方形。 由于刻度线分长刻度线和短刻度线,而长刻度线和短刻度线因为长度不同,所以长方形的起点位置不同。
if (_isLargeTick) {
// 绘制长刻度线,即一个长方形
context.fillRect(-1*this._halfCanvasWidth + this.circle_radius * 2 + this.circle_offset, -this.tick_thickness/2, tick_length, this.tick_thickness);
// 对于整数值的刻度线,旁边有一个示数,这里绘制示数
if (this.show_num) {
this._drawGaugeNum(tick_length, i);
}
} else {
// 绘制短刻度线
context.fillRect(-1*this._halfCanvasWidth + this.circle_radius * 2 + this.circle_offset + this.delatLength, -this.tick_thickness/2, tick_length, this.tick_thickness);
}
//每画完一条,就旋转一下画布。旋转的角度 = 总的刻度角度 / (刻度条的个数 - 1) * Math.PI / 180
context.rotate(this._rotation_deg);
}
// 全部绘制完之后,把前一个旧的canvas清除掉
this._context.clearRect(0, 0, this._canvas.width, this._canvas.height);
// 绘制新的图像
this._context.drawImage(this.canvas, 0, 0);
// 每次绘制完成后要回到画布的原始的状态
context.restore();

3.动画

通过上面的 render 函数,我们可以绘制出一个静态的仪表盘了。接下来我们需要让仪表盘的示数展示动起来。这里我们利用 requestAnimationFrame 函数,在函数回调中执行 render 函数,绘制出不一样的刻度亮/暗图。

      var lastUpdate = +new Date();
// 动画开始时已经亮起来的刻度的百分比
var start = this._percent;
// 目标百分比
var end = this._target_percent;
// 计算一下每毫秒我们需要完成多少百分比,然后后面每次执行时,根据经过了多少时间来计算出应该完成多少,即刻度应该亮起来多少
var change_per_ms = (end - start)/duration;
var increasing = change_per_ms > 0 ? 1 : 0;
// 首先计算一下所有刻度亮起来时应该是什么颜色的,保存到一个数组中。
// 后面动画过程中直接从数组中取值即可,不需要再次计算。
this.colorArray = this._gradientColorArray();
// 更新逻辑
var update = function () {
// 通过时间来计算应该完成的百分比
var now = +new Date();
var elapsed = now - lastUpdate;
_this._percent += elapsed*change_per_ms; lastUpdate= now;
//检测一下是否已经达到我们最终的百分比,如果达到了就停止动画;如果没有就继续绘制
if ((increasing && _this._percent < _this._target_percent)
|| (!increasing && _this._percent > _this._target_percent)) {
_this.render();
_this._requestAnimFrame(update);
}
else {
_this._percent = _this._target_percent;
_this.render();
}
};
_this._requestAnimFrame(update);

这样我们的仪表盘就有一开始从0到100刻度逐渐变亮的效果。

注:本文著作权归作者,由demo大师发表,拒绝转载,转载需要作者授权

基于canvas的仪表盘效果的更多相关文章

  1. canvas/CSS仪表盘效果

    <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...

  2. Particles.js基于Canvas画布创建粒子原子颗粒效果

    文章目录 使用方法 自定义参数 相关链接 Particles.js是一款基于HTML5 Canvas画布的轻量级粒子动画插件,可以设置粒子的形状.旋转.分布.颜色等属性,还可以动态添加粒子,效果非常炫 ...

  3. 【HTML5】Canvas 实现放大镜效果

    图片放大镜 效果 在线演示    源码 原理 首先选择图片的一块区域,然后将这块区域放大,然后再绘制到原先的图片上,保证两块区域的中心点一致, 如下图所示: 初始化 <canvas id=&qu ...

  4. 基于canvas的二维码邀请函生成插件

    去年是最忙碌的一年,实在没时间写博客了,看着互联网行业中一个又一个人的倒下,奉劝大家,健康要放在首位,保重身体.好了,言归正传,这是17年的第一篇博文,话说这天又是产品同学跑过来问我说:hi,lenn ...

  5. 7个华丽的基于Canvas的HTML5动画

    说起HTML5,可能让你印象更深的是其基于Canvas的动画特效,虽然Canvas在HTML5中的应用并不全都是动画制作,但其动画效果确实让人震惊.本文收集了7个最让人难忘的HTML5 Canvas动 ...

  6. 一个基于vue的仪表盘demo

    最近写了一个基于vue的仪表盘,其中 主要是和 transform 相关的 css 用的比较多.给大家分享一下,喜欢的话点个赞呗?嘿嘿 截图如下: 实际效果查看地址:https://jhcan333. ...

  7. 使用Canvas实现动画效果 | DKlogs -- 设计 | 生活

    使用Canvas实现动画效果 | DKlogs -- 设计 | 生活 使用Canvas实现动画效果

  8. canvas实现倒计时效果示例(vue组件内编写)

    前言: 此事例是在vue组件中,使用canvas实现倒计时动画的效果.其实,实现效果的逻辑跟vue没有关系,只要读懂canvas如何实现效果的这部分逻辑就可以了 canvas动画的原理:利用定时器,给 ...

  9. 原生js实现canvas气泡冒泡效果

    说明: 本文章主要分为ES5和ES6两个版本 ES5版本是早期版本,后面用ES6重写优化的,建议使用ES6版本. 1, 原生js实现canvas气泡冒泡效果的插件,api丰富,使用简单2, 只需引入J ...

随机推荐

  1. Codeforces Beta Round #6 (Div. 2 Only) B. President's Office 水题

    B. President's Office 题目连接: http://codeforces.com/contest/6/problem/B Description President of Berla ...

  2. Microsoft Visual Studio 2010导致系统C盘不断增大问题处理。

    一直用Microsoft Visual Studio 2010做开发,发现最近C盘空间是越来越小,一开始以为是IE或者一些系统补丁造成的临时文件,但是使用360,windows优化大师之类的软件都清过 ...

  3. Vue学习记录-状态管理

    要解决的问题 平时的系统开发中,基本都会碰到这个权限问题,需要根据用户的登录状态进行处理.最常见的情况就是“先登录,后使用”.除去打包成APP,无法看到连接外,如果地址栏里直接输入地址就能绕过登录的话 ...

  4. Ext中的get、getDom、getCmp、getBody、getDoc的区别

    Ext中的get.getDom.getCmp.getBody.getDoc的区别Ext中包含了几个以get开头的方法,这些方法可以用来得到文档中DOM.得到当前文档中的组件.得到Ext元素等,在使用中 ...

  5. HDU 4690 EBCDIC (2013多校 1005题 胡搞题)

    EBCDIC Time Limit: 2000/2000 MS (Java/Others)    Memory Limit: 102400/102400 K (Java/Others)Total Su ...

  6. Two-transistor circuit replaces IC

    Linear Technology's recently introduced LTC4300 chip buffers I2C clock and data lines to and from a ...

  7. 计蒜之道 初赛 第三场 题解 Manacher o(n)求最长公共回文串 线段树

    腾讯手机地图 腾讯手机地图的定位功能用到了用户手机的多种信号,这当中有的信号的作用范围近.有的信号作用的范围则远一些.有的信号相对于用户在不同的方位强度是不同的,有的则是在不论什么一个方向上信号强度都 ...

  8. 掌握11项技能,你就是优秀的前端开发project师

    导读: 你或许会认为前端开发是一个非常easy的工作,对呀,你就是刚刚从网页设计转型过来的.但当你深入当中时,一定会发现好像前端开发不是那么简单,光站点性能优化.响应式.框架就让你焦头烂额, 确实,做 ...

  9. 【mysql】mysql创建数据库,基字符集 和 数据库排序规则 的对比选择

    1.一般选择utf8.下面介绍一下utf8与utfmb4的区别. utf8mb4兼容utf8,且比utf8能表示更多的字符.至于什么时候用,看你的做什么项目了,到https://www.cnblogs ...

  10. jq设置样式

    单个样式: $(this).css("color","red"); 多个样式: $(this).css({color:"red",backg ...