Skip to content

Commit

Permalink
chore(docs): changes to support upcoming ts docs
Browse files Browse the repository at this point in the history
  • Loading branch information
mlaursen committed Nov 24, 2024
1 parent dc86769 commit 87d7dd3
Show file tree
Hide file tree
Showing 11 changed files with 162 additions and 128 deletions.
122 changes: 7 additions & 115 deletions apps/docs/mdx-components.tsx
Original file line number Diff line number Diff line change
@@ -1,122 +1,14 @@
import { Blockquote } from "@/components/Blockquote.jsx";
import { LinkableHeading } from "@/components/LinkableHeading.jsx";
import {
MarkdownCode,
type MarkdownCodeProps,
} from "@/components/MarkdownCode.jsx";
import { MarkdownLink } from "@/components/MarkdownLink.jsx";
import { PackageManagerCodeBlock } from "@/components/PackageManagerCodeBlock.jsx";
import { TableOfContents } from "@/components/TableOfContents/TableOfContents.jsx";
import { TypescriptCodeBlock } from "@/components/TypescriptCodeBlock.jsx";
import { Divider } from "@react-md/core/divider/Divider";
import { Table } from "@react-md/core/table/Table";
import { TableBody } from "@react-md/core/table/TableBody";
import { TableCell } from "@react-md/core/table/TableCell";
import { TableContainer } from "@react-md/core/table/TableContainer";
import { TableFooter } from "@react-md/core/table/TableFooter";
import { TableHeader } from "@react-md/core/table/TableHeader";
import { TableRow } from "@react-md/core/table/TableRow";
import { Typography } from "@react-md/core/typography/Typography";
CUSTOM_MDX_COMPONENTS,
type CustomMDXComponents,
} from "@/components/CustomMdxComponents.jsx";
import { type MDXComponents } from "mdx/types.js";
import {
cloneElement,
isValidElement,
type ComponentType,
type HTMLAttributes,
type ReactElement,
type ReactNode,
} from "react";
import styles from "./mdx-components.module.scss";

interface HeadingProps {
id: string;
children: ReactNode;
}

type RenderChildrenComponent = ComponentType<{ children: ReactNode }>;

interface RedefinedComponents {
h1(props: HeadingProps): ReactElement;
h2(props: HeadingProps): ReactElement;
h3(props: HeadingProps): ReactElement;
h4(props: HeadingProps): ReactElement;
h5(props: HeadingProps): ReactElement;
h6(props: HeadingProps): ReactElement;
hr(props: Record<string, never>): ReactElement;
TableOfContents: typeof TableOfContents;
TypescriptCodeBlock: typeof TypescriptCodeBlock;
PackageManagerCodeBlock: typeof PackageManagerCodeBlock;
table: RenderChildrenComponent;
tr: RenderChildrenComponent;
td: RenderChildrenComponent;
th: RenderChildrenComponent;
}

type Components = Omit<MDXComponents, keyof RedefinedComponents> &
RedefinedComponents;

export function useMDXComponents(components: MDXComponents): Components {
export function useMDXComponents(
components: MDXComponents
): CustomMDXComponents {
return {
...components,
h1: (props) => <LinkableHeading {...props} level={2} />,
h2: (props) => <LinkableHeading {...props} level={3} />,
h3: (props) => <LinkableHeading {...props} level={4} />,
h4: (props) => <LinkableHeading {...props} level={5} />,
h5: (props) => <LinkableHeading {...props} level={6} />,
h6: (props) => <LinkableHeading {...props} level={6} />,
p: (props) => <Typography {...props} margin="bottom" />,
a: MarkdownLink,
hr: () => <Divider />,
ul: (props) => <Typography type="body-1" as="ul" {...props} />,
ol: (props) => <Typography type="body-1" as="ol" {...props} />,
blockquote: (props) => <Blockquote {...props} />,
pre: (props: HTMLAttributes<HTMLPreElement>) => {
const { children, ...codeProps } = props;
if (!isValidElement<MarkdownCodeProps>(children)) {
throw new Error("Invalid pre element");
}

return cloneElement(children, codeProps);
},
code: MarkdownCode,
TableOfContents,
TypescriptCodeBlock,
PackageManagerCodeBlock,

// switch to the commented out code below if server-side only context
// is implemented by React
table: (props) => (
<TableContainer className={styles.table}>
<Table {...props} />
</TableContainer>
),
thead: TableHeader,
tbody: TableBody,
tfoot: TableFooter,
tr: TableRow,
td: TableCell,
th: TableCell,
// table: ({ children }) => (
// <div className={tableContainer()}>
// <table className={table({ fullWidth: true })}>{children}</table>
// </div>
// ),
// tr: ({ children }) => (
// <tr className={tableRow({ disableHover: true })}>{children}</tr>
// ),
// td: ({ children }) => <td className={tableCell()}>{children}</td>,
// th: ({ children }) => (
// <th
// className={tableCell({
// header: true,
// hAlign: "left",
// })}
// >
// {children}
// </th>
// ),
// thead: ({ children }) => {
// return <thead className={tableHeader()}>{children}</thead>;
// },
...CUSTOM_MDX_COMPONENTS,
};
}
7 changes: 2 additions & 5 deletions apps/docs/src/app/(main)/HomePageSection.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { LinkableHeading } from "@/components/LinkableHeading.jsx";
import { slug } from "@/utils/slug.js";
import { TextContainer } from "@react-md/core/typography/TextContainer";
import { Typography } from "@react-md/core/typography/Typography";
import { type ReactElement, type ReactNode } from "react";
Expand All @@ -14,11 +15,7 @@ export function HomePageSection(props: HomePageSectionProps): ReactElement {
const { heading, paragraph, children } = props;
return (
<TextContainer className={styles.container}>
<LinkableHeading
id={heading.toLowerCase().replace(/\s+/g, "0")}
level={3}
className={styles.row}
>
<LinkableHeading id={slug(heading)} level={3} className={styles.row}>
{heading}
</LinkableHeading>
<Typography as="p" type="headline-6">
Expand Down
File renamed without changes.
122 changes: 122 additions & 0 deletions apps/docs/src/components/CustomMdxComponents.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,122 @@
import { Blockquote } from "@/components/Blockquote.jsx";
import { LinkableHeading } from "@/components/LinkableHeading.jsx";
import {
MarkdownCode,
type MarkdownCodeProps,
} from "@/components/MarkdownCode.jsx";
import { MarkdownLink } from "@/components/MarkdownLink.jsx";
import { PackageManagerCodeBlock } from "@/components/PackageManagerCodeBlock.jsx";
import { TableOfContents } from "@/components/TableOfContents/TableOfContents.jsx";
import { TypescriptCodeBlock } from "@/components/TypescriptCodeBlock.jsx";
import { Divider } from "@react-md/core/divider/Divider";
import { Table } from "@react-md/core/table/Table";
import { TableBody } from "@react-md/core/table/TableBody";
import { TableCell } from "@react-md/core/table/TableCell";
import { TableContainer } from "@react-md/core/table/TableContainer";
import { TableFooter } from "@react-md/core/table/TableFooter";
import { TableHeader } from "@react-md/core/table/TableHeader";
import { TableRow } from "@react-md/core/table/TableRow";
import { Typography } from "@react-md/core/typography/Typography";
import { type MDXComponents } from "mdx/types.js";
import {
cloneElement,
isValidElement,
type ComponentType,
type HTMLAttributes,
type ReactElement,
type ReactNode,
} from "react";
import styles from "./CustomMdxComponents.module.scss";

interface HeadingProps {
id: string;
children: ReactNode;
}

type RenderChildrenComponent = ComponentType<{ children: ReactNode }>;

interface RedefinedComponents {
h1(props: HeadingProps): ReactElement;
h2(props: HeadingProps): ReactElement;
h3(props: HeadingProps): ReactElement;
h4(props: HeadingProps): ReactElement;
h5(props: HeadingProps): ReactElement;
h6(props: HeadingProps): ReactElement;
hr(props: Record<string, never>): ReactElement;
TableOfContents: typeof TableOfContents;
TypescriptCodeBlock: typeof TypescriptCodeBlock;
PackageManagerCodeBlock: typeof PackageManagerCodeBlock;
table: RenderChildrenComponent;
tr: RenderChildrenComponent;
td: RenderChildrenComponent;
th: RenderChildrenComponent;
}

export type CustomMDXComponents = Omit<
MDXComponents,
keyof RedefinedComponents
> &
RedefinedComponents;

export const CUSTOM_MDX_COMPONENTS: CustomMDXComponents = {
h1: (props) => <LinkableHeading {...props} level={2} />,
h2: (props) => <LinkableHeading {...props} level={3} />,
h3: (props) => <LinkableHeading {...props} level={4} />,
h4: (props) => <LinkableHeading {...props} level={5} />,
h5: (props) => <LinkableHeading {...props} level={6} />,
h6: (props) => <LinkableHeading {...props} level={6} />,
p: (props) => <Typography {...props} margin="bottom" />,
a: MarkdownLink,
hr: () => <Divider />,
ul: (props) => <Typography type="body-1" as="ul" {...props} />,
ol: (props) => <Typography type="body-1" as="ol" {...props} />,
blockquote: (props) => <Blockquote {...props} />,
pre: (props: HTMLAttributes<HTMLPreElement>) => {
const { children, ...codeProps } = props;
if (!isValidElement<MarkdownCodeProps>(children)) {
throw new Error("Invalid pre element");
}

return cloneElement(children, codeProps);
},
code: MarkdownCode,
TableOfContents,
TypescriptCodeBlock,
PackageManagerCodeBlock,

// switch to the commented out code below if server-side only context
// is implemented by React
table: (props) => (
<TableContainer className={styles.table}>
<Table {...props} />
</TableContainer>
),
thead: TableHeader,
tbody: TableBody,
tfoot: TableFooter,
tr: TableRow,
td: TableCell,
th: TableCell,
// table: ({ children }) => (
// <div className={tableContainer()}>
// <table className={table({ fullWidth: true })}>{children}</table>
// </div>
// ),
// tr: ({ children }) => (
// <tr className={tableRow({ disableHover: true })}>{children}</tr>
// ),
// td: ({ children }) => <td className={tableCell()}>{children}</td>,
// th: ({ children }) => (
// <th
// className={tableCell({
// header: true,
// hAlign: "left",
// })}
// >
// {children}
// </th>
// ),
// thead: ({ children }) => {
// return <thead className={tableHeader()}>{children}</thead>;
// },
};
16 changes: 16 additions & 0 deletions apps/docs/src/utils/slug.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
/**
* Very simple content slugger for title headers when the content is unique. A
* real slugger should be used for other use cases.
*
* @example Main Usage
* ```tsx
* const content = "This is Some Title";
*
* <LinkableHeading id={slug()} level={1}>{content}</LinkableHeading>
*
* // id === "this-is-some-title"
* ```
*/
export function slug(value: string): string {
return value.toLowerCase().replace(/\s+/g, "-");
}
1 change: 0 additions & 1 deletion packages/core/eslint.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
import { config, configs, gitignore } from "@mlaursen/eslint-config";
import { join } from "node:path";

// eslint-disable-next-line no-undef
const strict = process.env.STRICT_TYPING === "true";

const frontend = strict
Expand Down
4 changes: 2 additions & 2 deletions packages/core/src/files/validation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -347,7 +347,7 @@ export interface ValidatedFilesResult<CustomError> {
* };
* ```
*
* @typeparam E - An optional custom file validation error.
* @typeParam E - An optional custom file validation error.
* @param files - The list of files to check
* @param options - The {@link FilesValidationOptions}
* @returns the {@link ValidatedFilesResult}
Expand All @@ -364,7 +364,7 @@ export type FilesValidator<CustomError = never> = (
* {@link useFileUpload} that ensures the {@link FilesValidationOptions} are
* enforced before allowing a file to be uploaded.
*
* @typeparam E - An optional custom file validation error.
* @typeParam E - An optional custom file validation error.
* @param files - The list of files to check
* @param options - The {@link FilesValidationOptions}
* @returns the {@link ValidatedFilesResult}
Expand Down
6 changes: 4 additions & 2 deletions packages/core/src/icon/FontIcon.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,11 @@ export interface FontIconProps

/**
* Any children to render to create the font icon. This is required for
* material-icons.
* material-icons. For example:
*
* @example `<FontIcon>clear</FontIcon>`
* ```tsx
* <FontIcon>clear</FontIcon>
* ```
*/
children?: ReactNode;
}
Expand Down
2 changes: 1 addition & 1 deletion packages/core/src/icon/TextIconSpacing.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ export interface TextIconSpacingProps {
* If this is not a valid react element, the icon will be wrapped in a
* `<span>` instead with the class names applied.
*/
icon?: ReactElement | ReactNode;
icon?: ReactElement<{ className?: string }> | ReactNode;

/**
* Boolean if the icon should appear after the text instead of before.
Expand Down
2 changes: 1 addition & 1 deletion packages/core/src/utils/RenderRecursively.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ export interface RenderRecursivelyProps<
* ```
*
* @see {@link getRecursiveItemKey}
* @defaultValue `({ index, depth }) => ${depth}-${index}`.
* @defaultValue `` ({ index, depth }) => `${depth}-${index}` ``
*/
getItemKey?: (options: RecursiveItemKeyOptions<Item>) => string;
}
Expand Down
8 changes: 7 additions & 1 deletion packages/docs-generator/eslint.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,13 @@
import { config, configs, gitignore } from "@mlaursen/eslint-config";
import { join } from "node:path";

const strict = process.env.STRICT_TYPING === "true";

const typescript = strict
? configs.typescriptTypeChecking(import.meta.dirname)
: configs.typescript;

export default config(
gitignore(join(import.meta.url, "..", "..")),
...configs.typescriptTypeChecking(import.meta.dirname)
...typescript
);

0 comments on commit 87d7dd3

Please sign in to comment.