/* * @Author: 李佐宁 * @Description: * @Date: 2023-03-13 09:26:35 * @LastEditTime: 2023-03-18 17:29:25 * @LastEditors: 李佐宁 */ /** * 生成球体canvas * @param id - 元素id * @param value - 值(0-100) * @param color - 填充颜色 * @param bgColor - 背景颜色 * @param width - 球宽度 * @param hideText - 是否展示中间问题 */ export function initCanvas( id, value = 0, color = "#2BDBF5", bgColor = "#2BDBF5", width = 100, hideText = false ) { var canvas = id; var ctx = canvas.getContext("2d"); var nowRange = value; //用于做一个临时的range //画布属性 var mW = (canvas.width = width); var mH = (canvas.height = width); var lineWidth = 0.1; //圆属性 var r = mH / 2; //圆心 var cR = r - 16 * lineWidth; //圆半径 //Sin 曲线属性 var sX = 0; var sY = mH / 2; var axisLength = mW; //轴长 var waveWidth = 0.05; //波浪宽度,数越小越宽 var waveHeight = 6; //波浪高度,数越大越高 var speed = 0.09; //波浪速度,数越大速度越快 var xOffset = 0.5; //波浪x偏移量 ctx.lineWidth = 2; //画圈函数 var IsdrawCircled = false; var drawCircle = function () { ctx.beginPath(); ctx.strokeStyle = "transparent"; ctx.arc(r, r, cR + 1, 0, 2 * Math.PI); ctx.stroke(); ctx.beginPath(); ctx.arc(r, r, cR, 0, 2 * Math.PI); ctx.clip(); }; //画sin 曲线函数 var drawSin = function (xOffset) { ctx.save(); var points = []; //用于存放绘制Sin曲线的点 ctx.beginPath(); //在整个轴长上取点 for (var x = sX; x < sX + axisLength; x += 20 / axisLength) { //此处坐标(x,y)的取点,依靠公式 “振幅高*sin(x*振幅宽 + 振幅偏移量)” var y = -Math.sin((sX + x) * waveWidth + xOffset); var dY = mH * (1 - nowRange / 100); points.push([x, dY + y * waveHeight]); ctx.lineTo(x, dY + y * waveHeight); } //封闭路径 ctx.lineTo(axisLength, mH); ctx.lineTo(sX, mH); ctx.lineTo(points[0][0], points[0][1]); ctx.fillStyle = bgColor; ctx.fill(); ctx.restore(); }; //写百分比文本函数 var drawText = function () { if (hideText) return; ctx.save(); var size = 0.4 * cR; ctx.font = size + "px Microsoft Yahei"; ctx.textAlign = "center"; ctx.fillStyle = color; //百分比文字 ctx.fillText(nowRange + "%", r, r + size / 2); ctx.restore(); }; var render = function () { ctx.clearRect(0, 0, mW, mH); if (IsdrawCircled == false) { drawCircle(); } drawSin(xOffset); drawText(); xOffset += speed; requestAnimationFrame(render); }; render(); }