feat: 绘制Header和Legend
This commit is contained in:
@@ -0,0 +1,121 @@
|
||||
import { PAPER_SIZE } from './constant';
|
||||
|
||||
class TextDrawService {
|
||||
canvas: WechatMiniprogram.Canvas;
|
||||
ctx: RenderingContext;
|
||||
options: Record<string, any>;
|
||||
paperSize: PaperSize;
|
||||
currentX: number;
|
||||
currentY: number;
|
||||
|
||||
constructor(canvas: Canvas, ctx: RenderingContext, options?: Record<string, any>) {
|
||||
this.canvas = canvas;
|
||||
this.ctx = ctx;
|
||||
this.paperSize = 'A4';
|
||||
this.options = {
|
||||
title: '找一找 涂 色',
|
||||
radius: 80,
|
||||
colors: ['#2196F3', '#FFEB3B', '#FF9800', '#F44336'],
|
||||
characters: ['鱼', '鸟', '猫', '狗'],
|
||||
...options,
|
||||
};
|
||||
this.currentX = 0;
|
||||
this.currentY = 0;
|
||||
}
|
||||
|
||||
draw() {
|
||||
this.setPaper();
|
||||
this.drawHeader();
|
||||
this.drawLegend();
|
||||
}
|
||||
|
||||
drawHeader() {
|
||||
const { canvas, ctx } = this;
|
||||
const { title } = this.options;
|
||||
|
||||
ctx.font = 'bold 80px "Microsoft Yahei"';
|
||||
ctx.fillStyle = '#333';
|
||||
ctx.textAlign = 'center';
|
||||
const titleX = canvas.width / 2;
|
||||
const titleY = 120;
|
||||
ctx.fillText(title, titleX, titleY);
|
||||
|
||||
// 记录当前X、Y坐标
|
||||
this.currentX = titleX;
|
||||
this.currentY = titleY + 50;
|
||||
// 绘制分割线
|
||||
this.drawLine(this.currentY);
|
||||
}
|
||||
|
||||
// 绘制示例
|
||||
drawLegend() {
|
||||
const { ctx, options } = this;
|
||||
const { colors, characters, radius } = options;
|
||||
const startX = (this.canvas.width - colors.length * 400) / 2; // 计算起始X坐标以居中
|
||||
this.currentY = this.currentY + radius + 50; // radius 为圆的半径,再加上离线的边距为50
|
||||
const startY = this.currentY; // 设置起始Y坐标
|
||||
|
||||
ctx.moveTo(startX, startY);
|
||||
colors.forEach((color: string, index: number) => {
|
||||
const x = startX + index * 500; // 计算每个圆的X坐标
|
||||
const y = startY; // 计算圆的Y坐标
|
||||
|
||||
// 绘制圆
|
||||
ctx.beginPath();
|
||||
ctx.arc(x, y, radius, 0, Math.PI * 2);
|
||||
ctx.fillStyle = color;
|
||||
ctx.fill();
|
||||
ctx.fillStyle = '#333';
|
||||
ctx.stroke();
|
||||
ctx.closePath();
|
||||
|
||||
// 绘制长方形
|
||||
ctx.fillStyle = '#fff'; // 长方形背景色
|
||||
ctx.strokeStyle = '#333';
|
||||
ctx.lineWidth = 4;
|
||||
const rectangleX = x - 120; // 计算字符X坐标
|
||||
const rectangleY = y + radius + 40; // 计算字符Y坐标
|
||||
ctx.strokeRect(rectangleX, rectangleY, 240, 100); // 绘制长方形
|
||||
// ctx.fillRect(x - 75, y + 10, 240, 100); // 填充长方形
|
||||
|
||||
// 绘制字符
|
||||
ctx.fillStyle = '#333';
|
||||
ctx.font = 'bold 60px "Microsoft Yahei"';
|
||||
ctx.textAlign = 'center';
|
||||
ctx.fillText(characters[index], rectangleX + 120, rectangleY + 70);
|
||||
this.currentY = rectangleY + 100; // 100会矩形宽度
|
||||
});
|
||||
|
||||
this.currentY = this.currentY + 50; // 计算分割线的Y坐标,距离示例图20px
|
||||
this.drawLine(this.currentY);
|
||||
}
|
||||
|
||||
drawLine(linY: number) {
|
||||
const { canvas, ctx } = this;
|
||||
|
||||
ctx.strokeStyle = '#333';
|
||||
ctx.lineWidth = 4;
|
||||
ctx.beginPath();
|
||||
ctx.moveTo(20, linY);
|
||||
ctx.lineTo(canvas.width - 20, linY);
|
||||
ctx.stroke();
|
||||
}
|
||||
|
||||
setPaper() {
|
||||
const ctx = this.ctx;
|
||||
const { width, height } = PAPER_SIZE[this.paperSize];
|
||||
this.canvas.width = width;
|
||||
this.canvas.height = height;
|
||||
|
||||
this.clear();
|
||||
ctx.fillStyle = '#fff'; // 设置背景色为白色
|
||||
ctx.fillRect(0, 0, width, height);
|
||||
}
|
||||
|
||||
clear() {
|
||||
const canvas = this.canvas;
|
||||
this.ctx.clearRect(0, 0, canvas.width, canvas.height);
|
||||
}
|
||||
}
|
||||
|
||||
export default TextDrawService;
|
||||
Reference in New Issue
Block a user