Skip to content

Commit

Permalink
fix(date-range-quick-picker): support the time disabled of props (min…
Browse files Browse the repository at this point in the history
…, max) (#2070)

* fix: 修复DateRangeQuickPicker的min和max对时间不生效问题

Co-authored-by: daitingyuan <[email protected]>
  • Loading branch information
Tinsson and daitingyuan authored Oct 11, 2024
1 parent e215509 commit ce2a2e1
Show file tree
Hide file tree
Showing 4 changed files with 120 additions and 3 deletions.
21 changes: 19 additions & 2 deletions packages/zent/__tests__/date-range-quick-picker.spec.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -36,30 +36,47 @@ describe('DateRangeQuickPicker', () => {
value={[1524106071377, 1524107071377]}
onChange={onChange}
valueType="number"
format="YYYY-MM-DD HH:mm:ss"
min="2020-04-19 10:05:12"
max="2025-01-01 12:05:12"
/>
);

wrapper.instance().handleChosenDays(1);
expect(onChange.mock.calls.length).toBe(1);
wrapper.find('.zent-datepicker-trigger').at(1).simulate('click');
});

it('suppports default preset', () => {
const onChange = jest.fn();
mount(
const wrapper = mount(
<DateRangeQuickPicker
value={[1524106071377, 1524107071377]}
onChange={onChange}
defaultSelectedPresetIndex={0}
disabledDate={{
min: '2018-04-19 10:05:12',
max: '2018-04-19 15:05:12',
}}
/>
);
expect(onChange.mock.calls.length).toBe(0);
wrapper.find('.zent-datepicker-trigger').at(0).simulate('click');

mount(
const wrapper2 = mount(
<DateRangeQuickPicker
onChange={onChange}
defaultSelectedPresetIndex={0}
disabledTime={() => {
return {
disabledHours: () => [],
disabledMinutes: () => [],
disabledSeconds: () => [],
};
}}
/>
);
expect(onChange.mock.calls.length).toBe(1);
wrapper2.find('.zent-datepicker-trigger').at(1).simulate('click');
});
});
9 changes: 8 additions & 1 deletion packages/zent/src/date-picker/components/RangePickerBase.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import useRangeMergedProps from '../hooks/useRangeMergedProps';
import useRangeDisabledDate from '../hooks/useRangeDisabledDate';
import { useShowTimeRangeOption } from '../hooks/useShowTimeOption';
import useNormalizeDisabledDate from '../hooks/useNormalizeDisabledDate';
import useNormalizeDisabledTime from '../hooks/useNormalizeDisabledTime';
import { useEventCallbackRef } from '../../utils/hooks/useEventCallbackRef';

import {
Expand Down Expand Up @@ -46,7 +47,7 @@ const RangePicker: React.FC<IRangePickerProps> = ({
onChange,
onClose,
onOpen,
disabledTime,
disabledTime: disabledTimeProps,
generateDate,
PickerComponent,
showTime,
Expand Down Expand Up @@ -104,6 +105,12 @@ const RangePicker: React.FC<IRangePickerProps> = ({
[start, end, showTime, onChangeRef, getCallbackRangeValue, setSelected]
);

const disabledTime = useNormalizeDisabledTime(
format,
disabledDateProps,
disabledTimeProps
);

const { disabledStartTimes, disabledEndTimes } = useRangeDisabledTime({
selected,
disabledTime,
Expand Down
16 changes: 16 additions & 0 deletions packages/zent/src/date-picker/hooks/useNormalizeDisabledTime.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import { useCallback } from 'react';
import { IDisabledTime, IDisabledDate } from '../types';
import unifiedDisabledTimeFromProps from '../utils/unifiedDisabledTimeFromProps';

export default function useNormalizeDisabledTime(
format: string,
disabledDate: IDisabledDate,
disabledTime: IDisabledTime
) {
// eslint-disable-next-line react-hooks/exhaustive-deps
const normalizedDisabledTime = useCallback(
unifiedDisabledTimeFromProps(format, disabledDate, disabledTime),
[disabledDate, format, disabledTime]
);
return normalizedDisabledTime;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
import { endOfDay, isAfter, isBefore, startOfDay, isSameDay } from 'date-fns';
import { parseBase } from './index';
import { IDisabledDate, IDisabledTime, IDisabledDateSimple } from '../types';

function generateNumberArray(max) {
return Array.from({ length: max + 1 }, (_, i) => i);
}

/**
* props的DisabledDate参数 支持 {min, max} 格式
* 内部统一转成方法-输出disabledTime
* @param format
* @param disabledDateProps
* @param disabledTime
*/
export default function unifiedDisabledDateFromProps(
format: string,
disabledDateProps: IDisabledDate,
disabledTime: IDisabledTime
): IDisabledTime {
if (typeof disabledTime === 'function') {
return disabledTime;
}
if (typeof disabledDateProps === 'object') {
const { min, max } = disabledDateProps as IDisabledDateSimple;
const disabledDate = (date: Date) =>
(!!min && isBefore(endOfDay(date), parseBase(min, format))) ||
(!!max && isAfter(startOfDay(date), parseBase(max, format)));
return (date: Date) => {
const isDateDisabled = disabledDate(date);
if (isDateDisabled) {
return {
disabledHours: () => generateNumberArray(23),
disabledMinutes: () => generateNumberArray(59),
disabledSeconds: () => generateNumberArray(59),
};
}
if (!!min && isSameDay(endOfDay(date), parseBase(min, format))) {
// 如果是min当天,那么只有min之前的时间是disabled的
const minDate = parseBase(min, format);
return {
disabledHours: () => generateNumberArray(minDate.getHours() - 1),
disabledMinutes: (hour: number) =>
hour === minDate.getHours()
? generateNumberArray(minDate.getMinutes() - 1)
: [],
disabledSeconds: (hour: number, minute: number) =>
hour === minDate.getHours() && minute === minDate.getMinutes()
? generateNumberArray(minDate.getSeconds() - 1)
: [],
};
}
if (!!max && isSameDay(startOfDay(date), parseBase(max, format))) {
// 如果是max当天,那么只有max之后的时间是disabled的
const maxDate = parseBase(max, format);
return {
disabledHours: () =>
generateNumberArray(23).slice(maxDate.getHours() + 1),
disabledMinutes: (hour: number) =>
hour === maxDate.getHours()
? generateNumberArray(59).slice(maxDate.getMinutes() + 1)
: [],
disabledSeconds: (hour: number, minute: number) =>
hour === maxDate.getHours() && minute === maxDate.getMinutes()
? generateNumberArray(59).slice(maxDate.getSeconds() + 1)
: [],
};
}
return {
disabledHours: () => [],
disabledMinutes: () => [],
disabledSeconds: () => [],
};
};
}
return disabledTime;
}

0 comments on commit ce2a2e1

Please sign in to comment.