diff --git a/src/DatePicker/DatePicker.tsx b/src/DatePicker/DatePicker.tsx index d6caa19e..b316bf9d 100644 --- a/src/DatePicker/DatePicker.tsx +++ b/src/DatePicker/DatePicker.tsx @@ -365,8 +365,9 @@ export const DatePicker: BsPrefixRefForwardingComponent< })); if (newSelectedDates.end) { dropdownToggleRef?.current?.click(); + // onChangeDate calls only when both start and end dates are selected + props.onChangeDate?.(newSelectedDates); } - props.onChangeDate?.(newSelectedDates); }; const focusOnDateCalendar = () => { @@ -548,7 +549,8 @@ export const DatePicker: BsPrefixRefForwardingComponent< selectedDate: parsedDate, invalid: false, })); - updateFocusedDate(parsedDate); + updateFocusedDate(setTimeToNoon(parsedDate)); + props.onChangeDate?.(setTimeToNoon(parsedDate)); return; } @@ -557,6 +559,7 @@ export const DatePicker: BsPrefixRefForwardingComponent< inputDate: enteredDate, })); updateFocusedDate(displayDate); + }; const enterDateRange = (event: React.ChangeEvent) => { @@ -600,13 +603,14 @@ export const DatePicker: BsPrefixRefForwardingComponent< ...prevState, inputDate: inputDate, selectedDate: { - start: dateStart, - end: dateEnd, + start: setTimeToNoon(dateStart), + end: setTimeToNoon(dateEnd), }, displayDate: dateEnd, invalid: false, })); updateFocusedDate(dateEnd); + props.onChangeDate?.({start: setTimeToNoon(dateStart), end: setTimeToNoon(dateEnd) }) return; } diff --git a/tests/DatePicker/DatePicker.test.tsx b/tests/DatePicker/DatePicker.test.tsx index 114b0e6c..4154f0cc 100644 --- a/tests/DatePicker/DatePicker.test.tsx +++ b/tests/DatePicker/DatePicker.test.tsx @@ -214,6 +214,42 @@ describe('DatePicker', () => { expect(container.querySelector('button')).toHaveAttribute('disabled'); }); + it('onChangeDate fn fires when a valid date is typed in the Datepicker Input', async () => { + const mockFn = jest.fn(); + const { container } = render(); + const input = container.querySelector('input') as HTMLInputElement; + input?.focus(); + fireEvent.change(input, { target: { value: '24/05/2024' } }); + expect(mockFn).toHaveBeenCalled(); + }); + it('onChangeDate fn does not fire when an invalid date is typed in the Datepicker Input', async () => { + const mockFn = jest.fn(); + const { container } = render(); + const input = container.querySelector('input') as HTMLInputElement; + input?.focus(); + fireEvent.change(input, { target: { value: '24/05/1000' } }); + expect(mockFn).not.toHaveBeenCalled(); + }); + it('when mode=range, onChangeDate fn only fires when an start and end valid dates are typed in the Datepicker Input', async () => { + const mockFn = jest.fn(); + const { container } = render( + + ); + const input = container.querySelector('input') as HTMLInputElement; + input?.focus(); + // valid start date only + fireEvent.change(input, { target: { value: '24/05/2024' } }); + expect(mockFn).not.toHaveBeenCalled(); + // invalid end date + fireEvent.change(input, { target: { value: '24/05/2024 - 30/02/2024' } }); + expect(mockFn).not.toHaveBeenCalled(); + // clear input + fireEvent.change(input, { target: { value: '' } }); + expect(mockFn).not.toHaveBeenCalled(); + //valid start and end date + fireEvent.change(input, { target: { value: '24/05/2024 - 30/03/2024' } }); + expect(mockFn).toHaveBeenCalled(); + }); it('onChangeDate fn fires when dates clicked', async () => { const mockFn = jest.fn(); const { getByText, container } = render( @@ -226,6 +262,20 @@ describe('DatePicker', () => { fireEvent.click(getByText('1')); await waitFor(() => expect(mockFn).toHaveBeenCalled()); }); + it('in mode=range, onChangeDate fn fires only after both dates clicked', async () => { + const mockFn = jest.fn(); + const { getByText, container } = render( + + ); + fireEvent.click(container.querySelector('button.dropdown-toggle')!); + await waitFor(() => + expect(container.querySelector('.dropdown-menu.show')).toBeInTheDocument() + ); + fireEvent.click(getByText('1')); + expect(mockFn).not.toHaveBeenCalled(); + fireEvent.click(getByText('3')); + expect(mockFn).toHaveBeenCalled(); + }); it('onChange and onClear fn fires when click on Clear button', async () => { const onChangeDate = jest.fn();