import type { HTMLAttributes, LiHTMLAttributes, ReactNode } from "react";
import { cx } from "../../utils/cx.utils";
import "./list.component.css";
/**
* List style rendered by {@link List}. `"unordered"` renders a `
` with
* square bullets, `"ordered"` renders an `` with numbers, and
* `"detailed"` renders a bordered `` whose items show a title and
* description (see {@link ListItemProps}). Defaults to `"unordered"`.
*/
export type ListAs = "unordered" | "ordered" | "detailed";
/** Props accepted by {@link List}. */
export interface ListProps extends HTMLAttributes {
/** `"unordered"`, `"ordered"`, or `"detailed"`. Defaults to `"unordered"`. */
as?: ListAs;
}
/** Props accepted by {@link ListItem}. */
export interface ListItemProps extends Omit, "title"> {
/** Bold title, used by the `"detailed"` {@link List} variant instead of `children`. */
title?: ReactNode;
/** Supporting description, used by the `"detailed"` {@link List} variant instead of `children`. */
description?: ReactNode;
}
/**
* List component rendering `` (default), ``, or a bordered
* title/description layout via `as`. Unordered items use a small black
* square marker instead of the browser default. Use with {@link ListItem}
* for list rows.
*
* @example
* ```tsx
*
* First
* Second
*
*
* First
* Second
*
*
*
*
*
* ```
*/
export function List({ as = "unordered", className, children, ...rest }: ListProps) {
const Tag = as === "ordered" ? "ol" : "ul";
return (
)}
>
{children}
);
}
/** List item, used inside {@link List}. Also available as {@link List.Item}. */
export function ListItem({ className, children, title, description, ...rest }: ListItemProps) {
return (
-
{title !== undefined || description !== undefined ? (
{title !== undefined ? {title} : null}
{description !== undefined ? (
{description}
) : null}
) : (
children
)}
);
}
List.Item = ListItem;