import { BaseDrawService } from '../../../core/draw/baseDraw'; import { drawNumberPreview } from './numberPreviewDraw'; import { drawNumberWriteContent } from './numberWriteDraw'; /** * 数字涂色绘制服务 * 组合使用基础绘制服务、预览区域绘制服务和内容区域绘制服务 */ class NumberFindDraw extends BaseDrawService { selectedNumber: number; functionId: string; // 功能ID,用于判断绘制类型 constructor( canvas: Canvas, ctx: RenderingContext, options?: Record, ) { super(canvas, ctx, options); this.selectedNumber = 0; this.functionId = options?.functionId || 'number-find'; } async draw(selectedNumber: number) { if (selectedNumber <= 0 || selectedNumber > 10) { return; } this.selectedNumber = selectedNumber; this.prepareDraw(); await this.drawHeaderAndDivider(); // 绘制预览区域 await drawNumberPreview({ canvas: this.canvas, ctx: this.ctx, selectedNumber: this.selectedNumber, canvasWidth: this.canvasWidth, startY: this.currentY, onDrawn: (currentY) => { this.currentY = currentY; }, }); // 绘制内容区域(根据 functionId 选择不同的绘制方法) this.drawDivider(); if (this.functionId === 'number-write') { // 书写类型:绘制书写行 drawNumberWriteContent({ ctx: this.ctx, selectedNumber: this.selectedNumber, canvasWidth: this.canvasWidth, startY: this.currentY, }); } else { // 默认类型(number-find):绘制数字涂色内容 this.drawNumberContent({ ctx: this.ctx, selectedNumber: this.selectedNumber, canvasWidth: this.canvasWidth, startY: this.currentY, }); } } /** * 绘制数字涂色内容区域 */ private drawNumberContent(params: { ctx: RenderingContext; selectedNumber: number; canvasWidth: number; startY: number; }): void { const { ctx, selectedNumber, canvasWidth, startY } = params; const rows = 6; const radius = 26; // 约26.67 const fontSize = 24; // 24 const startYPos = startY + 10 + radius; // 约47.33 const startX1 = 100 + radius; // 约112.22 const startX2 = 60 + radius; // 约75.56 const spaceWidthFirst = (canvasWidth - startX1 * 2) / (5 - 1); const spaceWidthSecond = (canvasWidth - startX2 * 2) / (6 - 1); const spaceHeight = 18; // 18 ctx.moveTo(startX1, startYPos); for (let i = 0; i < rows; i++) { const cols = i % 2 === 0 ? 5 : 6; for (let j = 0; j < cols; j++) { const y = startYPos + i * (spaceHeight + radius * 2); const x = i % 2 === 0 ? startX1 + j * spaceWidthFirst : startX2 + j * spaceWidthSecond; // 随机生成1-10的数字,但确保包含选中的数字 let number: number; if (i === 0 && j === 0) { // 第一个位置固定为选中的数字 number = selectedNumber; } else { // 其他位置随机,但增加选中数字出现的概率 const random = Math.random(); if (random < 0.3) { // 30%概率是选中的数字 number = selectedNumber; } else { // 70%概率是其他随机数字 number = Math.floor(Math.random() * 10) + 1; } } // 绘制圆形背景(线宽除以3) ctx.fillStyle = '#fff'; ctx.strokeStyle = '#000'; ctx.lineWidth = 1; // 约1.33 ctx.beginPath(); ctx.arc(x, y, radius, 0, Math.PI * 2); ctx.fill(); ctx.stroke(); ctx.closePath(); // 绘制数字(字体大小除以3) ctx.fillStyle = '#333'; ctx.font = `bold ${fontSize}px "Microsoft Yahei"`; ctx.textBaseline = 'middle'; ctx.textAlign = 'center'; ctx.fillText(String(number), x, y, radius * 2); } } } } export default NumberFindDraw;