import React from 'react';
import DatePicker from '../index';
import BaseDatePicker from '../datePicker';
import ConfigProvider from '../../configProvider';
import * as _ from 'lodash';
import { clear } from 'jest-date-mock';
import { addDays, startOfWeek, endOfWeek, add, format, addWeeks, set } from 'date-fns';
import { zhCN, enUS } from "date-fns/locale";
import { zonedTimeToUtc } from 'date-fns-tz';
import { strings } from '../../../semi-foundation/datePicker/constants';
import { BASE_CLASS_PREFIX } from '../../../semi-foundation/base/constants';
import en_US from '../../locale/source/en_US';
import LocaleProvider from '../../locale/localeProvider';
import { genBeforeEach, genAfterEach, mount, sleep as baseSleep } from '../../_test_/utils';
import { utcToZonedTime, toIANA } from '../../../semi-foundation/utils/date-fns-extra';
const animationMs = 200;
const baseYear = 2019;
const baseDay = 8;
const baseMon = 8;
const baseDate = new Date(baseYear, baseMon, baseDay, 8, 8, 8, 8);
const popupSelector = `.${BASE_CLASS_PREFIX}-popover .${BASE_CLASS_PREFIX}-datepicker`;
const sleep = (ms = 200) => baseSleep(ms);
const getRandomIANATimeZone = function () {
const TIME_ZONE = Array.from({ length: 26 }).map((_, index) => index - 11);
const offset = Math.floor(Math.random() * TIME_ZONE.length);
const timeZone = toIANA(TIME_ZONE[offset]);
return [timeZone, offset];
};
describe(`DatePicker`, () => {
beforeEach(() => {
clear();
genBeforeEach()();
});
afterEach(genAfterEach());
it(`test appearance`, () => {
const defaultValue = new Date();
/**
* with default value
*/
const elem = mount();
expect(elem.find(`.${BASE_CLASS_PREFIX}-datepicker`).length).toBe(1);
expect(elem.find(`.${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-input-wrapper-clearable`).length).toBe(1);
});
it(`test defaultOpen`, async () => {
const defaultValue = new Date();
const open = true;
const motion = false;
const elem = mount();
expect(document.querySelectorAll(popupSelector).length).toBe(1);
// document.body.click();
document.dispatchEvent(new Event('mousedown', { bubbles: true }));
await sleep();
expect(document.querySelectorAll(popupSelector).length).toBe(0);
});
it(`test open`, async () => {
const defaultValue = new Date();
const open = true;
const motion = false;
const elem = mount();
expect(document.querySelectorAll(popupSelector).length).toBe(1);
/**
* click body without reset open
*/
document.body.click();
await sleep();
expect(document.querySelectorAll(popupSelector).length).toBe(1);
/**
* click body and set open
*/
elem.setProps({ open: false });
document.body.click();
await sleep();
expect(document.querySelectorAll(popupSelector).length).toBe(0);
});
it(`test presets`, async () => {
const dayOffset = 1;
const presets = [
{
text: 'Today',
start: new Date(baseDate),
end: new Date(baseDate),
},
{
text: 'Next Day',
start: addDays(new Date(baseDate), dayOffset),
end: addDays(new Date(baseDate), dayOffset),
},
];
const defaultValue = new Date(addDays(new Date(baseDate), -dayOffset));
const open = true;
const motion = false;
const demo = mount();
const elem = demo.find(BaseDatePicker);
const btns = document.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-quick-control-item`);
/**
* click next day
*/
btns[1].click();
let value = elem.state('value');
expect(value[0].getDate() - defaultValue.getDate()).toEqual(dayOffset * 2);
/**
* click current day
*/
btns[0].click();
value = elem.state('value');
expect(value[0].getDate()).toEqual(defaultValue.getDate() + 1);
});
it(`test value`, async () => {
const currentValue = new Date(baseDate);
const open = true;
const motion = false;
const dayOffset = 3;
const onChange = sinon.spy(async (date, str) => {
expect(date.getDate()).toBe(currentValue.getDate() + dayOffset);
elem.setProps({ value: date });
await sleep();
expect(_.first(datePickerElem.state('value')).getDate() - baseDate.getDate()).toBe(dayOffset);
});
const elem = mount();
const datePickerElem = elem.find(BaseDatePicker);
const popup = document.querySelector(`.${BASE_CLASS_PREFIX}-popover .${BASE_CLASS_PREFIX}-datepicker`);
const selectedDayElem = popup.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-day-selected`);
const nextOffsetDayElem = _.times(dayOffset).reduce(node => node.nextElementSibling, selectedDayElem);
nextOffsetDayElem.click();
await sleep(animationMs * 3);
expect(onChange.called).toBeTruthy();
});
it(`test needConfirm`, async () => {
const currentValue = new Date(baseDate);
const open = true;
const motion = false;
const type = 'dateTime';
const needConfirm = true;
const dayOffset = 3;
const demo = mount(
);
const elem = demo.find(BaseDatePicker);
const btns = document.querySelectorAll(`.${BASE_CLASS_PREFIX}-popover .${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-datepicker-footer .${BASE_CLASS_PREFIX}-button`);
expect(btns.length).toBe(2);
const selectedDayElem = document.querySelector(`.${BASE_CLASS_PREFIX}-popover .${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-datepicker-day-selected`);
const nextOffsetDayElem = _.times(dayOffset).reduce(node => node.nextElementSibling, selectedDayElem);
/**
* click next day
*/
nextOffsetDayElem.click();
await sleep();
expect(_.first(elem.state('value')).getDate() === currentValue.getDate()).toBeTruthy();
/**
* click cancel button
*/
btns[0].click();
await sleep();
expect(_.first(elem.state('value')).getDate() === currentValue.getDate()).toBeTruthy();
expect(_.isEqual(elem.state('cachedSelectedValue'), [currentValue])).toBe(true);
/**
* click ensure button
*/
btns[1].click();
await sleep();
expect(_.first(elem.state('value')).getDate() === currentValue.getDate()).toBe(true);
/**
* re click next day
*/
nextOffsetDayElem.click();
await sleep();
expect(_.first(elem.state('value')).getDate() === currentValue.getDate()).toBeTruthy();
/**
* re click ensure button
*/
btns[1].click();
await sleep();
expect(_.first(elem.state('value')).getDate() - currentValue.getDate()).toBe(dayOffset);
demo.unmount();
});
it(`test events`, async () => {
const currentValue = new Date(baseDate);
const open = true;
const motion = false;
const type = 'dateTime';
const needConfirm = true;
const dayOffset = 3;
const onOpenChange = sinon.spy();
const onChange = sinon.spy();
const elem = mount(
);
/**
* click outside
*/
document.body.click();
await sleep();
expect(onOpenChange.called).toBeFalsy();
/**
* click datePicker
*/
const inputWrapper = document.querySelector(`.${BASE_CLASS_PREFIX}-input-wrapper`);
const dateInputDom = inputWrapper.parentElement;
dateInputDom.click();
await sleep();
expect(onOpenChange.called).toBeTruthy();
/**
* input value change
*/
elem.find(`.${BASE_CLASS_PREFIX}-input-wrapper input`).simulate('change', { target: { value: '2019-10-02 08:30:02' } });
expect(onChange.called).toBeTruthy();
});
it(`test range picker`, async () => {
const open = true;
const motion = false;
const type = 'dateTimeRange';
const needConfirm = false;
const dayOffset = 3;
const leftPrevClickTimes = 3;
const currentValue = [new Date(baseDate), new Date(baseDate).setDate(baseDay + dayOffset)];
const demo = mount(
);
const elem = demo.find(BaseDatePicker);
const startDayDom = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-day-selected-start`);
const endDayDom = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-day-selected-end`);
/**
* check started day and ended day's gap offset
*/
expect(_.times(dayOffset).reduce(cur => cur.nextElementSibling, startDayDom)).toBe(endDayDom);
const leftPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-left`);
const leftNavBtns = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-navigation .${BASE_CLASS_PREFIX}-button`);
const rightPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-right`);
const rightNavBtns = rightPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-navigation .${BASE_CLASS_PREFIX}-button`);
// 点击右边面板下一月
_.get(rightNavBtns, 2).click();
await sleep();
// 点击左边面板上一月
_.times(leftPrevClickTimes).forEach(() => _.get(leftNavBtns, 1).click());
const leftSecondWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const leftSecondWeekDays = leftSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
const startIndex = 0;
/**
* select 2019-06-02 ~ 2019-06-05
*/
demo.find('input').at(0).simulate('focus');
leftSecondWeekDays[startIndex].click();
demo.find('input').at(1).simulate('focus');
leftSecondWeekDays[startIndex + dayOffset].click();
const value = elem.state('value');
const startDay = 2;
expect(value[0].getMonth()).toBe(baseMon - leftPrevClickTimes);
expect(value[0].getDate()).toBe(startDay);
expect(value[1].getMonth()).toBe(baseMon - leftPrevClickTimes);
expect(value[1].getDate()).toBe(startDay + dayOffset);
});
it(`test change panel in range picker`, async () => {
const motion = false;
const type = 'dateRange';
const needConfirm = false;
const dayOffset = 3;
const currentValue = [new Date(baseDate), new Date(baseDate).setDate(baseDay + dayOffset)];
const demo = mount(
);
const elem = demo.find(BaseDatePicker);
const leftPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-left`);
const leftSecondWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const leftSecondWeekDays = leftSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
const startIndex = 0;
demo.find('input').at(0).simulate('focus');
leftSecondWeekDays[startIndex].click();
await sleep();
expect(elem.state('rangeInputFocus')).toBe('rangeEnd');
expect(elem.instance().focusRecordsRef.current.rangeStart).toBe(true);
leftSecondWeekDays[startIndex + dayOffset].click();
await sleep();
expect(elem.instance().focusRecordsRef.current.rangeStart).toBe(false);
expect(elem.instance().focusRecordsRef.current.rangeEnd).toBe(false);
expect(elem.state('rangeInputFocus')).toBe(false);
});
it(`test change panel in range picker with start greater than endTime`, async () => {
const motion = false;
const type = 'dateRange';
const needConfirm = false;
const dayOffset = 3;
const currentValue = [new Date(baseDate), new Date(baseDate).setDate(baseDay + dayOffset)];
const demo = mount(
);
const elem = demo.find(BaseDatePicker);
const leftPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-left`);
const leftThirdWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[2];
const leftThirdWeekDays = leftThirdWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
const startIndex = 0;
demo.find('input').at(0).simulate('focus');
leftThirdWeekDays[startIndex].click();
await sleep();
expect(elem.state('rangeInputFocus')).toBe('rangeEnd');
const inputValue = elem.state('inputValue');
expect(inputValue.split('~')[1].trim()).toBe('');
});
/**
* this test suite won't end up with result
*/
it.skip(`test year or month picker`, async () => {
const open = true;
const motion = false;
const type = 'month';
const monOffset = 2;
const yearOffset = 3;
const currentValue = new Date(baseDate);
const elem = mount();
await sleep();
const lists = document.querySelectorAll(`.${BASE_CLASS_PREFIX}-scrolllist-item-wheel`);
/**
* select year
*/
const currentSelectedYear = lists[0].querySelector(`ul .${BASE_CLASS_PREFIX}-scrolllist-item-selected`);
_.times(yearOffset)
.reduce(cur => cur.nextElementSibling, currentSelectedYear)
.click();
/**
* select month
*/
const currentSelectedMon = lists[1].querySelector(`ul .${BASE_CLASS_PREFIX}-scrolllist-item-selected`);
_.times(monOffset)
.reduce(cur => cur.nextElementSibling, currentSelectedMon)
.click();
await sleep();
const value = elem.state('value');
expect(value[0].getYear()).toBe(baseYear + yearOffset);
expect(value[0].getMonth()).toBe(baseMon + monOffset);
});
it('test week select', async () => {
const demo = mount(
startOfWeek(date, { weekStartsOn: 1 })}
endDateOffset={date => endOfWeek(date, { weekStartsOn: 1 })}
/>
);
const elem = demo.find(BaseDatePicker);
const leftPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-left`);
const leftSecondWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const leftSecondWeekDays = leftSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
const startIndex = 3;
/**
* 点击当前月第二个星期的第四天
*/
leftSecondWeekDays[startIndex].click();
const now = new Date();
const year = now.getFullYear();
const month = now.getMonth();
const monthFirstDay = add(new Date(year, 0, 1, 0, 0, 0), { months: month });
const clickDay = addDays(startOfWeek(addWeeks(monthFirstDay, 1), { weekStartsOn: 1 }), 3);
const value = elem.state('value');
const dateFormat = 'yyyy-MM-dd';
expect(format(value[0], dateFormat)).toBe(format(startOfWeek(clickDay, { weekStartsOn: 1 }), dateFormat));
expect(format(value[1], dateFormat)).toBe(format(endOfWeek(clickDay, { weekStartsOn: 1 }), dateFormat));
});
it('test autoFocus', async () => {
const motion = false;
const elem = mount();
const elem2 = mount();
expect(elem.find(`.${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-input-wrapper-focus`).length).toBe(1);
expect(elem2.find(`.${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-input-wrapper-focus`).length).toBe(0);
});
it('custom dropdownClassName & dropdownStyle', async () => {
let props = {
dropdownClassName: 'my-datePicker',
dropdownStyle: {
color: 'red',
},
defaultOpen: true,
motion: false,
};
const elem = mount();
expect(elem.exists('.my-datePicker')).toEqual(true);
expect(elem.find('.my-datePicker')).toHaveStyle('color', 'red');
});
it('onClear', async () => {
const onClear = sinon.spy();
let props = {
defaultOpen: true,
motion: false,
autoFocus: true,
defaultValue: baseDate,
showClear: true,
onClear: onClear,
};
const elem = mount();
const clearBtn = elem.find('.semi-input-clearbtn');
clearBtn.simulate('mouseDown', { target: { value: 'test' } });
expect(onClear.called).toBeTruthy();
});
it('input disabled date should not trigger onChange', async () => {
const onChange = sinon.spy();
const defaultValue = '2021-04-12';
const disabeldDate = '2021-04-15';
const notDisabledDate = '2021-04-13';
let props = {
defaultOpen: true,
motion: false,
value: defaultValue,
onChange,
disabledDate: dateStr => {
const date = new Date(dateStr);
const day = date.getDate();
if (day === 15) {
return true;
}
return false;
}
};
const elem = mount();
elem.find(`.${BASE_CLASS_PREFIX}-input-wrapper input`).simulate('change', { target: { value: disabeldDate } });
await sleep();
expect(onChange.called).toBeFalsy();
elem.find(`.${BASE_CLASS_PREFIX}-input-wrapper input`).simulate('change', { target: { value: notDisabledDate } });
await sleep();
expect(onChange.called).toBeTruthy();
});
it('click presets disabled date should not trigger onChange', async () => {
const onChange = sinon.spy();
const defaultValue = '2021-04-12';
const disabledValue = '2021-04-15';
const notDisabledValue = '2021-04-30';
const defaultDate = new Date(`${defaultValue} 00:00:00`);
const disableDate = new Date(`${disabledValue} 00:00:00`);
const notDisabledDate = new Date(`${notDisabledValue} 00:00:00`);
let props = {
open: true,
motion: false,
defaultValue,
onChange,
disabledDate: date => {
const day = date.getDate();
if (day === 15) {
return true;
}
return false;
},
presets: [
{
text: 'disabled date',
start: disableDate,
},
{
text: 'valid date',
start: notDisabledValue,
},
],
};
const demo = mount();
const elem = demo.find(BaseDatePicker);
const btns = document.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-quick-control-item`);
// click disabled date
btns[0].click();
let value = elem.state('value');
expect(value[0].getDate()).toEqual(defaultDate.getDate());
expect(onChange.called).toBeFalsy();
// click valid date
btns[1].click();
await sleep();
value = elem.state('value');
expect(value[0].getDate()).toEqual(notDisabledDate.getDate());
expect(onChange.called).toBeTruthy();
});
it('check inputValue is correct when change timeZone', async () => {
const today = set(new Date(), { hours: 22, minutes: 0, seconds: 0 });
const [originZone, originOffset] = getRandomIANATimeZone();
const [newZone, newOffset] = getRandomIANATimeZone();
const elem = mount(
);
const demo = elem.find(BaseDatePicker);
// 选中一个日期
const days = document.querySelectorAll('.semi-datepicker-day');
// 6 无实际意义,第一行的第7个肯定是有效日期,如第一行最后一天是月首
days[6].click();
await sleep();
// 查看value值
expect(elem.find('.semi-datepicker-day-selected')).toBeTruthy();
const selectedDay = demo.state('value')[0];
const input = document.querySelector('.semi-input');
expect(input.value).toEqual(format(selectedDay, strings.FORMAT_DATE_TIME));
// 切换时区
elem.setProps({ timeZone: newZone });
const newZoneDate = add(selectedDay, { hours: newOffset - originOffset })
const formatNewZoneDate = format(newZoneDate, strings.FORMAT_DATE_TIME);
expect(input.value).toEqual(formatNewZoneDate);
});
it('check inputValue in controlled mode when change timeZone', async () => {
const now = new Date();
const [originZone, originOffset] = getRandomIANATimeZone();
const [newZone, newOffset] = getRandomIANATimeZone();
// 给定一个时区下的date value
const originZoneDate = zonedTimeToUtc(now, originZone);
const elem = mount(
);
const input = document.querySelector('.semi-input');
const originFormatDate = format(now, strings.FORMAT_DATE_TIME);
expect(input.value).toEqual(originFormatDate);
// 切换时区
elem.setProps({ timeZone: newZone });
const newZoneDate = add(now, { hours: newOffset - originOffset })
const formatNewZoneDate = format(newZoneDate, strings.FORMAT_DATE_TIME);
expect(input.value).toEqual(formatNewZoneDate);
});
it(`test locale format default`, () => {
const localeFormatten = 'yyyy-MM-dd EEEE';
const defaultValue = new Date('2021-04-30');
const localeValue = format(defaultValue, localeFormatten, { locale: zhCN })
// 默认为中文
const elem = mount();
expect(elem.find(`.${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-input`).instance().value).toBe(localeValue);
});
it(`test locale format enUS`, () => {
const localeFormatten = 'yyyy-MM-dd EEEE';
const defaultValue = new Date('2021-04-30');
const localeValue = format(defaultValue, localeFormatten, { locale: enUS })
// 英文
const elem = mount(
);
expect(elem.find(`.${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-input`).instance().value).toBe(localeValue);
});
it(`test onPresetClick`, async () => {
const dayOffset = 1;
const presets = [
{
text: 'Today',
start: new Date(baseDate),
end: new Date(baseDate),
},
{
text: 'Next Day',
start: addDays(new Date(baseDate), dayOffset),
end: addDays(new Date(baseDate), dayOffset),
},
];
const defaultValue = new Date(addDays(new Date(baseDate), -dayOffset));
const open = true;
const motion = false;
const handlePresetClick = sinon.spy();
const demo = mount();
const elem = demo.find(BaseDatePicker);
const btns = document.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-quick-control-item`);
btns[0].click();
btns[1].click();
expect(handlePresetClick.calledTwice).toBeTruthy();
const args0 = handlePresetClick.getCall(0).args;
const args1 = handlePresetClick.getCall(1).args;
expect(args0[0]).toEqual(presets[0]);
expect(args0[1] instanceof Event).toBeTruthy;
expect(args1[0]).toEqual(presets[1]);
expect(args1[1] instanceof Event).toBeTruthy;
});
it(`test range type click one not trigger notifyChange`, async () => {
const onChange = sinon.spy(async (date, str) => {
elem.setProps({ value: date });
});
let props = {
defaultOpen: true,
motion: false,
value: undefined,
onChange,
defaultPickerValue: '2021-08-13',
type: 'dateRange'
};
const elem = mount();
const leftPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-left`);
const leftSecondWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const leftSecondWeekDays = leftSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
const startIndex = 0;
const endIndex = 2;
elem.find('input').at(0).simulate('focus');
leftSecondWeekDays[startIndex].click();
expect(onChange.calledOnce).toBe(false);
elem.find('input').at(1).simulate('focus');
leftSecondWeekDays[endIndex].click();
expect(onChange.calledOnce).toBe(true);
const [rangeStart, rangeEnd] = onChange.getCall(0).args[0];
const dateFormat = 'yyyy-MM-dd';
expect(format(rangeStart, dateFormat)).toBe('2021-08-08');
expect(format(rangeEnd, dateFormat)).toBe('2021-08-10');
const inputs = elem.find(`.${BASE_CLASS_PREFIX}-datepicker .${BASE_CLASS_PREFIX}-input`);
expect(inputs.at(0).instance().value).toBe('2021-08-08');
expect(inputs.at(1).instance().value).toBe('2021-08-10');
});
/**
* test disabled rangeStart and select a not disabled range end
* e.g.
* You can select a no disabled date(like one day of september) when defaultValue=['2021-08-06', '2021-08-15'] and disabled august.
*/
it('test rangeStart disabled and select rangeEnd', async () => {
const onChange = sinon.spy();
const defaultValue = ['2021-08-06', '2021-08-15'];
let props = {
type: 'dateRange',
defaultOpen: true,
motion: false,
defaultValue,
onChange,
// disabled august
disabledDate: dateStr => {
const date = new Date(dateStr);
const month = date.getMonth();
if (month === 7) {
return true;
}
return false;
},
style: { width: 300 }
};
const elem = mount();
const baseElem = elem.find(BaseDatePicker);
const rightPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-right`);
const rightSecondWeek = rightPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const rightSecondWeekDays = rightSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
/**
* select 2021-09-10 as rangeEnd
*/
elem.find('input').at(1).simulate('focus');
const endIndex = 5; // 2021-09-10
rightSecondWeekDays[endIndex].click();
const value = baseElem.state('value');
// test rangeEnd is selected
expect(value[0].getMonth()).toBe(7);
expect(value[0].getDate()).toBe(6);
expect(value[1].getMonth()).toBe(8);
expect(value[1].getDate()).toBe(10);
// test input value is same with state value
expect(elem.find('input').at(0).instance().value).toBe(defaultValue[0]);
expect(elem.find('input').at(1).instance().value).toBe('2021-09-10');
// test event is called
expect(onChange.calledOnce).toBe(true);
});
/**
* test disabled some day and select a no disabled day in multiple mode
*/
it('test disabled multiple select', async () => {
const onChange = sinon.spy();
const defaultValue = ['2021-08-06', '2021-08-15'];
let props = {
type: 'date',
multiple: true,
defaultOpen: true,
motion: false,
defaultValue,
onChange,
// disabled august
disabledDate: dateStr => {
const date = new Date(dateStr);
const day = date.getDate();
if (day > 20 && day < 25) {
return true;
}
return false;
},
style: { width: 300 }
};
const elem = mount();
const baseElem = elem.find(BaseDatePicker);
const leftPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-left`);
const leftSecondWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const leftSecondWeekDays = leftSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
/**
* select 2021-08-10(not disabled)
*/
leftSecondWeekDays[2].click();
let value = baseElem.state('value');
// test 2021-08-10 is selected
expect(value.length).toBe(3);
expect(value[2].getMonth()).toBe(7);
expect(value[2].getDate()).toBe(10);
// test input value is same with state value
expect(elem.find('input').at(0).instance().value).toBe('2021-08-06,2021-08-15,2021-08-10');
// test event is called
expect(onChange.calledOnce).toBe(true);
/**
* select 2021-08-21(disabled)
*/
const leftThirdWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[2];
const leftThirdWeekDays = leftThirdWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
leftThirdWeekDays[6].click();
await sleep();
value = baseElem.state('value');
// test 2021-08-21 is not selected
expect(value.length).toBe(3);
expect(elem.find('input').at(0).instance().value).toBe('2021-08-06,2021-08-15,2021-08-10');
expect(onChange.calledOnce).toBe(true); // still calledOnce
});
it('test disabled time callback', async () => {
const disabledTime = sinon.spy((date, panelType) => {
if (panelType === 'left') {
return { disabledHours: () => [17, 18] };
} else {
return { disabledHours: () => [12, 13, 14, 15, 16, 17, 18] };
}
});
let props = {
type: 'dateTimeRange',
defaultValue: ['2021-09-08', '2021-10-03'],
defaultOpen: true,
motion: false,
disabledTime,
style: { width: 400 },
timePickerOpts: {
scrollItemProps: { cycled: false }
}
};
const elem = mount();
elem.find('.semi-datepicker-month-grid-left .semi-datepicker-switch-time').simulate('click');
const args = disabledTime.lastCall.args;
expect(args[0].length).toBe(2);
expect(args[1]).toBe('left');
elem.setProps({ type: 'dateTime' });
elem.update();
elem.find('.semi-datepicker-month-grid-left .semi-datepicker-switch-time').simulate('click');
const args2 = disabledTime.lastCall.args;
expect(Array.isArray(args2[0])).toBe(false);
expect(args2[1]).toBe('left');
});
it('test rangeSeparator', async () => {
const rangeSeparator = '-'
const defaultValue = ['2021-08-06', '2021-08-15'];
let props = {
type: 'dateRange',
motion: false,
defaultValue,
style: { width: 300 },
rangeSeparator,
};
const elem = mount(
);
const allSeparators = document.querySelectorAll('.semi-datepicker-range-input-separator');
expect(allSeparators[0].textContent.trim()).toBe(rangeSeparator);
expect(allSeparators[1].textContent.trim()).toBe(rangeSeparator);
});
/**
* fix https://github.com/DouyinFE/semi-design/issues/422
*/
it('test input year length larger than 4', async () => {
const props = {
motion: false,
defaultOpen: true,
defaultValue: '2021-12-21',
};
const handleChange = sinon.spy();
const elem = mount(
);
elem.find('input').simulate('change', { target: { value: '20221-12-21' }});
expect(handleChange.called).toBeFalsy();
});
it('test click next/prev year buttons', () => {
let props = {
type: 'dateRange',
motion: false,
style: { width: 300 },
defaultPickerValue: new Date('2021-12-01'),
defaultOpen: true,
};
const elem = mount();
const leftPanel = document.querySelector(`.semi-datepicker-month-grid-left`);
const leftNavBtns = leftPanel.querySelector(`.semi-datepicker-navigation`).children;
const rightPanel = document.querySelector(`.semi-datepicker-month-grid-right`);
const rightNavBtns = rightPanel.querySelector(`.semi-datepicker-navigation`).children;
// 点击左边面板上一年
_.get(leftNavBtns, 0).click();
expect(document.querySelector(`.semi-datepicker-month-grid-left .semi-datepicker-navigation-month`).textContent).toBe('2020年 12月');
// 点击左边面板下一年
_.get(leftNavBtns, 4).click();
expect(document.querySelector(`.semi-datepicker-month-grid-left .semi-datepicker-navigation-month`).textContent).toBe('2021年 12月');
// 点击右边面板下一年
_.get(rightNavBtns, 4).click();
expect(document.querySelector(`.semi-datepicker-month-grid-right .semi-datepicker-navigation-month`).textContent).toBe('2023年 1月');
// 点击右边面板上一年
_.get(rightNavBtns, 0).click();
expect(document.querySelector(`.semi-datepicker-month-grid-right .semi-datepicker-navigation-month`).textContent).toBe('2022年 1月');
});
const testMonthSyncChange = type => {
let props = {
type,
motion: false,
style: { width: 300 },
defaultPickerValue: new Date('2021-12-01'),
defaultOpen: true,
};
const elem = mount();
const leftPanel = document.querySelector(`.semi-datepicker-month-grid-left`);
const leftNavBtns = leftPanel.querySelector(`.semi-datepicker-navigation`).children;
const rightPanel = document.querySelector(`.semi-datepicker-month-grid-right`);
const rightNavBtns = rightPanel.querySelector(`.semi-datepicker-navigation`).children;
// 点击左边面板下一月,自动切换右面板
_.get(leftNavBtns, 3).click();
expect(document.querySelector(`.semi-datepicker-month-grid-left .semi-datepicker-navigation-month`).textContent).toBe('2022年 1月');
expect(document.querySelector(`.semi-datepicker-month-grid-right .semi-datepicker-navigation-month`).textContent).toBe('2022年 2月');
// 点击右边面板上一月,自动切换左面板
_.get(rightNavBtns, 1).click();
expect(document.querySelector(`.semi-datepicker-month-grid-left .semi-datepicker-navigation-month`).textContent).toBe('2021年 12月');
expect(document.querySelector(`.semi-datepicker-month-grid-right .semi-datepicker-navigation-month`).textContent).toBe('2022年 1月');
// 点击左边面板上一月,不需要自动切换右面板
_.get(leftNavBtns, 1).click();
expect(document.querySelector(`.semi-datepicker-month-grid-left .semi-datepicker-navigation-month`).textContent).toBe('2021年 11月');
elem.unmount();
}
it('test month sync change dateRange type', () => { testMonthSyncChange('dateRange') });
it('test month sync change dateTimeRange type', () => { testMonthSyncChange('dateTimeRange')});
it(`test preset given null`, async () => {
const props = {
presets: [
{
text: 'Today',
start: null,
end: null,
}
],
defaultValue: baseDate,
defaultOpen: true,
motion: false,
type: 'dateRange'
}
const handleChange = sinon.spy();
const demo = mount();
const elem = demo.find(BaseDatePicker);
const btns = document.querySelectorAll('.semi-datepicker-quick-control-item');
btns[0].click();
expect(handleChange.called).toBeTruthy();
const args = handleChange.getCall(0).args;
expect(args[0].length).toEqual(0);
expect(elem.state('panelShow')).toBeFalsy();
});
it(`test preset given null + needConfirm`, async () => {
const props = {
presets: [
{
text: 'Today',
start: null,
end: null,
}
],
defaultValue: baseDate,
defaultOpen: true,
motion: false,
type: 'dateTimeRange',
needConfirm: true,
}
const handleChange = sinon.spy();
const handleConfirm = sinon.spy();
const demo = mount();
const elem = demo.find(BaseDatePicker);
const btns = document.querySelectorAll('.semi-datepicker-quick-control-item');
// 点击 preset
btns[0].click();
expect(handleChange.called).toBe(true);
const argsChange = handleChange.getCall(0).args;
expect(argsChange[0].length).toBe(0);
expect(elem.state('panelShow')).toBe(true);
// 点击确定
const footerBtns = document.querySelectorAll('.semi-datepicker-footer .semi-button');
footerBtns[1].click();
expect(handleConfirm.called).toBe(true);
const argsConfirm = handleConfirm.getCall(0).args;
expect(argsConfirm[0].length).toBe(0);
expect(elem.state('panelShow')).toBe(false);
});
it('test dateRange triggerRender', async () => {
const elem = mount(
(
)}
/>
);
const trigger = document.querySelector('button');
trigger.click();
await sleep();
const leftPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-left`);
const leftSecondWeek = leftPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const leftSecondWeekDays = leftSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
const rightPanel = document.querySelector(`.${BASE_CLASS_PREFIX}-datepicker-month-grid-right`);
const rightSecondWeek = rightPanel.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-week`)[1];
const rightSecondWeekDays = rightSecondWeek.querySelectorAll(`.${BASE_CLASS_PREFIX}-datepicker-day`);
leftSecondWeekDays[0].click();
rightSecondWeekDays[0].click();
const baseElem = elem.find(BaseDatePicker);
expect(baseElem.state('panelShow')).toBeFalsy();
});
});