/*
|
* @Company: hugeInfo
|
* @Author: ldh
|
* @Date: 2022-08-29 15:35:35
|
* @LastEditTime: 2022-09-08 16:55:04
|
* @LastEditors: ldh
|
* @Version: 1.0.0
|
* @Description: 日历
|
*/
|
import React, { useEffect, useMemo, useState } from 'react';
|
import { LeftArrow2Outlined, RightArrow2Outlined } from 'dd-icons';
|
import { moment, myTimeFormat } from '../../utils/utility';
|
import './index.less';
|
|
/**
|
* time: date | string; // 当前月份时间
|
* activeTime: date | string; // 当前选择日期
|
* onClickDate: func; // 点击日期回调事件
|
* onChangeMonth: func, // 切换月份回调, 返回月份date格式
|
*/
|
const Calendar = ({ time = new Date(), activeTime, onClickDate, onChangeMonth }) => {
|
// 当前选择月份
|
const [nowTime, setNowTime] = useState(myTimeFormat(time, 'YYYY-MM'));
|
|
// 当前点击日期
|
const [activeDate, setActiveDate] = useState({});
|
|
// 当前月份的天数
|
const monthDays = useMemo(() => {
|
let monthDay = [];
|
let thisMonthDays = moment(nowTime).daysInMonth();
|
for (let i = 1; i <= thisMonthDays; i++) {
|
let key = `${nowTime}-${i}`;
|
if (myTimeFormat(`${nowTime}-${i}`, 'YYYY-MM-DD') === myTimeFormat(new Date(), 'YYYY-MM-DD')) {
|
key = 'today';
|
}
|
monthDay.push({ value: 'thisMonth', label: i, key });
|
}
|
// 当前月份第一天星期几
|
let firstDay = new Date(nowTime).getDay();
|
// 上一月,下一个月
|
let beforeMonth = moment(nowTime).add(-1, 'month'),
|
lastMonth = moment(nowTime).add(1, 'month');
|
// 上一个月的天数
|
let beforeMonthDays = moment(beforeMonth).daysInMonth();
|
// 计算上一个月有多少天在今月展示
|
let beforeDay = [];
|
for (let i = beforeMonthDays; i > beforeMonthDays - firstDay; i--) {
|
let key = myTimeFormat(beforeMonth, `YYYY-MM-${i}`);
|
if (myTimeFormat(beforeMonth, `YYYY-MM-${i}`) === myTimeFormat(new Date(), 'YYYY-MM-D')) {
|
key = 'today';
|
}
|
beforeDay = [{ value: 'beforeMonth', label: i, key }, ...beforeDay];
|
}
|
// 计算下一个月有多少天在今月展示
|
let lastDay = [];
|
for (let i = 1; i <= 42 - beforeDay.length - monthDay.length; i++) {
|
let key = myTimeFormat(lastMonth, `YYYY-MM-${i}`);
|
if (myTimeFormat(lastMonth, `YYYY-MM-${i}`) === myTimeFormat(new Date(), 'YYYY-MM-D')) {
|
key = 'today';
|
}
|
lastDay.push({ value: 'lastMonth', label: i, key });
|
}
|
return [...beforeDay, ...monthDay, ...lastDay];
|
}, [nowTime]);
|
|
// 点击上一月,下一月
|
function handleChangeMonth(key) {
|
let time = '';
|
if (key === 'before') {
|
time = moment(nowTime).add(-1, 'month');
|
} else {
|
time = moment(nowTime).add(1, 'month');
|
}
|
setNowTime(myTimeFormat(time, 'YYYY-MM'));
|
!!onChangeMonth && onChangeMonth(key, time);
|
}
|
|
// 点击日期
|
function handleClickDate(item) {
|
|
if (item.value === 'beforeMonth') {
|
handleChangeMonth('before');
|
}
|
if (item.value === 'lastMonth') {
|
handleChangeMonth('next');
|
}
|
setActiveDate(item);
|
!!onClickDate && onClickDate(item);
|
}
|
|
// 传入当前选择日期设置
|
let date = activeTime ? myTimeFormat(activeTime, 'YYYY-MM-DD') : '';
|
useEffect(() => {
|
if (date) {
|
let key = date === myTimeFormat(new Date(), 'YYYY-MM-DD') ? 'today' : date;
|
setActiveDate({ key });
|
}
|
}, [date]);
|
|
// 日期
|
const dateHeader = [{ label: '日' }, { label: '一' }, { label: '二' }, { label: '三' }, { label: '四' }, { label: '五' }, { label: '六' }];
|
|
return (
|
<div className="calendar">
|
<div className="calendar-header">
|
<LeftArrow2Outlined onClick={() => handleChangeMonth('before')} />
|
<div className="calendar-header-title">{myTimeFormat(nowTime, 'YYYY年M月')}</div>
|
<RightArrow2Outlined onClick={() => handleChangeMonth('next')} />
|
</div>
|
<div className="calendar-main">
|
<div className="calendar-main-header">
|
{dateHeader.map((x, t) => (
|
<div className="calendar-main-header-item" key={t}>
|
{x.label}
|
</div>
|
))}
|
</div>
|
<div className="calendar-main-content">
|
{monthDays.map((x, t) => (
|
<div onClick={() => handleClickDate(x)} className="calendar-main-content-item" key={t}>
|
{x.key === 'today' ? (
|
<div className={`calendar-main-content-itemBox calendar-today ${x.key === activeDate.key ? 'calendar-hover' : ''}`}>今</div>
|
) : (
|
<div
|
className={`calendar-main-content-itemBox ${x.value !== 'thisMonth' ? 'calendar-main-content-itemSubtitle' : ''} ${
|
x.key === activeDate.key ? 'calendar-hover' : ''
|
}`}
|
>
|
{x.label}
|
</div>
|
)}
|
</div>
|
))}
|
</div>
|
</div>
|
</div>
|
);
|
};
|
|
export default Calendar;
|