canvas實現餅狀圖


效果圖如下:

 

 

 

 html:

<canvas id="myCanvas" width="500" height="500"></canvas>

js:

 toCanvas(arr) {
        let canvas = document.getElementById('myCanvas');//獲取canvas
        let ctx = canvas.getContext('2d');//通過getContext獲取畫圖的環境
        let cont = 0; //總數
        let start = 0; //起始弧度
        let x = 250,
          y = 250; //圓點坐標
        let startCoordinate = {
          start: 200,
          end: 100
        }; //繪制起點坐標
        arr.forEach((item) => {
          cont += item.number;
        }); //獲取number之和
        arr.forEach((item) => {
          ctx.beginPath(); //初始化路徑
          let prop = item.number / cont; //計算比例
          let radian = prop * (Math.PI * 2); //計算弧度
          ctx.arc(x, y, 100, start, start + radian, false);//根據比例和弧度畫圓
          ctx.lineTo(x, y); //連接圓心畫線
          ctx.fillStyle = item.color; //設置圓弧顏色
          ctx.fill(); //填充樣式
          let x1 = x + Math.cos(radian / 2 + start) * 100;//獲取圓弧中間點X坐標
          let y1 = y + Math.sin(radian / 2 + start) * 100;//獲取圓弧中間點y坐標
          ctx.moveTo(x1, y1);//畫筆移動到圓弧中點
          ctx.lineTo(x1 + 30 * Math.cos(radian / 2 + start), y1 + 30 * Math.sin(radian / 2 + start));//在圓弧中點和圓心的連線上畫30單位長度的線
          let proNumber = null;
          if (Math.cos(radian / 2 + start) > 0) {
            proNumber = 1
          } else {
            proNumber = -1
          }//判斷起點半徑與當前圓弧線所成角的余弦值是為負數/正數
          ctx.lineTo(x1 + 30 * Math.cos(radian / 2 + start) + proNumber * 30, y1 + 30 * Math.sin(radian / 2 + start));//在之前線的基礎上畫一條30單位長度的水平線
          ctx.fillText(item.name, x1 + 30 * Math.cos(radian / 2 + start) + proNumber * 20, y1 + 30 * Math.sin(radian / 2 + start) - 5, 30);//在線上填充字體,設置字體的坐標,最大長度
          ctx.strokeStyle = item.color;//設置線條和字體的顏色
          ctx.font = "bold 10px consolas";//設置字體的樣式
          start += radian;//每次圓弧渲染完成將弧度累加作為下個圓弧的初始弧度
          ctx.stroke();//渲染線條
        })
        let small = new Path2D(ctx);//創建新的一個路徑
        small.arc(x, y, 60, 0, Math.PI * 2, false);//畫圓
        ctx.fillStyle = "#fff";//設置圓的顏色
        ctx.fill(small);//填充small
      },
 let arrs = [{
          name: '1號',
          color: '#CD853F',
          number: 500
        },
        {
          name: '2號',
          color: '#FFA500',
          number: 500
        },
        {
          name: '3號',
          color: '#FF4500',
          number: 200
        },
        {
          name: '4號',
          color: '#8B0000',
          number: 300
        },
        {
          name: '5號',
          color: '#DAA520',
          number: 50
        },
      ]
      this.toCanvas(arrs);

  有些不滿意的是文字沒有和底下的線條保持一致的margin,也找了很多方法依然沒有成功。有大神看到了麻煩指點一下。萬分感謝。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM