1import React from 'react';
2
3import { InlineCode } from '~/components/base/code';
4import { B, P } from '~/components/base/paragraph';
5import { H2, H3Code } from '~/components/plugins/Headings';
6import {
7  CommentData,
8  GeneratedData,
9  MethodSignatureData,
10  PropsDefinitionData,
11} from '~/components/plugins/api/APIDataTypes';
12import { APISectionDeprecationNote } from '~/components/plugins/api/APISectionDeprecationNote';
13import APISectionProps from '~/components/plugins/api/APISectionProps';
14import {
15  CommentTextBlock,
16  resolveTypeName,
17  getComponentName,
18  STYLES_APIBOX,
19} from '~/components/plugins/api/APISectionUtils';
20
21export type APISectionComponentsProps = {
22  data: GeneratedData[];
23  componentsProps: PropsDefinitionData[];
24};
25
26const getComponentComment = (comment: CommentData, signatures: MethodSignatureData[]) =>
27  comment || (signatures?.[0]?.comment ?? undefined);
28
29const renderComponent = (
30  { name, comment, type, extendedTypes, children, signatures }: GeneratedData,
31  componentsProps?: PropsDefinitionData[]
32): JSX.Element => {
33  const resolvedType = extendedTypes?.length ? extendedTypes[0] : type;
34  const resolvedName = getComponentName(name, children);
35  const extractedComment = getComponentComment(comment, signatures);
36  return (
37    <div key={`component-definition-${resolvedName}`} css={STYLES_APIBOX}>
38      <APISectionDeprecationNote comment={extractedComment} />
39      <H3Code>
40        <InlineCode>{resolvedName}</InlineCode>
41      </H3Code>
42      {resolvedType && (
43        <P>
44          <B>Type:</B> <InlineCode>{resolveTypeName(resolvedType)}</InlineCode>
45        </P>
46      )}
47      <CommentTextBlock comment={extractedComment} />
48      {componentsProps && componentsProps.length ? (
49        <APISectionProps
50          data={componentsProps}
51          header={componentsProps.length === 1 ? 'Props' : `${resolvedName}Props`}
52        />
53      ) : null}
54    </div>
55  );
56};
57
58const APISectionComponents = ({ data, componentsProps }: APISectionComponentsProps) =>
59  data?.length ? (
60    <>
61      <H2 key="components-header">{data.length === 1 ? 'Component' : 'Components'}</H2>
62      {data.map(component =>
63        renderComponent(
64          component,
65          componentsProps.filter(cp =>
66            cp.name.includes(getComponentName(component.name, component.children))
67          )
68        )
69      )}
70    </>
71  ) : null;
72
73export default APISectionComponents;
74