import CountMatchDraw from '../shared/service/countMatchDraw'; import NumberColorDraw from '../shared/service/numberColorDraw'; import { createMathPage, CanvasDataState, } from '../shared/common/mathPageMixin'; createMathPage({ canvas: null as Canvas | null, ctx: null as RenderingContext | null, boxHeight: 0, boxWidth: 0, drawService: null as CountMatchDraw | NumberColorDraw | null, matchData: null as { leftNumbers: number[]; rightNumbers: number[]; } | null, colorData: null as { numbers: number[]; } | null, data: { pageTitle: '数一数,连一连', functionId: '', hasContent: false, showShareDialog: false, showTypeSelector: true, // 控制是否显示类型选择器 currentMode: 'twelve-animals', // 'twelve-animals' 或 'fruits' 或 'circle' 或 'caterpillar' currentModeName: '十二生肖', typeActions: [ { name: '十二生肖', value: 'twelve-animals' }, { name: '水果', value: 'fruits' }, ], } as CanvasDataState & { showTypeSelector: boolean; currentMode: string; currentModeName: string; typeActions: Array<{ name: string; value: string }>; }, onLoad(options: { id?: string; mode?: string }) { const functionId = options.id || 'counting-matching'; this.initPageInfo(functionId, '数一数,连一连'); // 根据 functionId 设置不同的类型选择器 if (functionId === 'number-coloring') { const currentMode = options.mode || 'caterpillar'; this.setData({ currentMode: currentMode, currentModeName: currentMode === 'caterpillar' ? '毛毛虫' : '圆圈', typeActions: [ { name: '毛毛虫', value: 'caterpillar' }, { name: '圆圈', value: 'circle' }, ], }); } else { const currentMode = options.mode || 'twelve-animals'; this.setData({ currentMode, currentModeName: currentMode === 'twelve-animals' ? '十二生肖' : '水果', typeActions: [ { name: '十二生肖', value: 'twelve-animals' }, { name: '水果', value: 'fruits' }, ], }); } }, onReady() { this.initCanvas({ createDrawService: ( canvas: Canvas, ctx: RenderingContext, options?: Record, ) => { // 根据 functionId 创建不同的绘制服务 if (this.data.functionId === 'number-coloring') { return new NumberColorDraw(canvas, ctx, options); } else { return new CountMatchDraw(canvas, ctx, options); } }, drawServiceOptions: { subTitle: this.data.functionId === 'number-coloring' ? '按数字给相应的圆圈涂上颜色' : '通过连线配对数字和对应的数量图形', }, onCanvasReady: () => { // 初始随机生成 this.onRandom(); }, }); }, /** * 绘制Canvas内容 */ async drawCanvas() { if (!this.ctx || !this.drawService) { return; } try { if (this.data.functionId === 'number-coloring') { if (!this.colorData) { return; } await (this.drawService as NumberColorDraw).draw( this.colorData, this.data.currentMode, ); } else { if (!this.matchData) { return; } await (this.drawService as CountMatchDraw).draw( this.matchData, this.data.currentMode, ); } this.setData({ hasContent: true }); } catch (error) { console.error('绘制失败:', error); this.setData({ hasContent: false }); } }, /** * 随机生成 */ onRandom() { if (this.data.functionId === 'number-coloring') { // 按数字涂颜色模式:生成6个随机数字(1-10) const availableNumbers = Array.from( { length: 10 }, (_, i) => i + 1, ); const numbers: number[] = []; for (let i = 0; i < 6; i++) { const randomIndex = Math.floor( Math.random() * availableNumbers.length, ); const number = availableNumbers.splice(randomIndex, 1)[0]; numbers.push(number); } this.colorData = { numbers }; } else { // 数一数连一连模式:生成5个不同的数字(1-10) const availableNumbers = Array.from( { length: 10 }, (_, i) => i + 1, ); const leftNumbers: number[] = []; for (let i = 0; i < 5; i++) { const randomIndex = Math.floor( Math.random() * availableNumbers.length, ); const number = availableNumbers.splice(randomIndex, 1)[0]; leftNumbers.push(number); } // 复制数字数组并打乱顺序,作为右侧显示的数字 const rightNumbers = [...leftNumbers]; for (let i = rightNumbers.length - 1; i > 0; i--) { const j = Math.floor(Math.random() * (i + 1)); [rightNumbers[i], rightNumbers[j]] = [ rightNumbers[j], rightNumbers[i], ]; } this.matchData = { leftNumbers, rightNumbers }; } this.drawCanvas(); }, /** 选择类型 */ onSelectType(event: any) { const { name, value } = event.detail; this.setData({ currentMode: value, currentModeName: name, }); // 重新生成数据 this.onRandom(); }, });