question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

[Autocomplete] Type issue once wrapped with styled()

See original GitHub issue

I’m trying to use Autocomplete with styled-components in typescript environment. But when using the component, linter start to complain about styled autocomplete component. I checked for this issue but not sure if it is duplicate. Could not find something related?

  • The issue is present in the latest release.
  • I have searched the issues of this repository and believe that this is not a duplicate.

Current Behavior 😯

No overload matches this call.
  Overload 2 of 2, '(props: StyledComponentPropsWithAs<(<T, Multiple extends boolean | undefined = undefined, DisableClearable extends boolean | undefined = undefined, FreeSolo extends boolean | undefined = undefined>(props: AutocompleteProps<T, Multiple, DisableClearable, FreeSolo>) => Element), DefaultTheme, {}, never>): ReactElement<...>', gave the following error.
    Type '(_event: React.ChangeEvent<{}>, value: OptionData | null) => void | undefined' is not assignable to type '(event: ChangeEvent<{}>, value: unknown, reason: AutocompleteChangeReason, details?: AutocompleteChangeDetails<unknown> | undefined) => void'.
  Overload 2 of 2, '(props: StyledComponentPropsWithAs<(<T, Multiple extends boolean | undefined = undefined, DisableClearable extends boolean | undefined = undefined, FreeSolo extends boolean | undefined = undefined>(props: AutocompleteProps<T, Multiple, DisableClearable, FreeSolo>) => Element), DefaultTheme, {}, never>): ReactElement<...>', gave the following error.
    Type '(data: OptionData) => string' is not assignable to type '(option: unknown) => string'.
  Overload 2 of 2, '(props: StyledComponentPropsWithAs<(<T, Multiple extends boolean | undefined = undefined, DisableClearable extends boolean | undefined = undefined, FreeSolo extends boolean | undefined = undefined>(props: AutocompleteProps<T, Multiple, DisableClearable, FreeSolo>) => Element), DefaultTheme, {}, never>): ReactElement<...>', gave the following error.
    Type '(option: OptionData) => boolean' is not assignable to type '(option: unknown, value: unknown) => boolean'.  TS2769
     62 |   return (
     63 |     <StyledFormControl>
  > 64 |       <StyledAutocomplete
       |       ^
    65 |         id={id}
    66 |         options={options}
    67 |         // classes={classes}

I started to add one prop by another then i realised the following:

<StyledAutocomplete
        id={id}
        options={options}                                                                          // type of OptionData[]
        onChange={(_event: React.ChangeEvent<{}>, value) =>        // <<== if i set value: OptionData | null linter will complain
          onChange && onChange(value as OptionData | null)
        }
        value={currentValue}
        getOptionLabel={data => (data as OptionData).label}             // <<== if i set data: OptionData | null linter will complain
        getOptionSelected={option =>                                                // <<== if i set option: OptionData | null linter will complain
          (option as OptionData).label === currentValue?.label
        }
        autoHighlight
        renderInput={params => (
          <TextField
            {...params}
            error={!!error}
            name={name}
            label={label}
            variant="standard"
          />
        )}
      />

Expected Behavior 🤔

Would it be possible to take T type of the options property and pass it throw all function that working with the same type ?

Steps to Reproduce 🕹

Simply styled Autocomplete with styled-components.

[...]

const StyledAutocomplete = styled(Autocomplete)`
  & .MuiInputBase-root {
    height: 4.1rem;
  }
  & label: {
    fontsize: 2rem;
  }
`;

[....]


<StyledAutocomplete
        id={id}
        options={options}
        // onChange={(_event: React.ChangeEvent<{}>, value: OptionData | null) =>                 // <<== Linter error
        //   onChange && onChange(value)
        // }
        value={currentValue}
        // getOptionLabel={(data: OptionData) => data.label}         // <<== Linter error
        // getOptionSelected={(option: OptionData) =>.                  // <<== Linter error
        //   option.label === currentValue?.label
        // }
        autoHighlight
        renderInput={params => (
          <TextField
            {...params}
            error={!!error}
            name={name}
            label={label}
            variant="standard"
          />
        )}
      />

Context 🔦

As consistency we use styled-components as a generic way of styling. We need to use the same here. The styling suggestion works fine using makeStyles

Your Environment 🌎

Tech Version
Material-UI v4.9.12
React 16.13.1
Browser Chrome 83.0.4103.116
TypeScript 3.8.0
OS MacOS.

Issue Analytics

  • State:open
  • Created 3 years ago
  • Reactions:4
  • Comments:15 (6 by maintainers)

github_iconTop GitHub Comments

3reactions
oliviertassinaricommented, Jun 27, 2021
2reactions
hiahmedhameedcommented, Nov 6, 2020

@vinikatyal

I’m casting argument types as follow:

[...]

interface AutocompleteOptionData {
  value: string;
  label: string;
}

[...]

<StyledAutocomplete
        id={id}
        options={options}
        onChange={(_event: React.ChangeEvent<{}>, value) =>
          onChange &&
          onChange(
            (value as AutocompleteOptionData | null) || {
              label: '',
              value: '',
            }
          )
        }
        value={currentValue}
        getOptionLabel={data => (data as AutocompleteOptionData).label}
        getOptionSelected={option =>
          (option as AutocompleteOptionData).label === currentValue?.label
        }
        renderInput={params => (
          <TextField
            {...params}
            error={!!error}
            name={name}
            label={label}
            variant="standard"
          />
        )}
      />

[...]

TBH, Autocomplete is not easy component but i understand that is designed to be generic.

Read more comments on GitHub >

github_iconTop Results From Across the Web

[Autocomplete] Type issue once wrapped with styled() #21727
I'm trying to use Autocomplete with styled-components in typescript environment. But when using the component, linter start to complain ...
Read more >
Styling MUI Autocomplete with styled-components
I have the AutoComplete component from mui in my code, and I'm using it with their TextField component like so: <StyledAutoComplete id="xxx" ...
Read more >
Wrapping a MUI component with styled ... - YouTrack
Both components should autocomplete the alignContent prop, add ={} and then suggest values from the string union. What happens instead? The MUI import...
Read more >
Using styled-components in TypeScript: A tutorial with examples
Here, you can learn how to build and style a TypeScript app using styled-components, with an e-commerce page as an example.
Read more >
Releases - styled-components
Add suppressClassNameWarning prop to disable warning when wrapping a React component with styled() and the className isn't used, by @Fer0x (see #2156).
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found