// calendar.js const storage = require('../../utils/storage') const dateUtils = require('../../utils/date') Page({ data: { currentYear: 2024, currentMonth: 1, calendarDays: [], monthEvents: [] }, onLoad() { const today = new Date() this.setData({ currentYear: today.getFullYear(), currentMonth: today.getMonth() + 1 }) this.renderCalendar() this.loadMonthEvents() }, /** * 渲染日历 */ renderCalendar() { const { currentYear, currentMonth } = this.data const anniversaries = storage.getAnniversaries() // 获取本月第一天是星期几 const firstDay = new Date(currentYear, currentMonth - 1, 1) const startWeekday = firstDay.getDay() // 获取本月天数 const daysInMonth = new Date(currentYear, currentMonth, 0).getDate() // 获取上个月的天数 const prevMonthDays = new Date(currentYear, currentMonth - 1, 0).getDate() // 构建日历天数数组 const calendarDays = [] const today = new Date() // 填充上个月的日期 for (let i = startWeekday - 1; i >= 0; i--) { const day = prevMonthDays - i calendarDays.push({ day, date: new Date(currentYear, currentMonth - 2, day), isToday: false, isOtherMonth: true, events: [], hasMore: false }) } // 填充本月的日期 for (let day = 1; day <= daysInMonth; day++) { const date = new Date(currentYear, currentMonth - 1, day) const isToday = dateUtils.isToday(date) // 查找该日期的纪念日 const events = anniversaries .filter(a => this.isAnniversaryOnDate(a, date)) .map(a => ({ id: a.id, color: this.getEventColor(a) })) .slice(0, 3) calendarDays.push({ day, date, isToday, isOtherMonth: false, events, hasMore: events.length > 2, moreCount: anniversaries.filter(a => this.isAnniversaryOnDate(a, date)).length - 2 }) } // 填充下个月的日期(补全6行) const remainingDays = 42 - calendarDays.length for (let day = 1; day <= remainingDays; day++) { calendarDays.push({ day, date: new Date(currentYear, currentMonth, day), isToday: false, isOtherMonth: true, events: [], hasMore: false }) } this.setData({ calendarDays }) }, /** * 判断纪念日是否在某日期 */ isAnniversaryOnDate(anniversary, date) { return anniversary.solarYear === date.getFullYear() && anniversary.solarMonth === date.getMonth() + 1 && anniversary.solarDay === date.getDate() }, /** * 获取事件颜色 */ getEventColor(anniversary) { const colors = { high: '#ff5722', medium: '#ff9800', low: '#07c160' } return colors[anniversary.importance] || '#07c160' }, /** * 加载本月事件 */ loadMonthEvents() { const { currentYear, currentMonth } = this.data const persons = storage.getPersons() const anniversaries = storage.getAnniversaries() // 筛选本月纪念日 const monthEvents = anniversaries .filter(a => a.solarYear === currentYear && a.solarMonth === currentMonth) .map(a => { const person = persons.find(p => p.id === a.personId) const date = new Date(currentYear, currentMonth - 1, a.solarDay) const daysUntil = dateUtils.getDaysUntil(date) return { ...a, personName: person ? person.name : '未知', typeIcon: this.getTypeIcon(a.type), typeName: a.customTypeName || this.getTypeName(a.type), dateText: dateUtils.formatDate(date, 'MM月DD日'), daysUntil } }) .sort((a, b) => a.solarDay - b.solarDay) this.setData({ monthEvents }) }, /** * 获取类型图标 */ getTypeIcon(type) { const icons = { birthday: '🎂', lunar_birthday: '🌙', wedding: '💍', engagement: '💕', other: '📅' } return icons[type] || '📅' }, /** * 获取类型名称 */ getTypeName(type) { const names = { birthday: '公历生日', lunar_birthday: '农历生日', wedding: '结婚纪念日', engagement: '订婚纪念日', other: '其他纪念日' } return names[type] || '其他' }, /** * 上一个月 */ onPrevMonth() { let { currentYear, currentMonth } = this.data if (currentMonth === 1) { currentYear-- currentMonth = 12 } else { currentMonth-- } this.setData({ currentYear, currentMonth }) this.renderCalendar() this.loadMonthEvents() }, /** * 下一个月 */ onNextMonth() { let { currentYear, currentMonth } = this.data if (currentMonth === 12) { currentYear++ currentMonth = 1 } else { currentMonth++ } this.setData({ currentYear, currentMonth }) this.renderCalendar() this.loadMonthEvents() }, /** * 回到今天 */ onGoToday() { const today = new Date() this.setData({ currentYear: today.getFullYear(), currentMonth: today.getMonth() + 1 }) this.renderCalendar() this.loadMonthEvents() }, /** * 点击事件 */ onEventTap(e) { const id = e.currentTarget.dataset.id const anniversary = storage.getAnniversaries().find(a => a.id === id) if (anniversary) { wx.navigateTo({ url: `/pages/person-detail/person-detail?id=${anniversary.personId}` }) } } })