Skip to content

Commit

Permalink
feat(types): Add proper dynamic function component type (#37)
Browse files Browse the repository at this point in the history
  • Loading branch information
jquense authored Nov 17, 2021
1 parent 7660dd4 commit 1ad4213
Showing 1 changed file with 32 additions and 5 deletions.
37 changes: 32 additions & 5 deletions src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ export type EventKey = string | number;

export type IntrinsicElementTypes = keyof JSX.IntrinsicElements;

export type AssignProps<
export type AssignPropsWithRef<
Inner extends string | React.ComponentType<any>,
P,
> = Omit<
Expand All @@ -13,12 +13,39 @@ export type AssignProps<
> &
P;

export type { AssignPropsWithRef as AssignProps };

export type AssignPropsWithoutRef<
Inner extends string | React.ComponentType<any>,
P,
> = Omit<
React.ComponentPropsWithoutRef<
Inner extends React.ElementType ? Inner : never
>,
keyof P
> &
P;

export interface DynamicRefForwardingComponent<
TInitial extends string | React.ComponentType<any>,
P = unknown,
P = { children?: React.ReactNode },
> {
<As extends string | React.ComponentType<any> = TInitial>(
props: AssignPropsWithRef<As, { as?: As } & P>,
context?: any,
): React.ReactElement | null;
propTypes?: any;
contextTypes?: any;
defaultProps?: Partial<P>;
displayName?: string;
}

export interface DynamicFunctionComponent<
TInitial extends string | React.ComponentType<any>,
P = { children?: React.ReactNode },
> {
<As extends string | React.ComponentType<any> = TInitial>(
props: React.PropsWithChildren<AssignProps<As, { as?: As } & P>>,
props: AssignPropsWithoutRef<As, { as?: As } & P>,
context?: any,
): React.ReactElement | null;
propTypes?: any;
Expand All @@ -30,13 +57,13 @@ export interface DynamicRefForwardingComponent<
export class DynamicComponent<
As extends string | React.ComponentType<any>,
P = unknown,
> extends React.Component<AssignProps<As, { as?: As } & P>> {}
> extends React.Component<AssignPropsWithRef<As, { as?: As } & P>> {}

// Need to use this instead of typeof Component to get proper type checking.
export type DynamicComponentClass<
As extends string | React.ComponentType<any>,
P = unknown,
> = React.ComponentClass<AssignProps<As, { as?: As } & P>>;
> = React.ComponentClass<AssignPropsWithRef<As, { as?: As } & P>>;

export type SelectCallback = (
eventKey: string | null,
Expand Down

0 comments on commit 1ad4213

Please sign in to comment.