HTML5 rotate 做仪表盘

我们的项目中有关于数据仓库和挖掘,用户要求UI的界面需要仪表盘,我网上找了下,没有发现免费的HTML仪表盘,饼图啥图表的确很多,那就没有办法了,我和同事自己做了一个仪表盘,结果如下。

HTML5 rotate 做仪表盘

之后我们就来讨论下这个简单的仪表盘是怎么做的。我们先大致有一个想法,设定一个宽高2:1的canvas,仪表盘的半径就是canvas的高度,仪表盘需要的数据有上面分几个区域(一般是低中高三个区域,为了测试我们准备了四个区域),刻度线和文字,指针,和指针指向的值。

首先第一步自然是canvas的声明

  1. <body>  
  2.     <div>  
  3.         <canvas id="board" width="800" height="600">  
  4.         </canvas>  
  5.     </div>  
  6. </body>  
  7. </html>  
之后的工作都在javascript中完成,我们需要定义一些对象
  1. //仪表盘面板   
  2. var panel = function(id, option) {  
  3.     this.canvas = document.getElementById(id); //获取canvas元素   
  4.     this.cvs = this.canvas.getContext("2d"); //得到绘制上下文   
  5.     this.width = this.canvas.width; //对象宽度   
  6.     this.height = this.canvas.height; //对象高度   
  7.     this.level = option.level;  
  8.     this.outsideStyle = option.outsideStyle;  
  9. }  
这个panel就是我们的仪表盘对象,参数的id是canvas元素,option是我们需要提交给仪表盘的一些参数值。这个option的定义如下:option对象可以扩展,你可以通过optin定制更加自由强大的仪表盘对象的。
  1. var panelOption = {  
  2.     maxLength: 30,  
  3.     interval: 5,  
  4.     level: [//仪表盘需要呈现的数据隔离区域   
  5.           {start: 0, color: "red" },  
  6.           { start: 30, color: "yellow" },  
  7.           { start: 40, color: "blue" },  
  8.           { start: 100, color: "Lime" }  
  9.           ],  
  10.     outsideStyle: { lineWidth: 4, color: "rgba(100,100,100,1)" }  
  11. };  
在绘制元素的时候,我们常常需要保存和恢复现场,特别当我们使用转移,旋转等方法的时候,一定要记得先save最后restore。为了方便,我们编写了一个save函数提供这个方式,这个模式类似C#中的委托,和设计模式中的观察着模式
  1. panel.prototype.save = function(fn) {  
  2.     this.cvs.save();  
  3.     fn();  
  4.     this.cvs.restore();  
  5. }  
上面这个save可以方便的帮助我们保存和回复现场。

我们定义个用于画半圆的方法,这个方法中,我们将需要画半圆时做的translate放到save函数中,这样画半圆的变形操作不会对其他操作有影响。

  1. panel.prototype.drawArc = function() {  
  2.     var p = this;  
  3.     var cvs = this.cvs;  
  4.     p.save(function() {  
  5.         cvs.translate(p.width / 2, p.height); //将坐标点移到矩形的底部的中间   
  6.         cvs.beginPath();  
  7.         cvs.lineWidth = p.outsideStyle.lineWidth;  
  8.         cvs.strokeStyle = p.outsideStyle.color;  
  9.         cvs.arc(0, 0, p.height - cvs.lineWidth, 0, Math.PI / 180 * 180, true); //画半圆   
  10.         cvs.stroke();  
  11.     });  
  12. }  
然后我们绘制中间颜色的填充区域
  1. panel.prototype.drawLevelArea = function(level) {  
  2.     var p = this;  
  3.     var cvs = this.cvs;  
  4.     for (var i = 0; i < level.length; i++) {  
  5.         p.save(function() {  
  6.             cvs.translate(p.width / 2, p.height);  
  7.             cvs.rotate(Math.PI / 180 * level[i].start);  
  8.             p.save(function() {  
  9.                 cvs.beginPath();  
  10.                 cvs.arc(0, 0, p.height - p.outsideStyle.lineWidth, Math.PI / 180 * 180, Math.PI / 180 * 360);  
  11.                 cvs.fillStyle = level[i].color;  
  12.                 cvs.fill();  
  13.             });  
  14.         });  
  15.     }  
  16. }  

相关推荐