diff --git a/superset-frontend/src/explore/components/controls/DateFilterControl/DateFilterLabel.tsx b/superset-frontend/src/explore/components/controls/DateFilterControl/DateFilterLabel.tsx
index e5113d122cda0..ebdd716b91496 100644
--- a/superset-frontend/src/explore/components/controls/DateFilterControl/DateFilterLabel.tsx
+++ b/superset-frontend/src/explore/components/controls/DateFilterControl/DateFilterLabel.tsx
@@ -307,7 +307,11 @@ export default function DateFilterLabel(props: DateFilterControlProps) {
)}
{frame === 'Custom' && (
-
+
)}
{frame === 'No filter' &&
}
diff --git a/superset-frontend/src/explore/components/controls/DateFilterControl/components/CustomFrame.tsx b/superset-frontend/src/explore/components/controls/DateFilterControl/components/CustomFrame.tsx
index f046b7f0306ff..7a880a82953e7 100644
--- a/superset-frontend/src/explore/components/controls/DateFilterControl/components/CustomFrame.tsx
+++ b/superset-frontend/src/explore/components/controls/DateFilterControl/components/CustomFrame.tsx
@@ -166,6 +166,11 @@ export function CustomFrame(props: FrameComponentProps) {
}
allowClear={false}
locale={datePickerLocale}
+ getPopupContainer={triggerNode =>
+ props.isOverflowingFilterBar
+ ? (triggerNode.parentNode as HTMLElement)
+ : document.body
+ }
/>
)}
@@ -219,6 +224,11 @@ export function CustomFrame(props: FrameComponentProps) {
}
allowClear={false}
locale={datePickerLocale}
+ getPopupContainer={triggerNode =>
+ props.isOverflowingFilterBar
+ ? (triggerNode.parentNode as HTMLElement)
+ : document.body
+ }
/>
)}
@@ -277,6 +287,11 @@ export function CustomFrame(props: FrameComponentProps) {
allowClear={false}
className="control-anchor-to-datetime"
locale={datePickerLocale}
+ getPopupContainer={triggerNode =>
+ props.isOverflowingFilterBar
+ ? (triggerNode.parentNode as HTMLElement)
+ : document.body
+ }
/>
)}
diff --git a/superset-frontend/src/explore/components/controls/DateFilterControl/tests/CustomFrame.test.tsx b/superset-frontend/src/explore/components/controls/DateFilterControl/tests/CustomFrame.test.tsx
index f566d4f0fe7fe..e5ed701f32d66 100644
--- a/superset-frontend/src/explore/components/controls/DateFilterControl/tests/CustomFrame.test.tsx
+++ b/superset-frontend/src/explore/components/controls/DateFilterControl/tests/CustomFrame.test.tsx
@@ -28,7 +28,9 @@ import {
import userEvent from '@testing-library/user-event';
import { CustomFrame } from '../components';
+const TODAY = '2024-06-03';
jest.useFakeTimers();
+jest.setSystemTime(new Date(TODAY).getTime());
const emptyValue = '';
const nowValue = 'now : now';
@@ -280,3 +282,98 @@ test('should translate Date Picker', async () => {
expect(screen.getByText('sa')).toBeInTheDocument();
expect(screen.getByText('di')).toBeInTheDocument();
});
+
+test('calls onChange when START Specific Date/Time is selected', async () => {
+ const onChange = jest.fn();
+ render(
+
+
+ ,
+ );
+
+ await waitForElementToBeRemoved(() => screen.queryByLabelText('Loading'));
+
+ const specificDateTimeOptions = screen.getAllByText('Specific Date/Time');
+ expect(specificDateTimeOptions.length).toBe(2);
+
+ const calendarIcons = screen.getAllByRole('img', { name: 'calendar' });
+ userEvent.click(calendarIcons[0]);
+
+ const randomDate = screen.getByTitle('2021-03-11');
+ userEvent.click(randomDate);
+
+ const okButton = screen.getByText('Ok');
+ userEvent.click(okButton);
+
+ expect(onChange).toHaveBeenCalled();
+});
+
+test('calls onChange when END Specific Date/Time is selected', async () => {
+ const onChange = jest.fn();
+ render(
+
+
+ ,
+ );
+
+ await waitForElementToBeRemoved(() => screen.queryByLabelText('Loading'));
+
+ const specificDateTimeOptions = screen.getAllByText('Specific Date/Time');
+ expect(specificDateTimeOptions.length).toBe(2);
+
+ const calendarIcons = screen.getAllByRole('img', { name: 'calendar' });
+ userEvent.click(calendarIcons[1]);
+
+ const randomDate = screen.getByTitle('2021-03-28');
+ userEvent.click(randomDate);
+
+ const okButton = screen.getByText('Ok');
+ userEvent.click(okButton);
+
+ expect(onChange).toHaveBeenCalled();
+});
+
+test('calls onChange when a date is picked from anchor mode date picker', async () => {
+ const onChange = jest.fn();
+ render(
+
+
+ ,
+ );
+
+ await waitForElementToBeRemoved(() => screen.queryByLabelText('Loading'));
+
+ const relativeDateTimeOptions = screen.getAllByText('Relative Date/Time');
+ expect(relativeDateTimeOptions.length).toBe(2);
+
+ await waitFor(() =>
+ expect(screen.getByText('Anchor to')).toBeInTheDocument(),
+ );
+
+ const dateTimeRadio = screen.getByRole('radio', { name: 'Date/Time' });
+
+ expect(dateTimeRadio).toBeChecked();
+
+ const calendarIcon = screen.getByRole('img', { name: 'calendar' });
+ userEvent.click(calendarIcon);
+
+ const randomDate = screen.getByTitle('2024-06-05');
+ userEvent.click(randomDate);
+
+ const okButton = screen.getByText('Ok');
+ userEvent.click(okButton);
+
+ expect(onChange).toHaveBeenCalled();
+});
diff --git a/superset-frontend/src/explore/components/controls/DateFilterControl/types.ts b/superset-frontend/src/explore/components/controls/DateFilterControl/types.ts
index 7062b4858065b..0d0fbb9724d73 100644
--- a/superset-frontend/src/explore/components/controls/DateFilterControl/types.ts
+++ b/superset-frontend/src/explore/components/controls/DateFilterControl/types.ts
@@ -101,6 +101,7 @@ export type CurrentRangeType =
export type FrameComponentProps = {
onChange: (timeRange: string) => void;
value: string;
+ isOverflowingFilterBar?: boolean;
};
export interface DateFilterControlProps {