let c = document.getElementById("myc");
let ctx = c.getContext("2d");
// 随机值记录
let randomRes = [0, 0, 0, 0, 0, 0];
//const randomRes = [3, 0, 0, 0, 0, 0];
// 颜色值
let COLOR_INIT = "#737373";
// 单个梯形高度
let onceHeight = 30;
// 声明画布大小,及窗口文档的显示区的高度和宽度,以像素记
c.width = 600;
c.height = 600;
// 将坐标原点移至画布中心
ctx.translate(c.width/2,c.height/2);
// r多边形半径,n多边形个数,deg:多边形与夹角的度数,layerCount:多边形层数
let r=onceHeight, n=6, deg=360/n, layerCount=4;
// 初始坐标点
let prevPoint = {x: 0, y: r};
// 初始渐变色层级点
let prevLinearPoint = {x: 0, y: 0};
// 渐变色坐标点记录
let linearPointArray = [];
// 指数结果坐标点记录
let randomResPoint = [];
// 上一个结果组
let prevRandomRes = [];
var mmm = ["CB2329", "1853B7", "C3253A", "7C0A20"];
var mmmmm = 0;
setInterval(() => {
mmmmm === mmm.length && (mmmmm = 0);
console.log(mmm[mmmmm++])
setResult([getRandom(), getRandom(), getRandom(), getRandom(), getRandom(), getRandom()], ["粒子1", "粒子2", "粒子3", "粒子4", "粒子5", "粒子6"], mmm[mmmmm++]);
}, 1500)
/**
* 设置结果
* @param(randomResArr) array[int] 比例值 0-4
* @param(textArr) array[string] 文字说明
* @param(colorHex) string Hex基准颜色
*/
function setResult(randomResArr, textArr, colorHex) {
COLOR_INIT = colorHex;
prevRandomRes = randomRes;
randomRes = randomResArr;
var timer = setInterval(() => {
drawStatistics(textArr);
console.log("run");
}, 16);
// 偷个懒
setTimeout(() => {
clearInterval(timer);
}, 600);
}
function drawBg (textArr) {
r = onceHeight;
prevPoint = {x: 0, y: r};
prevLinearPoint = {x: 0, y: 0};
linearPointArray = [];
randomResPoint = []; // 指数坐标点记录
// 多边形线的颜色
ctx.strokeStyle="#fff";
// 多边形线的宽度
ctx.lineWidth=1;
ctx.globalAlpha = 1;
ctx.globalCompositeOperation="destination-over";
// 绘制多个线段
for(let j=0;j<=layerCount;j++){
// 恢复初始坐标点
prevPoint = {x: 0, y: r};
// 临时坐标变量
let temporary = {};
for(let i=1;i<=n;i++){
let currentLinearPoint = {x: angleDistance(r)*Math.sin(getrad((i*2-1)*(deg/2))), y: angleDistance(r)*Math.cos((i*2-1)*getrad(deg/2))};
let prevPointTemporary = {x: prevPoint.x, y: prevPoint.y};
let grd = null;
try {
grd = ctx.createLinearGradient(linearPointArray[j-1][i-1].x, linearPointArray[j-1][i-1].y, currentLinearPoint.x, currentLinearPoint.y);
} catch (err) {
grd = ctx.createLinearGradient(0, 0, currentLinearPoint.x, currentLinearPoint.y);
}
linearPointArray[j] ? linearPointArray[j].push({x: currentLinearPoint.x, y: currentLinearPoint.y}) : linearPointArray[j] = [{x: currentLinearPoint.x, y: currentLinearPoint.y}];
grd.addColorStop(0, getLightColor(COLOR_INIT, 0.6));
grd.addColorStop(1, getLightColor(COLOR_INIT, 0.9));
ctx.fillStyle = grd;
// 开始路径
ctx.beginPath();
ctx.moveTo(0,0);
ctx.lineTo(prevPoint.x, prevPoint.y);
prevPoint = {x: r*Math.sin(getrad(i*deg)), y: r*Math.cos(i*getrad(deg))};
ctx.lineTo(prevPoint.x, prevPoint.y);
// 结束路径
ctx.closePath();
// 绘制线段
ctx.stroke();
// 填充
ctx.fill();
switch (i) {
case 1:
if (j === randomRes[0]) {
temporary = {index: 1, x: prevPoint.x, y: prevPoint.y};
randomResPoint.push(temporary);
}
if (j === 4) {
ctx.beginPath();
ctx.fillStyle = "#333";
ctx.textBaseline = "top";
ctx.textAlign = "center";
ctx.fillText(textArr[0], prevPointTemporary.x, prevPointTemporary.y);
ctx.closePath();
}
break;
case 2:
if (j === randomRes[1]) {
temporary = {index: 2, x: prevPoint.x, y: prevPoint.y};
randomResPoint.push(temporary);
}
if (j === 4) {
ctx.beginPath();
ctx.fillStyle = "#333";
ctx.textBaseline = "middle";
ctx.textAlign = "left";
ctx.fillText(textArr[1], prevPointTemporary.x, prevPointTemporary.y);
ctx.closePath();
}
break;
case 3:
if (j === randomRes[2]) {
temporary = {index: 3, x: prevPoint.x, y: prevPoint.y};
randomResPoint.push(temporary);
}
if (j === 4) {
ctx.beginPath();
ctx.fillStyle = "#333";
ctx.textBaseline = "middle";
ctx.textAlign = "left";
ctx.fillText(textArr[2], prevPointTemporary.x, prevPointTemporary.y);
ctx.closePath();
}
break;
case 4:
if (j === randomRes[3]) {
temporary = {index: 4, x: prevPoint.x, y: prevPoint.y};
randomResPoint.push(temporary);
}
if (j === 4) {
ctx.beginPath();
ctx.fillStyle = "#333";
ctx.textBaseline = "bottom";
ctx.textAlign = "center";
ctx.fillText(textArr[3], prevPointTemporary.x, prevPointTemporary.y);
ctx.closePath();
}
break;
case 5:
if (j === randomRes[4]) {
temporary = {index: 5, x: prevPoint.x, y: prevPoint.y};
randomResPoint.push(temporary);
}
if (j === 4) {
ctx.beginPath();
ctx.fillStyle = "#333";
ctx.textBaseline = "middle";
ctx.textAlign = "right";
ctx.fillText(textArr[4], prevPointTemporary.x, prevPointTemporary.y);
ctx.closePath();
}
break;
case 6:
if (j === randomRes[5]) {
temporary = {index: 6, x: prevPoint.x, y: prevPoint.y};
randomResPoint.push(temporary);
}
if (j === 4) {
ctx.beginPath();
ctx.fillStyle = "#333";
ctx.textBaseline = "middle";
ctx.textAlign = "right";
ctx.fillText(textArr[5], prevPointTemporary.x, prevPointTemporary.y);
ctx.closePath();
}
break;
default :
}
}
// 递增层级半径
r += onceHeight;
}
}
function drawStatistics(textArr) {
ctx.clearRect(-c.width / 2, -c.height / 2, c.width * 2, c.height * 2); // 清除画布
// 画背景
drawBg (textArr);
// 画结果图
let grdRadial=ctx.createRadialGradient(0,0,0,0,0,r);
grdRadial.addColorStop(0,getLightColor(COLOR_INIT, 0.6));
grdRadial.addColorStop(1,getDarkColor(COLOR_INIT, 0.3));
// ctx.translate(c.width/2,c.height/2);
ctx.globalCompositeOperation="source-over";
ctx.lineWidth=2;
ctx.strokeStyle=getLightColor(COLOR_INIT, 0.5);
ctx.beginPath();
ctx.fillStyle = grdRadial;
ctx.globalAlpha = 0.8;
let result = randomResPoint.sort((a, b) => (a.index - b.index));
for(let randomIdx=0; randomIdx<result.length; randomIdx++) {
let currentIncremnet = 0;
if (prevRandomRes.length) {
prevRandomRes[randomIdx] += (randomRes[randomIdx] - prevRandomRes[randomIdx]) / 10;
}
randomIdx === 0 ? ctx.moveTo(
prevRandomRes.length ? 0 : result[randomIdx].x,
prevRandomRes.length ? (prevRandomRes[randomIdx]+1)*onceHeight : result[0].y
) : ctx.lineTo(
prevRandomRes.length ? ((prevRandomRes[randomIdx]+1)*onceHeight)*Math.sin(getrad(randomIdx*deg)) : result[randomIdx].x,
prevRandomRes.length ? ((prevRandomRes[randomIdx]+1)*onceHeight)*Math.cos(randomIdx*getrad(deg)) : result[randomIdx].y
);
}
ctx.closePath();
ctx.stroke();
ctx.fill();
}
console.log("randomRes", randomRes);
console.log(randomResPoint);
// 封装求弧度的方法 度->弧度
function getrad(deg){
return deg/180*Math.PI;
}
// 封装计算渐变色倾斜角度
function angleDistance(rAngle) {
return rAngle*Math.cos(getrad(deg/2));
}
// 获取随机指数
function getRandom() {
return Math.floor(Math.random() * 5)
}
// hex颜色转rgb颜色
function HexToRgb (str) {
var r = /^#?[0-9A-F]{6}$/;
// test方法检查在字符串中是否存在一个模式,如果存在则返回true,否则返回false
if (!r.test(str)) return window.alert("输入错误的hex");
// replace替换查找的到的字符串
str = str.replace("#", "");
// match得到查询数组
var hxs = str.match(/../g);
// alert('bf:'+hxs)
for (var i = 0; i < 3; i++) hxs[i] = parseInt(hxs[i], 16);
// alert(parseInt(80, 16))
// console.log(hxs);
return hxs;
}
// GRB颜色转Hex颜色
function RgbToHex (a, b, c) {
var r = /^d{1,3}$/;
if (!r.test(a) || !r.test(b) || !r.test(c)) return window.alert("输入错误的rgb颜色值");
var hexs = [a.toString(16), b.toString(16), c.toString(16)];
for (var i = 0; i < 3; i++) if (hexs[i].length == 1) hexs[i] = "0" + hexs[i];
return "#" + hexs.join("");
}
// 得到hex颜色值为color的加深颜色值,level为加深的程度,限0-1之间
function getDarkColor(color, level) {
var r = /^#?[0-9A-F]{6}$/;
if (!r.test(color)) return window.alert("输入错误的hex颜色值");
var rgbc = this.HexToRgb(color);
// floor 向下取整
for (var i = 0; i < 3; i++) rgbc[i] = Math.floor(rgbc[i] * (1 - level));
return this.RgbToHex(rgbc[0], rgbc[1], rgbc[2]);
}
// 得到hex颜色值为color的减淡颜色值,level为加深的程度,限0-1之间
function getLightColor(color, level) {
var r = /^#?[0-9A-F]{6}$/;
if (!r.test(color)) return window.alert("输入错误的hex颜色值");
var rgbc = this.HexToRgb(color);
for (var i = 0; i < 3; i++) rgbc[i] = Math.floor((255 - rgbc[i]) * level + rgbc[i]);
return this.RgbToHex(rgbc[0], rgbc[1], rgbc[2]);
}