效果图
//wxml
<view class='radar-container'>
<canvas class='radarCanvas' canvas-id='radarCanvas' style='width:360px'></canvas>
</view>
//wcss
.radar-container {
width: 100%;
height: 260px;
display: flex;
justify-content: center;
align-items: center;
position: relative;
}
.radarCanvas {
height: 240px;
margin: 0 auto;
position: absolute;
}
js数据初始化 (没写在data中)
let radCtx = wx.createCanvasContext("radarCanvas");//雷达图
let radar = {
mW: 360,//canvas宽
mH: 240,//canvas高
mCenter: 180, //中心点
hCenter: 120, //中心点
mAngle: Math.PI * 2 / 6,//角度
mRadius: 90, //半径(减去的值用于给绘制的文本留空间)
radarData: [["社会型(S)", 58], ["艺术型(A)", 30], ["研究型(I)", 66], ["现实型(R)", 70], ["常规型(C)", 65], ["企业型(E)", 88]],//数据
};
(1)绘制6条边
// 绘制6条边
drawEdge() {
radCtx.setStrokeStyle("#eee");
for (let i = 0; i < 3; i++) {
//计算半径
radCtx.beginPath();
let rdius = radar.mRadius / 3 * (i + 1) - 0;
//画6条线段
for (let j = 0; j < 6; j++) {
//坐标
let x = radar.mCenter + rdius * Math.sin(radar.mAngle * j);
let y = radar.hCenter + rdius * Math.cos(radar.mAngle * j);
radCtx.lineTo(x, y);
}
radCtx.closePath()
radCtx.stroke()
}
},
(2)绘制连接点
// 绘制连接点
drawLinePoint() {
for (let k = 0; k < 6; k++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * k);
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * k);
radCtx.moveTo(radar.mCenter, radar.hCenter);
radCtx.lineTo(x, y);
}
radCtx.stroke();
},
(3)绘制数据区域(数据和填充颜色)
drawRegion(mData, color) {
radCtx.beginPath();
for (let m = 0; m < 6; m++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * m) * mData[m][1] / 100;
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * m) * mData[m][1] / 100;
radCtx.lineTo(x, y);
}
radCtx.closePath();
radCtx.setFillStyle(color)
radCtx.fill();
},
(4)绘制文字
//绘制文字
drawTextCans(mData) {
radCtx.setFillStyle("#555")
radCtx.setFontSize(12) //设置字体
for (let n = 0; n < 6; n++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * n);
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * n);
//通过不同的位置,调整文本的显示位置
if (n == 0) {
radCtx.fillText(mData[0][0], x - 23, y + 20);
} else if (n == 1) {
radCtx.fillText(mData[1][0], x + 10, y + 5);
} else if (n == 2) {
radCtx.fillText(mData[2][0], x + 10, y + 5);
} else if (n == 3) {
radCtx.fillText(mData[3][0], x - 23, y - 10);
} else if (n == 4) {
radCtx.fillText(mData[4][0], x - 55, y + 5);
} else if (n == 5) {
radCtx.fillText(mData[5][0], x - 55, y + 5);
}
}
},
(5)画点
//画点
drawCircle(mData, color) {
const r = 5; //设置节点小圆点的半径
for (let i = 0; i < 6; i++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * i) * mData[i][1] / 100;
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * i) * mData[i][1] / 100;
radCtx.beginPath();
radCtx.arc(x, y, r, 0, Math.PI * 2);
radCtx.fillStyle = color;
radCtx.fill();
}
}
完整代码
let radCtx = wx.createCanvasContext("radarCanvas");//雷达图
let radar = {
mW: 360,//
mH: 240,
mCenter: 180, //中心点
hCenter: 120, //中心点
mAngle: Math.PI * 2 / 6,
mRadius: 90, //半径(减去的值用于给绘制的文本留空间)
radarData: [["社会型(S)", 58], ["艺术型(A)", 30], ["研究型(I)", 66], ["现实型(R)", 70], ["常规型(C)", 65], ["企业型(E)", 88]],
};
Page({
onReady() {
this.drawRadar();//雷达图
},
// ***************************雷达图开始**********************************
// 雷达图
drawRadar() {
const radarData = radar.radarData;
this.drawEdge() //画六边形
this.drawLinePoint()
this.drawRegion(radarData, 'rgba(51, 136, 255, 0.4)') //设置数据
this.drawTextCans(radarData)//设置文本数据
this.drawCircle(radarData, '#3388FF')//设置节点
radCtx.draw()//开始绘制
},
// 绘制6条边
drawEdge() {
radCtx.setStrokeStyle("#eee");
for (let i = 0; i < 3; i++) {
//计算半径
radCtx.beginPath();
let rdius = radar.mRadius / 3 * (i + 1) - 0;
//画6条线段
for (let j = 0; j < 6; j++) {
//坐标
let x = radar.mCenter + rdius * Math.sin(radar.mAngle * j);
let y = radar.hCenter + rdius * Math.cos(radar.mAngle * j);
radCtx.lineTo(x, y);
}
radCtx.closePath()
radCtx.stroke()
}
},
// 绘制连接点
drawLinePoint() {
for (let k = 0; k < 6; k++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * k);
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * k);
radCtx.moveTo(radar.mCenter, radar.hCenter);
radCtx.lineTo(x, y);
}
radCtx.stroke();
},
//绘制数据区域(数据和填充颜色)
drawRegion(mData, color) {
radCtx.beginPath();
for (let m = 0; m < 6; m++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * m) * mData[m][1] / 100;
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * m) * mData[m][1] / 100;
radCtx.lineTo(x, y);
}
radCtx.closePath();
radCtx.setFillStyle(color)
radCtx.fill();
},
//绘制文字
drawTextCans(mData) {
radCtx.setFillStyle("#555")
radCtx.setFontSize(12) //设置字体
for (let n = 0; n < 6; n++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * n);
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * n);
//通过不同的位置,调整文本的显示位置
if (n == 0) {
radCtx.fillText(mData[0][0], x - 23, y + 20);
} else if (n == 1) {
radCtx.fillText(mData[1][0], x + 10, y + 5);
} else if (n == 2) {
radCtx.fillText(mData[2][0], x + 10, y + 5);
} else if (n == 3) {
radCtx.fillText(mData[3][0], x - 23, y - 10);
} else if (n == 4) {
radCtx.fillText(mData[4][0], x - 55, y + 5);
} else if (n == 5) {
radCtx.fillText(mData[5][0], x - 55, y + 5);
}
}
},
//画点
drawCircle(mData, color) {
const r = 5; //设置节点小圆点的半径
for (let i = 0; i < 6; i++) {
let x = radar.mCenter + radar.mRadius * Math.sin(radar.mAngle * i) * mData[i][1] / 100;
let y = radar.hCenter + radar.mRadius * Math.cos(radar.mAngle * i) * mData[i][1] / 100;
radCtx.beginPath();
radCtx.arc(x, y, r, 0, Math.PI * 2);
radCtx.fillStyle = color;
radCtx.fill();
}
}
// ****************************雷达图结束**********************************
})