@fesjs/fes-design
Version:
fes-design for PC
155 lines (147 loc) • 4.87 kB
JavaScript
import { defineComponent, computed, createVNode } from 'vue';
import { isNumber } from 'lodash-es';
import { useTheme } from '../_theme/useTheme';
import { useLocale } from '../config-provider/useLocale';
import FSpace from '../space';
import FButton from '../button';
import { isValidRenderResult } from '../timeline/utils';
import { COMPONENT_NAME, prefixCls } from './const';
import { cls, convertCalendarDateToUnixTime, isSameMonth, isSameDate } from './utils';
import { calendarProps, CalendarEvent } from './props';
import useWeekNames from './useWeekNames';
import CalendarNavigator from './calendarNavigator';
import useCalendarData from './useCalendarData';
var calendar = defineComponent({
name: COMPONENT_NAME,
props: calendarProps,
emits: [CalendarEvent.UPDATE_MODEL, CalendarEvent.UPDATE_MODE, CalendarEvent.CELL_CLICK],
slots: Object,
setup: (props, _ref) => {
let {
emit,
slots
} = _ref;
useTheme();
const {
t
} = useLocale();
const {
activeDate,
mode,
displayAnchorDate,
displayCalendar,
today,
startDay,
handleShortcutClick,
handleCellClick
} = useCalendarData(props, emit);
const {
weekNames
} = useWeekNames(startDay, mode);
const renderCalendarCellContent = cellDate => {
// 插槽渲染
if (slots.cellMain) {
const customContent = slots.cellMain({
mode: mode.value,
date: convertCalendarDateToUnixTime(cellDate)
});
if (isValidRenderResult(customContent)) {
return customContent;
}
}
let mainContent;
if (mode.value === 'date') {
mainContent = cellDate.date.toString();
} else {
mainContent = t(`datePicker.month${cellDate.month + 1}`);
}
return createVNode("div", {
"class": cls('panel-cell-main-content')
}, [mainContent]);
};
const renderCalendarAppendantContent = cellDate => {
if (!slots.cellAppendant) {
return undefined;
}
return createVNode("div", {
"class": cls('panel-cell-appendant-content')
}, [slots.cellAppendant({
mode: mode.value,
date: convertCalendarDateToUnixTime(cellDate)
})]);
};
// 组件的 class
const classList = computed(() => [prefixCls, props.splitLine ? '' : cls('without-split-line')]);
// 组件的样式
const styles = computed(() => ({
height: isNumber(props.height) ? `${props.height}px` : props.height
}));
// 日历格子的样式
const calculateCellClassList = cell => {
const classList = [cls('panel-cell')];
const isSame = mode.value === 'month' ? isSameMonth : isSameDate;
if (isSame(cell, today)) {
classList.push(cls('panel-cell-today'));
}
if (isSame(cell, activeDate.value)) {
classList.push(cls('panel-cell-active'));
}
if (mode.value === 'date') {
if (!isSameMonth(cell, displayAnchorDate.value)) {
classList.push(cls('panel-cell-secondary'));
}
}
return classList;
};
// 操作栏
const renderActionBar = () => createVNode("div", {
"class": cls('action-bar')
}, [createVNode("div", {
"class": cls('action-bar-left')
}, [createVNode(CalendarNavigator, {
'date': displayAnchorDate.value,
"onUpdate:date": $event => displayAnchorDate.value = $event,
"navUnit": mode.value === 'date' ? 'month' : 'year'
}, null)]), createVNode(FSpace, {
"class": cls('action-bar-right'),
"justify": "end"
}, {
default: () => [props.shortcuts.map(_ref2 => {
let {
label,
time
} = _ref2;
return createVNode(FButton, {
"onClick": () => handleShortcutClick(time)
}, {
default: () => [label]
});
})]
})]);
// 星期栏
const renderWeekNameHeader = () => {
if (mode.value === 'month') {
return undefined;
}
return createVNode("div", {
"class": cls('week-name-header')
}, [weekNames.value.map(weekName => createVNode("div", {
"class": cls('week-name-header-cell')
}, [createVNode("div", {
"class": cls('week-name-header-cell-main-content')
}, [weekName])]))]);
};
return () => createVNode("div", {
"class": classList.value,
"style": styles.value
}, [renderActionBar(), createVNode("div", {
"class": cls('panel')
}, [renderWeekNameHeader(), createVNode("div", {
"class": cls(`${mode.value}-panel`)
}, [displayCalendar.value.map(cell => createVNode("div", {
"class": calculateCellClassList(cell),
"onClick": () => handleCellClick(cell)
}, [renderCalendarCellContent(cell), renderCalendarAppendantContent(cell)]))])])]);
}
});
export { calendar as default };