Quiero que mis accesorios sean del tipo A o B. Por ejemplo
export default function App() { type Checkbox = { type: "checkbox"; checked: boolean; }; type Dropdown = { type: "dropdown"; options: Array<any>; selectedOption: number; }; type CheckboxOrDropdown = Checkbox | Dropdown; const Component: FC<CheckboxOrDropdown> = (props) => { return <>"...correct component"</>; }; // these returns are just examples return <Component type="checkbox" checked={true} />; return <Component type="dropdown" options={[]} selectedOption={0} />; }Aquí hay unviolín
¿Cómo puedo lograr lo mismo, pero sin el accesorio "tipo"? ¿Entonces TS reconoce el tipo basado en otros accesorios?
Puede sobrecargar su componente. Por sobrecarga aquí me refiero a la intersección de dos componentes funcionales:
import React, { FC } from 'react' export default function App() { type Checkbox = { checked: boolean; }; type Dropdown = { options: Array<any>; selectedOption: number; }; const Component: FC<Checkbox> & FC<Dropdown> = (props) => { return <>"...correct component"</>; }; return [<Component checked={true} />, <Component options={[]} selectedOption={0} />]; }Esta es la versión menos detallada que conozco.
Si tiene muchos tipos de componentes y no quiere cruzarlos manualmente, puede usar distributivity .
import React, { FC } from 'react' export default function App() { type Checkbox = { checked: boolean; }; type Dropdown = { options: Array<any>; selectedOption: number; }; // credits goes to https://stackoverflow.com/a/50375286 type UnionToIntersection<U> = (U extends any ? (k: U) => void : never) extends ( k: infer I ) => void ? I : never; type Overload<T> = UnionToIntersection<T extends any ? FC<T> : never> const Component: Overload<Checkbox | Dropdown> = (props) => { return <>"...correct component"</>; }; return [<Component checked={true} />, <Component options={[]} selectedOption={0} />]; }