
前言
在"海风日记"的日历页中,月历网格使用 Grid 组件实现,通过 7 列模板、日期占位算法和条件渲染,实现了完整的月历展示功能。
本文将从 CalendarTab.ets 源码出发,深入讲解 Grid 构建月历的实现,包括列模板配置、日期偏移计算和条件渲染。
一、月历网格实现
1.1 基本布局
typescript
Grid() {
// 空白填充(月份第一天的偏移)
ForEach(this.createPlaceholderArray(this.getFirstDayOfMonth()), (i) => {
GridItem() {
Column().width('100%').height(52)
}
})
// 日期格子
ForEach(this.createDayArray(this.getDaysInMonth()), (day) => {
GridItem() {
// 日期内容
}
})
}
.columnsTemplate('1fr 1fr 1fr 1fr 1fr 1fr 1fr') // 7 列
.rowsGap(0)
.columnsGap(0)
二、日期计算工具函数
2.1 获取当月天数
typescript
private getDaysInMonth(year: number, month: number): number {
return new Date(year, month + 1, 0).getDate()
}
2.2 获取当月第一天是星期几
typescript
private getFirstDayOfMonth(year: number, month: number): number {
return new Date(year, month, 1).getDay() // 0=Sunday, 1=Monday...
}
2.3 数组生成函数
typescript
// 生成 1..count 的数字数组
private createDayArray(count: number): number[] {
const result: number[] = []
for (let i = 1; i <= count; i++) { result.push(i) }
return result
}
// 生成 0..count-1 的占位数组
private createPlaceholderArray(count: number): number[] {
const result: number[] = []
for (let i = 0; i < count; i++) { result.push(i) }
return result
}
三、日期占位算法
3.1 算法原理
假设 2025年4月1日是星期二(getDay() = 2)
需要 2 个空白占位格(星期日、星期一)
Grid 7列:
| 空 | 空 | 1 | 2 | 3 | 4 | 5 |
| 6 | 7 | 8 | 9 | 10 | 11 | 12 |
| 13 | 14 | 15 | 16 | 17 | 18 | 19 |
| 20 | 21 | 22 | 23 | 24 | 25 | 26 |
| 27 | 28 | 29 | 30 | | | |
3.2 完整实现
typescript
Grid() {
// 空白填充
ForEach(
this.createPlaceholderArray(this.getFirstDayOfMonth(this.curYear, this.curMonth)),
(i: number) => {
GridItem() {
Column().width('100%').height(52)
}
},
(i: number) => `placeholder_${i}`
)
// 日期格子
ForEach(
this.createDayArray(this.getDaysInMonth(this.curYear, this.curMonth)),
(day: number) => {
GridItem() {
// 日期内容
}
},
(day: number) => `day_${day}`
)
}
.columnsTemplate('1fr 1fr 1fr 1fr 1fr 1fr 1fr')
四、常见问题
4.1 日期对不齐
问题:日期数字与星期标题行不对齐。
原因 :getFirstDayOfMonth() 返回值与星期标题行不匹配。
解决方案 :确保星期标题行从星期日开始:['日','一','二','三','四','五','六']。
总结
本文通过"海风日记"的日历页,深入讲解了 Grid 构建月历的实现:
- 7 列模板 :
'1fr 1fr 1fr 1fr 1fr 1fr 1fr' - 日期计算:getDaysInMonth、getFirstDayOfMonth
- 占位算法:createPlaceholderArray
- 键值管理 :
placeholder_${i}和day_${day}
下一篇文章将深入讲解 日期计算工具函数,敬请期待。
如果这篇文章对你有帮助,欢迎点赞👍、收藏⭐、关注🔔,你的支持是我持续创作的动力!
相关资源:
- Grid 组件文档
- Date 对象文档
- ForEach 文档
- 海风日记项目源码
- HarmonyOS 开发者官网(https://atomgit.com/openharmony/docs
- 开源鸿蒙跨平台社区