Bug description

Using setControlValue()allows to update the value of a control panel input which trigger also the refresh of the whole chart explorer inputs set including the Data table section.

The issue reside in the fact that the filter input of the Data table section is taking the focus when setControlValue() which end in a UX behavior obstruction by the shouldFocus bit introduced in FilterInput component: see the following chunk: https://github.com/apache/superset/blob/34b1db219cbe155a9cf57f7c9abb36492c482106/superset-frontend/src/explore/components/DataTablesPane/components/DataTableControls.tsx#L71

Screenshots/recordings

The following screencast show that the focus is stolen by the filter input of Data table section while the user is trying to input another control which set to trigger on change (renderTrigger: true).

https://github.com/user-attachments/assets/87857b64-2b5e-496f-a67e-2be5977b28e9

Superset version

4.1.1

Python version

3.10

Node version

18 or greater

Browser

Chrome

Additional context

Developing a custom plugin...

Checklist

  • [x] I have searched Superset docs and Slack and didn't find a solution to my problem.
  • [x] I have searched the GitHub issue tracker and didn't find a similar bug report.
  • [x] I have checked Superset's logs for errors and if I found a relevant Python stacktrace, I included it here as text in the "additional context" section.

Comment From: dosubot[bot]

Hey, @trepmag! 👋 I'm here to help you with bug fixes, answer your questions, and guide you on your journey to becoming a contributor.

To address the focus issue caused by the setControlValue() function in the DataTableControls component, you can modify the FilterInput component to focus the input element only under specific conditions. This can be achieved by updating the useEffect hook to include shouldFocus as a dependency, ensuring that the input only gains focus when shouldFocus changes to true. Here's a potential solution:

export const FilterInput = ({
  onChangeHandler,
  shouldFocus = false,
}: {
  onChangeHandler(filterText: string): void;
  shouldFocus?: boolean;
}) => {
  const inputRef: RefObject<any> = useRef(null);

  useEffect(() => {
    // Focus the input element only when a specific condition is met
    if (inputRef.current && shouldFocus) {
      inputRef.current.focus();
    }
  }, [shouldFocus]); // Add shouldFocus as a dependency

  const theme = useTheme();
  const debouncedChangeHandler = debounce(onChangeHandler, SLOW_DEBOUNCE);
  return (
    <Input
      prefix={<Icons.SearchOutlined iconSize="l" />}
      placeholder={t('Search')}
      onChange={(event: any) => {
        const filterText = event.target.value;
        debouncedChangeHandler(filterText);
      }}
      css={css`
        width: 200px;
        margin-right: ${theme.gridUnit * 2}px;
      `}
      ref={inputRef}
    />
  );
};

By making this change, the input will only gain focus when shouldFocus changes, which should help improve the user experience by preventing unwanted focus changes [1].

To continue talking to Dosu, mention @dosu.


Help Dosu learn! Give it feedback: Great Response | Irrelevant Answer | Incorrect Sources | Too Verbose | Hallucination | Bug Report | Other

Comment From: sadpandajoe

Maybe @eschutho @justinpark or @kgabryje can give some insight on this issue.