173 lines
4.9 KiB
Markdown
173 lines
4.9 KiB
Markdown
# Service 目录绘制服务改造完成总结
|
||
|
||
## 改造目标
|
||
|
||
将所有绘制服务统一使用 `baseDraw.ts` 和 `baseHeaderDraw.ts` 作为基类,提取公共部分并统一 Header 绘制。
|
||
|
||
## 完成的工作
|
||
|
||
### 1. ✅ 统一基础服务类
|
||
|
||
所有绘制服务现在都继承自 `BaseDrawService`(位于 `service/baseDraw.ts`):
|
||
|
||
- ✅ `TextDrawService` - 文字涂色服务
|
||
- ✅ `ShapeDrawService` - 图形涂色服务
|
||
- ✅ `FindWordDrawService` - 找字涂色服务
|
||
- ✅ `WordDrawService` - 田字格练字服务
|
||
|
||
### 2. ✅ 统一 Header 绘制
|
||
|
||
所有服务使用统一的 Header 绘制功能(位于 `service/baseHeaderDraw.ts`):
|
||
|
||
- `drawBaseHeader()` - 完整 Header(包含 Logo、应用名称、标题、副标题)
|
||
- `drawBaseMiniHeader()` - 迷你 Header(简化版本)
|
||
|
||
### 3. ✅ 统一使用逻辑像素
|
||
|
||
所有服务现在使用逻辑像素(尺寸除以3),与数学模块保持一致:
|
||
|
||
- Canvas 尺寸通过 `setPaper()` 统一处理 DPR(device pixel ratio)
|
||
- 所有绘制代码中的硬编码尺寸都已转换为逻辑像素
|
||
- 坐标计算统一使用 `this.canvasWidth` 和 `this.canvasHeight`
|
||
|
||
### 4. ✅ 清理重复代码
|
||
|
||
删除了以下重复方法,统一使用基类实现:
|
||
|
||
- `setPrintConfig()` - 统一在基类中实现
|
||
- `setPaper()` - 统一在基类中实现
|
||
- `clear()` - 统一在基类中实现
|
||
- `drawHeader()` / `drawMiniHeader()` - 统一在基类中实现
|
||
- `drawDivider()` - 统一在基类中实现
|
||
|
||
## 改造详情
|
||
|
||
### TextDrawService
|
||
|
||
**改造内容:**
|
||
|
||
- 继承 `BaseDrawService`
|
||
- 移除自定义的 `setPaper()`, `clear()`, `drawHeader()`, `drawMiniHeader()`
|
||
- 所有尺寸转换为逻辑像素:
|
||
- 半径:80 → 27
|
||
- 字体:72px → 24px, 48px → 16px
|
||
- 边距:80 → 27, 220 → 73
|
||
- 坐标:200 → 67, 304 → 101
|
||
|
||
**关键方法:**
|
||
|
||
- `drawLegend()` - 绘制示例区域
|
||
- `drawContent()` - 绘制内容区域
|
||
|
||
### ShapeDrawService
|
||
|
||
**改造内容:**
|
||
|
||
- 继承 `BaseDrawService`
|
||
- 移除自定义的绘制方法
|
||
- 所有尺寸转换为逻辑像素:
|
||
- 图形大小:200 → 67, 180 → 60
|
||
- 字体:36px → 12px
|
||
- 间距:120 → 40, 160 → 53
|
||
|
||
**关键方法:**
|
||
|
||
- `drawLegend()` - 绘制示例区域
|
||
- `drawContent()` - 绘制内容区域
|
||
|
||
### FindWordDrawService
|
||
|
||
**改造内容:**
|
||
|
||
- 继承 `BaseDrawService`
|
||
- 移除自定义的绘制方法
|
||
- 所有尺寸转换为逻辑像素:
|
||
- 半径:80 → 27
|
||
- 字体:72px → 24px
|
||
- 模板坐标转换:`pos.x / 3`, `pos.y / 3`
|
||
|
||
**关键方法:**
|
||
|
||
- `drawContent()` - 绘制找字内容(中心大字 + 四周字符)
|
||
|
||
**特殊处理:**
|
||
|
||
- `getPositionsFromTemplate()` 函数中增加了坐标转换逻辑,将模板中的原始像素坐标转换为逻辑像素
|
||
|
||
### WordDrawService
|
||
|
||
**改造内容:**
|
||
|
||
- 继承 `BaseDrawService`
|
||
- 移除自定义的绘制方法
|
||
- 所有尺寸转换为逻辑像素:
|
||
- 田字格大小:140 → 47
|
||
- 边距:120 → 40, 50 → 17
|
||
- 间距:24 → 8, 36 → 12
|
||
|
||
**关键方法:**
|
||
|
||
- `drawLayout()` - 绘制页眉和基础布局
|
||
- `drawContent()` - 绘制田字格和练字内容
|
||
- `drawPracticeContent()` - 绘制练习内容
|
||
- `getMaxGridLayout()` - 计算最大网格布局
|
||
|
||
## 架构优势
|
||
|
||
1. ✅ **代码复用**:公共逻辑集中在 `BaseDrawService` 基类中
|
||
2. ✅ **统一 Header**:所有服务使用相同的 Header 绘制逻辑
|
||
3. ✅ **统一像素标准**:所有服务使用逻辑像素,保持一致
|
||
4. ✅ **易于维护**:修改 Header 或基础功能只需修改一个地方
|
||
5. ✅ **类型安全**:TypeScript 类型支持完整
|
||
|
||
## 注意事项
|
||
|
||
### 坐标转换
|
||
|
||
所有硬编码的尺寸值都已转换为逻辑像素(除以3):
|
||
|
||
```typescript
|
||
// 原始像素 → 逻辑像素
|
||
const radius = 27; // 80/3≈27
|
||
const fontSize = 24; // 72/3=24
|
||
const margin = 40; // 120/3=40
|
||
```
|
||
|
||
### 模板坐标转换
|
||
|
||
`FindWordDrawService` 中使用的 `POSITION_TEMPLATES` 坐标是基于原始像素的,需要在使用时转换:
|
||
|
||
```typescript
|
||
const x = centerX + pos.x / 3; // 转换为逻辑像素
|
||
const y = centerY + pos.y / 3; // 转换为逻辑像素
|
||
```
|
||
|
||
### Canvas 尺寸
|
||
|
||
所有服务现在统一使用:
|
||
|
||
- `this.canvasWidth` - 逻辑像素宽度
|
||
- `this.canvasHeight` - 逻辑像素高度
|
||
|
||
这些值在 `setPaper()` 中设置,已经处理了 DPR。
|
||
|
||
## 向后兼容性
|
||
|
||
- ✅ `drawServiceFactory.ts` 接口无需修改
|
||
- ✅ 所有服务的公共接口保持不变
|
||
- ✅ 只改变了内部实现方式
|
||
|
||
## 后续优化建议
|
||
|
||
1. 可以考虑将 `findWordTemplate.ts` 中的坐标模板也转换为逻辑像素,避免运行时转换
|
||
2. 可以考虑创建更多的基础绘制工具函数(如绘制表格、绘制网格等)
|
||
3. 可以考虑支持更多 Paper 尺寸(目前仅支持 A4)
|
||
|
||
## 测试建议
|
||
|
||
1. 验证所有绘制服务功能正常
|
||
2. 验证 Header 正确显示
|
||
3. 验证尺寸和比例正确
|
||
4. 验证不同 Header 类型(wechat, LogoImage, noLogoImage, minimal)
|
||
5. 验证打印输出质量
|