Manifest Debugger

All66 components ok241 stories ok2 docs ok
Using react-component-meta. Generation took 27.2s.

Components

Badge

design-system-components-badge · ../packages/ui/src/badge/stories/index.story.tsx
A badge component for displaying labels with semantic intent.
Prop types (react-component-meta) 5 prop types
Component: ../packages/ui/src/badge/index.ts::Badge
Props:
/**
 * The text to display in the badge.
 */
children: string

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * The semantic intent of the badge, communicating its meaning through color.
 */
intent?: "high" | "medium" | "low" | "stable" | "informational" | "draft" | "none" = 'none'

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Imports
import { Badge } from "@wordpress/ui";
import { Fragment } from "@wordpress/element";
Default story ok
const Default = () => <Badge>Badge</Badge>;
High story ok
const High = () => <Badge intent="high" />;
Medium story ok
const Medium = () => <Badge intent="medium" />;
Low story ok
const Low = () => <Badge intent="low" />;
Stable story ok
const Stable = () => <Badge intent="stable" />;
Informational story ok
const Informational = () => <Badge intent="informational" />;
Draft story ok
const Draft = () => <Badge intent="draft" />;
None story ok
const None = () => <Badge intent="none" />;
All Intents story ok
const AllIntents = ( args ) => (
    <div
        style={ {
            display: 'grid',
            gridTemplateColumns: 'max-content min-content',
            gap: '1rem',
            color: 'var(--wpds-color-foreground-content-neutral)',
        } }
    >
        { (
            [
                'high',
                'medium',
                'low',
                'stable',
                'informational',
                'draft',
                'none',
            ] as const
         ).map( ( intent ) => (
            <Fragment key={ intent }>
                <div
                    style={ {
                        paddingInlineEnd: '1rem',
                        display: 'flex',
                        alignItems: 'center',
                    } }
                >
                    { intent }
                </div>
                <div
                    style={ {
                        padding: '0.5rem 1rem',
                        display: 'flex',
                        alignItems: 'center',
                    } }
                >
                    <Badge { ...args } intent={ intent } />
                </div>
            </Fragment>
        ) ) }
    </div>
);

BaseControl

components-basecontrol · ../packages/components/src/base-control/stories/index.story.tsx
`BaseControl` is a low-level component used to generate labels and help text for components handling user inputs. ```jsx import { BaseControl, useBaseControlProps } from '@wordpress/components'; // Render a `BaseControl` for a textarea input const MyCustomTextareaControl = ({ children, ...baseProps }) => ( // `useBaseControlProps` is a convenience hook to get the props for the `BaseControl` // and the inner control itself. Namely, it takes care of generating a unique `id`, // properly associating it with the `label` and `help` elements. const { baseControlProps, controlProps } = useBaseControlProps( baseProps ); return ( <BaseControl { ...baseControlProps }> <textarea { ...controlProps }> { children } </textarea> </BaseControl> ); ); ```
Prop types (react-component-meta) 8 prop types
Component: ../packages/components/src/base-control/index.tsx::default
Props:
/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * The HTML element or React component to render the component as.
 */
as?: keyof IntrinsicElements | null | undefined

/**
 * The content to be displayed within the `BaseControl`.
 */
children: ReactNode

className?: string

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * The HTML `id` of the control element (passed in as a child to `BaseControl`) to which labels and help text are being generated.
 * This is necessary to accessibly associate the label with that element.
 * 
 * The recommended way is to use the `useBaseControlProps` hook, which takes care of generating a unique `id` for you.
 * Otherwise, if you choose to pass an explicit `id` to this prop, you are responsible for ensuring the uniqueness of the `id`.
 */
id?: string

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode
Imports
import { BaseControl, Button } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	const { baseControlProps, controlProps } = useBaseControlProps( props );

	return (
		<BaseControl { ...baseControlProps }>
			<textarea style={ { display: 'block' } } { ...controlProps } />
		</BaseControl>
	);
};
With Help Text story ok
const WithHelpText = ( props ) => {
	const { baseControlProps, controlProps } = useBaseControlProps( props );

	return (
		<BaseControl { ...baseControlProps }>
			<textarea style={ { display: 'block' } } { ...controlProps } />
		</BaseControl>
	);
};
With Visual Label story ok
`BaseControl.VisualLabel` is used to render a purely visual label inside a `BaseControl` component. It should only be used in cases where the children being rendered inside `BaseControl` are already accessibly labeled, e.g., a button, but we want an additional visual label for that section equivalent to the labels `BaseControl` would otherwise use if the `label` prop was passed.
const WithVisualLabel = ( props ) => {
	BaseControl.VisualLabel.displayName = 'BaseControl.VisualLabel';

	return (
		<BaseControl { ...props }>
			<BaseControl.VisualLabel>Visual label</BaseControl.VisualLabel>
			<div>
				<Button __next40pxDefaultSize variant="secondary">
					Select an author
				</Button>
			</div>
		</BaseControl>
	);
};
BaseControl.VisualLabel 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/base-control/index.tsx
import { BaseControl } from "@wordpress/components";
Component: ../packages/components/src/base-control/index.tsx::default (react-component-meta)
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The content to be displayed within the `BaseControl.VisualLabel`.
 */
children: ReactNode

Button

components-button · ../packages/components/src/button/stories/index.story.tsx
Lets users take actions and make choices with a single click or tap. ```jsx import { Button } from '@wordpress/components'; const Mybutton = () => ( <Button variant="primary" onClick={ handleClick } > Click here </Button> ); ```
Prop types (react-component-meta) 28 prop types
Component: ../packages/components/src/button/index.tsx::default
Props:
/**
 * Whether to keep the button focusable when disabled.
 */
__experimentalIsFocusable?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the
 * default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined = false

/**
 * Whether to keep the button focusable when disabled.
 * 
 * In most cases, it is recommended to set this to `true`. Disabling a control without maintaining focusability
 * can cause accessibility issues, by hiding their presence from screen reader users,
 * or by preventing focus from returning to a trigger element.
 * 
 * Learn more about the [focusability of disabled controls](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#focusabilityofdisabledcontrols)
 * in the WAI-ARIA Authoring Practices Guide.
 */
accessibleWhenDisabled?: boolean | undefined = false

/**
 * The button's children.
 */
children?: ReactNode

/**
 * A visually hidden accessible description for the button.
 */
describedBy?: string

/**
 * A visually hidden accessible description for the button.
 */
description?: string

/**
 * Whether the button is disabled. If `true`, this will force a `button` element
 * to be rendered, even when an `href` is given.
 * 
 * In most cases, it is recommended to also set the `accessibleWhenDisabled` prop to `true`.
 */
disabled?: boolean | undefined

/**
 * If provided, renders `a` instead of `button`.
 */
href?: string

/**
 * If provided, renders an Icon component inside the button.
 */
icon?: IconType | null | undefined

/**
 * If provided with `icon`, sets the position of icon relative to the `text`.
 */
iconPosition?: "left" | "right" = 'left'

/**
 * If provided with `icon`, sets the icon size.
 * Please refer to the Icon component for more details regarding
 * the default value of its `size` prop.
 */
iconSize?: number

/**
 * Indicates activity while a action is being performed.
 */
isBusy?: boolean | undefined

/**
 * Gives the button a default style.
 */
isDefault?: boolean | undefined

/**
 * Renders a red text-based button style to indicate destructive behavior.
 */
isDestructive?: boolean | undefined

/**
 * Gives the button a link style.
 */
isLink?: boolean | undefined

/**
 * Renders a pressed button style.
 */
isPressed?: boolean | undefined

/**
 * Gives the button a primary style.
 */
isPrimary?: boolean | undefined

/**
 * Gives the button a default style.
 */
isSecondary?: boolean | undefined

/**
 * Decreases the size of the button.
 */
isSmall?: boolean | undefined

/**
 * Gives the button a text-based style.
 */
isTertiary?: boolean | undefined

/**
 * Sets the `aria-label` of the component, if none is provided.
 * Sets the Tooltip content if `showTooltip` is provided.
 */
label?: string

/**
 * If provided with `showTooltip`, appends the Shortcut label to the tooltip content.
 * If an object is provided, it should contain `display` and `ariaLabel` keys.
 */
shortcut?: string | { display: string; ariaLabel: string; } | undefined

/**
 * If provided, renders a Tooltip component for the button.
 */
showTooltip?: boolean | undefined

/**
 * The size of the button.
 * 
 * - `'default'`: For normal text-label buttons, unless it is a toggle button.
 * - `'compact'`: For toggle buttons, icon buttons, and buttons when used in context of either.
 * - `'small'`: For icon buttons associated with more advanced or auxiliary features.
 * 
 * If the deprecated `isSmall` prop is also defined, this prop will take precedence.
 */
size?: "small" | "default" | "compact" = 'default'

/**
 * If provided with `href`, sets the `target` attribute to the `a`.
 */
target?: string

/**
 * If provided, displays the given text inside the button. If the button contains children elements, the text is displayed before them.
 */
text?: string

/**
 * If provided with `showTooltip`, sets the position of the tooltip.
 * Please refer to the Tooltip component for more details regarding the defaults.
 */
tooltipPosition?: "top" | "middle" | "bottom" | "top center" | "top left" | "top right" | "middle center" | "middle left" | "middle right" | "bottom center" | "bottom left" | "bottom right" | "top center left" | "top center right" | "top center top" | "top center bottom" | "top left left" | "top left right" | "top left top" | "top left bottom" | "top right left" | "top right right" | "top right top" | "top right bottom" | "middle center left" | "middle center right" | "middle center top" | "middle center bottom" | "middle left left" | "middle left right" | "middle left top" | "middle left bottom" | "middle right left" | "middle right right" | "middle right top" | "middle right bottom" | "bottom center left" | "bottom center right" | "bottom center top" | "bottom center bottom" | "bottom left left" | "bottom left right" | "bottom left top" | "bottom left bottom" | "bottom right left" | "bottom right right" | "bottom right top" | "bottom right bottom"

/**
 * Specifies the button's style.
 * 
 * The accepted values are:
 * 
 * 1. `'primary'` (the primary button styles)
 * 2. `'secondary'` (the default button styles)
 * 3. `'tertiary'` (the text-based button styles)
 * 4. `'link'` (the link button styles)
 */
variant?: "link" | "primary" | "secondary" | "tertiary"
Imports
import { Button } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	return <Button __next40pxDefaultSize { ...props }></Button>;
};
Primary story ok
Primary buttons stand out with bold color fills, making them distinct from the background. Since they naturally draw attention, each layout should contain only one primary button to guide users toward the most important action.
const Primary = ( props ) => {
	return <Button __next40pxDefaultSize { ...props }></Button>;
};
Secondary story ok
Secondary buttons complement primary buttons. Use them for standard actions that may appear alongside a primary action.
const Secondary = ( props ) => {
	return <Button __next40pxDefaultSize { ...props }></Button>;
};
Tertiary story ok
Tertiary buttons have minimal emphasis. Use them sparingly to subtly highlight an action.
const Tertiary = ( props ) => {
	return <Button __next40pxDefaultSize { ...props }></Button>;
};
Link story ok
Link buttons have low emphasis and blend into the page, making them suitable for supplementary actions, especially those involving navigation away from the current view.
const Link = ( props ) => {
	return <Button __next40pxDefaultSize { ...props }></Button>;
};
Is Destructive story ok
Use this variant for irreversible actions. Apply sparingly and only for actions with significant impact.
const IsDestructive = ( props ) => {
	return <Button __next40pxDefaultSize { ...props }></Button>;
};
Icon story ok
const Icon = ( props ) => {
	return <Button __next40pxDefaultSize { ...props }></Button>;
};
Grouped Icons story ok
function GroupedIcons() {
	return (
		<GroupContainer>
			<Button __next40pxDefaultSize icon={ formatBold } label="Bold" />
			<Button
				__next40pxDefaultSize
				icon={ formatItalic }
				label="Italic"
			/>
			<Button __next40pxDefaultSize icon={ link } label="Link" />
		</GroupContainer>
	);
}

Card.Root

design-system-components-card · ../packages/ui/src/card/stories/index.story.tsx
A visually contained surface that groups related content and actions. ```jsx import { Card } from '@wordpress/ui'; function MyComponent() { return ( <Card.Root> <Card.Header> <Card.Title>Heading</Card.Title> </Card.Header> <Card.Content> <p>Main content here.</p> </Card.Content> </Card.Root> ); } ```
Prop types (react-component-meta) 4 prop types
Component: ../packages/ui/src/card/index.ts::Root
Props:
/**
 * The content to be rendered inside the card.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Imports
import { Content, FullBleed, Header, Root, Title, Stack } from "@wordpress/ui";
Default story ok
const Default = () => <Card.Root><>
        <Card.Header>
            <Card.Title>Card title</Card.Title>
        </Card.Header>
        <Card.Content>
            <Text>This is the main content area. It can contain any
                                        elements. This is the main content area. It can contain
                                        any elements. This is the main content area. It can
                                        contain any elements. This is the main content area. It
                                        can contain any elements. This is the main content area.
                                        It can contain any elements. This is the main content
                                        area. It can contain any elements.
                                    </Text>
            <Text>This is the main content area. It can contain any
                                        elements.
                                    </Text>
        </Card.Content>
    </></Card.Root>;
Full Bleed Cover Only story ok
`Card.FullBleed` as the sole child of `Card.Content` spans edge-to-edge with no padding around it.
const FullBleedCoverOnly = () => <Card.Root><Card.Content>
        <Card.FullBleed>
            <div
                style={ {
                    height: 180,
                    background:
                        'linear-gradient(135deg, #f093fb 0%, #f5576c 100%)',
                } } />
        </Card.FullBleed>
    </Card.Content></Card.Root>;
Full Bleed Cover With Header story ok
When `Card.FullBleed` is the sole child of `Card.Content` and a `Card.Header` sits above it, the image bumps against the card's side and bottom edges while the header retains its normal padding.
const FullBleedCoverWithHeader = () => <Card.Root><>
        <Card.Header>
            <Card.Title>Card title</Card.Title>
        </Card.Header>
        <Card.Content>
            <Card.FullBleed>
                <div
                    style={ {
                        height: 180,
                        background:
                            'linear-gradient(135deg, #f093fb 0%, #f5576c 100%)',
                    } } />
            </Card.FullBleed>
        </Card.Content>
    </></Card.Root>;
With Full Bleed story ok
`Card.FullBleed` breaks out of the card's padding to span edge-to-edge. Useful for images, dividers, or embedded content.
const WithFullBleed = () => <Card.Root><>
        <Card.Header>
            <Card.Title>Featured image</Card.Title>
        </Card.Header>
        <Card.Content render={ <Stack direction="column" gap="lg" /> }>
            <Card.FullBleed>
                <div
                    style={ {
                        height: 160,
                        background:
                            'linear-gradient(135deg, #667eea 0%, #764ba2 100%)',
                    } } />
            </Card.FullBleed>
            <Text>Content below the full-bleed area.</Text>
        </Card.Content>
    </></Card.Root>;
Header Only story ok
A minimal card with only a header.
const HeaderOnly = () => <Card.Root><Card.Header>
        <Card.Title>Simple card</Card.Title>
    </Card.Header></Card.Root>;
Full Bleed Hero With Title story ok
When `Card.FullBleed` is the **first child** of `Card.Header`, it extends flush to the card's top and side edges — ideal for hero images. Content that follows inside the header is padded normally.
const FullBleedHeroWithTitle = () => <Card.Root><>
        <Card.Header render={ <Stack direction="column" gap="lg" /> }>
            <Card.FullBleed>
                <div
                    style={ {
                        height: 180,
                        background:
                            'linear-gradient(135deg, #f093fb 0%, #f5576c 100%)',
                    } } />
            </Card.FullBleed>
            <Card.Title>Hero image card</Card.Title>
        </Card.Header>
        <Card.Content>
            <Text>The image above bleeds to the card's top and side
                                        edges.
                                    </Text>
        </Card.Content>
    </></Card.Root>;
Full Bleed Hero Only story ok
When `Card.FullBleed` is the **only child** of `Card.Header`, it fills the header entirely — top and sides flush to the card edges, no extra padding below.
const FullBleedHeroOnly = () => <Card.Root><>
        <Card.Header>
            <Card.FullBleed>
                <div
                    style={ {
                        height: 180,
                        background:
                            'linear-gradient(135deg, #f093fb 0%, #f5576c 100%)',
                    } } />
            </Card.FullBleed>
        </Card.Header>
        <Card.Content>
            <Text>The image above bleeds to the card's top and side
                                        edges.
                                    </Text>
        </Card.Content>
    </></Card.Root>;
Custom Semantics story ok
Use the `render` prop to change the underlying HTML elements for better semantics. Here, `Card.Root` renders as a `<section>` and `Card.Title` renders as an `<h2>`.
const CustomSemantics = () => <Card.Root render={<section />}><>
        <Card.Header>
            <Card.Title render={ <h2 /> }>Section heading</Card.Title>
        </Card.Header>
        <Card.Content>
            <Text>Semantically meaningful card content.</Text>
        </Card.Content>
    </></Card.Root>;
Card.Header 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/card/index.ts
A structural container for the card's heading area, typically containing `Card.Title`.
import { Header } from "@wordpress/ui";
Component: ../packages/ui/src/card/index.ts::Header (react-component-meta)
/**
 * The content to be rendered inside the header.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Card.Content 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/card/index.ts
The main content area of the card.
import { Content } from "@wordpress/ui";
Component: ../packages/ui/src/card/index.ts::Content (react-component-meta)
/**
 * The content to be rendered inside the content area.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Card.FullBleed 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/card/index.ts
A container that breaks out of the card's padding to span edge-to-edge. Useful for full-width images, dividers, or embedded content. Additional edge-bumping behavior based on placement: - As the **first child** of `Card.Header`, it extends flush to the card's top edge — ideal for hero images. - As the **only child** of `Card.Content`, it extends flush to the card's top edge when `Content` is the first card section, and to the bottom edge when it is the last. Inter-sibling spacing inside `Card.Header` / `Card.Content` is consumer- managed. To add space between a hero `FullBleed` and the following siblings, compose the parent with `Stack` via the `render` prop: `<Card.Header render={ <Stack direction="column" gap="lg" /> }>`. This keeps `FullBleed` a direct child of `Card.Header` so the edge-bump still fires, while `Stack` provides the gap. Inside `CollapsibleCard`, place full-bleed media in `CollapsibleCard.Content` (not the header). The trigger/panel gap is preserved by design. Must be used as a direct child of `Card.Content` or `Card.Header`.
import { FullBleed } from "@wordpress/ui";
Component: ../packages/ui/src/card/index.ts::FullBleed (react-component-meta)
/**
 * The content to be rendered edge-to-edge, breaking out of the
 * card's padding.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Card.Title 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/card/index.ts
The title for a card. Renders as a `<div>` by default — use the `render` prop to swap in a semantic heading element when appropriate.
import { Title } from "@wordpress/ui";
Component: ../packages/ui/src/card/index.ts::Title (react-component-meta)
/**
 * The title text for the card.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined = <div />

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

CheckboxControl

components-checkboxcontrol · ../packages/components/src/checkbox-control/stories/index.story.tsx
Checkboxes allow the user to select one or more items from a set. ```jsx import { CheckboxControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyCheckboxControl = () => { const [ isChecked, setChecked ] = useState( true ); return ( <CheckboxControl label="Is author" help="Is the user a author or not?" checked={ isChecked } onChange={ setChecked } /> ); }; ```
Prop types (react-component-meta) 8 prop types
Component: ../packages/components/src/checkbox-control/index.tsx::default
Props:
/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * If checked is true the checkbox will be checked. If checked is false the
 * checkbox will be unchecked. If no value is passed the checkbox will be
 * unchecked.
 */
checked?: boolean | undefined

/**
 * Whether the checkbox should be disabled.
 */
disabled?: boolean | undefined

heading?: ReactNode

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If indeterminate is true the state of the checkbox will be indeterminate.
 */
indeterminate?: boolean | undefined

/**
 * A label for the input field, that appears at the side of the checkbox.
 * The prop will be rendered as content a label element. If no prop is
 * passed an empty label is rendered.
 */
label?: string

/**
 * A function that receives the checked state (boolean) as input.
 */
onChange: (value: boolean) => void
Imports
import { CheckboxControl, HStack, VStack } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ isChecked, setChecked ] = useState( true );

    return (
        <CheckboxControl
            label="Is author"
            help="Is the user an author or not?"
            checked={ isChecked }
            onChange={ ( v ) => {
				setChecked( v );
				onChange( v );
			} } />
    );
};
Indeterminate story ok
const Indeterminate = () => {
    const [ fruits, setFruits ] = useState( { apple: false, orange: false } );

    const isAllChecked = Object.values( fruits ).every( Boolean );
    const isIndeterminate =
		Object.values( fruits ).some( Boolean ) && ! isAllChecked;

    return (
        <VStack>
            <CheckboxControl
                label="Select all"
                checked={ isAllChecked }
                indeterminate={ isIndeterminate }
                onChange={ ( v ) => {
					setFruits( {
						apple: v,
						orange: v,
					} );
					onChange( v );
				} } />
            <CheckboxControl
                label="Apple"
                checked={ fruits.apple }
                onChange={ ( apple ) =>
					setFruits( ( prevState ) => ( {
						...prevState,
						apple,
					} ) )
				} />
            <CheckboxControl
                label="Orange"
                checked={ fruits.orange }
                onChange={ ( orange ) =>
					setFruits( ( prevState ) => ( {
						...prevState,
						orange,
					} ) )
				} />
        </VStack>
    );
};
With Custom Label story ok
For more complex designs, a custom `<label>` element can be associated with the checkbox by leaving the `label` prop undefined and using the `id` and `htmlFor` props instead. Because the label element also functions as a click target for the checkbox, [do not place interactive elements](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/label#interactive_content) such as links or buttons inside the `<label>` node. Similarly, a custom description can be added by omitting the `help` prop and using the `aria-describedby` prop instead.
const WithCustomLabel = () => {
    const [ isChecked, setChecked ] = useState( true );

    return (
        <HStack justify="flex-start" alignment="top" spacing={ 0 }>
            <CheckboxControl
                checked={ isChecked }
                onChange={ ( v ) => {
					setChecked( v );
					onChange( v );
				} }
                // Disable reason: For simplicity of the code snippet.
                // eslint-disable-next-line no-restricted-syntax
                id="my-checkbox-with-custom-label"
                aria-describedby="my-custom-description" />
            <VStack>
                <label htmlFor="my-checkbox-with-custom-label">My custom label
                                    </label>
                { /* eslint-disable-next-line no-restricted-syntax */ }
                <div id="my-custom-description" style={ { fontSize: 13 } }>A custom description.
                                    </div>
            </VStack>
        </HStack>
    );
};

Collapsible.Root

design-system-components-collapsible · ../packages/ui/src/collapsible/stories/index.story.tsx
Groups all parts of the collapsible. `Collapsible` is a collection of React components that combine to render a collapsible panel controlled by a button.
Prop types (react-component-meta) 8 prop types
Component: ../packages/ui/src/collapsible/index.ts::Root
Props:
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Whether the collapsible panel is initially open.
 * 
 * To render a controlled collapsible, use the `open` prop instead.
 */
defaultOpen?: boolean | undefined = false

/**
 * Whether the component should ignore user interaction.
 */
disabled?: boolean | undefined = false

/**
 * Event handler called when the panel is opened or closed.
 */
onOpenChange?: (open: boolean, eventDetails: CollapsibleRootChangeEventDetails) => void

/**
 * Whether the collapsible panel is currently open.
 * 
 * To render an uncontrolled collapsible, use the `defaultOpen` prop instead.
 */
open?: boolean | undefined

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Imports
import { Panel, Root, Trigger } from "@wordpress/ui";
Default story ok
const Default = () => <Collapsible.Root>(<>
        <Collapsible.Trigger>Toggle</Collapsible.Trigger>
        <Collapsible.Panel>
            <p>Collapsible content here.</p>
        </Collapsible.Panel>
    </>)</Collapsible.Root>;
Default Open story ok
const DefaultOpen = () => <Collapsible.Root defaultOpen>(<>
        <Collapsible.Trigger>Toggle</Collapsible.Trigger>
        <Collapsible.Panel>
            <p>This panel is open by default.</p>
        </Collapsible.Panel>
    </>)</Collapsible.Root>;
Disabled story ok
const Disabled = () => <Collapsible.Root disabled>(<>
        <Collapsible.Trigger>Toggle (disabled)</Collapsible.Trigger>
        <Collapsible.Panel>
            <p>This content cannot be toggled.</p>
        </Collapsible.Panel>
    </>)</Collapsible.Root>;
Hidden Until Found story ok
When `hiddenUntilFound` is set on `Collapsible.Panel`, the collapsed content remains in the DOM using the `hidden="until-found"` HTML attribute instead of being removed entirely. This lets the browser's native page search (Ctrl/Cmd+F) find text inside collapsed panels and automatically expand them to reveal the match — improving discoverability without sacrificing the collapsed layout.
const HiddenUntilFound = function HiddenUntilFound() {
    return (
        <div>
            <p>
                Use the browser&apos;s find-in-page (Ctrl/Cmd+F) to search
                for &quot;hidden treasure&quot;. The collapsed panel will
                automatically expand to reveal the match.
            </p>
            <Collapsible.Root>
                <Collapsible.Trigger>Expand to reveal</Collapsible.Trigger>
                <Collapsible.Panel hiddenUntilFound>
                    <p>
                        This is the hidden treasure that can be found via
                        the browser&apos;s built-in page search even while
                        the panel is collapsed.
                    </p>
                </Collapsible.Panel>
            </Collapsible.Root>
        </div>
    );
};
Controlled story ok
const Controlled = function Controlled() {
    const [ open, setOpen ] = useState( false );
    return (
        <Collapsible.Root open={ open } onOpenChange={ setOpen }>
            <Collapsible.Trigger>
                { open ? 'Close' : 'Open' }
            </Collapsible.Trigger>
            <Collapsible.Panel>
                <p>Controlled collapsible panel.</p>
            </Collapsible.Panel>
        </Collapsible.Root>
    );
};
Collapsible.Trigger 5 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/collapsible/index.ts
A button that opens and closes the collapsible panel. `Collapsible` is a collection of React components that combine to render a collapsible panel controlled by a button.
import { Trigger } from "@wordpress/ui";
Component: ../packages/ui/src/collapsible/index.ts::Trigger (react-component-meta)
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Whether the component renders a native `<button>` element when replacing it
 * via the `render` prop.
 * Set to `false` if the rendered element is not a button (for example, `<div>`).
 */
nativeButton?: boolean | undefined = true

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Collapsible.Panel 6 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/collapsible/index.ts
A panel with the collapsible contents. Hidden when collapsed, visible when expanded. `Collapsible` is a collection of React components that combine to render a collapsible panel controlled by a button.
import { Panel } from "@wordpress/ui";
Component: ../packages/ui/src/collapsible/index.ts::Panel (react-component-meta)
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Allows the browser's built-in page search to find and expand the panel contents.
 * 
 * Overrides the `keepMounted` prop and uses `hidden="until-found"`
 * to hide the element without removing it from the DOM.
 */
hiddenUntilFound?: boolean | undefined = false

/**
 * Whether to keep the element in the DOM while the panel is hidden.
 * This prop is ignored when `hiddenUntilFound` is used.
 */
keepMounted?: boolean | undefined = false

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

CollapsibleCard.Root

design-system-components-collapsiblecard · ../packages/ui/src/collapsible-card/stories/index.story.tsx
A card that can be expanded and collapsed. When collapsed, only the header is visible. ```jsx import { CollapsibleCard, Card } from '@wordpress/ui'; function MyComponent() { return ( <CollapsibleCard.Root defaultOpen> <CollapsibleCard.Header> <Card.Title>Heading</Card.Title> </CollapsibleCard.Header> <CollapsibleCard.Content> <p>Collapsible content here.</p> </CollapsibleCard.Content> </CollapsibleCard.Root> ); } ```
Prop types (react-component-meta) 8 prop types
Component: ../packages/ui/src/collapsible-card/index.ts::Root
Props:
/**
 * The content to be rendered inside the collapsible card.
 * Should include `CollapsibleCard.Header` and `CollapsibleCard.Content`.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Whether the collapsible panel is initially open (uncontrolled).
 */
defaultOpen?: boolean | undefined = false

/**
 * Whether the component should ignore user interaction.
 */
disabled?: boolean | undefined = false

/**
 * Event handler called when the panel is opened or closed.
 */
onOpenChange?: (open: boolean) => void

/**
 * Whether the collapsible panel is currently open (controlled).
 * 
 * To render an uncontrolled collapsible card, use `defaultOpen` instead.
 */
open?: boolean | undefined

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Imports
import { Content, FullBleed, Header, Root, Title, HeaderDescription, Stack } from "@wordpress/ui";
Default story ok
A collapsible card that is open by default.
const Default = () => <CollapsibleCard.Root>(<>
        <CollapsibleCard.Header>
            <Card.Title>
                Collapsible card (closed by default)
            </Card.Title>
        </CollapsibleCard.Header>
        <CollapsibleCard.Content>
            <Text>
                This is the collapsible content area. It can contain any
                elements, just like a regular Card.Content.
            </Text>
            <Text>
                When collapsed, only the header and chevron are visible.
            </Text>
        </CollapsibleCard.Content>
    </>)</CollapsibleCard.Root>;
Initially Opened story ok
A collapsible card that starts collapsed.
const InitiallyOpened = () => <CollapsibleCard.Root defaultOpen>(<>
        <CollapsibleCard.Header>
            <Card.Title>Collapsed by default</Card.Title>
        </CollapsibleCard.Header>
        <CollapsibleCard.Content>
            <Text>This content was hidden until you expanded it.</Text>
        </CollapsibleCard.Content>
    </>)</CollapsibleCard.Root>;
Disabled story ok
A disabled collapsible card cannot be toggled by the user.
const Disabled = () => <CollapsibleCard.Root disabled>(<>
        <CollapsibleCard.Header>
            <Card.Title>Disabled card</Card.Title>
        </CollapsibleCard.Header>
        <CollapsibleCard.Content>
            <Text>The header is not interactive when disabled.</Text>
        </CollapsibleCard.Content>
    </>)</CollapsibleCard.Root>;
Stacked story ok
Multiple collapsible cards stacked vertically, simulating a typical settings-panel or FAQ-style layout.
const Stacked = () => (
    <div
        style={ {
            display: 'flex',
            flexDirection: 'column',
            gap: 'var(--wpds-dimension-gap-lg)',
        } }
    >
        { [
            'General',
            'Advanced',
            'Accessibility',
            'Performance',
            'Privacy',
            'Notifications',
        ].map( ( title ) => (
            <CollapsibleCard.Root key={ title }>
                <CollapsibleCard.Header>
                    <Card.Title>{ title }</Card.Title>
                </CollapsibleCard.Header>
                <CollapsibleCard.Content>
                    <Text>
                        Configure all { title.toLowerCase() } settings for
                        your site. Changes here affect how your site behaves
                        across all pages and posts.
                    </Text>
                    <Text>
                        Review each option carefully before saving. Some
                        changes may require a page reload to take effect.
                        Hover over individual options for more details about
                        what they control.
                    </Text>
                    <Text>
                        If you&apos;re unsure about a setting, you can
                        always reset to defaults using the button at the
                        bottom of this section. Your previous configuration
                        will be saved as a backup.
                    </Text>
                </CollapsibleCard.Content>
            </CollapsibleCard.Root>
        ) ) }
    </div>
);
With Heading Element story ok
`CollapsibleCard.Header` renders a `<div>` wrapper by default. Pass an `<h1>`–`<h6>` React element to the `render` prop to wrap the trigger in a heading and contribute to the document outline. The right level depends on the surrounding outline, so the consumer is expected to opt in.
const WithHeadingElement = () => (
    <div
        style={ {
            display: 'flex',
            flexDirection: 'column',
            gap: 'var(--wpds-dimension-gap-lg)',
        } }
    >
        <CollapsibleCard.Root>
            <CollapsibleCard.Header render={ <h2 /> }>
                <Card.Title>Heading level 2</Card.Title>
            </CollapsibleCard.Header>
            <CollapsibleCard.Content>
                <Text>
                    The wrapper renders as an h2 element when the consumer
                    passes an h2 React element to the render prop.
                </Text>
            </CollapsibleCard.Content>
        </CollapsibleCard.Root>
        <CollapsibleCard.Root>
            <CollapsibleCard.Header render={ <h3 /> }>
                <Card.Title>Heading level 3</Card.Title>
            </CollapsibleCard.Header>
            <CollapsibleCard.Content>
                <Text>
                    Pass any of h1–h6 to choose the level that fits the
                    surrounding document outline.
                </Text>
            </CollapsibleCard.Content>
        </CollapsibleCard.Root>
        <CollapsibleCard.Root>
            <CollapsibleCard.Header>
                <Card.Title>No heading (default)</Card.Title>
            </CollapsibleCard.Header>
            <CollapsibleCard.Content>
                <Text>
                    Without a render prop, the header wraps the trigger in a
                    plain div and does not contribute to the document
                    outline.
                </Text>
            </CollapsibleCard.Content>
        </CollapsibleCard.Root>
    </div>
);
With Header Description story ok
A collapsible card with a `HeaderDescription` that provides supplementary information (e.g. status, summary) as an `aria-describedby` relationship.
const WithHeaderDescription = ( { open, defaultOpen, onOpenChange, disabled, ...restArgs } ) => (
    <CollapsibleCard.Root
        open={ open }
        defaultOpen={ defaultOpen }
        onOpenChange={ onOpenChange }
        disabled={ disabled }
        { ...restArgs }
    >
        <CollapsibleCard.Header>
            <Stack justify="space-between">
                <Card.Title>Settings</Card.Title>
                <CollapsibleCard.HeaderDescription>
                    <span
                        style={ {
                            fontSize: 'var(--wpds-typography-font-size-sm)',
                            color: 'var(--wpds-color-foreground-content-neutral-weak)',
                        } }
                    >
                        3 items configured
                    </span>
                </CollapsibleCard.HeaderDescription>
            </Stack>
        </CollapsibleCard.Header>
        <CollapsibleCard.Content>
            <Text>
                The header description provides supplementary context to the
                trigger button. Assistive technologies will announce the
                description alongside the button label.
            </Text>
        </CollapsibleCard.Content>
    </CollapsibleCard.Root>
);
Compared To Card story ok
Visual comparison: a `CollapsibleCard` (open) next to a regular `Card` to verify identical spacing and layout.
const ComparedToCard = ( { open, defaultOpen, onOpenChange, disabled, ...restArgs } ) => (
    <div
        style={ {
            display: 'flex',
            flexDirection: 'column',
            gap: 'var( --wpds-dimension-gap-lg )',
        } }
    >
        <CollapsibleCard.Root
            open={ open }
            defaultOpen={ defaultOpen }
            onOpenChange={ onOpenChange }
            disabled={ disabled }
            { ...restArgs }
        >
            <CollapsibleCard.Header>
                <Card.Title>CollapsibleCard (open)</Card.Title>
            </CollapsibleCard.Header>
            <CollapsibleCard.Content>
                <Text>
                    Content should align with the regular card below.
                </Text>
            </CollapsibleCard.Content>
        </CollapsibleCard.Root>
        <Card.Root { ...restArgs }>
            <Card.Header>
                <Card.Title>Regular Card</Card.Title>
            </Card.Header>
            <Card.Content>
                <Text>
                    Content should align with the collapsible card above.
                </Text>
            </Card.Content>
        </Card.Root>
    </div>
);
Full Bleed Cover With Header story ok
When `Card.FullBleed` is the sole child of `CollapsibleCard.Content` and a header sits above it, the media bumps against the card&apos;s side and bottom edges while the header retains its normal padding. (Unlike a plain `Card`, a header is always required here for the collapse trigger — see `Card` stories for a body-only `FullBleedCoverOnly` example.)
const FullBleedCoverWithHeader = () => <CollapsibleCard.Root defaultOpen>(<>
        <CollapsibleCard.Header>
            <Card.Title>Card title</Card.Title>
        </CollapsibleCard.Header>
        <CollapsibleCard.Content>
            <Card.FullBleed>
                <div
                    style={ {
                        height: 180,
                        background:
                            'linear-gradient(135deg, #f093fb 0%, #f5576c 100%)',
                    } }
                />
            </Card.FullBleed>
        </CollapsibleCard.Content>
    </>)</CollapsibleCard.Root>;
With Full Bleed story ok
`Card.FullBleed` breaks out of the content padding to span edge-to-edge. Useful for images, dividers, or embedded content inside the collapsible region.
const WithFullBleed = () => <CollapsibleCard.Root defaultOpen>(<>
        <CollapsibleCard.Header>
            <Card.Title>Featured image</Card.Title>
        </CollapsibleCard.Header>
        <CollapsibleCard.Content
            render={ <Stack direction="column" gap="lg" /> }
        >
            <Card.FullBleed>
                <div
                    style={ {
                        height: 160,
                        background:
                            'linear-gradient(135deg, #667eea 0%, #764ba2 100%)',
                    } }
                />
            </Card.FullBleed>
            <Text>Content below the full-bleed area.</Text>
        </CollapsibleCard.Content>
    </>)</CollapsibleCard.Root>;
CollapsibleCard.Header 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/collapsible-card/index.ts
The header of a collapsible card. Always visible, and acts as the toggle trigger — clicking anywhere on it expands or collapses the card's content. Defaults to a `<div>` wrapper around the trigger. Since the right heading level depends on the surrounding document outline, the consumer is expected to opt in to heading semantics. Pass `render` to wrap the trigger in a heading (e.g. `render={ <h2 /> }`), following the W3C APG accordion pattern (heading wraps button). Avoid placing interactive elements (buttons, links, inputs) inside the header, since the entire area is clickable and their events will bubble to trigger the collapse toggle. Place full-bleed media in `CollapsibleCard.Content`, not the header.
import { Header } from "@wordpress/ui";
Component: ../packages/ui/src/collapsible-card/index.ts::Header (react-component-meta)
/**
 * The content to be rendered inside the header.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
CollapsibleCard.HeaderDescription 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/collapsible-card/index.ts
Secondary content placed in the collapsible card header that describes the trigger button via `aria-describedby`. Use it for supplementary information such as status badges or summary values. The content is visually rendered but marked `aria-hidden` so that assistive technologies consume it only through the `aria-describedby` relationship on the trigger, avoiding double announcements. Avoid interactive elements (buttons, links, inputs) inside this component — the entire header is the toggle trigger.
import { HeaderDescription } from "@wordpress/ui";
Component: ../packages/ui/src/collapsible-card/index.ts::HeaderDescription (react-component-meta)
/**
 * Secondary content that describes the header trigger via
 * `aria-describedby`. Rendered visually but marked `aria-hidden`
 * so assistive technologies consume it only through the description
 * relationship, avoiding double announcements.
 * 
 * Avoid interactive elements — the entire header is the toggle trigger.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
CollapsibleCard.Content 5 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/collapsible-card/index.ts
The collapsible content area of the card. Hidden when collapsed, visible when expanded.
import { Content } from "@wordpress/ui";
Component: ../packages/ui/src/collapsible-card/index.ts::Content (react-component-meta)
/**
 * The content to be rendered inside the collapsible content area.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Allows the browser’s built-in page search to find and expand the panel contents.
 * 
 * Overrides the `keepMounted` prop and uses `hidden="until-found"`
 * to hide the element without removing it from the DOM.
 */
hiddenUntilFound?: boolean | undefined = true

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Card.FullBleed 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/card/index.ts
A container that breaks out of the card's padding to span edge-to-edge. Useful for full-width images, dividers, or embedded content. Additional edge-bumping behavior based on placement: - As the **first child** of `Card.Header`, it extends flush to the card's top edge — ideal for hero images. - As the **only child** of `Card.Content`, it extends flush to the card's top edge when `Content` is the first card section, and to the bottom edge when it is the last. Inter-sibling spacing inside `Card.Header` / `Card.Content` is consumer- managed. To add space between a hero `FullBleed` and the following siblings, compose the parent with `Stack` via the `render` prop: `<Card.Header render={ <Stack direction="column" gap="lg" /> }>`. This keeps `FullBleed` a direct child of `Card.Header` so the edge-bump still fires, while `Stack` provides the gap. Inside `CollapsibleCard`, place full-bleed media in `CollapsibleCard.Content` (not the header). The trigger/panel gap is preserved by design. Must be used as a direct child of `Card.Content` or `Card.Header`.
import { FullBleed } from "@wordpress/ui";
Component: ../packages/ui/src/card/index.ts::FullBleed (react-component-meta)
/**
 * The content to be rendered edge-to-edge, breaking out of the
 * card's padding.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

ColorIndicator

components-colorindicator · ../packages/components/src/color-indicator/stories/index.story.tsx
ColorIndicator is a React component that renders a specific color in a circle. It's often used to summarize a collection of used colors in a child component. ```jsx import { ColorIndicator } from '@wordpress/components'; const MyColorIndicator = () => <ColorIndicator colorValue="#0073aa" />; ```
Prop types (react-component-meta) 1 prop type
Component: ../packages/components/src/color-indicator/index.tsx::default
Props:
/**
 * The color of the indicator. Any value from the CSS `background` property
 * is supported.
 */
colorValue: Background<string | number> | undefined
Imports
import { ColorIndicator } from "@wordpress/components";
Default story ok
const Default = () => <ColorIndicator colorValue="#0073aa" />;

ColorPalette

components-colorpalette · ../packages/components/src/color-palette/stories/index.story.tsx
Allows the user to pick a color from a list of pre-defined color entries. ```jsx import { ColorPalette } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyColorPalette = () => { const [ color, setColor ] = useState ( '#f00' ) const colors = [ { name: 'red', color: '#f00' }, { name: 'white', color: '#fff' }, { name: 'blue', color: '#00f' }, ]; return ( <ColorPalette colors={ colors } value={ color } onChange={ ( color ) => setColor( color ) } /> ); } ); ```
Prop types (react-component-meta) 14 prop types
Component: ../packages/components/src/color-palette/index.tsx::default
Props:
/**
 * Whether this is rendered in the sidebar.
 */
__experimentalIsRenderedInSidebar?: boolean | undefined = false

/**
 * A label to identify the purpose of the control.
 */
aria-label?: string

/**
 * An ID of an element to provide a label for the control.
 */
aria-labelledby?: string

/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * Whether the control should present as a set of buttons,
 * each with its own tab stop.
 */
asButtons?: boolean | undefined = false

/**
 * Whether the palette should have a clearing button.
 */
clearable?: boolean | undefined = true

/**
 * Array with the colors to be shown. When displaying multiple color palettes
 * to choose from, the format of the array changes from an array of colors
 * objects, to an array of color palettes.
 */
colors?: PaletteObject[] | ColorObject[] | undefined = []

/**
 * Whether to allow the user to pick a custom color on top of the predefined
 * choices (defined via the `colors` prop).
 */
disableCustomColors?: boolean | undefined = false

/**
 * This controls whether the alpha channel will be offered when selecting
 * custom colors.
 */
enableAlpha?: boolean | undefined = false

/**
 * The heading level.
 */
headingLevel?: 1 | 2 | "1" | 3 | 4 | 5 | 6 | "2" | "3" | "4" | "5" | "6" = 2

/**
 * Prevents keyboard interaction from wrapping around.
 * Only used when `asButtons` is not true.
 */
loop?: boolean | undefined = true

/**
 * Callback called when a color is selected.
 * The third argument is the slug of the selected palette entry, when available.
 */
onChange: (newColor?: string | undefined, index?: number | undefined, slug?: string | undefined) => void

/**
 * The slug of the currently selected palette entry.
 * 
 * When set to a non-empty string, selection is determined by slug rather
 * than by color value — this correctly handles palettes where two entries
 * share the same color. Palette entries without a slug will not appear
 * selected in this mode, even if their color value matches `value`.
 * 
 * An empty string is treated the same as `undefined`: selection falls
 * back to matching by color value.
 */
selectedSlug?: string

/**
 * Currently active value.
 */
value?: string
Imports
import { ColorPalette } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ color, setColor ] = useState< string | undefined >( value );
    const [ slug, setSlug ] = useState< string | undefined >( selectedSlug );

    return (
        <ColorPalette
            colors={[
                { name: 'Red', color: '#f00' },
                { name: 'White', color: '#fff' },
                { name: 'Blue', color: '#00f' },
            ]}
            value={ color }
            selectedSlug={ slug }
            onChange={ ( newColor, index, newSlug ) => {
				setColor( newColor );
				setSlug( newSlug );
				onChange?.( newColor, index, newSlug );
			} } />
    );
};
Initial Value story ok
const InitialValue = () => {
    const [ color, setColor ] = useState< string | undefined >( value );
    const [ slug, setSlug ] = useState< string | undefined >( selectedSlug );

    return (
        <ColorPalette
            colors={[
                { name: 'Red', color: '#f00' },
                { name: 'White', color: '#fff' },
                { name: 'Blue', color: '#00f' },
            ]}
            value={ color }
            selectedSlug={ slug }
            onChange={ ( newColor, index, newSlug ) => {
				setColor( newColor );
				setSlug( newSlug );
				onChange?.( newColor, index, newSlug );
			} } />
    );
};
Multiple Origins story ok
const MultipleOrigins = () => {
    const [ color, setColor ] = useState< string | undefined >( value );
    const [ slug, setSlug ] = useState< string | undefined >( selectedSlug );

    return (
        <ColorPalette
            colors={[
                {
                    name: 'Primary colors',
                    colors: [
                        { name: 'Red', color: '#f00' },
                        { name: 'Yellow', color: '#ff0' },
                        { name: 'Blue', color: '#00f' },
                    ],
                },
                {
                    name: 'Secondary colors',
                    colors: [
                        { name: 'Orange', color: '#f60' },
                        { name: 'Green', color: '#0f0' },
                        { name: 'Purple', color: '#60f' },
                    ],
                },
            ]}
            value={ color }
            selectedSlug={ slug }
            onChange={ ( newColor, index, newSlug ) => {
				setColor( newColor );
				setSlug( newSlug );
				onChange?.( newColor, index, newSlug );
			} } />
    );
};
Duplicate Colors story ok
const DuplicateColors = () => {
    const [ color, setColor ] = useState< string | undefined >( value );
    const [ slug, setSlug ] = useState< string | undefined >( selectedSlug );

    return (
        <ColorPalette
            colors={[
                { name: 'Dark Background', slug: 'dark-background', color: '#000' },
                { name: 'Dark Text', slug: 'dark-text', color: '#000' },
                { name: 'Brand', slug: 'brand', color: '#0073aa' },
            ]}
            value={ color }
            selectedSlug={ slug }
            onChange={ ( newColor, index, newSlug ) => {
				setColor( newColor );
				setSlug( newSlug );
				onChange?.( newColor, index, newSlug );
			} } />
    );
};
CSS Variables story ok
const CSSVariables = () => <div
    style={ {
        '--red': '#f00',
        '--yellow': '#ff0',
        '--blue': '#00f',
    } }>
    <Template
        colors={[
			{ name: 'Red', color: 'var(--red)' },
			{ name: 'Yellow', color: 'var(--yellow)' },
			{ name: 'Blue', color: 'var(--blue)' },
		]} />
</div>;

ColorPicker

components-colorpicker · ../packages/components/src/color-picker/stories/index.story.tsx
`ColorPicker` lets users select a color from a visual color surface, or by editing its hex, RGB, or HSL values.
Prop types (react-component-meta) 6 prop types
Component: ../packages/components/src/color-picker/component.tsx::ColorPicker
Props:
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | ... 161 more ... | undefined

/**
 * The current color value to display in the picker.
 * Must be a hex or hex8 string.
 */
color?: string

/**
 * The format to copy when clicking the displayed color format.
 */
copyFormat?: "rgb" | "hsl" | "hex"

/**
 * An optional default value to use for the color picker.
 */
defaultValue?: string = '#fff'

/**
 * When `true` the color picker will display the alpha channel both in
 * the bottom inputs as well as in the color picker itself.
 */
enableAlpha?: boolean | undefined = false

/**
 * Fired when the color changes. Always passes a hex or hex8 color string.
 */
onChange?: (color: string) => void
Imports
import { ColorPicker } from "@wordpress/components";
Default story ok
const Default = () => <ColorPicker onChange={fn()} />;

ComboboxControl

components-comboboxcontrol · ../packages/components/src/combobox-control/stories/index.story.tsx
`ComboboxControl` is an enhanced version of a [`SelectControl`](../select-control/README.md) with the addition of being able to search for options using a search input. ```jsx import { ComboboxControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const options = [ { value: 'small', label: 'Small', }, { value: 'normal', label: 'Normal', disabled: true, }, { value: 'large', label: 'Large', disabled: false, }, ]; function MyComboboxControl() { const [ fontSize, setFontSize ] = useState(); const [ filteredOptions, setFilteredOptions ] = useState( options ); return ( <ComboboxControl label="Font Size" value={ fontSize } onChange={ setFontSize } options={ filteredOptions } onFilterValueChange={ ( inputValue ) => setFilteredOptions( options.filter( ( option ) => option.label .toLowerCase() .startsWith( inputValue.toLowerCase() ) ) ) } /> ); } ```
Prop types (react-component-meta) 17 prop types
Component: ../packages/components/src/combobox-control/index.tsx::default
Props:
/**
 * Custom renderer invoked for each option in the suggestion list.
 * The render prop receives as its argument an object containing, under the `item` key,
 * the single option's data (directly from the array of data passed to the `options` prop).
 */
__experimentalRenderItem?: (args: { item: ComboboxControlOption; }) => ReactNode

/**
 * Deprecated. Use `__next40pxDefaultSize` instead.
 */
__next36pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * Show a reset button to clear the input.
 */
allowReset?: boolean | undefined = true

className?: string

/**
 * Automatically expand the dropdown when the control is focused.
 * If the control is clicked, the dropdown will expand regardless of this prop.
 */
expandOnFocus?: boolean | undefined = true

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * Show a spinner (and hide the suggestions dropdown) while data
 * about the matching suggestions (ie the `options` prop) is loading
 */
isLoading?: boolean | undefined = false

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * Customizable UI messages.
 */
messages?: { selected: string; } = {
			selected: __( 'Item selected.' ),
		}

/**
 * Function called with the selected value changes.
 */
onChange?: (value: string | null | undefined) => void

/**
 * Function called when the control's search input value changes. The argument contains the next input value.
 */
onFilterValueChange?: (value: string) => void = () => {}

/**
 * The options that can be chosen from.
 */
options: ComboboxControlOption[]

/**
 * If passed, the combobox input will show a placeholder string if no values are present.
 */
placeholder?: string

/**
 * The current value of the control.
 */
value?: string | null | undefined
Imports
import { ComboboxControl } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ value, setValue ] =
		useState< ComboboxControlProps[ 'value' ] >( null );

    return (
        <>
            <ComboboxControl
                onFilterValueChange={fn()}
                label="Country"
                options={countryOptions}
                help="Help text to describe the control."
                value={ value }
                onChange={ ( ...changeArgs ) => {
					setValue( ...changeArgs );
					onChange?.( ...changeArgs );
				} } />
        </>
    );
};
With Custom Render Item story ok
The rendered output of each suggestion can be customized by passing a render function to the `__experimentalRenderItem` prop. (This is still an experimental feature and is subject to change.)
const WithCustomRenderItem = () => {
    const [ value, setValue ] =
		useState< ComboboxControlProps[ 'value' ] >( null );

    return (
        <>
            <ComboboxControl
                onFilterValueChange={fn()}
                label="Author"
                options={[
                    {
                        value: 'parsley',
                        label: 'Parsley Montana',
                        age: 48,
                        country: 'Germany',
                    },
                    {
                        value: 'cabbage',
                        label: 'Cabbage New York',
                        age: 44,
                        country: 'France',
                    },
                    {
                        value: 'jake',
                        label: 'Jake Weary',
                        age: 41,
                        country: 'United Kingdom',
                    },
                ]}
                __experimentalRenderItem={( { item } ) => {
                    const { label, age, country } = item;
                    return (
                        <div>
                            <div style={ { marginBottom: '0.2rem' } }>{ label }</div>
                            <small>
                                Age: { age }, Country: { country }
                            </small>
                        </div>
                    );
                }}
                value={ value }
                onChange={ ( ...changeArgs ) => {
					setValue( ...changeArgs );
					onChange?.( ...changeArgs );
				} } />
        </>
    );
};
With Disabled Options story ok
You can disable options in the list by setting the `disabled` property to true for individual items in the option object.
const WithDisabledOptions = () => {
    const [ value, setValue ] =
		useState< ComboboxControlProps[ 'value' ] >( null );

    return (
        <>
            <ComboboxControl
                onFilterValueChange={fn()}
                options={optionsWithDisabledOptions}
                value={ value }
                onChange={ ( ...changeArgs ) => {
					setValue( ...changeArgs );
					onChange?.( ...changeArgs );
				} } />
        </>
    );
};
Not Expand On Focus story ok
By default, the combobox expands when focused. You can disable this behavior by setting the `expandOnFocus` prop to `false`. This is useful when you want to show the suggestions only when the user interacts with the input.
const NotExpandOnFocus = () => {
    const [ value, setValue ] =
		useState< ComboboxControlProps[ 'value' ] >( null );

    return (
        <>
            <ComboboxControl
                onFilterValueChange={fn()}
                options={countryOptions}
                expandOnFocus={false}
                value={ value }
                onChange={ ( ...changeArgs ) => {
					setValue( ...changeArgs );
					onChange?.( ...changeArgs );
				} } />
        </>
    );
};

Composite

components-composite · ../packages/components/src/composite/stories/index.story.tsx
Renders a widget based on the WAI-ARIA [`composite`](https://w3c.github.io/aria/#composite) role, which provides a single tab stop on the page and arrow key navigation through the focusable descendants.
example: ```jsx import { Composite } from '@wordpress/components'; <Composite> <Composite.Item>Item 1</Composite.Item> <Composite.Item>Item 2</Composite.Item> </Composite> ```
Prop types (react-component-meta) 15 prop types
Component: ../packages/components/src/composite/index.tsx::Composite
Props:
/**
 * Indicates whether the element should be focusable even when it is
 * `disabled`.
 * 
 * This is important when discoverability is a concern. For example:
 * 
 * > A toolbar in an editor contains a set of special smart paste functions
 * that are disabled when the clipboard is empty or when the function is not
 * applicable to the current content of the clipboard. It could be helpful to
 * keep the disabled buttons focusable if the ability to discover their
 * functionality is primarily via their presence on the toolbar.
 * 
 * Learn more on [Focusability of disabled
 * controls](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#focusabilityofdisabledcontrols).
 */
accessibleWhenDisabled?: boolean | undefined

/**
 * The current active item `id`. The active item is the element within the
 * composite widget that has either DOM or virtual focus (in case
 * the `virtualFocus` prop is enabled).
 * - `null` represents the base composite element (the one with a [composite
 *   role](https://w3c.github.io/aria/#composite)). Users will be able to
 *   navigate out of it using arrow keys.
 * - If `activeId` is initially set to `null`, the base composite element
 *   itself will have focus and users will be able to navigate to it using
 *   arrow keys.
 */
activeId?: string | null | undefined

/**
 * The contents of the component.
 */
children?: ReactNode

/**
 * The composite item id that should be active by default when the composite
 * widget is rendered. If `null`, the composite element itself will have focus
 * and users will be able to navigate to it using arrow keys. If `undefined`,
 * the first enabled item will be focused.
 */
defaultActiveId?: string | null | undefined

/**
 * Determines if the element is disabled. This sets the `aria-disabled`
 * attribute accordingly, enabling support for all elements, including those
 * that don't support the native `disabled` attribute.
 * 
 * This feature can be combined with the `accessibleWhenDisabled` prop to
 * make disabled elements still accessible via keyboard.
 * 
 * **Note**: For this prop to work, the `focusable` prop must be set to
 * `true`, if it's not set by default.
 */
disabled?: boolean | undefined = false

/**
 * Makes the component a focusable element. When this element gains keyboard
 * focus, it gets a `data-focus-visible` attribute and triggers the
 * `onFocusVisible` prop.
 * The component supports the `disabled` prop even for those elements not
 * supporting the native `disabled` attribute. Disabled elements may be
 * still accessible via keyboard by using the the `accessibleWhenDisabled`
 * prop.
 * Non-native focusable elements will lose their focusability entirely.
 * However, native focusable elements will retain their inherent focusability.
 */
focusable?: boolean | undefined

/**
 * Determines how the focus behaves when the user reaches the end of the
 * composite widget.
 * 
 * On one-dimensional composite widgets:
 * - `true` loops from the last item to the first item and vice-versa.
 * - `horizontal` loops only if `orientation` is `horizontal` or not set.
 * - `vertical` loops only if `orientation` is `vertical` or not set.
 * - If `activeId` is initially set to `null`, the composite element will
 *   be focused in between the last and first items.
 * 
 * On two-dimensional composite widgets (ie. when using `CompositeRow`):
 * - `true` loops from the last row/column item to the first item in the same
 *   row/column and vice-versa. If it's the last item in the last row, it
 *   moves to the first item in the first row and vice-versa.
 * - `horizontal` loops only from the last row item to the first item in the
 *   same row.
 * - `vertical` loops only from the last column item to the first item in the
 *   column row.
 * - If `activeId` is initially set to `null`, vertical loop will have no
 *   effect as moving down from the last row or up from the first row will
 *   focus on the composite element.
 * - If `focusWrap` matches the value of `focusLoop`, it'll wrap between the
 *   last item in the last row or column and the first item in the first row or
 *   column and vice-versa.
 */
focusLoop?: boolean | Orientation | undefined = false

/**
 * **Works only on two-dimensional composite widgets**.
 * 
 * If enabled, moving up or down when there's no next item or when the next
 * item is disabled will shift to the item right before it.
 */
focusShift?: boolean | undefined = false

/**
 * **Works only on two-dimensional composite widgets**.
 * 
 * If enabled, moving to the next item from the last one in a row or column
 * will focus on the first item in the next row or column and vice-versa.
 * - `true` wraps between rows and columns.
 * - `horizontal` wraps only between rows.
 * - `vertical` wraps only between columns.
 * - If `focusLoop` matches the value of `focusWrap`, it'll wrap between the
 *   last item in the last row or column and the first item in the first row or
 *   column and vice-versa.
 */
focusWrap?: boolean | Orientation | undefined = false

/**
 * Custom event handler invoked when the element gains focus through keyboard
 * interaction or a key press occurs while the element is in focus. This is
 * the programmatic equivalent of the `data-focus-visible` attribute.
 * 
 * **Note**: For this prop to work, the `focusable` prop must be set to `true`
 * if it's not set by default.
 */
onFocusVisible?: BivariantCallback<(event: SyntheticEvent<HTMLElement, Event>) => void>

/**
 * Defines the orientation of the composite widget. If the composite has a
 * single row or column (one-dimensional), the `orientation` value determines
 * which arrow keys can be used to move focus:
 * - `both`: all arrow keys work.
 * - `horizontal`: only left and right arrow keys work.
 * - `vertical`: only up and down arrow keys work.
 * 
 * It doesn't have any effect on two-dimensional composites.
 */
orientation?: "both" | "horizontal" | "vertical" = 'both'

/**
 * Allows the component to be rendered as a different HTML element or React
 * component. The value can be a React element or a function that takes in the
 * original component props and gives back a React element with the props
 * merged.
 */
render?: ReactElement<any, string | JSXElementConstructor<any>> | RenderProp<HTMLAttributes<any> & { ref?: Ref<any> | undefined; }> | undefined

/**
 * Controls how the previous and next items are determined.
 * If `rtl` is set to `true`, they will be inverted.
 * 
 * This only affects the composite widget behavior. You still need to set
 * `dir="rtl"` on HTML/CSS.
 */
rtl?: boolean | undefined = isRTL()

/**
 * A callback that gets called when the `activeId` state changes.
 */
setActiveId?: (activeId: string | null | undefined) => void

/**
 * If enabled, the composite element will act as an
 * [`aria-activedescendant`](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#kbd_focus_activedescendant)
 * container instead of [roving
 * tabindex](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#kbd_roving_tabindex).
 * DOM focus will remain on the composite element while its items receive
 * virtual focus.
 * 
 * In both scenarios, the item in focus will carry the `data-active-item`
 * attribute.
 */
virtualFocus?: boolean | undefined = false
Imports
import { Composite, Provider as SlotFillProvider, Tooltip } from "@wordpress/components";
Default story ok
const Default = () => <Composite><>
        <Composite.Item>Item one</Composite.Item>
        <Composite.Item>Item two</Composite.Item>
        <Composite.Item>Item three</Composite.Item>
    </></Composite>;
Groups story ok
const Groups = () => <Composite><>
        <Composite.Group>
            <Composite.GroupLabel>Group one</Composite.GroupLabel>
            <Composite.Item>Item 1.1</Composite.Item>
            <Composite.Item>Item 1.2</Composite.Item>
        </Composite.Group>
        <Composite.Group>
            <Composite.GroupLabel>Group two</Composite.GroupLabel>
            <Composite.Item>Item 2.1</Composite.Item>
            <Composite.Item>Item 2.1</Composite.Item>
        </Composite.Group>
    </></Composite>;
Grid story ok
const Grid = () => <Composite role="grid" aria-label="Composite"><>
        <Composite.Row role="row">
            <Composite.Item role="gridcell">Item A1</Composite.Item>
            <Composite.Item role="gridcell">Item A2</Composite.Item>
            <Composite.Item role="gridcell">Item A3</Composite.Item>
        </Composite.Row>
        <Composite.Row role="row">
            <Composite.Item role="gridcell">Item B1</Composite.Item>
            <Composite.Item role="gridcell">Item B2</Composite.Item>
            <Composite.Item role="gridcell">Item B3</Composite.Item>
        </Composite.Row>
        <Composite.Row role="row">
            <Composite.Item role="gridcell">Item C1</Composite.Item>
            <Composite.Item role="gridcell">Item C2</Composite.Item>
            <Composite.Item role="gridcell">Item C3</Composite.Item>
        </Composite.Row>
    </></Composite>;
Hover story ok
const Hover = () => <Composite><>
        <Composite.Hover render={ <Composite.Item /> }>Hover item one
                            </Composite.Hover>
        <Composite.Hover render={ <Composite.Item /> }>Hover item two
                            </Composite.Hover>
        <Composite.Hover render={ <Composite.Item /> }>Hover item three
                            </Composite.Hover>
    </></Composite>;
Typeahead story ok
const Typeahead = () => <Composite render={<Composite.Typeahead />}><>
        <Composite.Item>Apple</Composite.Item>
        <Composite.Item>Banana</Composite.Item>
        <Composite.Item>Peach</Composite.Item>
    </></Composite>;
With Slot Fill story ok
const WithSlotFill = () => <Composite><>
        <Composite.Item>Item one (direct child)</Composite.Item>
        <Slot />
        <Composite.Item>Item four (direct child)</Composite.Item>
    </></Composite>;
With Tooltips story ok
Combining the `Tooltip` and `Composite` component has a few caveats. And while there are a few ways to compose these two components, our recommendation is to render `Composite.Item` as a child of `Tooltip`. ```jsx // 🔴 Does not work <Composite.Item render={ <Tooltip text="Tooltip"> <button>Item</button> </Tooltip> } /> // 🟢 Good <Tooltip text="Tooltip one"> <Composite.Item> Item one </Composite.Item> </Tooltip> ```
const WithTooltips = () => <Composite><>
        <Tooltip text="Tooltip one">
            <Composite.Item>Item one</Composite.Item>
        </Tooltip>
        <Tooltip text="Tooltip two">
            <Composite.Item>Item two</Composite.Item>
        </Tooltip>
        <Tooltip text="Tooltip three">
            <Composite.Item>Item three</Composite.Item>
        </Tooltip>
    </></Composite>;
Composite.Group 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/composite/index.tsx
Renders a group element for composite items.
example: ```jsx import { Composite } from '@wordpress/components'; <Composite> <Composite.Group> <Composite.GroupLabel>Label</Composite.GroupLabel> <Composite.Item>Item 1</Composite.Item> <Composite.Item>Item 2</Composite.Item> </CompositeGroup> </Composite> ```
import { Composite } from "@wordpress/components";
Component: ../packages/components/src/composite/index.tsx::Composite (react-component-meta)
/**
 * The contents of the component.
 */
children?: ReactNode

/**
 * Allows the component to be rendered as a different HTML element or React
 * component. The value can be a React element or a function that takes in the
 * original component props and gives back a React element with the props
 * merged.
 */
render?: ReactElement<any, string | JSXElementConstructor<any>> | RenderProp<HTMLAttributes<any> & { ref?: Ref<any> | undefined; }> | undefined
Composite.GroupLabel 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/composite/index.tsx
Renders a label in a composite group. This component must be wrapped with `Composite.Group` so the `aria-labelledby` prop is properly set on the composite group element.
example: ```jsx import { Composite } from '@wordpress/components'; <Composite> <Composite.Group> <Composite.GroupLabel>Label</Composite.GroupLabel> <Composite.Item>Item 1</Composite.Item> <Composite.Item>Item 2</Composite.Item> </CompositeGroup> </Composite> ```
import { Composite } from "@wordpress/components";
Component: ../packages/components/src/composite/index.tsx::Composite (react-component-meta)
/**
 * The contents of the component.
 */
children?: ReactNode

/**
 * Allows the component to be rendered as a different HTML element or React
 * component. The value can be a React element or a function that takes in the
 * original component props and gives back a React element with the props
 * merged.
 */
render?: ReactElement<any, string | JSXElementConstructor<any>> | RenderProp<HTMLAttributes<any> & { ref?: Ref<any> | undefined; }> | undefined
Composite.Row 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/composite/index.tsx
Renders a composite row. Wrapping `Composite.Item` elements within `Composite.Row` will create a two-dimensional composite widget, such as a grid.
example: ```jsx import { Composite } from '@wordpress/components'; <Composite> <Composite.Row> <Composite.Item>Item 1.1</Composite.Item> <Composite.Item>Item 1.2</Composite.Item> <Composite.Item>Item 1.3</Composite.Item> </Composite.Row> <Composite.Row> <Composite.Item>Item 2.1</Composite.Item> <Composite.Item>Item 2.2</Composite.Item> <Composite.Item>Item 2.3</Composite.Item> </Composite.Row> </Composite> ```
import { Composite } from "@wordpress/components";
Component: ../packages/components/src/composite/index.tsx::Composite (react-component-meta)
/**
 * The contents of the component.
 */
children?: ReactNode

/**
 * Allows the component to be rendered as a different HTML element or React
 * component. The value can be a React element or a function that takes in the
 * original component props and gives back a React element with the props
 * merged.
 */
render?: ReactElement<any, string | JSXElementConstructor<any>> | RenderProp<HTMLAttributes<any> & { ref?: Ref<any> | undefined; }> | undefined
Composite.Item 3 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/composite/index.tsx
Renders a composite item.
example: ```jsx import { Composite } from '@wordpress/components'; <Composite> <Composite.Item>Item 1</Composite.Item> <Composite.Item>Item 2</Composite.Item> <Composite.Item>Item 3</Composite.Item> </Composite> ```
import { Composite } from "@wordpress/components";
Component: ../packages/components/src/composite/index.tsx::Composite (react-component-meta)
/**
 * Indicates whether the element should be focusable even when it is
 * `disabled`.
 * 
 * This is important when discoverability is a concern. For example:
 * 
 * > A toolbar in an editor contains a set of special smart paste functions
 * that are disabled when the clipboard is empty or when the function is not
 * applicable to the current content of the clipboard. It could be helpful to
 * keep the disabled buttons focusable if the ability to discover their
 * functionality is primarily via their presence on the toolbar.
 * 
 * Learn more on [Focusability of disabled
 * controls](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#focusabilityofdisabledcontrols).
 */
accessibleWhenDisabled?: boolean | undefined

/**
 * The contents of the component.
 */
children?: ReactNode

/**
 * Allows the component to be rendered as a different HTML element or React
 * component. The value can be a React element or a function that takes in the
 * original component props and gives back a React element with the props
 * merged.
 */
render?: ReactElement<any, string | JSXElementConstructor<any>> | RenderProp<HTMLAttributes<any> & { ref?: Ref<any> | undefined; }> | undefined
Composite.Hover 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/composite/index.tsx
Renders an element in a composite widget that receives focus on mouse move and loses focus to the composite base element on mouse leave. This should be combined with the `Composite.Item` component.
example: ```jsx import { Composite } from '@wordpress/components'; <Composite> <Composite.Hover render={ <Composite.Item /> }> Item 1 </Composite.Hover> <Composite.Hover render={ <Composite.Item /> }> Item 2 </Composite.Hover> </Composite> ```
import { Composite } from "@wordpress/components";
Component: ../packages/components/src/composite/index.tsx::Composite (react-component-meta)
/**
 * The contents of the component.
 */
children?: ReactNode

/**
 * Allows the component to be rendered as a different HTML element or React
 * component. The value can be a React element or a function that takes in the
 * original component props and gives back a React element with the props
 * merged.
 */
render?: ReactElement<any, string | JSXElementConstructor<any>> | RenderProp<HTMLAttributes<any> & { ref?: Ref<any> | undefined; }> | undefined
Composite.Typeahead 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/composite/index.tsx
Renders a component that adds typeahead functionality to composite components. Hitting printable character keys will move focus to the next composite item that begins with the input characters.
example: ```jsx import { Composite } from '@wordpress/components'; <Composite render={ <CompositeTypeahead /> }> <Composite.Item>Item 1</Composite.Item> <Composite.Item>Item 2</Composite.Item> </Composite> ```
import { Composite } from "@wordpress/components";
Component: ../packages/components/src/composite/index.tsx::Composite (react-component-meta)
/**
 * The contents of the component.
 */
children?: ReactNode

/**
 * Allows the component to be rendered as a different HTML element or React
 * component. The value can be a React element or a function that takes in the
 * original component props and gives back a React element with the props
 * merged.
 */
render?: ReactElement<any, string | JSXElementConstructor<any>> | RenderProp<HTMLAttributes<any> & { ref?: Ref<any> | undefined; }> | undefined
Composite.Context no prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/composite/index.tsx
import { Composite } from "@wordpress/components";

ConfirmDialog

components-confirmdialog · ../packages/components/src/confirm-dialog/stories/index.story.tsx
`ConfirmDialog` is built of top of [`Modal`](/packages/components/src/modal/README.md) and displays a confirmation dialog, with _confirm_ and _cancel_ buttons. The dialog is confirmed by clicking the _confirm_ button or by pressing the `Enter` key. It is cancelled (closed) by clicking the _cancel_ button, by pressing the `ESC` key, or by clicking outside the dialog focus (i.e, the overlay). `ConfirmDialog` has two main implicit modes: controlled and uncontrolled. UnControlled: Allows the component to be used standalone, just by declaring it as part of another React's component render method: - It will be automatically open (displayed) upon mounting; - It will be automatically closed when clicking the _cancel_ button, by pressing the `ESC` key, or by clicking outside the dialog focus (i.e, the overlay); - `onCancel` is not mandatory but can be passed. Even if passed, the dialog will still be able to close itself. Activating this mode is as simple as omitting the `isOpen` prop. The only mandatory prop, in this case, is the `onConfirm` callback. The message is passed as the `children`. You can pass any JSX you'd like, which allows to further format the message or include sub-component if you'd like: ```jsx import { __experimentalConfirmDialog as ConfirmDialog } from '@wordpress/components'; function Example() { return ( <ConfirmDialog onConfirm={ () => console.debug( ' Confirmed! ' ) }> Are you sure? <strong>This action cannot be undone!</strong> </ConfirmDialog> ); } ``` Controlled mode: Let the parent component control when the dialog is open/closed. It's activated when a boolean value is passed to `isOpen`: - It will not be automatically closed. You need to let it know when to open/close by updating the value of the `isOpen` prop; - Both `onConfirm` and the `onCancel` callbacks are mandatory props in this mode; - You'll want to update the state that controls `isOpen` by updating it from the `onCancel` and `onConfirm` callbacks. ```jsx import { __experimentalConfirmDialog as ConfirmDialog } from '@wordpress/components'; import { useState } from '@wordpress/element'; function Example() { const [ isOpen, setIsOpen ] = useState( true ); const handleConfirm = () => { console.debug( 'Confirmed!' ); setIsOpen( false ); }; const handleCancel = () => { console.debug( 'Cancelled!' ); setIsOpen( false ); }; return ( <ConfirmDialog isOpen={ isOpen } onConfirm={ handleConfirm } onCancel={ handleCancel } > Are you sure? <strong>This action cannot be undone!</strong> </ConfirmDialog> ); } ```
Prop types (react-component-meta) 7 prop types
Component: ../packages/components/src/confirm-dialog/component.tsx::ConfirmDialog
Props:
/**
 * The optional custom text to display as the cancellation button's label.
 */
cancelButtonText?: string

/**
 * The actual message for the dialog. It's passed as children and any valid `ReactNode` is accepted.
 */
children: ReactNode

/**
 * The optional custom text to display as the confirmation button's label.
 */
confirmButtonText?: string

/**
 * Indicates activity while an action is being performed.
 * When `true`, the confirm button will show a busy state.
 * Both buttons will be disabled.
 */
isBusy?: boolean | undefined

/**
 * Defines if the dialog is open (displayed) or closed (not rendered/displayed).
 * It also implicitly toggles the controlled mode if set or the uncontrolled mode if it's not set.
 */
isOpen?: boolean | undefined

/**
 * The callback that's called when the user cancels. A cancellation can happen
 * when the `Cancel` button is clicked, when the `ESC` key is pressed, or when
 * a click outside of the dialog focus is detected (i.e. in the overlay).
 * 
 * It's not required if `isOpen` is not set (uncontrolled mode), as the component
 * will take care of closing itself, but you can still pass a callback if something
 * must be done upon cancelling (the component will still close itself in this case).
 * 
 * If `isOpen` is set (controlled mode), then it's required, and you need to set
 * the state that defines `isOpen` to `false` as part of this callback if you want the
 * dialog to close when the user cancels.
 */
onCancel?: (event: DialogInputEvent) => void

/**
 * The callback that's called when the user confirms.
 * A confirmation can happen when the `OK` button is clicked or when `Enter` is pressed.
 */
onConfirm: (event: DialogInputEvent) => void
Imports
import { Button, ConfirmDialog } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ isOpen, setIsOpen ] = useState( false );

    const handleConfirm: typeof onConfirm = ( confirmArgs ) => {
		onConfirm( confirmArgs );
		setIsOpen( false );
	};

    const handleCancel: typeof onCancel = ( cancelArgs ) => {
		onCancel?.( cancelArgs );
		setIsOpen( false );
	};

    return (
        <>
            <Button
                __next40pxDefaultSize
                variant="primary"
                onClick={ () => setIsOpen( true ) }>Open ConfirmDialog
                            </Button>
            <ConfirmDialog isOpen={ isOpen } onConfirm={ handleConfirm } onCancel={ handleCancel }>
                Would you like to privately publish the post now?
            </ConfirmDialog>
        </>
    );
};
With Custom Button Labels story ok
const WithCustomButtonLabels = () => {
    const [ isOpen, setIsOpen ] = useState( false );

    const handleConfirm: typeof onConfirm = ( confirmArgs ) => {
		onConfirm( confirmArgs );
		setIsOpen( false );
	};

    const handleCancel: typeof onCancel = ( cancelArgs ) => {
		onCancel?.( cancelArgs );
		setIsOpen( false );
	};

    return (
        <>
            <Button
                __next40pxDefaultSize
                variant="primary"
                onClick={ () => setIsOpen( true ) }>Open ConfirmDialog
                            </Button>
            <ConfirmDialog
                cancelButtonText="No thanks"
                confirmButtonText="Yes please!"
                isOpen={ isOpen }
                onConfirm={ handleConfirm }
                onCancel={ handleCancel }>
                { args.children }
            </ConfirmDialog>
        </>
    );
};

CustomSelectControl

components-customselectcontrol · ../packages/components/src/custom-select-control/stories/index.story.tsx
`CustomSelectControl` is a dropdown for selecting a single option from a list, with support for custom styling. Use it instead of the `SelectControl` when options need richer markup (e.g. per-option styles or hints).
Prop types (react-component-meta) 17 prop types
Component: ../packages/components/src/custom-select-control/index.tsx::default
Props:
/**
 * Use the `showSelectedHint` property instead.
 */
__experimentalShowSelectedHint?: boolean | undefined

/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Opt-in prop for an unconstrained width style which became the default in
 * WordPress 6.5. The prop is no longer needed and can be safely removed.
 */
__nextUnconstrainedWidth?: boolean | undefined

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

/**
 * Optional classname for the component.
 */
className?: string

/**
 * Description for the select trigger button used by assistive technology.
 * If no value is passed, the text "Currently selected: selectedItem.name"
 * will be used fully translated.
 */
describedBy?: string

/**
 * Hide the label visually, while keeping available to assistive technology.
 */
hideLabelFromVision?: boolean | undefined

/**
 * Label for the control.
 */
label: string

/**
 * A handler for `blur` events on the trigger button.
 */
onBlur?: FocusEventHandler<HTMLButtonElement>

/**
 * Function called with the control's internal state changes. The `selectedItem`
 * property contains the next selected item.
 */
onChange?: (newValue: CustomSelectChangeObject<NoInfer<CustomSelectOption>>) => void

/**
 * A handler for `focus` events on the trigger button.
 */
onFocus?: FocusEventHandler<HTMLButtonElement>

/**
 * A handler for `mouseout` events on the trigger button.
 */
onMouseOut?: MouseEventHandler<HTMLButtonElement>

/**
 * A handler for `mouseover` events on the trigger button.
 */
onMouseOver?: MouseEventHandler<HTMLButtonElement>

/**
 * The list of options that can be chosen from.
 */
options: readonly CustomSelectOption[]

/**
 * Show the hint of the selected item in the trigger button.
 */
showSelectedHint?: boolean | undefined = false

/**
 * The size of the control.
 */
size?: "small" | "default" | "__unstable-large" = 'default'

/**
 * Can be used to externally control the value of the control.
 */
value?: NoInfer<CustomSelectOption>
Imports
import { CustomSelectControl } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	const [ value, setValue ] = useState( props.options[ 0 ] );

	const onChange: React.ComponentProps<
		typeof CustomSelectControl
	>[ 'onChange' ] = ( changeObject ) => {
		setValue( changeObject.selectedItem );
		props.onChange?.( changeObject );
	};

	return (
		<CustomSelectControl
			{ ...props }
			onChange={ onChange }
			value={ value }
		/>
	);
};
With Long Labels story ok
const WithLongLabels = ( props ) => {
	const [ value, setValue ] = useState( props.options[ 0 ] );

	const onChange: React.ComponentProps<
		typeof CustomSelectControl
	>[ 'onChange' ] = ( changeObject ) => {
		setValue( changeObject.selectedItem );
		props.onChange?.( changeObject );
	};

	return (
		<CustomSelectControl
			{ ...props }
			onChange={ onChange }
			value={ value }
		/>
	);
};
With Hints story ok
const WithHints = ( props ) => {
	const [ value, setValue ] = useState( props.options[ 0 ] );

	const onChange: React.ComponentProps<
		typeof CustomSelectControl
	>[ 'onChange' ] = ( changeObject ) => {
		setValue( changeObject.selectedItem );
		props.onChange?.( changeObject );
	};

	return (
		<CustomSelectControl
			{ ...props }
			onChange={ onChange }
			value={ value }
		/>
	);
};

DataForm

dataviews-dataform-content · ../packages/dataviews/src/dataform/stories/content.story.tsx
`DataForm` renders an auto-generated form for viewing and editing the fields of a data item, driven by a fields and form layout configuration. Use it to edit items of a dataset, often alongside `DataViews`.
Prop types (react-component-meta) 5 prop types
Component: ../packages/dataviews/src/dataform/index.tsx::default
Props:
data: SampleData

fields: Field<SampleData>[]

form: Form

onChange: (value: Record<string, any>) => void

validity?: Record<string, FieldValidity>
Imports
import { DataForm } from "@wordpress/dataviews";
import { Stack } from "@wordpress/ui";
Labels story ok
const Labels = () => {
    const [ data, setData ] = useState< SampleData >( {
        name: '',
        email: '',
        phone: '',
    } );

    const fields: Field< SampleData >[] = useMemo(
        () => [
            {
                id: 'name',
                label: 'Name',
                type: 'text',
            },
            {
                id: 'email',
                label: 'Email',
                type: 'email',
            },
            {
                id: 'phone',
                label: 'Phone number',
                type: 'telephone',
            },
        ],
        []
    );

    const form: Form = useMemo(
        () => ( {
            layout: { type: 'regular' },
            fields: [ 'name', 'email', 'phone' ],
        } ),
        []
    );

    return (
        <Stack direction="column" gap="lg">
            <DataForm< SampleData >
                data={ data }
                fields={ fields }
                form={ form }
                onChange={ ( edits ) =>
                    setData( ( prev ) => ( { ...prev, ...edits } ) )
                }
            />
        </Stack>
    );
};
Help Text story ok
const HelpText = () => {
    const [ data, setData ] = useState< HelpTextData >( {
        name: '',
        email: '',
        phone: '',
    } );

    const fields: Field< HelpTextData >[] = useMemo(
        () => [
            {
                id: 'name',
                label: 'Name',
                type: 'text',
                placeholder: 'Jane Doe',
                description:
                    'Enter your full legal name as it appears on official documents.',
            },
            {
                id: 'email',
                label: 'Email',
                type: 'email',
                placeholder: 'you@example.com',
                description:
                    'We will use this to send you important account notifications and updates.',
            },
            {
                id: 'phone',
                label: 'Phone number',
                type: 'telephone',
                placeholder: '+1 (555) 123-4567',
                description:
                    'Include your country code. This number will be used for account verification.',
            },
        ],
        []
    );

    const form: Form = useMemo(
        () => ( {
            layout: { type: 'regular' },
            fields: [ 'name', 'email', 'phone' ],
        } ),
        []
    );

    return (
        <Stack direction="column" gap="lg">
            <DataForm< HelpTextData >
                data={ data }
                fields={ fields }
                form={ form }
                onChange={ ( edits ) =>
                    setData( ( prev ) => ( { ...prev, ...edits } ) )
                }
            />
        </Stack>
    );
};
Validation Messages story ok
const ValidationMessages = () => {
    const [ data, setData ] = useState< ValidationMessagesData >( {
        name: '',
        email: 'invalid-email',
        phone: '123',
    } );

    const fields: Field< ValidationMessagesData >[] = useMemo(
        () => [
            {
                id: 'name',
                label: 'Name',
                type: 'text',
                placeholder: 'Jane Doe',
                isValid: {
                    required: true,
                },
            },
            {
                id: 'email',
                label: 'Email',
                type: 'email',
                placeholder: 'you@example.com',
                isValid: {
                    required: true,
                    custom: ( item ) => {
                        if ( ! item.email ) {
                            return null;
                        }
                        if ( ! item.email.includes( '@' ) ) {
                            return 'Please enter a valid email address.';
                        }
                        return null;
                    },
                },
            },
            {
                id: 'phone',
                label: 'Phone number',
                type: 'telephone',
                placeholder: '+1 (555) 123-4567',
                isValid: {
                    required: true,
                    custom: ( item ) => {
                        if ( ! item.phone ) {
                            return null;
                        }
                        if ( item.phone.length < 10 ) {
                            return 'Phone number must be at least 10 digits long.';
                        }
                        return null;
                    },
                },
            },
        ],
        []
    );

    const form: Form = useMemo(
        () => ( {
            layout: { type: 'regular' },
            fields: [ 'name', 'email', 'phone' ],
        } ),
        []
    );

    const { validity } = useFormValidity( data, fields, form );
    const containerRef = useRef< HTMLDivElement >( null );

    // Show validation messages on load without focusing
    useEffect( () => {
        if ( validity && containerRef.current ) {
            const inputs = containerRef.current.querySelectorAll( 'input' );
            inputs.forEach( ( input ) => {
                // Dispatch 'invalid' event to trigger the validation message display
                input.dispatchEvent(
                    new Event( 'invalid', { bubbles: false } )
                );
            } );
        }
    }, [ validity ] );

    return (
        <div ref={ containerRef }>
            <Stack direction="column" gap="xl">
                <DataForm< ValidationMessagesData >
                    data={ data }
                    fields={ fields }
                    form={ form }
                    validity={ validity }
                    onChange={ ( edits ) =>
                        setData( ( prev ) => ( { ...prev, ...edits } ) )
                    }
                />
            </Stack>
        </div>
    );
};
High Level Help Text story ok
const HighLevelHelpText = () => {
    const [ data, setData ] = useState< HighLevelHelpTextData >( {
        name: '',
        email: '',
        phone: '',
    } );

    const fields: Field< HighLevelHelpTextData >[] = useMemo(
        () => [
            {
                id: 'name',
                label: 'Name',
                type: 'text',
            },
            {
                id: 'email',
                label: 'Email',
                type: 'email',
            },
            {
                id: 'phone',
                label: 'Phone number',
                type: 'telephone',
            },
        ],
        []
    );

    const form: Form = useMemo(
        () => ( {
            layout: { type: 'regular' },
            fields: [
                {
                    id: 'accountForm',
                    label: 'Account information',
                    description:
                        'We collect this information to create your account and provide personalized services. Your data will be kept secure and used only for account management and service improvements.',
                    children: [ 'name', 'email', 'phone' ],
                    layout: {
                        isCollapsible: false,
                        summary: 'account-form',
                        type: 'card',
                        withHeader: true,
                    },
                },
            ],
        } ),
        []
    );

    return (
        <Stack direction="column" gap="lg">
            <DataForm< HighLevelHelpTextData >
                data={ data }
                fields={ fields }
                form={ form }
                onChange={ ( edits ) =>
                    setData( ( prev ) => ( { ...prev, ...edits } ) )
                }
            />
        </Stack>
    );
};
Placeholders story ok
const Placeholders = () => {
    const [ data, setData ] = useState< PlaceholdersData >( {
        name: '',
        email: '',
        phone: '',
    } );

    const fields: Field< PlaceholdersData >[] = useMemo(
        () => [
            {
                id: 'name',
                label: 'Name',
                type: 'text',
                placeholder: 'Jane Doe',
            },
            {
                id: 'email',
                label: 'Email',
                type: 'email',
                placeholder: 'you@example.com',
            },
            {
                id: 'phone',
                label: 'Phone number',
                type: 'telephone',
                placeholder: '+1 (555) 123-4567',
            },
        ],
        []
    );

    const form: Form = useMemo(
        () => ( {
            layout: { type: 'regular' },
            fields: [ 'name', 'email', 'phone' ],
        } ),
        []
    );

    return (
        <Stack direction="column" gap="lg">
            <DataForm< PlaceholdersData >
                data={ data }
                fields={ fields }
                form={ form }
                onChange={ ( edits ) =>
                    setData( ( prev ) => ( { ...prev, ...edits } ) )
                }
            />
        </Stack>
    );
};
Docs doc ok
../packages/dataviews/src/dataform/stories/content.story.mdx
import { Canvas, Meta } from '@storybook/addon-docs/blocks';
import * as ContentStories from './content.story';

<Meta of={ ContentStories } />

# Content Elements

Guidance on understanding the semantics and proper usage of content elements in `DataForm` instances, including when and how to use high-level help text, labels, placeholders, field-level help text, and validation messages.

## Accessibility

Proper use of content elements is essential for accessibility. Each element serves a specific semantic purpose that assistive technologies rely on:

- **Labels** are announced by screen readers to identify form fields. Every field must have a label.
- **Placeholders** provide example input to hint at expected format. They are not a substitute for labels—they disappear on input and are not reliably announced.
- **Help text** provides additional context that is programmatically associated with fields and read by assistive technologies.
- **Validation messages** are announced when they appear so users know how to correct errors.

Following these semantics benefits all users, including those navigating with keyboards, using screen readers, or experiencing cognitive challenges.

## High-level help text

High-level help text provides context and guidance for an entire form. It should be used to explain the purpose of the form, the information that will be collected, and how the information will be used. To add high-level help text, use the `description` property on a field group object (a `FormField` type) in the form configuration's `fields` array that wraps all the form fields as children.

<Canvas of={ ContentStories.HighLevelHelpText } />

## Labels

A label tells users what information they need to enter in a field. Labels must be short, clear, and descriptive to avoid confusion.

<Canvas of={ ContentStories.Labels } />

### Guidelines

<table style={ { width: '100%' } }>
	<thead>
		<tr>
			<th style={ { width: '50%' } }>✅ Do</th>
			<th style={ { width: '50%' } }>🚫 Don't</th>
		</tr>
	</thead>
	<tbody>
		<tr>
			<td style={ { width: '50%' } }>Use clear and straightforward language.</td>
			<td style={ { width: '50%' } }>Use vague or ambiguous terms like "Information" or "Details".</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Limit labels to 1 to 3 concise words.</td>
			<td style={ { width: '50%' } }>Exceed 3 words—longer labels create visual clutter.</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Remove filler words and redundant phrasing.</td>
			<td style={ { width: '50%' } }>Include filler words like "Please enter your" or "Kindly provide".</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Use plain language that users understand.</td>
			<td style={ { width: '50%' } }>Use technical jargon that users might not understand.</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Be specific and descriptive.</td>
			<td style={ { width: '50%' } }>Use generic labels like "Input" or "Field 1".</td>
		</tr>
	</tbody>
</table>

## Placeholders

A placeholder provides example input to help users understand the expected format. Use placeholders sparingly, keep them short (1 to 3 words), and use real-world examples where possible. They should only be used for formatting hints or common examples, never as a replacement for labels or instructions.

<Canvas of={ ContentStories.Placeholders } />

<table style={ { width: '100%' } }>
	<thead>
		<tr>
			<th style={ { width: '50%' } }>✅ Good</th>
			<th style={ { width: '50%' } }>🚫 Bad</th>
		</tr>
	</thead>
	<tbody>
		<tr>
			<td style={ { width: '50%' } }>For a name field: "Jane Doe".</td>
			<td style={ { width: '50%' } }>For a name field: "Enter your full name here" (Should be a label or help text, not a placeholder).</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>For an email field: "you@example.com".</td>
			<td style={ { width: '50%' } }>For a password field: "At least 8 characters" (Belongs in help text, not a placeholder).</td>
		</tr>
	</tbody>
</table>

## Help text

For complicated inputs, use help text to explain how the user should proceed. Help text is always visible, appears immediately after the input, and provides essential guidance for completing the input correctly. Help text can also inform users about how their information might be used, providing transparency and context that helps build trust and sets appropriate expectations.

Use help text when the user needs contextual guidance upfront to avoid errors, when the instruction explains why or how to complete the field correctly, when the form field has complex requirements or constraints (e.g., password rules, business logic), or when the information should be accessible without additional interaction.

<Canvas of={ ContentStories.HelpText } />

### Guidelines

<table style={ { width: '100%' } }>
	<thead>
		<tr>
			<th style={ { width: '50%' } }>✅ Do</th>
			<th style={ { width: '50%' } }>🚫 Don't</th>
		</tr>
	</thead>
	<tbody>
		<tr>
			<td style={ { width: '50%' } }>Keep help text concise—one to two sentences maximum.</td>
			<td style={ { width: '50%' } }>Write lengthy paragraphs that overwhelm the user.</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Provide actionable, contextual guidance about why or how to complete the field.</td>
			<td style={ { width: '50%' } }>State the obvious or repeat what the label already conveys.</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Explain requirements or constraints that aren't obvious from the label.</td>
			<td style={ { width: '50%' } }>Duplicate format examples that belong in placeholders (e.g., "Use YYYY-MM-DD format").</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Focus on what the user needs to know to succeed.</td>
			<td style={ { width: '50%' } }>Include unnecessary background information or explanations.</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>Write in plain, user-friendly language.</td>
			<td style={ { width: '50%' } }>Use technical terms or system-specific jargon.</td>
		</tr>
		<tr>
			<td style={ { width: '50%' } }>For radios or selects, explain how to choose between options.</td>
			<td style={ { width: '50%' } }>Use help text to describe what a selected value means after selection.</td>
		</tr>
	</tbody>
</table>

## Validation messages

Validation messages help users understand and fix errors in a form. They should be clear, concise, and actionable to guide users toward correcting their input.

Where possible, messages should infer what is wrong and how the user can fix it.

<Canvas of={ ContentStories.ValidationMessages } />

### Guidelines

<table style={ { width: '100%' } }>
	<thead>
		<tr>
			<th style={ { width: '50%' } }>✅ Good</th>
			<th style={ { width: '50%' } }>🚫 Bad</th>
		</tr>
	</thead>
	<tbody>
		<tr>
			<td style={ { width: '50%' } }>Name must be at least 2 characters long.</td>
			<td style={ { width: '50%' } }>Invalid name.</td>
		</tr>
	</tbody>
</table>

DataForm

dataviews-dataform · ../packages/dataviews/src/dataform/stories/index.story.tsx
`DataForm` renders an auto-generated form for viewing and editing the fields of a data item, driven by a fields and form layout configuration. Use it to edit items of a dataset, often alongside `DataViews`.
Prop types (react-component-meta) 5 prop types
Component: ../packages/dataviews/src/dataform/index.tsx::default
Props:
data: Item

fields: Field<Item>[]

form: Form

onChange: (value: Record<string, any>) => void

validity?: Record<string, FieldValidity>
Imports
import { DataForm } from "@wordpress/dataviews";
Layout Card story ok
const LayoutCard = () => <DataForm withHeader withSummary isCollapsible />;
Layout Details story ok
const LayoutDetails = () => <DataForm />;
Layout Panel story ok
const LayoutPanel = () => <DataForm openAs="default" />;
Layout Regular story ok
const LayoutRegular = () => <DataForm disabled={false} />;
Layout Row story ok
const LayoutRow = () => <DataForm alignment="default" />;
Layout Mixed story ok
const LayoutMixed = () => <DataForm />;
Validation story ok
const Validation = () => <DataForm
    layout="regular"
    required
    elements="sync"
    custom="sync"
    pattern={false}
    minMax={false} />;
Visibility story ok
const Visibility = () => <DataForm />;
Data Adapter story ok
const DataAdapter = () => <DataForm />;

DataViews

dataviews-dataviews · ../packages/dataviews/src/dataviews/stories/index.story.tsx
`DataViews` renders a dataset using configurable layouts (table, grid, list) with built-in search, filtering, sorting, pagination, and actions. Use it to display and manage a collection of records.
Prop types (react-component-meta) 22 prop types
Component: ../packages/dataviews/src/dataviews/index.tsx::default
Props:
actions?: Action<unknown>[] = []

children?: ReactNode

config?: { perPageSizes: number[]; } = { perPageSizes: [ 10, 20, 50, 100 ] }

data: unknown[]

defaultLayouts?: SupportedLayouts = { table: {}, grid: {}, list: {} }

empty?: ReactNode

fields: Field<unknown>[]

getItemId: (item: unknown) => string = ( item: ItemWithId ) => item.id

getItemLevel?: (item: unknown) => number

header?: ReactNode

isItemClickable?: (item: unknown) => boolean = () => true

isLoading?: boolean | undefined = false

onChangeSelection?: (items: string[]) => void

onChangeView: (view: View) => void

onClickItem?: (item: unknown) => void

onReset?: false | (() => void) | undefined

paginationInfo: { totalItems: number; totalPages: number; }

renderItemLink?: (props: { item: unknown; } & ClassAttributes<HTMLAnchorElement> & AnchorHTMLAttributes<HTMLAnchorElement>) => ReactElement<...>

search?: boolean | undefined = true

searchLabel?: string = undefined

selection?: string[]

view: View
Imports
import { DataViews } from "@wordpress/dataviews";
Layout Table story ok
const LayoutTable = () => <DataViews
    containerHeight="auto"
    groupBy={false}
    groupByLabel
    hasClickableItems
    perPageSizes={[ 10, 25, 50, 100 ]}
    showMedia />;
Layout Grid story ok
const LayoutGrid = () => <DataViews
    containerHeight="auto"
    groupBy={false}
    groupByLabel
    hasClickableItems
    perPageSizes={[ 10, 25, 50, 100 ]}
    showMedia />;
Layout List story ok
const LayoutList = () => <DataViews
    containerHeight="auto"
    fullWidth={false}
    groupBy={false}
    groupByLabel
    hasClickableItems
    perPageSizes={[ 10, 25, 50, 100 ]}
    showMedia />;
Layout Activity story ok
const LayoutActivity = () => <DataViews
    containerHeight="auto"
    fullWidth={false}
    groupBy={false}
    groupByLabel
    hasClickableItems
    perPageSizes={[ 10, 25, 50, 100 ]}
    showMedia />;
Layout Custom story ok
const LayoutCustom = () => <DataViews containerHeight="auto" />;
Empty story ok
const Empty = () => <DataViews containerHeight="auto" customEmpty={false} isLoading={false} />;
Minimal UI story ok
const MinimalUI = () => <DataViews containerHeight="auto" />;
Free Composition story ok
const FreeComposition = () => <DataViews containerHeight="auto" />;
With Card story ok
const WithCard = () => <DataViews containerHeight="auto" />;
Infinite Scroll story ok
const InfiniteScroll = () => <DataViews containerHeight="auto" />;
Best practices doc ok
../packages/dataviews/src/dataviews/stories/best-practices.story.mdx
import { Meta } from '@storybook/addon-docs/blocks';

import * as DataViewsStories from './index.story';

<Meta of={ DataViewsStories } name="Best practices" />

# Data Views

Data Views allow users to display and interact with information through different layouts such as table or grid. It includes features like search, filtering, sorting, pagination, and customization options to adjust column order, items per page, and hide columns, enhancing data exploration and flexibility. 

A typical flow might be:

- Use search and filters to narrow down a large collection.
- Adjust the layout and visible fields to match the task (compare, skim, or visually scan).
- Take inline actions on item metadata, or open an editing interface when more detail is needed.

## Choosing a layout

### When to use **List**

Use the **List** layout when:

- **Content needs the most compact layout**, whether because it's used in a constrained context, or if paired with a preview surface.
- Default information density allows for a reduced set of secondary metadata.
- The view needs to work well in **narrow spaces**.

List is a good fit for items like Pages that benefit from a live preview next to the list.

### When to use **Grid**

Use the **Grid** layout when:

-   **Visual previews across multiple items at once are important** for recognition (patterns, templates, media, products).
-   You want a **card‑based experience**, with each item having its own tile (image + metadata).
-   You expect more **browsing and scanning by look** than comparing raw values.

Grid works well when choosing “by look” is more important than comparing precise numbers or dates.

### When to use **Table**

Use the **Table** layout when:

-   Users need to **compare multiple attributes across items** at once.
-   **Column headers and alignment** are critical for understanding the data.
-   The task involves working with structured data.

Table is ideal for dense, structured information where sorting and scanning down aligned columns is the primary workflow, such as posts or comments where metadata is important for choosing the next action.

## When to use something else

Data Views are designed for **browsing and managing collections**. In other situations, consider other components in the `@wordpress/dataviews` package:

- **Use `DataForm`** when the primary workflow primarily relates to **creating or editing a single item** at a level that doesn't require a full editor.
- **Use `DataViewsPicker`** when the goal is **selecting one or more items** and returning that selection to another part of the UI. This is a better fit for dialogs and sidebars where the outcome is a selection, not ongoing management of a collection, e.g. inserting from a media library.

DataViewsPicker

dataviews-dataviewspicker · ../packages/dataviews/src/dataviews-picker/stories/index.story.tsx
`DataViewsPicker` renders a dataset allowing users to select one or multiple items. It shares the layouts, search, and filtering of `DataViews` but is geared toward choosing items rather than managing them.
Prop types (react-component-meta) 18 prop types
Component: ../packages/dataviews/src/dataviews-picker/index.tsx::default
Props:
actions?: ActionButton<SpaceObject>[] = []

children?: ReactNode

config?: { perPageSizes: number[]; } = { perPageSizes: [ 10, 20, 50, 100 ] }

data: SpaceObject[]

defaultLayouts?: SupportedLayouts = {
	pickerGrid: true,
	pickerTable: true,
}

empty?: ReactNode

fields: Field<SpaceObject>[]

getItemId: (item: SpaceObject) => string = ( item: ItemWithId ) => item.id

isLoading?: boolean | undefined = false

itemListLabel?: string

onChangeSelection: (items: string[]) => void

onChangeView: (view: View) => void

onReset?: false | (() => void) | undefined

paginationInfo: { totalItems: number; totalPages: number; }

search?: boolean | undefined = true

searchLabel?: string = undefined

selection: string[]

view: View
Imports
import { Button, Modal } from "@wordpress/components";
import { DataViewsPicker } from "@wordpress/dataviews";
import { Stack } from "@wordpress/ui";
Default story ok
const Default = ( {
	perPageSizes = [ 10, 25, 50, 100 ],
	isMultiselectable,
	isGrouped,
	infiniteScrollEnabled,
}: {
	perPageSizes: number[];
	isMultiselectable: boolean;
	isGrouped: boolean;
	infiniteScrollEnabled: boolean;
} ) => (
	<DataViewsPickerContent
		perPageSizes={ perPageSizes }
		isMultiselectable={ isMultiselectable }
		isGrouped={ isGrouped }
		infiniteScrollEnabled={ infiniteScrollEnabled }
	/>
);
With Modal story ok
const WithModal = ( {
	perPageSizes = [ 10, 25, 50, 100 ],
	isMultiselectable,
	isGrouped,
	infiniteScrollEnabled,
}: {
	perPageSizes: number[];
	isMultiselectable: boolean;
	isGrouped: boolean;
	infiniteScrollEnabled: boolean;
} ) => {
	const [ isModalOpen, setIsModalOpen ] = useState( false );
	const [ selectedItems, setSelectedItems ] = useState< SpaceObject[] >( [] );

	const modalActions: ActionButton< SpaceObject >[] = [
		{
			id: 'cancel',
			label: 'Cancel',
			supportsBulk: isMultiselectable,
			callback() {
				setIsModalOpen( false );
			},
		},
		{
			id: 'confirm',
			label: 'Confirm',
			isPrimary: true,
			supportsBulk: isMultiselectable,
			callback( items ) {
				setSelectedItems( items );
				setIsModalOpen( false );
			},
		},
	];

	return (
		<>
			<Stack direction="row" justify="left" gap="sm">
				<Button
					variant="primary"
					__next40pxDefaultSize
					onClick={ () => setIsModalOpen( true ) }
				>
					Open Picker Modal
				</Button>
				<Button
					onClick={ () => setSelectedItems( [] ) }
					disabled={ ! selectedItems.length }
					accessibleWhenDisabled
					__next40pxDefaultSize
				>
					Clear Selection
				</Button>
			</Stack>
			{ selectedItems.length > 0 && (
				<p>
					Selected:{ ' ' }
					{ selectedItems
						.map( ( item ) => item.name.title )
						.join( ', ' ) }
				</p>
			) }
			{ isModalOpen && (
				<>
					<style>{ `
						.components-modal__content {
							padding: 0;
						}
						.components-modal__frame.is-full-screen .components-modal__content {
							margin-bottom: 0;
						}
					` }</style>
					<Modal
						title="Select Items"
						onRequestClose={ () => setIsModalOpen( false ) }
						isFullScreen={ false }
						size="fill"
					>
						<DataViewsPickerContent
							perPageSizes={ perPageSizes }
							isMultiselectable={ isMultiselectable }
							isGrouped={ isGrouped }
							infiniteScrollEnabled={ infiniteScrollEnabled }
							actions={ modalActions }
							selection={ selectedItems.map( ( item ) =>
								String( item.id )
							) }
						/>
					</Modal>
				</>
			) }
		</>
	);
};

Disabled

components-disabled · ../packages/components/src/disabled/stories/index.story.tsx
`Disabled` is a component which disables descendant tabbable elements and prevents pointer interaction. _Note: this component may not behave as expected in browsers that don't support the `inert` HTML attribute. We recommend adding the official WICG polyfill when using this component in your project._
see: https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/inert ```jsx import { Button, Disabled, TextControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyDisabled = () => { const [ isDisabled, setIsDisabled ] = useState( true ); let input = ( <TextControl label="Input" onChange={ () => {} } /> ); if ( isDisabled ) { input = <Disabled>{ input }</Disabled>; } const toggleDisabled = () => { setIsDisabled( ( state ) => ! state ); }; return ( <div> { input } <Button variant="primary" onClick={ toggleDisabled }> Toggle Disabled </Button> </div> ); }; ```
Prop types (react-component-meta) 3 prop types
Component: ../packages/components/src/disabled/index.tsx::default
Props:
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The children elements.
 */
children: ReactNode

/**
 * Whether to disable all the descendant fields.
 */
isDisabled?: boolean | undefined = true
Imports
import { Disabled, SelectControl, TextareaControl, TextControl, VStack } from "@wordpress/components";
Default story ok
const Default = () => {
    return (
        <Disabled isDisabled>
            <Form />
        </Disabled>
    );
};
Content Editable story ok
const ContentEditable = () => {
    return (
        <Disabled isDisabled>
            <div contentEditable tabIndex={ 0 } suppressContentEditableWarning>contentEditable
                            </div>
        </Disabled>
    );
};

Dropdown

components-dropdown · ../packages/components/src/dropdown/stories/index.story.tsx
Renders a button that opens a floating content modal when clicked. ```jsx import { Button, Dropdown } from '@wordpress/components'; const MyDropdown = () => ( <Dropdown className="my-container-class-name" contentClassName="my-dropdown-content-classname" popoverProps={ { placement: 'bottom-start' } } renderToggle={ ( { isOpen, onToggle } ) => ( <Button variant="primary" onClick={ onToggle } aria-expanded={ isOpen } > Toggle Dropdown! </Button> ) } renderContent={ () => <div>This is the content of the dropdown.</div> } /> ); ```
Prop types (react-component-meta) 15 prop types
Component: ../packages/components/src/dropdown/index.tsx::default
Props:
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | ... 161 more ... | undefined

/**
 * The className of the global container.
 */
className?: string

/**
 * If you want to target the dropdown menu for styling purposes,
 * you need to provide a contentClassName because it's not being rendered
 * as a child of the container node.
 */
contentClassName?: string

/**
 * The open state of the dropdown when initially rendered.
 * Use when you do not need to control its open state. It will be overridden
 * by the `open` prop if it is specified on the component's first render.
 */
defaultOpen?: boolean | undefined

/**
 * Opt-in prop to show popovers fullscreen on mobile.
 */
expandOnMobile?: boolean | undefined = false

/**
 * Determines focus behavior when the dialog mounts.
 * 
 * - `"firstElement"` focuses the first tabbable element within.
 * - `"firstInputElement"` focuses the first value control within.
 * - `true` focuses the element itself.
 * - `false` does nothing and _should not be used unless an accessible
 *    substitute behavior is implemented_.
 */
focusOnMount?: any = 'firstElement'

/**
 * Set this to customize the text that is shown in the dropdown's header
 * when it is fullscreen on mobile.
 */
headerTitle?: string

/**
 * A callback invoked when the popover should be closed.
 */
onClose?: () => void

/**
 * A callback invoked when the state of the dropdown changes
 * from open to closed and vice versa.
 */
onToggle?: (willOpen: boolean) => void

/**
 * The controlled open state of the dropdown.
 * Must be used in conjunction with `onToggle`.
 */
open?: boolean | undefined

/**
 * Properties of popoverProps object will be passed as props
 * to the Popover component.
 * Use this object to access properties/features
 * of the Popover component that are not already exposed
 * in the Dropdown component,
 * e.g.: the ability to have the popover without an arrow.
 */
popoverProps?: Omit<ComponentPropsWithoutRef<WordPressComponent<ElementType<any, keyof IntrinsicElements> | null, Omit<WordPressComponentProps<PopoverProps, "div", false>, "onDrag" | ... 56 more ... | "ignoreStrict"> & RefAttributes<...>, boolean> & { ...; }>, "children">

/**
 * Legacy way to specify the popover's position with respect to its anchor.
 * For details about the possible values, see the `Popover` component's docs.
 * _Note: this prop is deprecated. Use the `popoverProps.placement` prop
 * instead._
 */
position?: "top" | "middle" | "bottom" | "top center" | "top left" | "top right" | "middle center" | "middle left" | "middle right" | "bottom center" | "bottom left" | "bottom right" | "top center left" | "top center right" | "top center top" | "top center bottom" | "top left left" | "top left right" | "top left top" | "top left bottom" | "top right left" | "top right right" | "top right top" | "top right bottom" | "middle center left" | "middle center right" | "middle center top" | "middle center bottom" | "middle left left" | "middle left right" | "middle left top" | "middle left bottom" | "middle right left" | "middle right right" | "middle right top" | "middle right bottom" | "bottom center left" | "bottom center right" | "bottom center top" | "bottom center bottom" | "bottom left left" | "bottom left right" | "bottom left top" | "bottom left bottom" | "bottom right left" | "bottom right right" | "bottom right top" | "bottom right bottom"

/**
 * A callback invoked to render the content of the dropdown menu.
 * Its first argument is the same as the renderToggle prop.
 */
renderContent: (props: CallbackProps) => ReactNode

/**
 * A callback invoked to render the Dropdown Toggle Button.
 * 
 * The first argument of the callback is an object
 * containing the following properties:
 * 
 * - isOpen: whether the dropdown menu is opened or not
 * - onToggle: A function switching the dropdown menu's state
 * from open to closed and vice versa
 * - onClose: A function that closes the menu if invoked
 */
renderToggle: (props: CallbackProps) => ReactNode

/**
 * The style of the global container.
 */
style?: CSSProperties
Imports
import { Button, Dropdown, DropdownContentWrapper, MenuGroup, MenuItem } from "@wordpress/components";
Default story ok
const Default = () => <Dropdown
    onClose={fn()}
    onToggle={fn()}
    renderToggle={( { isOpen, onToggle } ) => (
        <Button
            __next40pxDefaultSize
            onClick={ onToggle }
            aria-expanded={ isOpen }
            variant="primary"
        >
            Open dropdown
        </Button>
    )}
    renderContent={() => <div>This is the dropdown content.</div>} />;
With More Padding story ok
To apply more padding to the dropdown content, use the provided `<DropdownContentWrapper>` convenience wrapper. A `paddingSize` of `"medium"` is suitable for relatively larger dropdowns (default is `"small"`).
const WithMorePadding = () => <Dropdown
    onClose={fn()}
    onToggle={fn()}
    renderContent={() => (
        <DropdownContentWrapper paddingSize="medium">
            { /* eslint-disable react/no-unescaped-entities */ }
            Content wrapped with <code>paddingSize="medium"</code>.
            { /* eslint-enable react/no-unescaped-entities */ }
        </DropdownContentWrapper>
    )} />;
With No Padding story ok
The `<DropdownContentWrapper>` convenience wrapper can also be used to remove padding entirely, with a `paddingSize` of `"none"`. This can also serve as a clean foundation to add arbitrary paddings, for example when child components already have padding on their own.
const WithNoPadding = () => <Dropdown
    onClose={fn()}
    onToggle={fn()}
    renderContent={() => (
        <DropdownContentWrapper paddingSize="none">
            { /* eslint-disable react/no-unescaped-entities */ }
            Content wrapped with <code>paddingSize="none"</code>.
            { /* eslint-enable react/no-unescaped-entities */ }
        </DropdownContentWrapper>
    )} />;
With Menu Items story ok
const WithMenuItems = () => <Dropdown
    onClose={fn()}
    onToggle={fn()}
    renderContent={() => (
        <>
            <MenuItem>Standalone Item</MenuItem>
            <MenuGroup label="Group 1">
                <MenuItem>Item 1</MenuItem>
                <MenuItem>Item 2</MenuItem>
            </MenuGroup>
            <MenuGroup label="Group 2">
                <MenuItem>Item 1</MenuItem>
                <MenuItem>Item 2</MenuItem>
            </MenuGroup>
        </>
    )} />;
DropdownContentWrapper 1 prop type
/home/runner/work/gutenberg/gutenberg/packages/components/src/dropdown/dropdown-content-wrapper.tsx
A convenience wrapper for the `renderContent` when you want to apply different padding. (Default is `paddingSize="small"`). ```jsx import { Dropdown, __experimentalDropdownContentWrapper as DropdownContentWrapper, } from '@wordpress/components'; <Dropdown renderContent={ () => ( <DropdownContentWrapper paddingSize="medium"> My dropdown content </DropdownContentWrapper> ) } /> ```
import { DropdownContentWrapper } from "@wordpress/components";
Component: ../packages/components/src/dropdown/dropdown-content-wrapper.tsx::DropdownContentWrapper (react-component-meta)
/**
 * Amount of padding to apply on the dropdown content.
 */
paddingSize?: "small" | "none" | "medium" = 'small'

DropZone

components-dropzone · ../packages/components/src/drop-zone/stories/index.story.tsx
`DropZone` is a component creating a drop zone area taking the full size of its parent element. It supports dropping files, HTML content or any other HTML drop event. ```jsx import { DropZone } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyDropZone = () => { const [ hasDropped, setHasDropped ] = useState( false ); return ( <div> { hasDropped ? 'Dropped!' : 'Drop something here' } <DropZone onFilesDrop={ () => setHasDropped( true ) } onHTMLDrop={ () => setHasDropped( true ) } onDrop={ () => setHasDropped( true ) } /> </div> ); } ```
Prop types (react-component-meta) 7 prop types
Component: ../packages/components/src/drop-zone/index.tsx::default
Props:
/**
 * A CSS `class` to give to the wrapper element.
 */
className?: string

/**
 * An icon to be shown within the drop zone area.
 */
icon?: Element = jsx(SVG, { xmlns: "http://www.w3.org/2000/svg", viewBox: "0 0 24 24", fill: "currentColor", children: /* @__PURE__ */ jsx(Path, { d: "M18.5 15v3.5H13V6.7l4.5 4.1 1-1.1-6.2-5.8-5.8 5.8 1 1.1 4-4v11.7h-6V15H4v5h16v-5z" }) })

/**
 * A function to determine if the drop zone is eligible to handle the drop
 * data transfer items.
 */
isEligible?: (dataTransfer: DataTransfer) => boolean = () => true

/**
 * A string to be shown within the drop zone area.
 */
label?: string = `__( 'Drop files to upload' )`

/**
 * The function is generic drop handler called if the `onFilesDrop` or `onHTMLDrop` are not called.
 * It receives the drop `event` object as an argument.
 */
onDrop?: (event: DragEvent) => void

/**
 * The function is called when dropping a file into the `DropZone`.
 * It receives an array of dropped files as an argument.
 */
onFilesDrop?: (files: File[]) => void

/**
 * The function is called when dropping HTML into the `DropZone`.
 * It receives the HTML being dropped as an argument.
 */
onHTMLDrop?: (html: string) => void
Imports
import { DropZone } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	return (
		<div
			style={ {
				background: 'lightgray',
				padding: 32,
				position: 'relative',
			} }
		>
			Drop something here
			<DropZone { ...props } />
		</div>
	);
};

EmptyState.Root

design-system-components-emptystate · ../packages/ui/src/empty-state/stories/index.story.tsx
The root container for an empty state component.
Prop types (react-component-meta) 4 prop types
Component: ../packages/ui/src/empty-state/index.ts::Root
Props:
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Imports
import { Button, Actions, Description, Icon, Root, Title, Visual } from "@wordpress/ui";
Default story ok
const Default = () => <EmptyState.Root><>
        <EmptyState.Icon icon={ search } />
        <EmptyState.Title>No results found</EmptyState.Title>
        <EmptyState.Description>Try adjusting your search or filter to find what you're
                                looking for.
                            </EmptyState.Description>
        <EmptyState.Actions>
            <Button variant="outline">Clear filters</Button>
            <Button>Add item</Button>
        </EmptyState.Actions>
    </></EmptyState.Root>;
With Custom Visual story ok
const WithCustomVisual = () => <EmptyState.Root><>
        <EmptyState.Visual>
            <svg
                width="50"
                height="50"
                viewBox="0 0 50 50"
                fill="none"
                xmlns="http://www.w3.org/2000/svg">
                <circle cx="25" cy="25" r="25" fill="currentColor" />
            </svg>
        </EmptyState.Visual>
        <EmptyState.Title>All caught up!</EmptyState.Title>
        <EmptyState.Description>You've completed all your tasks. Great work!
                            </EmptyState.Description>
        <EmptyState.Actions>
            <Button>Create new task</Button>
        </EmptyState.Actions>
    </></EmptyState.Root>;
EmptyState.Visual 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/empty-state/index.ts
A container for visual content in an empty state (e.g., icons, illustrations). Provides appropriate spacing and alignment for visual elements.
import { Visual } from "@wordpress/ui";
Component: ../packages/ui/src/empty-state/index.ts::Visual (react-component-meta)
/**
 * The visual content of the empty state (e.g., icon, illustration).
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
EmptyState.Icon 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/empty-state/index.ts
An icon visual for empty states. Renders an icon with styling treatment for empty states.
import { Icon } from "@wordpress/ui";
Component: ../packages/ui/src/empty-state/index.ts::Icon (react-component-meta)
/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * The icon to render.
 */
icon: ReactElement<SVGProps<SVGSVGElement>, string | JSXElementConstructor<any>>

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
EmptyState.Title 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/empty-state/index.ts
The title is a short heading that communicates the empty state.
import { Title } from "@wordpress/ui";
Component: ../packages/ui/src/empty-state/index.ts::Title (react-component-meta)
/**
 * The title text of the empty state.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined = <h2 />

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
EmptyState.Description 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/empty-state/index.ts
The description text for an empty state, providing additional context and guidance on what the user should do next.
import { Description } from "@wordpress/ui";
Component: ../packages/ui/src/empty-state/index.ts::Description (react-component-meta)
/**
 * The description text of the empty state.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined = <p />

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
EmptyState.Actions 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/empty-state/index.ts
A container for action buttons in an empty state. Actions are optional, and can include a primary and optional secondary action button.
import { Actions } from "@wordpress/ui";
Component: ../packages/ui/src/empty-state/index.ts::Actions (react-component-meta)
/**
 * The action buttons for the empty state.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

FormFileUpload

components-formfileupload · ../packages/components/src/form-file-upload/stories/index.story.tsx
FormFileUpload allows users to select files from their local device. ```jsx import { FormFileUpload } from '@wordpress/components'; const MyFormFileUpload = () => ( <FormFileUpload accept="image/*" onChange={ ( event ) => console.log( event.currentTarget.files ) } > Upload </FormFileUpload> ); ```
Prop types (react-component-meta) 8 prop types
Component: ../packages/components/src/form-file-upload/index.tsx::default
Props:
/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * A string passed to the `input` element that tells the browser which
 * [file types](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input/file#Unique_file_type_specifiers)
 * can be uploaded by the user. e.g: `image/*,video/*`.
 */
accept?: string

/**
 * Children are passed as children of `Button`.
 */
children?: ReactNode

/**
 * The icon to render in the default button.
 * 
 * See the `Icon` component docs for more information.
 */
icon?: IconType | null | undefined

/**
 * Whether to allow multiple selection of files or not.
 */
multiple?: boolean | undefined = false

/**
 * Callback function passed directly to the `input` file element.
 * 
 * Select files will be available in `event.currentTarget.files`.
 */
onChange: ChangeEventHandler<HTMLInputElement> | undefined

/**
 * Callback function passed directly to the `input` file element.
 * 
 * This can be useful when you want to force a `change` event to fire when
 * the user chooses the same file again. To do this, set the target value to
 * an empty string in the `onClick` function.
 * 
 * ```jsx
 * <FormFileUpload
 *   onClick={ ( event ) => ( event.target.value = '' ) }
 *   onChange={ onChange }
 * >
 *   Upload
 * </FormFileUpload>
 * ```
 */
onClick?: MouseEventHandler<HTMLInputElement>

/**
 * Optional callback function used to render the UI.
 * 
 * If passed, the component does not render the default UI (a button) and
 * calls this function to render it. The function receives an object with
 * property `openFileDialog`, a function that, when called, opens the browser
 * native file upload modal window.
 */
render?: (arg: { openFileDialog: () => void; }) => ReactNode
Imports
import { FormFileUpload } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	return <FormFileUpload { ...props } />;
};
Restrict File Types story ok
const RestrictFileTypes = ( props ) => {
	return <FormFileUpload { ...props } />;
};
Allow Multiple Files story ok
const AllowMultipleFiles = ( props ) => {
	return <FormFileUpload { ...props } />;
};
With Icon story ok
const WithIcon = ( props ) => {
	return <FormFileUpload { ...props } />;
};
With Custom Render story ok
Render a custom trigger button by passing a render function to the `render` prop. ```jsx ( { openFileDialog } ) => <button onClick={ openFileDialog }>Custom Upload Button</button> ```
const WithCustomRender = ( props ) => {
	return <FormFileUpload { ...props } />;
};

FormToggle

components-formtoggle · ../packages/components/src/form-toggle/stories/index.story.tsx
FormToggle switches a single setting on or off. ```jsx import { FormToggle } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyFormToggle = () => { const [ isChecked, setChecked ] = useState( true ); return ( <FormToggle checked={ isChecked } onChange={ () => setChecked( ( state ) => ! state ) } /> ); }; ```
Prop types (react-component-meta) 3 prop types
Component: ../packages/components/src/form-toggle/index.tsx::default
Props:
/**
 * If checked is true the toggle will be checked. If checked is false the
 * toggle will be unchecked. If no value is passed the toggle will be
 * unchecked.
 */
checked?: boolean | undefined

/**
 * If disabled is true the toggle will be disabled and apply the appropriate
 * styles.
 */
disabled?: boolean | undefined

/**
 * A callback function invoked when the toggle is clicked.
 */
onChange: (event: ChangeEvent<HTMLInputElement>) => void = () => {}
Imports
import { FormToggle } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ isChecked, setChecked ] = useState( true );

    return (
        <FormToggle
            checked={ isChecked }
            onChange={ ( e ) => {
				setChecked( ( state ) => ! state );
				onChange( e );
			} } />
    );
};

FormTokenField

components-formtokenfield · ../packages/components/src/form-token-field/stories/index.story.tsx
A `FormTokenField` is a field similar to the tags and categories fields in the interim editor chrome, or the "to" field in Mail on OS X. Tokens can be entered by typing them or selecting them from a list of suggested tokens. Up to one hundred suggestions that match what the user has typed so far will be shown from which the user can pick from (auto-complete). Tokens are separated by the "," character. Suggestions can be selected with the up or down arrows and added with the tab or enter key. The `value` property is handled in a manner similar to controlled form components. See [Forms](https://react.dev/reference/react-dom/components#form-components) in the React Documentation for more information.
Prop types (react-component-meta) 28 prop types
Component: ../packages/components/src/form-token-field/index.tsx::default
Props:
/**
 * If true, the select the first matching suggestion when the user presses
 * the Enter key (or space when tokenizeOnSpace is true).
 */
__experimentalAutoSelectFirstMatch?: boolean | undefined = false

/**
 * If true, the suggestions list will be always expanded when the input field has the focus.
 */
__experimentalExpandOnFocus?: boolean | undefined = false

/**
 * Custom renderer for suggestions.
 */
__experimentalRenderItem?: (args: { item: string; }) => ReactNode

/**
 * Use the `help` prop instead. The `help` prop now defaults to the previous
 * how-to text; if you were passing `__experimentalShowHowTo={ false }` to
 * hide it, pass an empty string to `help` instead.
 */
__experimentalShowHowTo?: boolean | undefined

/**
 * If passed, all introduced values will be validated before being added as tokens.
 */
__experimentalValidateInput?: (token: string) => boolean = () => true

/**
 * Deprecated. Use `__next40pxDefaultSize` instead.
 */
__next36pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the
 * default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined = false

autoCapitalize?: "off" | "none" | "on" | "sentences" | "words" | "characters" | (string & {}) | undefined

autoComplete?: HTMLInputAutoCompleteAttribute | undefined

className?: string

/**
 * When true, tokens are not able to be added or removed.
 */
disabled?: boolean | undefined = false

/**
 * Function to call to transform tokens for display.
 * (In the editor, this is needed to decode HTML entities embedded in tags
 * - otherwise entities like `&` in tag names are double-encoded like `&amp;`,
 * once by the REST API and once by React).
 */
displayTransform?: (token: string) => string = ( value: string ) => value

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An
 * element containing the description will be programmatically associated to
 * the `FormTokenField` via `aria-describedby`.
 * 
 * Defaults to a how-to message (e.g. _Separate with commas or the Enter key._);
 * pass an empty string to hide it.
 */
help?: ReactNode

/**
 * When true, renders tokens as without a background.
 */
isBorderless?: boolean | undefined = false

label?: string = __( 'Add item' )

/**
 * If passed, `TokenField` will disable ability to add new tokens once number of tokens is greater than or equal to `maxLength`.
 */
maxLength?: number

/**
 * The maximum number of suggestions to display at a time.
 */
maxSuggestions?: number = 100

/**
 * Allows customizing the messages presented by screen readers in different occasions:
 * 
 * -   `added`: The user added a new token.
 * -   `removed`: The user removed an existing token.
 * -   `remove` : The user focused the button to remove the token.
 * -   `__experimentalInvalid`: The user tried to add a token that didn't pass the validation.
 */
messages?: Messages = {
			added: __( 'Item added.' ),
			removed: __( 'Item removed.' ),
			remove: __( 'Remove item' ),
			__experimentalInvalid: __( 'Invalid item' ),
		}

/**
 * Function to call when the tokens have changed. An array of new tokens is passed to the callback.
 */
onChange?: (tokens: (string | TokenItem)[]) => void = () => {}

/**
 * Function to call when the TokenField has been focused on. The event is passed to the callback. Useful for analytics.
 */
onFocus?: (event: FocusEvent<Element, Element>) => void = undefined

/**
 * Function to call when the users types in the input field. It can be used to trigger autocomplete requests.
 */
onInputChange?: (input: string) => void = () => {}

/**
 * If passed, the `TokenField` input will show a placeholder string if no value tokens are present.
 */
placeholder?: string

/**
 * Function to call to transform tokens for saving. The default is to trim the token value.
 * This function is also applied when matching suggestions against the current value
 * so that matching works correctly with leading or trailing spaces. (In the editor,
 * this is needed to remove leading and trailing spaces from tag names, like wp-admin does.
 * Otherwise the REST API won't save them.)
 */
saveTransform?: (token: string) => string = ( token ) => token.trim()

/**
 * An array of strings to present to the user as suggested tokens.
 */
suggestions?: string[] = []

/**
 * If true, add any incompleteTokenValue as a new token when the field loses focus.
 */
tokenizeOnBlur?: boolean | undefined = false

/**
 * If true, will add a token when `TokenField` is focused and `space` is pressed.
 */
tokenizeOnSpace?: boolean | undefined = false

/**
 * An array of strings or objects to display as tokens in the field.
 * If objects are present in the array, they **must** have a property of `value`.
 */
value?: (string | TokenItem)[] = []
Imports
import { FormTokenField } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ selectedContinents, setSelectedContinents ] = useState<
		ComponentProps< typeof FormTokenField >[ 'value' ]
	>( [] );

    return (
        <FormTokenField
            label="Type a continent"
            suggestions={continents}
            value={ selectedContinents }
            onChange={ ( tokens ) => setSelectedContinents( tokens ) } />
    );
};
Async story ok
const Async = () => {
    const [ selectedContinents, setSelectedContinents ] = useState<
		ComponentProps< typeof FormTokenField >[ 'value' ]
	>( [] );
    const [ availableContinents, setAvailableContinents ] = useState<
		string[]
	>( [] );

    const searchContinents = ( input: string ) => {
		const timeout = setTimeout( () => {
			const available = ( suggestions || [] ).filter( ( continent ) =>
				continent.toLowerCase().includes( input.toLowerCase() )
			);
			setAvailableContinents( available );
		}, 1000 );

		return () => clearTimeout( timeout );
	};

    return (
        <FormTokenField
            label="Type a continent"
            value={ selectedContinents }
            suggestions={ availableContinents }
            onChange={ ( tokens ) => setSelectedContinents( tokens ) }
            onInputChange={ searchContinents } />
    );
};
Dropdown Selector story ok
const DropdownSelector = () => {
    const [ selectedContinents, setSelectedContinents ] = useState<
		ComponentProps< typeof FormTokenField >[ 'value' ]
	>( [] );

    return (
        <FormTokenField
            __experimentalExpandOnFocus
            __experimentalAutoSelectFirstMatch
            value={ selectedContinents }
            onChange={ ( tokens ) => setSelectedContinents( tokens ) } />
    );
};
With Custom Rendered Items story ok
The rendered content of each token can be customized by passing a render function to the `displayTransform` prop. Similarly, each suggestion can be customized by passing a render function to the `__experimentalRenderItem` prop. (This is still an experimental feature and is subject to change.)
const WithCustomRenderedItems = () => {
    const [ selectedContinents, setSelectedContinents ] = useState<
		ComponentProps< typeof FormTokenField >[ 'value' ]
	>( [] );

    return (
        <FormTokenField
            displayTransform={( token ) => `📍 ${ token }`}
            __experimentalRenderItem={( { item } ) => (
                <div>{ `${ item } — a nice place to visit` }</div>
            )}
            __experimentalExpandOnFocus
            value={ selectedContinents }
            onChange={ ( tokens ) => setSelectedContinents( tokens ) } />
    );
};
Validate New Tokens story ok
Only values for which the `__experimentalValidateInput` function returns `true` will be tokenized. (This is still an experimental feature and is subject to change.) In this example, the user can only add tokens that are already in the list.
const ValidateNewTokens = () => {
    const [ selectedContinents, setSelectedContinents ] = useState<
		ComponentProps< typeof FormTokenField >[ 'value' ]
	>( [] );

    return (
        <FormTokenField
            __experimentalValidateInput={( input: string ) =>
                continents.includes( input )}
            __experimentalExpandOnFocus
            value={ selectedContinents }
            onChange={ ( tokens ) => setSelectedContinents( tokens ) } />
    );
};

GradientPicker

components-gradientpicker · ../packages/components/src/gradient-picker/stories/index.story.tsx
GradientPicker is a React component that renders a color gradient picker to define a multi step gradient. There's either a _linear_ or a _radial_ type available. ```jsx import { useState } from 'react'; import { GradientPicker } from '@wordpress/components'; const MyGradientPicker = () => { const [ gradient, setGradient ] = useState( null ); return ( <GradientPicker value={ gradient } onChange={ ( currentGradient ) => setGradient( currentGradient ) } gradients={ [ { name: 'JShine', gradient: 'linear-gradient(135deg,#12c2e9 0%,#c471ed 50%,#f64f59 100%)', slug: 'jshine', }, { name: 'Moonlit Asteroid', gradient: 'linear-gradient(135deg,#0F2027 0%, #203A43 0%, #2c5364 100%)', slug: 'moonlit-asteroid', }, { name: 'Rastafarie', gradient: 'linear-gradient(135deg,#1E9600 0%, #FFF200 0%, #FF0000 100%)', slug: 'rastafari', }, ] } /> ); }; ```
Prop types (react-component-meta) 14 prop types
Component: ../packages/components/src/gradient-picker/index.tsx::default
Props:
/**
 * Whether this is rendered in the sidebar.
 */
__experimentalIsRenderedInSidebar?: boolean | undefined = false

/**
 * Start opting in to the new margin-free styles that will become the default
 * in a future version, currently scheduled to be WordPress 6.4. (The prop
 * can be safely removed once this happens.)
 */
__nextHasNoMargin?: boolean | undefined = false

/**
 * A label to identify the purpose of the control.
 */
aria-label?: string

/**
 * An ID of an element to provide a label for the control.
 */
aria-labelledby?: string

/**
 * Whether the control should present as a set of buttons,
 * each with its own tab stop.
 */
asButtons?: boolean | undefined = false

/**
 * The class name added to the wrapper.
 */
className?: string

/**
 * Whether the palette should have a clearing button or not.
 */
clearable?: boolean | undefined = true

/**
 * If true, the gradient picker will not be displayed and only defined
 * gradients from `gradients` will be shown.
 */
disableCustomGradients?: boolean | undefined = false

/**
 * Whether to enable alpha transparency options in the picker.
 */
enableAlpha?: boolean | undefined = true

/**
 * An array of objects as predefined gradients displayed above the gradient
 * selector. Alternatively, if there are multiple sets (or 'origins') of
 * gradients, you can pass an array of objects each with a `name` and a
 * `gradients` array which will in turn contain the predefined gradient objects.
 */
gradients?: GradientsProp | undefined = []

/**
 * The heading level. Only applies in cases where gradients are provided
 * from multiple origins (i.e. when the array passed as the `gradients` prop
 * contains two or more items).
 */
headingLevel?: 1 | 2 | "1" | 3 | 4 | 5 | 6 | "2" | "3" | "4" | "5" | "6" = 2

/**
 * Prevents keyboard interaction from wrapping around.
 * Only used when `asButtons` is not true.
 */
loop?: boolean | undefined = true

/**
 * The function called when a new gradient has been defined. It is passed to
 * the `currentGradient` as an argument.
 */
onChange: (currentGradient: string | undefined) => void

/**
 * The current value of the gradient. Pass a css gradient string (See default value for example).
 * Optionally pass in a `null` value to specify no gradient is currently selected.
 */
value?: string | null | undefined = 'linear-gradient(135deg,rgba(6,147,227,1) 0%,rgb(155,81,224) 100%)'
Imports
import { GradientPicker } from "@wordpress/components";
Default story ok
const Default = ( {
	onChange,
	...props
}: React.ComponentProps< typeof GradientPicker > ) => {
	const [ gradient, setGradient ] =
		useState< ( typeof props )[ 'value' ] >( null );
	return (
		<GradientPicker
			{ ...props }
			value={ gradient }
			onChange={ ( ...changeArgs ) => {
				setGradient( ...changeArgs );
				onChange?.( ...changeArgs );
			} }
		/>
	);
};
With No Existing Gradients story ok
const WithNoExistingGradients = ( {
	onChange,
	...props
}: React.ComponentProps< typeof GradientPicker > ) => {
	const [ gradient, setGradient ] =
		useState< ( typeof props )[ 'value' ] >( null );
	return (
		<GradientPicker
			{ ...props }
			value={ gradient }
			onChange={ ( ...changeArgs ) => {
				setGradient( ...changeArgs );
				onChange?.( ...changeArgs );
			} }
		/>
	);
};
Multiple Origins story ok
const MultipleOrigins = ( {
	onChange,
	...props
}: React.ComponentProps< typeof GradientPicker > ) => {
	const [ gradient, setGradient ] =
		useState< ( typeof props )[ 'value' ] >( null );
	return (
		<GradientPicker
			{ ...props }
			value={ gradient }
			onChange={ ( ...changeArgs ) => {
				setGradient( ...changeArgs );
				onChange?.( ...changeArgs );
			} }
		/>
	);
};
CSS Variables story ok
const CSSVariables = () => <div
    style={ {
        '--red': '#f00',
        '--yellow': '#ff0',
        '--blue': '#00f',
    } }>
    <Template
        onChange={fn()}
        gradients={[
			{
				name: 'Red to Yellow',
				gradient:
					'linear-gradient(135deg,var(--red) 0%,var(--yellow) 100%)',
				slug: 'red-to-yellow',
			},
			{
				name: 'Yellow to Blue',
				gradient:
					'linear-gradient(135deg,var(--yellow) 0%,var(--blue) 100%)',
				slug: 'yellow-to-blue',
			},
			{
				name: 'Blue to Red',
				gradient:
					'linear-gradient(135deg,var(--blue) 0%,var(--red) 100%)',
				slug: 'blue-to-red',
			},
		]} />
</div>;

Icon

design-system-components-icon · ../packages/ui/src/icon/stories/index.story.tsx
Renders an SVG icon with a 24px default size. ```jsx import { wordpress } from '@wordpress/icons'; <Icon icon={ wordpress } /> ```
Prop types (react-component-meta) 2 prop types
Component: ../packages/ui/src/icon/index.ts::Icon
Props:
/**
 * The icon to render, which must be an svg element or an `SVG` from `@wordpress/primitives`.
 * 
 * In most cases, you should use an icon from
 * [the `@wordpress/icons` package](https://wordpress.github.io/gutenberg/?path=/story/icons-icon--library).
 */
icon: ReactElement<SVGProps<SVGSVGElement>, string | JSXElementConstructor<any>>

/**
 * The size (width and height) of the icon.
 */
size?: number = 24
Imports
import { Icon } from "@wordpress/ui";
Default story ok
const Default = () => <Icon icon={wordpress} />;

InputControl

components-inputcontrol · ../packages/components/src/input-control/stories/index.story.tsx
InputControl components let users enter and edit text. This is an experimental component intended to (in time) merge with or replace `TextControl`. ```jsx import { __experimentalInputControl as InputControl } from '@wordpress/components'; import { useState } from 'react'; const Example = () => { const [ value, setValue ] = useState( '' ); return ( <InputControl __next40pxDefaultSize value={ value } onChange={ ( nextValue ) => setValue( nextValue ?? '' ) } /> ); }; ```
Prop types (react-component-meta) 24 prop types
Component: ../packages/components/src/input-control/index.tsx::default
Props:
/**
 * Deprecated. Use `__next40pxDefaultSize` instead.
 */
__next36pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined = false

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

__unstableInputWidth?: Width<string | number> | undefined

__unstableStateReducer?: StateReducer = ( state ) => state

/**
 * If true, the `input` will be disabled.
 */
disabled?: boolean | undefined = false

/**
 * Determines the drag axis.
 */
dragDirection?: "s" | "n" | "e" | "w" = 'n'

/**
 * If `isDragEnabled` is true, this controls the amount of `px` to have been dragged before
 * the drag gesture is actually triggered.
 */
dragThreshold?: number = 10

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If true, enables mouse drag gestures.
 */
isDragEnabled?: boolean | undefined = false

/**
 * If true, the `ENTER` key press is required in order to trigger an `onChange`.
 * If enabled, a change is also triggered when tabbing away (`onBlur`).
 */
isPressEnterToChange?: boolean | undefined = false

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * The position of the label.
 */
labelPosition?: "top" | "bottom" | "side" | "edge" = 'top'

/**
 * A function that receives the value of the input.
 */
onChange?: InputChangeCallback<{}> = () => {}

onDrag?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragEnd?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragStart?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onValidate?: (nextValue: string, event?: SyntheticEvent<HTMLInputElement, Event> | undefined) => void = () => {}

/**
 * Renders an element on the left side of the input.
 * 
 * By default, the prefix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlPrefixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlPrefixWrapper as InputControlPrefixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   prefix={<InputControlPrefixWrapper>@</InputControlPrefixWrapper>}
 * />
 * ```
 */
prefix?: ReactNode

/**
 * Adjusts the size of the input.
 */
size?: "small" | "default" | "compact" | "__unstable-large" = 'default'

/**
 * Renders an element on the right side of the input.
 * 
 * By default, the suffix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlSuffixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlSuffixWrapper as InputControlSuffixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   suffix={<InputControlSuffixWrapper>%</InputControlSuffixWrapper>}
 * />
 * ```
 */
suffix?: ReactNode

/**
 * Type of the input element to render.
 */
type?: HTMLInputTypeAttribute | undefined = 'text'

/**
 * The current value of the input.
 */
value?: string
Imports
import { Button, InputControl, InputControlPrefixWrapper, InputControlSuffixWrapper } from "@wordpress/components";
import { Icon } from "@wordpress/icons";
Default story ok
const Default = () => <InputControl
    __next40pxDefaultSize
    onChange={fn()}
    onValidate={fn()}
    onKeyDown={fn()}
    label="Value"
    placeholder="Placeholder" />;
With Help Text story ok
const WithHelpText = () => <InputControl
    __next40pxDefaultSize
    onChange={fn()}
    onValidate={fn()}
    onKeyDown={fn()}
    help="Help text to describe the control." />;
With Prefix story ok
A `prefix` can be inserted before the input. By default, the prefix is aligned with the edge of the input border, with no padding. If you want to apply standard padding in accordance with the size variant, use the provided `<InputControlPrefixWrapper>` convenience wrapper.
const WithPrefix = () => <InputControl
    __next40pxDefaultSize
    onChange={fn()}
    onValidate={fn()}
    onKeyDown={fn()}
    prefix={<InputControlPrefixWrapper>@</InputControlPrefixWrapper>} />;
With Suffix story ok
A `suffix` can be inserted after the input. By default, the suffix is aligned with the edge of the input border, with no padding. If you want to apply standard padding in accordance with the size variant, use the provided `<InputControlSuffixWrapper>` convenience wrapper.
const WithSuffix = () => <InputControl
    __next40pxDefaultSize
    onChange={fn()}
    onValidate={fn()}
    onKeyDown={fn()}
    suffix={<InputControlSuffixWrapper>%</InputControlSuffixWrapper>} />;
With Icon Or Control story ok
`<InputControlPrefixWrapper>` and `<InputControlSuffixWrapper>` have a `variant` prop that can be used to adjust the wrapper based on the prefix or suffix content. - `'default'`: Standard padding for text content. - `'icon'`: For icons. - `'control'`: For controls, like buttons or selects.
const WithIconOrControl = () => <InputControl
    __next40pxDefaultSize
    onChange={fn()}
    onValidate={fn()}
    onKeyDown={fn()}
    prefix={(<InputControlPrefixWrapper variant="icon">
        <Icon icon={ link } />
    </InputControlPrefixWrapper>)}
    suffix={(<InputControlSuffixWrapper variant="control">
        <Button icon={ closeSmall } size="small" label="Clear" />
    </InputControlSuffixWrapper>)} />;
With Side Label story ok
const WithSideLabel = () => <InputControl
    __next40pxDefaultSize
    onChange={fn()}
    onValidate={fn()}
    onKeyDown={fn()}
    labelPosition="side" />;
With Edge Label story ok
const WithEdgeLabel = () => <InputControl
    __next40pxDefaultSize
    onChange={fn()}
    onValidate={fn()}
    onKeyDown={fn()}
    __unstableInputWidth="20em"
    labelPosition="edge" />;
Show Password story ok
const ShowPassword = () => {
    const [ visible, setVisible ] = useState( false );

    return (
        <InputControl
            __next40pxDefaultSize
            type={ visible ? 'text' : 'password' }
            suffix={
				<InputControlSuffixWrapper variant="control">
					<Button
						size="small"
						icon={ visible ? unseen : seen }
						onClick={ () => setVisible( ( value ) => ! value ) }
						label={ visible ? 'Hide password' : 'Show password' }
					/>
				</InputControlSuffixWrapper>
			}
            onChange={fn()}
            onValidate={fn()}
            onKeyDown={fn()}
            label="Password"
            placeholder={undefined} />
    );
};
InputControlPrefixWrapper 5 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/input-control/input-prefix-wrapper.tsx
A convenience wrapper for the `prefix` when you want to apply standard padding in accordance with the size variant. ```jsx import { __experimentalInputControl as InputControl, __experimentalInputControlPrefixWrapper as InputControlPrefixWrapper, } from '@wordpress/components'; <InputControl prefix={<InputControlPrefixWrapper>@</InputControlPrefixWrapper>} /> ```
import { InputControlPrefixWrapper } from "@wordpress/components";
Component: ../packages/components/src/input-control/input-prefix-wrapper.tsx::InputControlPrefixWrapper (react-component-meta)
/**
 * Internal prop used to control the padding size of the wrapper.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The content to be inserted.
 */
children: ReactNode

/**
 * Internal prop used to control the padding size of the wrapper.
 */
size?: "small" | "default" | "compact" | "__unstable-large"

/**
 * Adjust the wrapper based on the prefix or suffix content.
 * 
 * - `'default'`: Standard padding for text content.
 * - `'icon'`: For icons.
 * - `'control'`: For controls, like buttons or selects.
 */
variant?: "icon" | "default" | "control" = 'default'
InputControlSuffixWrapper 5 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/input-control/input-suffix-wrapper.tsx
A convenience wrapper for the `suffix` when you want to apply standard padding in accordance with the size variant. ```jsx import { __experimentalInputControl as InputControl, __experimentalInputControlSuffixWrapper as InputControlSuffixWrapper, } from '@wordpress/components'; <InputControl suffix={<InputControlSuffixWrapper>%</InputControlSuffixWrapper>} /> ```
import { InputControlSuffixWrapper } from "@wordpress/components";
Component: ../packages/components/src/input-control/input-suffix-wrapper.tsx::InputControlSuffixWrapper (react-component-meta)
/**
 * Internal prop used to control the padding size of the wrapper.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The content to be inserted.
 */
children: ReactNode

/**
 * Internal prop used to control the padding size of the wrapper.
 */
size?: "small" | "default" | "compact" | "__unstable-large"

/**
 * Adjust the wrapper based on the prefix or suffix content.
 * 
 * - `'default'`: Standard padding for text content.
 * - `'icon'`: For icons.
 * - `'control'`: For controls, like buttons or selects.
 */
variant?: "icon" | "default" | "control" = 'default'

ItemGroup

components-itemgroup · ../packages/components/src/item-group/stories/index.story.tsx
`ItemGroup` displays a list of `Item`s grouped and styled together. ```jsx import { __experimentalItemGroup as ItemGroup, __experimentalItem as Item, } from '@wordpress/components'; function Example() { return ( <ItemGroup> <Item>Code</Item> <Item>is</Item> <Item>Poetry</Item> </ItemGroup> ); } ```
Prop types (react-component-meta) 6 prop types
Component: ../packages/components/src/item-group/item-group/component.tsx::ItemGroup
Props:
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The children elements.
 */
children: ReactNode

/**
 * Renders a border around the itemgroup.
 */
isBordered?: boolean | undefined = false

/**
 * Renders with rounded corners.
 */
isRounded?: boolean | undefined = true

/**
 * Renders a separator between each item.
 */
isSeparated?: boolean | undefined = false

/**
 * Determines the amount of padding within the component.
 */
size?: "small" | "medium" | "large" = 'medium'
Imports
import { Item, ItemGroup } from "@wordpress/components";
Default story ok
const Default = ( props ) => (
	<ItemGroup { ...props } />
);
Non Clickable Items story ok
const NonClickableItems = ( props ) => (
	<ItemGroup { ...props } />
);
Custom Item Size story ok
const CustomItemSize = ( props ) => (
	<ItemGroup { ...props } />
);
Without Border story ok
const WithoutBorder = ( props ) => (
	<ItemGroup { ...props } />
);
Item 3 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/item-group/item/component.tsx
`Item` is used in combination with `ItemGroup` to display a list of items grouped and styled together. ```jsx import { __experimentalItemGroup as ItemGroup, __experimentalItem as Item, } from '@wordpress/components'; function Example() { return ( <ItemGroup> <Item>Code</Item> <Item>is</Item> <Item>Poetry</Item> </ItemGroup> ); } ```
import { Item } from "@wordpress/components";
Component: ../packages/components/src/item-group/item/component.tsx::Item (react-component-meta)
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The children elements.
 */
children: ReactNode

/**
 * Determines the amount of padding within the component.
 */
size?: "small" | "medium" | "large" = 'medium'

KeyboardShortcuts

components-keyboardshortcuts · ../packages/components/src/keyboard-shortcuts/stories/index.story.tsx
`KeyboardShortcuts` is a component which handles keyboard sequences during the lifetime of the rendering element. When passed children, it will capture key events which occur on or within the children. If no children are passed, events are captured on the document. It uses the [Mousetrap](https://craig.is/killing/mice) library to implement keyboard sequence bindings. ```jsx import { KeyboardShortcuts } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyKeyboardShortcuts = () => { const [ isAllSelected, setIsAllSelected ] = useState( false ); const selectAll = () => { setIsAllSelected( true ); }; return ( <div> <KeyboardShortcuts shortcuts={ { 'mod+a': selectAll, } } /> [cmd/ctrl + A] Combination pressed? { isAllSelected ? 'Yes' : 'No' } </div> ); }; ```
Prop types (react-component-meta) 4 prop types
Component: ../packages/components/src/keyboard-shortcuts/index.tsx::default
Props:
/**
 * By default, a callback will not be invoked if the key combination occurs in an editable field.
 * Pass `bindGlobal` as `true` if the key events should be observed globally, including within editable fields.
 * 
 * Tip: If you need some but not all keyboard events to be observed globally,
 * simply render two distinct `KeyboardShortcuts` elements, one with and one without the `bindGlobal` prop.
 */
bindGlobal?: boolean | undefined

/**
 * Elements to render, upon whom key events are to be monitored.
 */
children?: ReactNode

/**
 * By default, a callback is invoked in response to the `keydown` event.
 * To override this, pass `eventName` with the name of a specific keyboard event.
 */
eventName?: string

/**
 * An object of shortcut bindings, where each key is a keyboard combination,
 * the value of which is the callback to be invoked when the key combination is pressed.
 * 
 * The value of each shortcut should be a consistent function reference, not an anonymous function.
 * Otherwise, the callback will not be correctly unbound when the component unmounts.
 * 
 * The `KeyboardShortcuts` component will not update to reflect a changed `shortcuts` prop.
 * If you need to change shortcuts, mount a separate `KeyboardShortcuts` element,
 * which can be achieved by assigning a unique `key` prop.
 */
shortcuts: Record<string, (event: ExtendedKeyboardEvent, combo: string) => void>
Imports
import { KeyboardShortcuts } from "@wordpress/components";
Default story ok
const Default = ( props ) => (
	<KeyboardShortcuts { ...props } />
);

Link

design-system-components-link · ../packages/ui/src/link/stories/index.story.tsx
A styled anchor element with support for semantic color tones and an unstyled escape hatch. See the [Usage Guidelines](https://wordpress.github.io/gutenberg/?path=/docs/design-system-components-button-usage-guidelines--docs) for when to use `Button`, `IconButton`, `Link`, or `LinkButton`.
Prop types (react-component-meta) 7 prop types
Component: ../packages/ui/src/link/index.ts::Link
Props:
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Whether to open the link in a new browser tab.
 * When true, sets `target="_blank"` and appends a visual arrow indicator.
 */
openInNewTab?: boolean | undefined = false

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

/**
 * The tone of the link. Tone describes a semantic color intent.
 * Only applies when `variant` is `default`.
 */
tone?: "brand" | "neutral" = 'brand'

/**
 * The visual treatment of the link.
 * 
 * - `default`: Applies tone-based color and underline styles.
 * - `unstyled`: Strips all visual styles so consumers can bring their own.
 */
variant?: "default" | "unstyled" = 'default'
Imports
import { Link, Stack, Text } from "@wordpress/ui";
Default story ok
const Default = () => <Link href="#">Learn more</Link>;
All Tones And Variants story ok
Note: `tone` has no effect on `unstyled` variant
const AllTonesAndVariants = ( args ) => (
    <Stack direction="column" gap="lg">
        { ( [ 'brand', 'neutral' ] as const ).map( ( tone ) =>
            ( [ 'default', 'unstyled' ] as const ).map( ( variant ) => (
                <Stack
                    direction="column"
                    gap="xs"
                    key={ `${ tone }-${ variant }` }
                >
                    <Text variant="heading-sm">
                        { tone } tone, { variant } variant
                    </Text>
                    <Link { ...args } tone={ tone } variant={ variant } />
                </Stack>
            ) )
        ) }
    </Stack>
);
Inline story ok
const Inline = () => <Text variant="body-md" render={ <p /> }>This is a paragraph with an <Link>inline link</Link>that inherits its
                typography from the parent Text component.
            </Text>;
Standalone story ok
When composing `Text` and `Link` via the `render` prop, keep `Text` as the host and pass `Link` via `render` so the resulting element stays an `<a>`.
const Standalone = ( args ) => (
    <Text variant="body-md" render={ <Link { ...args } /> }>
        A standalone link with body-md typography
    </Text>
);

MenuGroup

components-menugroup · ../packages/components/src/menu-group/stories/index.story.tsx
`MenuGroup` wraps a series of related `MenuItem` components into a common section. ```jsx import { MenuGroup, MenuItem } from '@wordpress/components'; const MyMenuGroup = () => ( <MenuGroup label="Settings"> <MenuItem>Setting 1</MenuItem> <MenuItem>Setting 2</MenuItem> </MenuGroup> ); ```
Prop types (react-component-meta) 4 prop types
Component: ../packages/components/src/menu-group/index.tsx::default
Props:
/**
 * The children elements.
 */
children?: ReactNode

/**
 * A CSS `class` to give to the container element.
 */
className?: string = ''

/**
 * Hide the top border on the container.
 */
hideSeparator?: boolean | undefined

/**
 * Text to be displayed as the menu group header.
 */
label?: string
Imports
import { MenuGroup, MenuItem, MenuItemsChoice } from "@wordpress/components";
Default story ok
const Default = () => {
    return (
        <MenuGroup>
            <MenuItem>Menu Item 1</MenuItem>
            <MenuItem>Menu Item 2</MenuItem>
        </MenuGroup>
    );
};
With Separator story ok
When other menu items exist above or below a MenuGroup, the group should have a divider line between it and the adjacent item.
const WithSeparator = () => {
    const [ mode, setMode ] = useState( 'visual' );
    const choices = [
		{
			value: 'visual',
			label: 'Visual editor',
		},
		{
			value: 'text',
			label: 'Code editor',
		},
	];

    return (
        <>
            <MenuGroup label="View">
                <MenuItem>Top Toolbar</MenuItem>
                <MenuItem>Spotlight Mode</MenuItem>
                <MenuItem>Distraction Free</MenuItem>
            </MenuGroup>
            <MenuGroup hideSeparator={false} label="Editor">
                <MenuItemsChoice
                    choices={ choices }
                    value={ mode }
                    onSelect={ ( newMode: string ) => setMode( newMode ) }
                    onHover={ () => {} } />
            </MenuGroup>
        </>
    );
};

MenuItem

components-menuitem · ../packages/components/src/menu-item/stories/index.story.tsx
MenuItem is a component which renders a button intended to be used in combination with the `DropdownMenu` component. ```jsx import { MenuItem } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyMenuItem = () => { const [ isActive, setIsActive ] = useState( true ); return ( <MenuItem icon={ isActive ? 'yes' : 'no' } isSelected={ isActive } role="menuitemcheckbox" onClick={ () => setIsActive( ( state ) => ! state ) } > Toggle </MenuItem> ); }; ```
Prop types (react-component-meta) 11 prop types
Component: ../packages/components/src/menu-item/index.tsx::default
Props:
/**
 * The children elements.
 */
children?: ReactNode

/**
 * A CSS `class` to give to the container element.
 */
className?: string

/**
 * The icon to render. Supported values are: Dashicons (specified as
 * strings), functions, Component instances and `null`.
 */
icon?: Element | null | undefined = null

/**
 * Determines where to display the provided `icon`.
 */
iconPosition?: "left" | "right" = 'right'

/**
 * Text to use as description for button text.
 */
info?: string

/**
 * Renders a red text-based button style to indicate destructive behavior.
 */
isDestructive?: boolean | undefined

/**
 * Whether or not the menu item is currently selected, `isSelected` is only taken into
 * account when the `role` prop is either `"menuitemcheckbox"` or `"menuitemradio"`.
 */
isSelected?: boolean | undefined

/**
 * Human-readable label for item.
 */
label?: string

/**
 * If you need to have selectable menu items use menuitemradio for single select,
 * and menuitemcheckbox for multiselect.
 */
role?: string = 'menuitem'

/**
 * If shortcut is a string, it is expecting the display text. If shortcut is an object,
 * it will accept the properties of `display` (string) and `ariaLabel` (string).
 */
shortcut?: string | { display: string; ariaLabel: string; } | undefined

/**
 * Allows for markup other than icons or shortcuts to be added to the menu item.
 */
suffix?: ReactNode
Imports
import { MenuGroup, MenuItem, Shortcut } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	return (
		<MenuGroup>
			<MenuItem { ...props }>Menu Item 1</MenuItem>
		</MenuGroup>
	);
};
Is Selected story ok
When the `role` prop is either `"menuitemcheckbox"` or `"menuitemradio"`, the `isSelected` prop should be used so screen readers can tell which item is currently selected.
const IsSelected = ( props ) => {
	return (
		<MenuGroup>
			<MenuItem { ...props }>Menu Item 1</MenuItem>
		</MenuGroup>
	);
};
With Icon story ok
const WithIcon = ( props ) => {
	return (
		<MenuGroup>
			<MenuItem { ...props }>Menu Item 1</MenuItem>
		</MenuGroup>
	);
};
With Info story ok
const WithInfo = ( props ) => {
	return (
		<MenuGroup>
			<MenuItem { ...props }>Menu Item 1</MenuItem>
		</MenuGroup>
	);
};
With Suffix story ok
const WithSuffix = ( props ) => {
	return (
		<MenuGroup>
			<MenuItem { ...props }>Menu Item 1</MenuItem>
		</MenuGroup>
	);
};

MenuItemsChoice

components-menuitemschoice · ../packages/components/src/menu-items-choice/stories/index.story.tsx
`MenuItemsChoice` functions similarly to a set of `MenuItem`s, but allows the user to select one option from a set of multiple choices. ```jsx import { MenuGroup, MenuItemsChoice } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyMenuItemsChoice = () => { const [ mode, setMode ] = useState( 'visual' ); const choices = [ { value: 'visual', label: 'Visual editor', }, { value: 'text', label: 'Code editor', }, ]; return ( <MenuGroup label="Editor"> <MenuItemsChoice choices={ choices } value={ mode } onSelect={ ( newMode ) => setMode( newMode ) } /> </MenuGroup> ); }; ```
Prop types (react-component-meta) 4 prop types
Component: ../packages/components/src/menu-items-choice/index.tsx::default
Props:
/**
 * Array of choices.
 */
choices: readonly MenuItemChoice[] = []

/**
 * Callback function to be called with a choice when user
 * hovers over a new choice (will be empty on mouse leave).
 */
onHover: (value: string | null) => void = () => {}

/**
 * Callback function to be called with the selected choice when user
 * selects a new choice.
 */
onSelect: (value: string) => void

/**
 * Value of currently selected choice (should match a `value` property
 * from a choice in `choices`).
 */
value: string
Imports
import { MenuGroup, MenuItemsChoice } from "@wordpress/components";
Default story ok
const Default = ( {
	onHover,
	onSelect,
	choices,
} ) => {
	const [ choice, setChoice ] = useState( choices[ 0 ]?.value ?? '' );

	return (
		<MenuGroup label="Editor">
			<MenuItemsChoice
				choices={ choices }
				value={ choice }
				onSelect={ ( ...selectArgs ) => {
					onSelect( ...selectArgs );
					setChoice( ...selectArgs );
				} }
				onHover={ onHover }
			/>
		</MenuGroup>
	);
};

Modal

components-modal · ../packages/components/src/modal/stories/index.story.tsx
Modals give users information and choices related to a task they’re trying to accomplish. They can contain critical information, require decisions, or involve multiple tasks. ```jsx import { Button, Modal } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyModal = () => { const [ isOpen, setOpen ] = useState( false ); const openModal = () => setOpen( true ); const closeModal = () => setOpen( false ); return ( <> <Button variant="secondary" onClick={ openModal }> Open Modal </Button> { isOpen && ( <Modal title="This is my modal" onRequestClose={ closeModal }> <Button variant="secondary" onClick={ closeModal }> My custom close button </Button> </Modal> ) } </> ); }; ```
Prop types (react-component-meta) 23 prop types
Component: ../packages/components/src/modal/index.tsx::default
Props:
/**
 * When set to `true`, the Modal's header (including the icon, title and
 * close button) will not be rendered.
 * 
 * _Warning_: This property is still experimental. “Experimental” means this
 * is an early implementation subject to drastic and breaking changes.
 */
__experimentalHideHeader?: boolean | undefined = false

aria?: { describedby?: string | undefined; labelledby?: string | undefined; } = {
			labelledby: undefined,
			describedby: undefined,
		}

/**
 * Class name added to the body element when the modal is open.
 */
bodyOpenClassName?: string = 'modal-open'

/**
 * The children elements.
 */
children: ReactNode

/**
 * If this property is added, it will an additional class name to the modal
 * content `div`.
 */
className?: string

/**
 * Label on the close button.
 */
closeButtonLabel?: string = `__( 'Close' )`

/**
 * If this property is added, it will be added to the modal content `div` as
 * `aria-label`.
 * 
 * Titles are required for accessibility reasons, see `aria.labelledby` and
 * `title` for other ways to provide a title.
 */
contentLabel?: string

/**
 * Determines focus behavior when the modal opens.
 * 
 * - `"firstElement"` focuses the first tabbable element within.
 * - `"firstInputElement"` focuses the first value control within.
 * - `"firstContentElement"` focuses the first tabbable element within the modal’s content element.
 * - `true` focuses the element itself.
 * - `false` does nothing and _should not be used unless an accessible
 *    substitute behavior is implemented_.
 */
focusOnMount?: any = true

/**
 * Elements that are injected into the modal header to the left of the close button (if rendered).
 * Hidden if `__experimentalHideHeader` is `true`.
 */
headerActions?: ReactNode = null

/**
 * If this property is added, an icon will be added before the title.
 */
icon?: Element

/**
 * If this property is set to false, the modal will not display a close icon
 * and cannot be dismissed.
 */
isDismissible?: boolean | undefined = true

/**
 * This property when set to `true` will render a full screen modal.
 */
isFullScreen?: boolean | undefined = false

key?: Key | null | undefined

/**
 * Handle the key down on the modal frame `div`.
 */
onKeyDown?: KeyboardEventHandler<HTMLDivElement>

/**
 * This function is called to indicate that the modal should be closed.
 */
onRequestClose: (event?: KeyboardEvent<HTMLDivElement> | SyntheticEvent<Element, Event> | undefined) => void

/**
 * If this property is added, it will an additional class name to the modal
 * overlay `div`.
 */
overlayClassName?: string

/**
 * Allows getting a ref to the component instance.
 * Once the component unmounts, React will set `ref.current` to `null`
 * (or call the ref with `null` if you passed a callback ref).
 */
ref?: LegacyRef<HTMLDivElement> | undefined

/**
 * If this property is added, it will override the default role of the
 * modal.
 */
role?: AriaRole | undefined = 'dialog'

/**
 * If this property is added, it will determine whether the modal requests
 * to close when a mouse click occurs outside of the modal content.
 */
shouldCloseOnClickOutside?: boolean | undefined = true

/**
 * If this property is added, it will determine whether the modal requests
 * to close when the escape key is pressed.
 */
shouldCloseOnEsc?: boolean | undefined = true

/**
 * If this property is added it will cause the modal to render at a preset
 * width, or expand to fill the screen. This prop will be ignored if
 * `isFullScreen` is set to `true`.
 * 
 * Note: `Modal`'s width can also be controlled by adjusting the width of the
 * modal's contents, or via CSS using the `style` prop.
 */
size?: "small" | "fill" | "medium" | "large"

/**
 * If this property is added, it will be added to the modal frame `div`.
 */
style?: CSSProperties

/**
 * This property is used as the modal header's title.
 * 
 * Titles are required for accessibility reasons, see `aria.labelledby` and
 * `contentLabel` for other ways to provide a title.
 */
title?: string = null
Imports
import { Button, InputControl, Modal } from "@wordpress/components";
Default story ok
const Default = ( { onRequestClose, ...args } ) => {
	const [ isOpen, setOpen ] = useState( false );
	const openModal = () => setOpen( true );
	const closeModal: ModalProps[ 'onRequestClose' ] = ( event ) => {
		setOpen( false );
		onRequestClose( event );
	};

	return (
		<>
			<Button
				__next40pxDefaultSize
				variant="secondary"
				onClick={ openModal }
			>
				Open Modal
			</Button>
			{ isOpen && (
				<Modal onRequestClose={ closeModal } { ...args }>
					<p>
						Lorem ipsum dolor sit amet, consectetur adipiscing elit,
						sed do eiusmod tempor incididunt ut labore et magna
						aliqua. Ut enim ad minim veniam, quis nostrud
						exercitation ullamco laboris nisi ut aliquip ex ea ea
						commodo consequat. Duis aute irure dolor in
						reprehenderit in voluptate velit esse cillum dolore eu
						fugiat nulla pariatur. Excepteur sint occaecat cupidatat
						non proident, sunt in culpa qui officia deserunt mollit
						anim id est laborum.
					</p>

					<InputControl
						__next40pxDefaultSize
						style={ { marginBottom: '20px' } }
					/>

					<Button
						__next40pxDefaultSize
						variant="secondary"
						onClick={ closeModal }
					>
						Close Modal
					</Button>
				</Modal>
			) }
		</>
	);
};
With size: small story ok
const WithsizeSmall = ( { onRequestClose, ...args } ) => {
	const [ isOpen, setOpen ] = useState( false );
	const openModal = () => setOpen( true );
	const closeModal: ModalProps[ 'onRequestClose' ] = ( event ) => {
		setOpen( false );
		onRequestClose( event );
	};

	return (
		<>
			<Button
				__next40pxDefaultSize
				variant="secondary"
				onClick={ openModal }
			>
				Open Modal
			</Button>
			{ isOpen && (
				<Modal onRequestClose={ closeModal } { ...args }>
					<p>
						Lorem ipsum dolor sit amet, consectetur adipiscing elit,
						sed do eiusmod tempor incididunt ut labore et magna
						aliqua. Ut enim ad minim veniam, quis nostrud
						exercitation ullamco laboris nisi ut aliquip ex ea ea
						commodo consequat. Duis aute irure dolor in
						reprehenderit in voluptate velit esse cillum dolore eu
						fugiat nulla pariatur. Excepteur sint occaecat cupidatat
						non proident, sunt in culpa qui officia deserunt mollit
						anim id est laborum.
					</p>

					<InputControl
						__next40pxDefaultSize
						style={ { marginBottom: '20px' } }
					/>

					<Button
						__next40pxDefaultSize
						variant="secondary"
						onClick={ closeModal }
					>
						Close Modal
					</Button>
				</Modal>
			) }
		</>
	);
};
With Header Actions story ok
The `headerActions` prop can be used to add auxiliary actions to the header, for example a fullscreen mode toggle.
const WithHeaderActions = ( { onRequestClose, ...args } ) => {
	const [ isOpen, setOpen ] = useState( false );
	const openModal = () => setOpen( true );
	const closeModal: ModalProps[ 'onRequestClose' ] = ( event ) => {
		setOpen( false );
		onRequestClose( event );
	};

	return (
		<>
			<Button
				__next40pxDefaultSize
				variant="secondary"
				onClick={ openModal }
			>
				Open Modal
			</Button>
			{ isOpen && (
				<Modal onRequestClose={ closeModal } { ...args }>
					<p>
						Lorem ipsum dolor sit amet, consectetur adipiscing elit,
						sed do eiusmod tempor incididunt ut labore et magna
						aliqua. Ut enim ad minim veniam, quis nostrud
						exercitation ullamco laboris nisi ut aliquip ex ea ea
						commodo consequat. Duis aute irure dolor in
						reprehenderit in voluptate velit esse cillum dolore eu
						fugiat nulla pariatur. Excepteur sint occaecat cupidatat
						non proident, sunt in culpa qui officia deserunt mollit
						anim id est laborum.
					</p>

					<InputControl
						__next40pxDefaultSize
						style={ { marginBottom: '20px' } }
					/>

					<Button
						__next40pxDefaultSize
						variant="secondary"
						onClick={ closeModal }
					>
						Close Modal
					</Button>
				</Modal>
			) }
		</>
	);
};

Navigator

components-navigator · ../packages/components/src/navigator/stories/index.story.tsx
The `Navigator` component allows rendering nested views/panels/menus (via the `Navigator.Screen` component) and navigate between them (via the `Navigator.Button` and `Navigator.BackButton` components). ```jsx import { Navigator } from '@wordpress/components'; const MyNavigation = () => ( <Navigator initialPath="/"> <Navigator.Screen path="/"> <p>This is the home screen.</p> <Navigator.Button path="/child"> Navigate to child screen. </Navigator.Button> </Navigator.Screen> <Navigator.Screen path="/child"> <p>This is the child screen.</p> <Navigator.BackButton> Go back </Navigator.BackButton> </Navigator.Screen> </Navigator> ); ```
Prop types (react-component-meta) 3 prop types
Component: ../packages/components/src/navigator/index.tsx::Navigator
Props:
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The children elements.
 */
children: ReactNode

/**
 * The initial active path.
 */
initialPath: string
Imports
import { Button, HStack, Navigator, VStack } from "@wordpress/components";
Default story ok
const Default = () => <Navigator initialPath="/"><>
        <Navigator.Screen path="/">
            <h2>This is the home screen.</h2>
            <VStack alignment="left">
                <Navigator.Button variant="primary" path="/child">Go to child screen.
                                            </Navigator.Button>
                <Navigator.Button variant="primary" path="/product/1">Go to dynamic path screen with id 1.
                                            </Navigator.Button>
                <Navigator.Button variant="primary" path="/product/2">Go to dynamic path screen with id 2.
                                            </Navigator.Button>
            </VStack>
        </Navigator.Screen>
        <Navigator.Screen path="/child">
            <h2>This is the child screen.</h2>
            <HStack spacing={ 2 } alignment="left">
                <Navigator.BackButton variant="secondary">Go back
                                            </Navigator.BackButton>
                <Navigator.Button variant="primary" path="/child/grandchild">Go to grand child screen.
                                            </Navigator.Button>
            </HStack>
        </Navigator.Screen>
        <Navigator.Screen path="/child/grandchild">
            <h2>This is the grand child screen.</h2>
            <Navigator.BackButton variant="secondary">Go back
                                    </Navigator.BackButton>
        </Navigator.Screen>
        <Navigator.Screen path="/product/:id">
            <DynamicScreen />
        </Navigator.Screen>
    </></Navigator>;
With Nested Initial Path story ok
const WithNestedInitialPath = () => <Navigator initialPath="/child/grandchild" />;
Skip Focus story ok
const SkipFocus = () => <Navigator initialPath="/"><>
        <div
            style={ {
                height: 150,
                outline: '1px solid black',
                outlineOffset: '-1px',
                marginBlockEnd: '1rem',
                display: 'contents',
            } }>
            <Navigator.Screen path="/">
                <h2>Home screen</h2>
                <Navigator.Button variant="primary" path="/child">Go to child screen.
                                            </Navigator.Button>
            </Navigator.Screen>
            <Navigator.Screen path="/child">
                <h2>Child screen</h2>
                <Navigator.BackButton variant="secondary">Go back to home screen
                                            </Navigator.BackButton>
            </Navigator.Screen>
        </div>
        <NavigatorButtonWithSkipFocus path="/child">Go to child screen, but keep focus on this button
                            </NavigatorButtonWithSkipFocus>
    </></Navigator>;
Screen 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/navigator/index.tsx
The `Navigator.Screen` component represents a single view/screen/panel and should be used in combination with the `Navigator`, the `Navigator.Button` and the `Navigator.BackButton` components.
example: ```jsx import { Navigator } from '@wordpress/components'; const MyNavigation = () => ( <Navigator initialPath="/"> <Navigator.Screen path="/"> <p>This is the home screen.</p> <Navigator.Button path="/child"> Navigate to child screen. </Navigator.Button> </Navigator.Screen> <Navigator.Screen path="/child"> <p>This is the child screen.</p> <Navigator.BackButton> Go back </Navigator.BackButton> </Navigator.Screen> </Navigator> ); ```
import { Navigator } from "@wordpress/components";
Component: ../packages/components/src/navigator/index.tsx::Navigator (react-component-meta)
/**
 * The children elements.
 */
children: ReactNode

/**
 * The screen's path, matched against the current path stored in the navigator.
 * 
 * `Navigator` assumes that screens are organized hierarchically according
 * to their `path`, which should follow a URL-like scheme where each path
 * segment starts with and is separated by the `/` character.
 * 
 * `Navigator` will treat "back" navigations as going to the parent screen —
 * it is, therefore, the responsibility of the consumer of the component to
 * create the correct screen hierarchy.
 * 
 * For example:
 *  - `/` is the root of all paths. There should always be a screen with
 *    `path="/"`;
 *  - `/parent/child` is a child of `/parent`;
 *  - `/parent/child/grand-child` is a child of `/parent/child`;
 *  - `/parent/:param` is a child of `/parent` as well;
 *  - if the current screen has a `path="/parent/child/grand-child"`, when
 *    going "back" `Navigator` will try to recursively navigate the path
 *    hierarchy until a matching screen (or the root `/`) is found.
 */
path: string
Button 21 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/navigator/index.tsx
The `Navigator.Button` component can be used to navigate to a screen and should be used in combination with the `Navigator`, the `Navigator.Screen` and the `Navigator.BackButton` components.
example: ```jsx import { Navigator } from '@wordpress/components'; const MyNavigation = () => ( <Navigator initialPath="/"> <Navigator.Screen path="/"> <p>This is the home screen.</p> <Navigator.Button path="/child"> Navigate to child screen. </Navigator.Button> </Navigator.Screen> <Navigator.Screen path="/child"> <p>This is the child screen.</p> <Navigator.BackButton> Go back </Navigator.BackButton> </Navigator.Screen> </Navigator> ); ```
import { Navigator } from "@wordpress/components";
Component: ../packages/components/src/navigator/index.tsx::Navigator (react-component-meta)
/**
 * Start opting into the larger default height that will become the
 * default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined = false

/**
 * Whether to keep the button focusable when disabled.
 * 
 * In most cases, it is recommended to set this to `true`. Disabling a control without maintaining focusability
 * can cause accessibility issues, by hiding their presence from screen reader users,
 * or by preventing focus from returning to a trigger element.
 * 
 * Learn more about the [focusability of disabled controls](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#focusabilityofdisabledcontrols)
 * in the WAI-ARIA Authoring Practices Guide.
 */
accessibleWhenDisabled?: boolean | undefined = false

/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The HTML attribute used to identify the `NavigatorButton`, which is used
 * by `Navigator` to restore focus.
 */
attributeName?: string = 'id'

/**
 * The button's children.
 */
children?: ReactNode

/**
 * A visually hidden accessible description for the button.
 */
description?: string

/**
 * Whether the button is disabled. If `true`, this will force a `button` element
 * to be rendered, even when an `href` is given.
 * 
 * In most cases, it is recommended to also set the `accessibleWhenDisabled` prop to `true`.
 */
disabled?: boolean | undefined

/**
 * If provided, renders an Icon component inside the button.
 */
icon?: IconType | null | undefined

/**
 * If provided with `icon`, sets the position of icon relative to the `text`.
 */
iconPosition?: "left" | "right" = 'left'

/**
 * If provided with `icon`, sets the icon size.
 * Please refer to the Icon component for more details regarding
 * the default value of its `size` prop.
 */
iconSize?: number

/**
 * Indicates activity while a action is being performed.
 */
isBusy?: boolean | undefined

/**
 * Renders a red text-based button style to indicate destructive behavior.
 */
isDestructive?: boolean | undefined

/**
 * Renders a pressed button style.
 */
isPressed?: boolean | undefined

/**
 * Sets the `aria-label` of the component, if none is provided.
 * Sets the Tooltip content if `showTooltip` is provided.
 */
label?: string

/**
 * The path of the screen to navigate to. The value of this prop needs to be
 * a valid value for an HTML attribute.
 */
path: string

/**
 * If provided with `showTooltip`, appends the Shortcut label to the tooltip content.
 * If an object is provided, it should contain `display` and `ariaLabel` keys.
 */
shortcut?: string | { display: string; ariaLabel: string; } | undefined

/**
 * If provided, renders a Tooltip component for the button.
 */
showTooltip?: boolean | undefined

/**
 * The size of the button.
 * 
 * - `'default'`: For normal text-label buttons, unless it is a toggle button.
 * - `'compact'`: For toggle buttons, icon buttons, and buttons when used in context of either.
 * - `'small'`: For icon buttons associated with more advanced or auxiliary features.
 * 
 * If the deprecated `isSmall` prop is also defined, this prop will take precedence.
 */
size?: "small" | "default" | "compact" = 'default'

/**
 * If provided, displays the given text inside the button. If the button contains children elements, the text is displayed before them.
 */
text?: string

/**
 * If provided with `showTooltip`, sets the position of the tooltip.
 * Please refer to the Tooltip component for more details regarding the defaults.
 */
tooltipPosition?: "top" | "middle" | "bottom" | "top center" | "top left" | "top right" | "middle center" | "middle left" | "middle right" | "bottom center" | "bottom left" | "bottom right" | "top center left" | "top center right" | "top center top" | "top center bottom" | "top left left" | "top left right" | "top left top" | "top left bottom" | "top right left" | "top right right" | "top right top" | "top right bottom" | "middle center left" | "middle center right" | "middle center top" | "middle center bottom" | "middle left left" | "middle left right" | "middle left top" | "middle left bottom" | "middle right left" | "middle right right" | "middle right top" | "middle right bottom" | "bottom center left" | "bottom center right" | "bottom center top" | "bottom center bottom" | "bottom left left" | "bottom left right" | "bottom left top" | "bottom left bottom" | "bottom right left" | "bottom right right" | "bottom right top" | "bottom right bottom"

/**
 * Specifies the button's style.
 * 
 * The accepted values are:
 * 
 * 1. `'primary'` (the primary button styles)
 * 2. `'secondary'` (the default button styles)
 * 3. `'tertiary'` (the text-based button styles)
 * 4. `'link'` (the link button styles)
 */
variant?: "link" | "primary" | "secondary" | "tertiary"
BackButton 19 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/navigator/index.tsx
The `Navigator.BackButton` component can be used to navigate to a screen and should be used in combination with the `Navigator`, the `Navigator.Screen` and the `Navigator.Button` components.
example: ```jsx import { Navigator } from '@wordpress/components'; const MyNavigation = () => ( <Navigator initialPath="/"> <Navigator.Screen path="/"> <p>This is the home screen.</p> <Navigator.Button path="/child"> Navigate to child screen. </Navigator.Button> </Navigator.Screen> <Navigator.Screen path="/child"> <p>This is the child screen.</p> <Navigator.BackButton> Go back </Navigator.BackButton> </Navigator.Screen> </Navigator> ); ```
import { Navigator } from "@wordpress/components";
Component: ../packages/components/src/navigator/index.tsx::Navigator (react-component-meta)
/**
 * Start opting into the larger default height that will become the
 * default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined = false

/**
 * Whether to keep the button focusable when disabled.
 * 
 * In most cases, it is recommended to set this to `true`. Disabling a control without maintaining focusability
 * can cause accessibility issues, by hiding their presence from screen reader users,
 * or by preventing focus from returning to a trigger element.
 * 
 * Learn more about the [focusability of disabled controls](https://www.w3.org/WAI/ARIA/apg/practices/keyboard-interface/#focusabilityofdisabledcontrols)
 * in the WAI-ARIA Authoring Practices Guide.
 */
accessibleWhenDisabled?: boolean | undefined = false

/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The button's children.
 */
children?: ReactNode

/**
 * A visually hidden accessible description for the button.
 */
description?: string

/**
 * Whether the button is disabled. If `true`, this will force a `button` element
 * to be rendered, even when an `href` is given.
 * 
 * In most cases, it is recommended to also set the `accessibleWhenDisabled` prop to `true`.
 */
disabled?: boolean | undefined

/**
 * If provided, renders an Icon component inside the button.
 */
icon?: IconType | null | undefined

/**
 * If provided with `icon`, sets the position of icon relative to the `text`.
 */
iconPosition?: "left" | "right" = 'left'

/**
 * If provided with `icon`, sets the icon size.
 * Please refer to the Icon component for more details regarding
 * the default value of its `size` prop.
 */
iconSize?: number

/**
 * Indicates activity while a action is being performed.
 */
isBusy?: boolean | undefined

/**
 * Renders a red text-based button style to indicate destructive behavior.
 */
isDestructive?: boolean | undefined

/**
 * Renders a pressed button style.
 */
isPressed?: boolean | undefined

/**
 * Sets the `aria-label` of the component, if none is provided.
 * Sets the Tooltip content if `showTooltip` is provided.
 */
label?: string

/**
 * If provided with `showTooltip`, appends the Shortcut label to the tooltip content.
 * If an object is provided, it should contain `display` and `ariaLabel` keys.
 */
shortcut?: string | { display: string; ariaLabel: string; } | undefined

/**
 * If provided, renders a Tooltip component for the button.
 */
showTooltip?: boolean | undefined

/**
 * The size of the button.
 * 
 * - `'default'`: For normal text-label buttons, unless it is a toggle button.
 * - `'compact'`: For toggle buttons, icon buttons, and buttons when used in context of either.
 * - `'small'`: For icon buttons associated with more advanced or auxiliary features.
 * 
 * If the deprecated `isSmall` prop is also defined, this prop will take precedence.
 */
size?: "small" | "default" | "compact" = 'default'

/**
 * If provided, displays the given text inside the button. If the button contains children elements, the text is displayed before them.
 */
text?: string

/**
 * If provided with `showTooltip`, sets the position of the tooltip.
 * Please refer to the Tooltip component for more details regarding the defaults.
 */
tooltipPosition?: "top" | "middle" | "bottom" | "top center" | "top left" | "top right" | "middle center" | "middle left" | "middle right" | "bottom center" | "bottom left" | "bottom right" | "top center left" | "top center right" | "top center top" | "top center bottom" | "top left left" | "top left right" | "top left top" | "top left bottom" | "top right left" | "top right right" | "top right top" | "top right bottom" | "middle center left" | "middle center right" | "middle center top" | "middle center bottom" | "middle left left" | "middle left right" | "middle left top" | "middle left bottom" | "middle right left" | "middle right right" | "middle right top" | "middle right bottom" | "bottom center left" | "bottom center right" | "bottom center top" | "bottom center bottom" | "bottom left left" | "bottom left right" | "bottom left top" | "bottom left bottom" | "bottom right left" | "bottom right right" | "bottom right top" | "bottom right bottom"

/**
 * Specifies the button's style.
 * 
 * The accepted values are:
 * 
 * 1. `'primary'` (the primary button styles)
 * 2. `'secondary'` (the default button styles)
 * 3. `'tertiary'` (the text-based button styles)
 * 4. `'link'` (the link button styles)
 */
variant?: "link" | "primary" | "secondary" | "tertiary"

Notice

components-notice · ../packages/components/src/notice/stories/index.story.tsx
`Notice` is a component used to communicate feedback to the user. ```jsx import { Notice } from `@wordpress/components`; const MyNotice = () => ( <Notice status="error">An unknown error occurred.</Notice> ); ```
Prop types (react-component-meta) 10 prop types
Component: ../packages/components/src/notice/index.tsx::default
Props:
/**
 * Determines whether or not the message should be parsed as custom HTML
 * instead of a string.
 */
__unstableHTML?: boolean | undefined

/**
 * An array of action objects. Each member object should contain:
 * 
 * - `label`: `string` containing the text of the button/link
 * - `url`: `string` OR `onClick`: `( event: SyntheticEvent ) => void` to specify
 *    what the action does.
 * - `className`: `string` (optional) to add custom classes to the button styles.
 * - `noDefaultClasses`: `boolean` (optional) A value of `true` will remove all
 *    default styling.
 * - `variant`: `'primary' | 'secondary' | 'link'` (optional) You can denote a
 *    primary button action for a notice by passing a value of `primary`.
 * 
 * The default appearance of an action button is inferred based on whether
 * `url` or `onClick` are provided, rendering the button as a link if
 * appropriate. If both props are provided, `url` takes precedence, and the
 * action button will render as an anchor tag.
 */
actions?: NoticeAction[] = []

/**
 * The displayed message of a notice. Also used as the spoken message for
 * assistive technology, unless `spokenMessage` is provided as an alternative message.
 */
children: ReactNode

/**
 * A CSS `class` to give to the wrapper element.
 */
className?: string

/**
 * Whether the notice should be dismissible or not
 */
isDismissible?: boolean | undefined = true

/**
 * A deprecated alternative to `onRemove`. This prop is kept for
 * compatibility reasons but should be avoided.
 */
onDismiss?: () => void = () => {}

/**
 * Function called when dismissing the notice
 */
onRemove?: () => void = () => {}

/**
 * A politeness level for the notice's spoken message. Should be provided as
 * one of the valid options for an `aria-live` attribute value.
 * 
 * A value of `'assertive'` is to be used for important, and usually
 * time-sensitive, information. It will interrupt anything else the screen
 * reader is announcing in that moment.
 * A value of `'polite'` is to be used for advisory information. It should
 * not interrupt what the screen reader is announcing in that moment
 * (the "speech queue") or interrupt the current task.
 * 
 * Note that this value should be considered a suggestion; assistive
 * technologies may override it based on internal heuristics.
 */
politeness?: "assertive" | "polite" = getDefaultPoliteness( status )

/**
 * Used to provide a custom spoken message in place of the `children` default.
 */
spokenMessage?: ReactNode = children

/**
 * Determines the color of the notice: `warning` (yellow),
 * `success` (green), `error` (red), or `'info'`.
 * By default `'info'` will be blue.
 */
status?: "info" | "warning" | "success" | "error" = 'info'
Imports
import { Button, Notice, NoticeList } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	return <Notice { ...props } />;
};
With Custom Spoken Message story ok
const WithCustomSpokenMessage = ( props ) => {
	return <Notice { ...props } />;
};
With JSX Children story ok
const WithJSXChildren = ( props ) => {
	return <Notice { ...props } />;
};
With Actions story ok
const WithActions = ( props ) => {
	return <Notice { ...props } />;
};
NoticeList Subcomponent story ok
const NoticeListSubcomponent = () => {
	const exampleNotices: NoticeListProps[ 'notices' ] = [
		{
			id: 'second-notice',
			content: 'second notice content',
		},
		{
			id: 'first-notice',
			content: 'first notice content',
			actions: [
				{
					label: 'Click me!',
					onClick: () => {},
					variant: 'primary',
				},
				{
					label: 'Or click me instead!',
					onClick: () => {},
				},
				{
					label: 'Or visit a link for more info',
					url: 'https://wordpress.org',
					variant: 'link',
				},
			],
		},
	];
	const [ notices, setNotices ] = useState( exampleNotices );

	const removeNotice = (
		id: NoticeListProps[ 'notices' ][ number ][ 'id' ]
	) => {
		setNotices( notices.filter( ( notice ) => notice.id !== id ) );
	};

	const resetNotices = () => {
		setNotices( exampleNotices );
	};

	return (
		<>
			<NoticeList notices={ notices } onRemove={ removeNotice } />
			<Button
				__next40pxDefaultSize
				variant="primary"
				onClick={ resetNotices }
			>
				Reset Notices
			</Button>
		</>
	);
};
With Disabled Action story ok
Action buttons can be disabled.
const WithDisabledAction = ( props ) => {
	return <Notice { ...props } />;
};
NoticeList 3 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/notice/list.tsx
`NoticeList` is a component used to render a collection of notices. ```jsx import { Notice, NoticeList } from `@wordpress/components`; const MyNoticeList = () => { const [ notices, setNotices ] = useState( [ { id: 'second-notice', content: 'second notice content', }, { id: 'fist-notice', content: 'first notice content', }, ] ); const removeNotice = ( id ) => { setNotices( notices.filter( ( notice ) => notice.id !== id ) ); }; return <NoticeList notices={ notices } onRemove={ removeNotice } />; }; ```
import { NoticeList } from "@wordpress/components";
Component: ../packages/components/src/notice/list.tsx::default (react-component-meta)
/**
 * Children to be rendered inside the notice list.
 */
children?: ReactNode

/**
 * Array of notices to render.
 */
notices: (Omit<NoticeProps, "children"> & { id: string; content: string; })[]

/**
 * Function called when a notice should be removed / dismissed.
 */
onRemove?: (id: string) => void = () => {}

NumberControl

components-numbercontrol · ../packages/components/src/number-control/stories/index.story.tsx
`NumberControl` is a text input control that lets users enter and adjust a numeric value.
Prop types (react-component-meta) 33 prop types
Component: ../packages/components/src/number-control/index.tsx::default
Props:
/**
 * Deprecated. Use `__next40pxDefaultSize` instead.
 */
__next36pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined = false

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

__unstableInputWidth?: Width<string | number> | undefined

__unstableStateReducer?: StateReducer

/**
 * If true, the `input` will be disabled.
 */
disabled?: boolean | undefined = false

/**
 * Determines the drag axis.
 */
dragDirection?: "s" | "n" | "e" | "w" = 'n'

/**
 * If `isDragEnabled` is true, this controls the amount of `px` to have been dragged before
 * the drag gesture is actually triggered.
 */
dragThreshold?: number = 10

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the default `input` HTML arrows will be hidden.
 */
hideHTMLArrows?: boolean | undefined = false

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If true, enables mouse drag gestures.
 */
isDragEnabled?: boolean | undefined = true

/**
 * If true, the `ENTER` key press is required in order to trigger an `onChange`.
 * If enabled, a change is also triggered when tabbing away (`onBlur`).
 */
isPressEnterToChange?: boolean | undefined = false

/**
 * If true, pressing `UP` or `DOWN` along with the `SHIFT` key will increment the
 * value by the `shiftStep` value.
 */
isShiftStepEnabled?: boolean | undefined = true

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * The position of the label.
 */
labelPosition?: "top" | "bottom" | "side" | "edge" = 'top'

/**
 * The maximum `value` allowed.
 */
max?: number = Infinity

/**
 * The minimum `value` allowed.
 */
min?: number = -Infinity

/**
 * A function that receives the value of the input.
 */
onChange?: InputChangeCallback<{}> = () => {}

onDrag?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragEnd?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragStart?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onValidate?: (nextValue: string, event?: SyntheticEvent<HTMLInputElement, Event> | undefined) => void

/**
 * Renders an element on the left side of the input.
 * 
 * By default, the prefix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlPrefixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlPrefixWrapper as InputControlPrefixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   prefix={<InputControlPrefixWrapper>@</InputControlPrefixWrapper>}
 * />
 * ```
 */
prefix?: ReactNode

/**
 * If `true` enforces a valid number within the control's min/max range.
 * If `false` allows an empty string as a valid value.
 */
required?: boolean | undefined = false

/**
 * Amount to increment by when the `SHIFT` key is held down. This shift value is
 * a multiplier to the `step` value. For example, if the `step` value is `5`,
 * and `shiftStep` is `10`, each jump would increment/decrement by `50`.
 */
shiftStep?: number = 10

/**
 * Adjusts the size of the input.
 */
size?: "small" | "default" | "compact" | "__unstable-large" = 'default'

/**
 * The type of spin controls to display. These are buttons that allow the
 * user to quickly increment and decrement the number.
 * 
 * - 'none' - Do not show spin controls.
 * - 'native' - Use browser's native HTML `input` controls.
 * - 'custom' - Use plus and minus icon buttons.
 */
spinControls?: "none" | "custom" | "native" = hideHTMLArrows ? 'none' : 'native'

/**
 * Optional multiplication factor in spin changes. i.e. A spin changes
 * by `spinFactor * step` (if `step` is "any", 1 is used instead).
 */
spinFactor?: number = 1

/**
 * Amount by which the `value` is changed when incrementing/decrementing.
 * It is also a factor in validation as `value` must be a multiple of `step`
 * (offset by `min`, if specified) to be valid. Accepts the special string value `any`
 * that voids the validation constraint and causes stepping actions to increment/decrement by `1`.
 */
step?: string | number | undefined = 1

/**
 * Renders an element on the right side of the input.
 * 
 * By default, the suffix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlSuffixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlSuffixWrapper as InputControlSuffixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   suffix={<InputControlSuffixWrapper>%</InputControlSuffixWrapper>}
 * />
 * ```
 */
suffix?: ReactNode

/**
 * The `type` attribute of the `input` element.
 */
type?: HTMLInputTypeAttribute | undefined = 'number'

/**
 * The value of the input.
 */
value?: string | number | undefined
Imports
import { NumberControl } from "@wordpress/components";
Default story ok
const Default = ( {
	onChange,
	...props
} ) => {
	const [ value, setValue ] = useState< string | undefined >( '0' );
	const [ isValidValue, setIsValidValue ] = useState( true );

	return (
		<>
			<NumberControl
				__next40pxDefaultSize
				{ ...props }
				value={ value }
				onChange={ ( v, extra ) => {
					setValue( v );
					setIsValidValue(
						( extra.event.target as HTMLInputElement ).validity
							.valid
					);
					onChange?.( v, extra );
				} }
			/>
			<p>Is valid? { isValidValue ? 'Yes' : 'No' }</p>
		</>
	);
};

Popover

components-popover · ../packages/components/src/popover/stories/index.story.tsx
`Popover` renders its content in a floating modal. If no explicit anchor is passed via props, it anchors to its parent element by default. ```jsx import { Button, Popover } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyPopover = () => { const [ isVisible, setIsVisible ] = useState( false ); const toggleVisible = () => { setIsVisible( ( state ) => ! state ); }; return ( <Button variant="secondary" onClick={ toggleVisible }> Toggle Popover! { isVisible && <Popover>Popover is toggled!</Popover> } </Button> ); }; ```
Prop types (react-component-meta) 25 prop types
Component: ../packages/components/src/popover/index.tsx::Popover
Props:
/**
 * Prevent the popover from flipping and resizing when meeting the viewport
 * edges. _Note: this prop is deprecated. Instead, provide use the individual
 * `flip` and `resize` props._
 */
__unstableForcePosition?: boolean | undefined

/**
 * The name of the Slot in which the popover should be rendered. It should
 * be also passed to the corresponding `PopoverSlot` component.
 */
__unstableSlotName?: string = 'Popover'

/**
 * The element that should be used by the popover as its anchor. It can either
 * be an `Element` or, alternatively, a `VirtualElement` — ie. an object with
 * the `getBoundingClientRect()` and the `ownerDocument` properties defined.
 * 
 * **The anchor element should be stored in local state** rather than a
 * plain React ref to ensure reactive updating when it changes.
 */
anchor?: Element | VirtualElement | null | undefined

/**
 * An object extending a `DOMRect` with an additional optional `ownerDocument`
 * property, used to specify a fixed popover position.
 */
anchorRect?: DomRectWithOwnerDocument

/**
 * Used to specify a fixed popover position. It can be an `Element`, a React
 * reference to an `element`, an object with a `top` and a `bottom` properties
 * (both pointing to elements), or a `range`.
 */
anchorRef?: Element | PopoverAnchorRefReference | PopoverAnchorRefTopBottom | Range | undefined

/**
 * Whether the popover should animate when opening.
 */
animate?: boolean | undefined = true

/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | ... 161 more ... | undefined

/**
 * The `children` elements rendered as the popover's content.
 */
children: ReactNode

/**
 * Determines whether tabbing is constrained to within the popover,
 * preventing keyboard focus from leaving the popover content without
 * explicit focus elswhere, or whether the popover remains part of the wider
 * tab order. If no value is passed, it will be derived from `focusOnMount`.
 */
constrainTabbing?: boolean | undefined = `focusOnMount` !== false

/**
 * Show the popover fullscreen on mobile viewports.
 */
expandOnMobile?: boolean | undefined

/**
 * Specifies whether the popover should flip across its axis if there isn't
 * space for it in the normal placement.
 * When the using a 'top' placement, the popover will switch to a 'bottom'
 * placement. When using a 'left' placement, the popover will switch to a
 * `right' placement.
 * The popover will retain its alignment of 'start' or 'end' when flipping.
 */
flip?: boolean | undefined = true

/**
 * Determines focus behavior when the popover mounts.
 * 
 * - `"firstElement"` focuses the first tabbable element within.
 * - `"firstInputElement"` focuses the first value control within.
 * - `true` focuses the element itself.
 * - `false` does nothing and _should not be used unless an accessible
 *    substitute behavior is implemented_.
 */
focusOnMount?: any = 'firstElement'

/**
 * A function returning the same value as the one expected by the `anchorRect`
 * prop, used to specify a dynamic popover position.
 */
getAnchorRect?: (fallbackReferenceElement: Element | null) => DomRectWithOwnerDocument

/**
 * Used to customize the header text shown when the popover is toggled to
 * fullscreen on mobile viewports (see the `expandOnMobile` prop).
 */
headerTitle?: string

/**
 * Whether to render the popover inline or within the slot.
 */
inline?: boolean | undefined = false

/**
 * Used to enable a different visual style for the popover.
 * _Note: this prop is deprecated. Use the `variant` prop with the
 * 'toolbar' value instead._
 */
isAlternate?: boolean | undefined

/**
 * Used to show/hide the arrow that points at the popover's anchor.
 */
noArrow?: boolean | undefined = true

/**
 * The distance (in px) between the anchor and the popover.
 */
offset?: number = 0

/**
 * A callback invoked when the popover should be closed.
 */
onClose?: () => void

/**
 * A callback invoked when the focus leaves the opened popover. This should
 * only be provided in advanced use-cases when a popover should close under
 * specific circumstances (for example, if the new `document.activeElement`
 * is content of or otherwise controlling popover visibility).
 * 
 * When not provided, the `onClose` callback will be called instead.
 */
onFocusOutside?: (event: SyntheticEvent<Element, Event>) => void

/**
 * Used to specify the popover's position with respect to its anchor.
 */
placement?: "left" | "right" | "top" | "bottom" | "overlay" | "left-end" | "left-start" | "right-end" | "right-start" | "top-end" | "top-start" | "bottom-end" | "bottom-start" = 'bottom-start'

/**
 * Legacy way to specify the popover's position with respect to its anchor.
 * _Note: this prop is deprecated. Use the `placement` prop instead._
 */
position?: "top" | "middle" | "bottom" | "top center" | "top left" | "top right" | "middle center" | "middle left" | "middle right" | "bottom center" | "bottom left" | "bottom right" | "top center left" | "top center right" | "top center top" | "top center bottom" | "top left left" | "top left right" | "top left top" | "top left bottom" | "top right left" | "top right right" | "top right top" | "top right bottom" | "middle center left" | "middle center right" | "middle center top" | "middle center bottom" | "middle left left" | "middle left right" | "middle left top" | "middle left bottom" | "middle right left" | "middle right right" | "middle right top" | "middle right bottom" | "bottom center left" | "bottom center right" | "bottom center top" | "bottom center bottom" | "bottom left left" | "bottom left right" | "bottom left top" | "bottom left bottom" | "bottom right left" | "bottom right right" | "bottom right top" | "bottom right bottom"

/**
 * Adjusts the size of the popover to prevent its contents from going out of
 * view when meeting the viewport edges.
 * _Note: The `resize` and `shift` props are not intended to be used together.
 * Enabling both can cause unexpected behavior._
 */
resize?: boolean | undefined = true

/**
 * Enables the `Popover` to shift in order to stay in view when meeting the
 * viewport edges.
 * _Note: The `resize` and `shift` props are not intended to be used together.
 * Enabling both can cause unexpected behavior._
 */
shift?: boolean | undefined = false

/**
 * Specifies the popover's style.
 * 
 * Leave undefined for the default style. Other values are:
 * - 'unstyled':  The popover is essentially without any visible style, it
 *                has no background, border, outline or drop shadow, but
 *                the popover contents are still displayed.
 * - 'toolbar':   A style that has no elevation, but a high contrast with
 *                other elements. This is matches the style of the
 *                `Toolbar` component.
 */
variant?: "toolbar" | "unstyled" = undefined
Imports
import { Button, Popover, PopoverInsideIframeRenderedInExternalSlot } from "@wordpress/components";
Default story ok
const Default = () => <Popover>(<div style={ { width: '280px', whiteSpace: 'normal' } }>Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do
                        eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut
                        enim ad minim veniam, quis nostrud exercitation ullamco laboris
                        nisi ut aliquip ex ea commodo consequat.
                    </div>)</Popover>;
Unstyled story ok
const Unstyled = () => <Popover variant="unstyled" />;
All Placements story ok
const AllPlacements = ( { children, ...args } ) => (
    <div
        style={ {
            minWidth: '600px',
            marginLeft: 'auto',
            marginRight: 'auto',
        } }
    >
        <h2>
            Resize / scroll the viewport to test the behavior of the
            popovers when they reach the viewport boundaries.
        </h2>
        <div>
            { AVAILABLE_PLACEMENTS.map( ( p ) => (
                <PopoverWithAnchor
                    key={ p }
                    placement={ p }
                    { ...args }
                    resize={ p === 'overlay' ? true : args.resize }
                >
                    { children }
                    <div>
                        <small>(placement: { p })</small>
                    </div>
                </PopoverWithAnchor>
            ) ) }
        </div>
    </div>
);
Dynamic Height story ok
const DynamicHeight = () => <Popover>(<div
        style={ {
            height: 'var(--dynamic-height)',
            background: '#eee',
            padding: '20px',
        } }
    >Content with dynamic height
                    </div>)</Popover>;
With Slot Outside Iframe story ok
const WithSlotOutsideIframe = () => <PopoverInsideIframeRenderedInExternalSlot />;
With Close Handlers story ok
const WithCloseHandlers = function WithCloseHandlersStory( args ) {
    const [ isVisible, setIsVisible ] = useState( false );
    const buttonRef = useRef< HTMLButtonElement >( null );

    const toggleVisible = ( event: React.MouseEvent ) => {
        if ( buttonRef.current && event.target !== buttonRef.current ) {
            return;
        }
        setIsVisible( ( prev ) => ! prev );
    };

    const handleClose = () => {
        args.onClose?.();
        setIsVisible( false );
    };

    const handleFocusOutside = ( e: React.SyntheticEvent ) => {
        args.onFocusOutside?.( e );
        setIsVisible( false );
    };

    useEffect( () => {
        buttonRef.current?.scrollIntoView( {
            block: 'center',
            inline: 'center',
        } );
    }, [] );

    return (
        <div
            style={ {
                width: '300vw',
                height: '300vh',
                display: 'flex',
                alignItems: 'center',
                justifyContent: 'center',
            } }
        >
            <Button
                __next40pxDefaultSize
                variant="secondary"
                onClick={ toggleVisible }
                ref={ buttonRef }
            >
                Toggle Popover
                { isVisible && (
                    <Popover
                        { ...args }
                        onClose={ handleClose }
                        onFocusOutside={ handleFocusOutside }
                    >
                        { args.children }
                    </Popover>
                ) }
            </Button>
        </div>
    );
};
Popover.Slot no prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/popover/index.tsx
import { Popover } from "@wordpress/components";

ProgressBar

components-progressbar · ../packages/components/src/progress-bar/stories/index.story.tsx
A simple horizontal progress bar component. Supports two modes: determinate and indeterminate. A progress bar is determinate when a specific progress value has been specified (from 0 to 100), and indeterminate when a value hasn't been specified. ```jsx import { ProgressBar } from '@wordpress/components'; const MyLoadingComponent = () => { return <ProgressBar />; }; ```
Prop types (react-component-meta) 2 prop types
Component: ../packages/components/src/progress-bar/index.tsx::ProgressBar
Props:
/**
 * A CSS class to apply to the progress bar wrapper (track) element.
 */
className?: string

/**
 * Value of the progress bar.
 */
value?: number
Imports
import { ProgressBar } from "@wordpress/components";
Default story ok
const Default = () => {
    return <ProgressBar />;
};
With Custom Width story ok
A progress bar with a custom width. You can override the default `width` by passing a custom CSS class via the `className` prop. This example shows a progress bar with an overridden `width` of `100%` which makes it fit all available horizontal space of the parent element. The CSS class looks like this: ```css .custom-progress-bar { width: 100%; } ```
const WithCustomWidth = () => {
    return <ProgressBar className="custom-progress-bar" />;
};

RadioControl

components-radiocontrol · ../packages/components/src/radio-control/stories/index.story.tsx
Render a user interface to select the user type using radio inputs. ```jsx import { RadioControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyRadioControl = () => { const [ option, setOption ] = useState( 'a' ); return ( <RadioControl label="User type" help="The type of the current user" selected={ option } options={ [ { label: 'Author', value: 'a' }, { label: 'Editor', value: 'e' }, ] } onChange={ ( value ) => setOption( value ) } /> ); }; ```
Prop types (react-component-meta) 7 prop types
Component: ../packages/components/src/radio-control/index.tsx::default
Props:
/**
 * Whether the radio group should be disabled.
 */
disabled?: boolean | undefined = false

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * A function that receives the value of the new option that is being
 * selected as input.
 */
onChange: (value: string) => void

/**
 * An array of objects containing the value and label of the options.
 */
options?: { label: string; value: string; description?: string | undefined; }[] = []

/**
 * The value property of the currently selected option.
 */
selected?: string
Imports
import { RadioControl } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ value, setValue ] = useState( options?.[ 0 ]?.value );

    return (
        <RadioControl
            label="Post visibility"
            selected={ value }
            options={ options }
            onChange={ ( v ) => {
				setValue( v );
				onChange( v );
			} } />
    );
};
With Option Descriptions story ok
const WithOptionDescriptions = () => {
    const [ value, setValue ] = useState( options?.[ 0 ]?.value );

    return (
        <RadioControl
            selected={ value }
            options={ options }
            onChange={ ( v ) => {
				setValue( v );
				onChange( v );
			} } />
    );
};

RangeControl

components-rangecontrol · ../packages/components/src/range-control/stories/index.story.tsx
RangeControls are used to make selections from a range of incremental values. ```jsx import { RangeControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyRangeControl = () => { const [ value, setValue ] = useState(); return ( <RangeControl help="Please select how transparent you would like this." initialPosition={ 50 } label="Opacity" max={ 100 } min={ 0 } value={ value } onChange={ setValue } /> ); }; ```
Prop types (react-component-meta) 33 prop types
Component: ../packages/components/src/range-control/index.tsx::default
Props:
/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

/**
 * If this property is added, an Icon component will be rendered
 * after the slider with the icon equal to afterIcon.
 * 
 * For more information on `IconType` see the Icon component:
 * /packages/components/src/icon/index.tsx
 */
afterIcon?: IconType | undefined

/**
 * If this property is true, a button to reset the slider is
 * rendered.
 */
allowReset?: boolean | undefined = false

/**
 * If this property is added, an Icon component will be rendered
 * before the slider with the icon equal to beforeIcon.
 * 
 * For more information on `IconType` see the Icon component:
 * /packages/components/src/icon/index.tsx
 */
beforeIcon?: IconType | undefined

/**
 * CSS color string for the `RangeControl` wrapper.
 */
color?: Color | undefined = `var(--wp-components-color-accent, var(--wp-admin-theme-color, #3858e9))`

/**
 * The current input to use as a fallback if `value` is currently
 * `undefined`.
 */
currentInput?: number

/**
 * Disables the `input`, preventing new values from being applied.
 */
disabled?: boolean | undefined = false

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * The slider starting position, used when no `value` is passed.
 * The `initialPosition` will be clamped between the provided `min`
 * and `max` prop values.
 */
initialPosition?: number

/**
 * Passed as a prop to the `NumberControl` component and is only
 * applicable if `withInputField` is true. If true, while the number
 * input has focus, pressing `UP` or `DOWN` along with the `SHIFT` key
 * will change the value by the `shiftStep` value.
 */
isShiftStepEnabled?: boolean | undefined = true

/**
 * If this property is added, a label will be generated using label
 * property as the content.
 */
label?: string

/**
 * Renders a visual representation of `step` ticks. Custom mark indicators
 * can be provided by an `Array`.
 */
marks?: boolean | { value: number; label?: string | undefined; }[] | undefined = false

/**
 * The maximum `value` allowed.
 */
max?: number = 100

/**
 * The minimum `value` allowed.
 */
min?: number = 0

/**
 * Callback for when `RangeControl` input loses focus.
 */
onBlur?: FocusEventHandler<HTMLInputElement> = () => {}

/**
 * A function that receives the new value. The value will be less than
 * `max` and more than `min` unless a reset (enabled by `allowReset`)
 * has occurred. In which case the value will be either that of
 * `resetFallbackValue` if it has been specified or otherwise
 * `undefined`.
 */
onChange?: (value?: number | undefined) => void = () => {}

/**
 * Callback for when `RangeControl` input gains focus.
 */
onFocus?: FocusEventHandler<HTMLInputElement> = () => {}

/**
 * Callback for when mouse exits the `RangeControl`.
 */
onMouseLeave?: MouseEventHandler<HTMLInputElement> = () => {}

/**
 * Callback for when mouse moves within the `RangeControl`.
 */
onMouseMove?: MouseEventHandler<HTMLInputElement> = () => {}

/**
 * CSS color string to customize the rail element's background.
 */
railColor?: Color | undefined

/**
 * A way to customize the rendered UI of the value.
 */
renderTooltipContent?: (value?: ControlledRangeValue | undefined) => string | number | null | undefined = ( v ) => v

/**
 * The value to revert to if the Reset button is clicked (enabled by
 * `allowReset`)
 */
resetFallbackValue?: number

/**
 * Define if separator line under/above control row should be disabled
 * or full width. By default it is placed below excluding underline the
 * control icon.
 */
separatorType?: "none" | "fullWidth" | "topFullWidth"

/**
 * Passed as a prop to the `NumberControl` component and is only
 * applicable if `withInputField` and `isShiftStepEnabled` are both true
 * and while the number input has focus. Acts as a multiplier of `step`.
 */
shiftStep?: number = 10

/**
 * Forcing the Tooltip UI to show or hide. This is overridden to `false`
 * when `step` is set to the special string value `any`.
 */
showTooltip?: boolean | undefined

/**
 * The minimum amount by which `value` changes. It is also a factor in
 * validation as `value` must be a multiple of `step` (offset by `min`) to
 * be valid. Accepts the special string value `any` that voids the
 * validation constraint and overrides both `withInputField` and
 * `showTooltip` props to `false`.
 */
step?: number | "any" | undefined = 1

/**
 * CSS color string to customize the track element's background.
 */
trackColor?: Color | undefined

/**
 * Define if the value selection should present a stepper control or a
 * slider control in the bottom sheet on mobile. To use the stepper set
 * the type value as `stepper`. Defaults to slider if no option is
 * provided.
 */
type?: "stepper"

/**
 * The current value of the range slider.
 */
value?: number

/**
 * Determines if the `input` number field will render next to the
 * RangeControl. This is overridden to `false` when `step` is set to the
 * special string value `any`.
 */
withInputField?: boolean | undefined = true
Imports
import { RangeControl } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ value, setValue ] = useState< number >();

    return (
        <RangeControl
            onBlur={fn()}
            onFocus={fn()}
            onMouseLeave={fn()}
            onMouseMove={fn()}
            help="Please select how transparent you would like this."
            initialPosition={50}
            label="Opacity"
            max={100}
            min={0}
            value={ value }
            onChange={ ( v ) => {
				setValue( v );
				onChange?.( v );
			} } />
    );
};
With Any Step story ok
Setting the `step` prop to `"any"` will allow users to select non-integer values. This also overrides both `withInputField` and `showTooltip` props to `false`.
const WithAnyStep = () => {
    const [ value, setValue ] = useState< number >();

    return (
        <>
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                label="Brightness"
                step="any"
                value={ value }
                onChange={ ( v ) => {
					setValue( v );
					onChange?.( v );
				} } />
            <hr style={ { marginTop: '5em' } } />
            <p>Current value: { value }</p>
        </>
    );
};
With Integer Step And Marks story ok
Use `marks` to render a visual representation of `step` ticks. Marks may be automatically generated or custom mark indicators can be provided by an `Array`.
const WithIntegerStepAndMarks = () => {
    const [ automaticValue, setAutomaticValue ] = useState< number >();
    const [ customValue, setCustomValue ] = useState< number >();

    return (
        <>
            <h2>{ label }</h2>
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                max={10}
                min={0}
                step={1}
                label="Automatic marks"
                marks
                onChange={ ( v ) => {
					setAutomaticValue( v );
					onChange?.( v );
				} }
                value={ automaticValue } />
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                marks={marksBase}
                max={10}
                min={0}
                step={1}
                label="Custom marks"
                onChange={ ( v ) => {
					setCustomValue( v );
					onChange?.( v );
				} }
                value={ customValue } />
        </>
    );
};
With Decimal Step And Marks story ok
Decimal values may be used for `marks` rendered as a visual representation of `step` ticks. Marks may be automatically generated or custom mark indicators can be provided by an `Array`.
const WithDecimalStepAndMarks = () => {
    const [ automaticValue, setAutomaticValue ] = useState< number >();
    const [ customValue, setCustomValue ] = useState< number >();

    return (
        <>
            <h2>{ label }</h2>
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                max={10}
                min={0}
                step={0.1}
                label="Automatic marks"
                marks
                onChange={ ( v ) => {
					setAutomaticValue( v );
					onChange?.( v );
				} }
                value={ automaticValue } />
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                marks={[
                    ...marksBase,
                    { value: 3.5, label: '3.5' },
                    { value: 5.8, label: '5.8' },
                ]}
                max={10}
                min={0}
                step={0.1}
                label="Custom marks"
                onChange={ ( v ) => {
					setCustomValue( v );
					onChange?.( v );
				} }
                value={ customValue } />
        </>
    );
};
With Negative Minimum And Marks story ok
A negative `min` value can be used to constrain `RangeControl` values. Mark indicators can represent negative values as well. Marks may be automatically generated or custom mark indicators can be provided by an `Array`.
const WithNegativeMinimumAndMarks = () => {
    const [ automaticValue, setAutomaticValue ] = useState< number >();
    const [ customValue, setCustomValue ] = useState< number >();

    return (
        <>
            <h2>{ label }</h2>
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                max={10}
                min={-10}
                step={1}
                label="Automatic marks"
                marks
                onChange={ ( v ) => {
					setAutomaticValue( v );
					onChange?.( v );
				} }
                value={ automaticValue } />
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                marks={marksWithNegatives}
                max={10}
                min={-10}
                step={1}
                label="Custom marks"
                onChange={ ( v ) => {
					setCustomValue( v );
					onChange?.( v );
				} }
                value={ customValue } />
        </>
    );
};
With Negative Range And Marks story ok
The entire range of valid values for a `RangeControl` may be negative. Mark indicators can represent negative values as well. Marks may be automatically generated or custom mark indicators can be provided by an `Array`.
const WithNegativeRangeAndMarks = () => {
    const [ automaticValue, setAutomaticValue ] = useState< number >();
    const [ customValue, setCustomValue ] = useState< number >();

    return (
        <>
            <h2>{ label }</h2>
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                max={-1}
                min={-10}
                step={1}
                label="Automatic marks"
                marks
                onChange={ ( v ) => {
					setAutomaticValue( v );
					onChange?.( v );
				} }
                value={ automaticValue } />
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                marks={marksWithNegatives}
                max={-1}
                min={-10}
                step={1}
                label="Custom marks"
                onChange={ ( v ) => {
					setCustomValue( v );
					onChange?.( v );
				} }
                value={ customValue } />
        </>
    );
};
With Any Step And Marks story ok
When a `RangeControl` has a `step` value of `any` a user may select non-integer values. This may still be used in conjunction with `marks` rendering a visual representation of `step` ticks.
const WithAnyStepAndMarks = () => {
    const [ automaticValue, setAutomaticValue ] = useState< number >();
    const [ customValue, setCustomValue ] = useState< number >();

    return (
        <>
            <h2>{ label }</h2>
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                max={10}
                min={0}
                step="any"
                label="Automatic marks"
                marks
                onChange={ ( v ) => {
					setAutomaticValue( v );
					onChange?.( v );
				} }
                value={ automaticValue } />
            <RangeControl
                onBlur={fn()}
                onFocus={fn()}
                onMouseLeave={fn()}
                onMouseMove={fn()}
                marks={marksBase}
                max={10}
                min={0}
                step="any"
                label="Custom marks"
                onChange={ ( v ) => {
					setCustomValue( v );
					onChange?.( v );
				} }
                value={ customValue } />
        </>
    );
};

ResizableBox

components-resizablebox · ../packages/components/src/resizable-box/stories/index.story.tsx
`ResizableBox` wraps content in a container with draggable handles, letting users interactively resize it along one or more edges or corners.
Prop types (react-component-meta) 34 prop types
Component: ../packages/components/src/resizable-box/index.tsx::default
Props:
__experimentalShowTooltip?: boolean | undefined = false

__experimentalTooltipProps?: Omit<ResizeTooltipProps, "ref"> & RefAttributes<HTMLDivElement> = {}

as?: string | ComponentType<any> | undefined

bounds?: HTMLElement | "window" | "parent" | undefined

boundsByDirection?: boolean | undefined

children?: ReactNode

className?: string

defaultSize?: Size

enable?: Enable

grid?: [number, number]

handleClasses?: HandleClassName

handleComponent?: HandleComponent

handleStyles?: HandleStyles

handleWrapperClass?: string

handleWrapperStyle?: CSSProperties

key?: Key | null | undefined

lockAspectRatio?: number | boolean | undefined

lockAspectRatioExtraHeight?: number

lockAspectRatioExtraWidth?: number

maxHeight?: string | number | undefined

maxWidth?: string | number | undefined

minHeight?: string | number | undefined

minWidth?: string | number | undefined

onResize?: ResizeCallback

onResizeStart?: ResizeStartCallback

onResizeStop?: ResizeCallback

/**
 * Allows getting a ref to the component instance.
 * Once the component unmounts, React will set `ref.current` to `null`
 * (or call the ref with `null` if you passed a callback ref).
 */
ref?: LegacyRef<Resizable> | undefined

resizeRatio?: number

scale?: number

showHandle?: boolean | undefined = true

size?: Size

snap?: { x?: number[] | undefined; y?: number[] | undefined; }

snapGap?: number

style?: CSSProperties
Imports
import { ResizableBox } from "@wordpress/components";
Default story ok
const Default = ( {
	onResizeStop,
	...props
} ) => {
	const [ { height, width }, setAttributes ] = useState( {
		height: 200,
		width: 400,
	} );

	return (
		<ResizableBox
			{ ...props }
			size={ {
				height,
				width,
			} }
			onResizeStop={ ( event, direction, elt, delta ) => {
				onResizeStop?.( event, direction, elt, delta );
				setAttributes( {
					height: height + delta.height,
					width: width + delta.width,
				} );
			} }
		/>
	);
};
Disabled Directions story ok
The `enable` prop can be used to disable resizing in specific directions.
const DisabledDirections = ( {
	onResizeStop,
	...props
} ) => {
	const [ { height, width }, setAttributes ] = useState( {
		height: 200,
		width: 400,
	} );

	return (
		<ResizableBox
			{ ...props }
			size={ {
				height,
				width,
			} }
			onResizeStop={ ( event, direction, elt, delta ) => {
				onResizeStop?.( event, direction, elt, delta );
				setAttributes( {
					height: height + delta.height,
					width: width + delta.width,
				} );
			} }
		/>
	);
};

SandBox

components-sandbox · ../packages/components/src/sandbox/stories/index.story.tsx
This component provides an isolated environment for arbitrary HTML via iframes. ```jsx import { SandBox } from '@wordpress/components'; const MySandBox = () => ( <SandBox html="<p>Content</p>" title="SandBox" type="embed" /> ); ```
Prop types (react-component-meta) 8 prop types
Component: ../packages/components/src/sandbox/index.tsx::default
Props:
/**
 * Whether to include `allow-same-origin` in the iframe's sandbox
 * attribute. When true, nested iframes (such as third-party embeds)
 * can access their own origin's cookies and storage.
 * 
 * Only enable this for content that is NOT directly user-controlled,
 * such as server-fetched oEmbed previews.
 */
allowSameOrigin?: boolean | undefined = false

/**
 * The HTML to render in the body of the iframe document.
 */
html?: string = ''

/**
 * The `onFocus` callback for the iframe.
 */
onFocus?: FocusEventHandler<HTMLIFrameElement>

/**
 * An array of script URLs to inject as `<script>` tags into the bottom of the `<body>` of the iframe document.
 */
scripts?: string[] = []

/**
 * An array of CSS strings to inject into the `<head>` of the iframe document.
 */
styles?: string[] = []

/**
 * The `tabindex` the iframe should receive.
 */
tabIndex?: number = 0

/**
 * The `<title>` of the iframe document.
 */
title?: string = ''

/**
 * The CSS class name to apply to the `<html>` and `<body>` elements of the iframe.
 */
type?: string
Imports
import { SandBox } from "@wordpress/components";
Default story ok
const Default = () => <SandBox onFocus={fn()} html="<p>Arbitrary HTML content</p>" />;

ScrollLock

components-scrolllock · ../packages/components/src/scroll-lock/stories/index.story.tsx
ScrollLock is a content-free React component for declaratively preventing scroll bleed from modal UI to the page body. This component applies a `lockscroll` class to the `document.documentElement` and `document.scrollingElement` elements to stop the body from scrolling. When it is present, the lock is applied. ```jsx import { ScrollLock, Button } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyScrollLock = () => { const [ isScrollLocked, setIsScrollLocked ] = useState( false ); const toggleLock = () => { setIsScrollLocked( ( locked ) => ! locked ) ); }; return ( <div> <Button variant="secondary" onClick={ toggleLock }> Toggle scroll lock </Button> { isScrollLocked && <ScrollLock /> } <p> Scroll locked: <strong>{ isScrollLocked ? 'Yes' : 'No' }</strong> </p> </div> ); }; ```
Imports
import { Button, ScrollLock } from "@wordpress/components";
Default story ok
const Default = () => {
	const [ isScrollLocked, setScrollLocked ] = useState( false );
	const toggleLock = () => setScrollLocked( ! isScrollLocked );

	return (
		<div style={ { height: 1000 } }>
			<div
				style={ {
					overflow: 'auto',
					height: 240,
					border: '1px solid lightgray',
				} }
			>
				<StripedBackground>
					<div>
						Start scrolling down. Once you scroll to the end of this
						container with the stripes, the rest of the page will
						continue scrolling. <code>ScrollLock</code> prevents
						this &quot;scroll bleed&quot; from happening.
					</div>
					<ToggleContainer>
						<Button
							__next40pxDefaultSize
							variant="primary"
							onClick={ toggleLock }
						>
							Toggle Scroll Lock
						</Button>
						{ isScrollLocked && <ScrollLock /> }
						<p>
							Scroll locked:{ ' ' }
							<strong>{ isScrollLocked ? 'Yes' : 'No' }</strong>
						</p>
					</ToggleContainer>
				</StripedBackground>
			</div>
		</div>
	);
};

SearchControl

components-searchcontrol · ../packages/components/src/search-control/stories/index.story.tsx
SearchControl components let users display a search control. ```jsx import { SearchControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; function MySearchControl( { className, setState } ) { const [ searchInput, setSearchInput ] = useState( '' ); return ( <SearchControl value={ searchInput } onChange={ setSearchInput } /> ); } ```
Prop types (react-component-meta) 13 prop types
Component: ../packages/components/src/search-control/index.tsx::default
Props:
__next40pxDefaultSize?: boolean | undefined

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined = false

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = true

/**
 * The accessible label for the input.
 * 
 * A label should always be provided as an accessibility best practice,
 * even when a placeholder is defined and `hideLabelFromVision` is `true`.
 */
label?: string = __( 'Search' )

/**
 * A function that receives the value of the input when the value is changed.
 */
onChange: (value: string) => void

/**
 * When an `onClose` callback is provided, the search control will render a close button
 * that will trigger the given callback.
 * 
 * Use this if you want the button to trigger your own logic to close the search field entirely,
 * rather than just clearing the input value.
 */
onClose?: () => void

onDrag?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragEnd?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragStart?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

/**
 * A placeholder for the input.
 */
placeholder?: string = __( 'Search' )

/**
 * The size of the component
 */
size?: "default" | "compact" = 'default'

/**
 * The current value of the input.
 */
value?: string
Imports
import { SearchControl } from "@wordpress/components";
Default story ok
const Default = ( {
	onChange,
	...props
} ) => {
	const [ value, setValue ] = useState< string >();

	return (
		<SearchControl
			{ ...props }
			value={ value }
			onChange={ ( ...changeArgs ) => {
				setValue( ...changeArgs );
				onChange( ...changeArgs );
			} }
		/>
	);
};

SelectControl

components-selectcontrol · ../packages/components/src/select-control/stories/index.story.tsx
`SelectControl` allows users to select from a single or multiple option menu. It functions as a wrapper around the browser's native `<select>` element. ```jsx import { SelectControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MySelectControl = () => { const [ size, setSize ] = useState( '50%' ); return ( <SelectControl __next40pxDefaultSize label="Size" value={ size } options={ [ { label: 'Big', value: '100%' }, { label: 'Medium', value: '50%' }, { label: 'Small', value: '25%' }, ] } onChange={ setSize } /> ); }; ```
Prop types (react-component-meta) 19 prop types
Component: ../packages/components/src/select-control/index.tsx::default
Props:
/**
 * Deprecated. Use `__next40pxDefaultSize` instead.
 */
__next36pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

/**
 * As an alternative to the `options` prop, `optgroup`s and `options` can be
 * passed in as `children` for more customizability.
 */
children?: ReactNode

/**
 * If true, the `input` will be disabled.
 */
disabled?: boolean | undefined = false

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * The position of the label.
 */
labelPosition?: "top" | "bottom" | "side" | "edge" = 'top'

/**
 * If this property is added, multiple values can be selected. The `value` passed should be an array.
 * 
 * In most cases, it is preferable to use the `FormTokenField` or `CheckboxControl` components instead.
 */
multiple?: false = false

/**
 * A function that receives the value of the new option that is being selected as input.
 * 
 * If `multiple` is `true`, the value received is an array of the selected value.
 * Otherwise, the value received is a single value with the new selected value.
 */
onChange?: (value: string, extra?: { event?: ChangeEvent<HTMLSelectElement> | undefined; } | undefined) => void

/**
 * An array of option property objects to be rendered,
 * each with a `label` and `value` property, as well as any other
 * `<option>` attributes.
 */
options?: readonly ({ label: string; value: string; } & Omit<OptionHTMLAttributes<HTMLOptionElement>, "label" | "value">)[] = []

/**
 * Renders an element on the left side of the input.
 * 
 * By default, the prefix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlPrefixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlPrefixWrapper as InputControlPrefixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   prefix={<InputControlPrefixWrapper>@</InputControlPrefixWrapper>}
 * />
 * ```
 */
prefix?: ReactNode

ref?: Ref<HTMLSelectElement> | undefined

/**
 * Adjusts the size of the input.
 */
size?: "small" | "default" | "compact" | "__unstable-large" = 'default'

/**
 * Renders an element on the right side of the input.
 * 
 * By default, the suffix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlSuffixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlSuffixWrapper as InputControlSuffixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   suffix={<InputControlSuffixWrapper>%</InputControlSuffixWrapper>}
 * />
 * ```
 */
suffix?: ReactNode

/**
 * The value of the selected option.
 * 
 * If `multiple` is true, the `value` should be an array with the values of the selected options.
 */
value?: string

/**
 * The style variant of the control.
 */
variant?: "default" | "minimal" = 'default'
Imports
import { InputControlPrefixWrapper, SelectControl } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	const [ selection, setSelection ] = useState< string[] >();

	if ( props.multiple ) {
		return (
			<SelectControl
				__next40pxDefaultSize
				{ ...props }
				multiple
				value={ selection }
				onChange={ ( value ) => {
					setSelection( value );
					props.onChange?.( value );
				} }
			/>
		);
	}

	return (
		<SelectControl
			__next40pxDefaultSize
			{ ...props }
			multiple={ false }
			value={ selection?.[ 0 ] }
			onChange={ ( value ) => {
				setSelection( [ value ] );
				props.onChange?.( value );
			} }
		/>
	);
};
With Label And Help Text story ok
const WithLabelAndHelpText = ( props ) => {
	const [ selection, setSelection ] = useState< string[] >();

	if ( props.multiple ) {
		return (
			<SelectControl
				__next40pxDefaultSize
				{ ...props }
				multiple
				value={ selection }
				onChange={ ( value ) => {
					setSelection( value );
					props.onChange?.( value );
				} }
			/>
		);
	}

	return (
		<SelectControl
			__next40pxDefaultSize
			{ ...props }
			multiple={ false }
			value={ selection?.[ 0 ] }
			onChange={ ( value ) => {
				setSelection( [ value ] );
				props.onChange?.( value );
			} }
		/>
	);
};
With Custom Children story ok
As an alternative to the `options` prop, `optgroup`s and `options` can be passed in as `children` for more customizeability.
const WithCustomChildren = ( props ) => {
	const [ selection, setSelection ] = useState< string[] >();

	if ( props.multiple ) {
		return (
			<SelectControl
				__next40pxDefaultSize
				{ ...props }
				multiple
				value={ selection }
				onChange={ ( value ) => {
					setSelection( value );
					props.onChange?.( value );
				} }
			/>
		);
	}

	return (
		<SelectControl
			__next40pxDefaultSize
			{ ...props }
			multiple={ false }
			value={ selection?.[ 0 ] }
			onChange={ ( value ) => {
				setSelection( [ value ] );
				props.onChange?.( value );
			} }
		/>
	);
};
With Prefix story ok
By default, the prefix is aligned with the edge of the input border, with no padding. If you want to apply standard padding in accordance with the size variant, wrap the element in the `<InputControlPrefixWrapper>` component.
const WithPrefix = ( props ) => {
	const [ selection, setSelection ] = useState< string[] >();

	if ( props.multiple ) {
		return (
			<SelectControl
				__next40pxDefaultSize
				{ ...props }
				multiple
				value={ selection }
				onChange={ ( value ) => {
					setSelection( value );
					props.onChange?.( value );
				} }
			/>
		);
	}

	return (
		<SelectControl
			__next40pxDefaultSize
			{ ...props }
			multiple={ false }
			value={ selection?.[ 0 ] }
			onChange={ ( value ) => {
				setSelection( [ value ] );
				props.onChange?.( value );
			} }
		/>
	);
};
Minimal story ok
const Minimal = ( props ) => {
	const [ selection, setSelection ] = useState< string[] >();

	if ( props.multiple ) {
		return (
			<SelectControl
				__next40pxDefaultSize
				{ ...props }
				multiple
				value={ selection }
				onChange={ ( value ) => {
					setSelection( value );
					props.onChange?.( value );
				} }
			/>
		);
	}

	return (
		<SelectControl
			__next40pxDefaultSize
			{ ...props }
			multiple={ false }
			value={ selection?.[ 0 ] }
			onChange={ ( value ) => {
				setSelection( [ value ] );
				props.onChange?.( value );
			} }
		/>
	);
};

Shortcut

components-shortcut · ../packages/components/src/shortcut/stories/index.story.tsx
Shortcut component is used to display keyboard shortcuts, and it can be customized with a custom display and aria label if needed. ```jsx import { Shortcut } from '@wordpress/components'; const MyShortcut = () => { return ( <Shortcut shortcut={{ display: 'Ctrl + S', ariaLabel: 'Save' }} /> ); }; ```
Prop types (react-component-meta) 2 prop types
Component: ../packages/components/src/shortcut/index.tsx::default
Props:
/**
 * Classname to apply to the shortcut.
 */
className?: string

/**
 * Shortcut configuration
 */
shortcut?: string | { display: string; ariaLabel: string; } | undefined
Imports
import { Shortcut } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	return <Shortcut shortcut="Ctrl + S" { ...props } />;
};
With Aria Label story ok
const WithAriaLabel = ( props ) => {
	return <Shortcut shortcut="Ctrl + S" { ...props } />;
};

Skeleton

design-system-components-skeleton · ../packages/ui/src/skeleton/stories/index.story.tsx
A placeholder shown while content is loading. Size and corner radius are controlled via standard `div` props such as `style` and `className`.
Prop types (react-component-meta) 3 prop types
Component: ../packages/ui/src/skeleton/index.ts::Skeleton
Props:
/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Imports
import { Skeleton } from "@wordpress/ui";
Default story ok
const Default = () => <Skeleton
    style={{
        width: 'var(--wpds-dimension-surface-width-xs)',
        height: textLineHeight,
        borderRadius: 'var(--wpds-border-radius-md)',
    }} />;
Circle story ok
const Circle = () => <Skeleton
    style={{
        width: 'var(--wpds-dimension-size-lg)',
        height: 'var(--wpds-dimension-size-lg)',
        borderRadius: '50%',
    }} />;
Text Lines story ok
const TextLines = () => <div
    style={ {
        display: 'flex',
        flexDirection: 'column',
        gap: '0.5rem',
    } }>
    <Skeleton
        style={ {
            width: '100%',
            height: textLineHeight,
            borderRadius: 'var(--wpds-border-radius-md)',
        } } />
    <Skeleton
        style={ {
            width: '100%',
            height: textLineHeight,
            borderRadius: 'var(--wpds-border-radius-md)',
        } } />
    <Skeleton
        style={ {
            width: '60%',
            height: textLineHeight,
            borderRadius: 'var(--wpds-border-radius-md)',
        } } />
</div>;
Card Placeholder story ok
const CardPlaceholder = () => <div
    style={ {
        display: 'flex',
        gap: '1rem',
        alignItems: 'center',
        maxWidth: 320,
    } }>
    <Skeleton
        style={ {
            width: 'var(--wpds-dimension-size-lg)',
            height: 'var(--wpds-dimension-size-lg)',
            borderRadius: '50%',
        } } />
    <div
        style={ {
            display: 'flex',
            flexDirection: 'column',
            gap: '0.5rem',
            flex: 1,
        } }>
        <Skeleton
            style={ {
                width: '80%',
                height: textLineHeight,
                borderRadius: 'var(--wpds-border-radius-md)',
            } } />
        <Skeleton
            style={ {
                width: '50%',
                height: textLineHeight,
                borderRadius: 'var(--wpds-border-radius-md)',
            } } />
    </div>
</div>;

Slot

components-slotfill · ../packages/components/src/slot-fill/stories/index.story.tsx
`Slot` marks a location where content rendered by matching `Fill` components elsewhere will appear. Use it to allow a component to define UI areas that can be extended from other parts of the application.
Prop types (react-component-meta) 7 prop types
Component: ../packages/components/src/slot-fill/index.tsx::Slot
Props:
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * By default, events will bubble to their parents on the DOM hierarchy (native event bubbling).
 * If set to true, events will bubble to their virtual parent in the React elements hierarchy instead,
 * also accept an optional `className`, `id`, etc.  to add to the slot container.
 */
bubblesVirtually?: true

/**
 * A function that returns nodes to be rendered.
 * Supported only when `bubblesVirtually` is `false`.
 */
children?: (fills: ReactNode) => ReactNode

/**
 * Additional className for the `Slot` component.
 * Supported only when `bubblesVirtually` is `true`.
 */
className?: string

/**
 * props to pass from `Slot` to `Fill`.
 */
fillProps?: FillProps = {}

/**
 * Slot name.
 */
name: SlotKey

/**
 * Additional styles for the `Slot` component.
 * Supported only when `bubblesVirtually` is `true`.
 */
style?: CSSProperties
Imports
import { Fill, Slot, Provider as SlotFillProvider } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	return (
		<SlotFillProvider>
			<h2>Profile</h2>
			<p>
				Name: <Slot { ...props } name="name" />
			</p>
			<p>
				Age: <Slot { ...props } name="age" />
			</p>
			<Fill name="name">Grace</Fill>
			<Fill name="age">33</Fill>
		</SlotFillProvider>
	);
};
With Fill Props story ok
const WithFillProps = ( props ) => {
	return (
		<SlotFillProvider>
			<h2>Profile</h2>
			<p>
				Name:{ ' ' }
				<Slot
					{ ...props }
					name="name"
					fillProps={ { name: 'Grace' } }
				/>
			</p>
			<p>
				Age: <Slot { ...props } name="age" fillProps={ { age: 33 } } />
			</p>

			<Fill name="name">{ ( fillProps ) => fillProps.name }</Fill>
			<Fill name="age">{ ( fillProps ) => fillProps.age }</Fill>
		</SlotFillProvider>
	);
};
With Slot Children story ok
const WithSlotChildren = ( props ) => {
	return (
		<SlotFillProvider>
			<h2>Profile</h2>
			<p>
				Name:
				{ /* @ts-expect-error Not supported children for `<Slot />` when `bubblesVirtually` is true. */ }
				<Slot { ...props } name="name">
					{ ( fills ) => {
						return (
							<span style={ { color: 'red' } }>{ fills }</span>
						);
					} }
				</Slot>
			</p>
			<p>
				Age:
				{ /* @ts-expect-error Not support children for `<Slot />` when `bubblesVirtually` is true. */ }
				<Slot { ...props } name="age">
					{ ( fills ) => {
						return (
							<span style={ { color: 'red' } }>{ fills }</span>
						);
					} }
				</Slot>
			</p>
			<Fill name="name">Alice</Fill>
			<Fill name="age">18</Fill>
		</SlotFillProvider>
	);
};
With Context story ok
const WithContext = ( props ) => {
	const Context = createContext< string | number >( '' );
	const ContextFill = ( { name }: { name: string } ) => {
		const value = useContext( Context );
		return <Fill name={ name }>{ value }</Fill>;
	};
	return (
		<SlotFillProvider>
			<h2>Profile</h2>
			<p>
				Name: <Slot { ...props } name="name" />
			</p>
			<p>
				Age: <Slot { ...props } name="age" />
			</p>
			<Context.Provider value="Grace">
				<ContextFill name="name" />
			</Context.Provider>
			<Context.Provider value={ 33 }>
				<ContextFill name="age" />
			</Context.Provider>
		</SlotFillProvider>
	);
};
Fill 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/slot-fill/index.tsx
import { Fill } from "@wordpress/components";
Component: ../packages/components/src/slot-fill/index.tsx::Fill (react-component-meta)
/**
 * Children elements or render function.
 */
children?: FillChildren

/**
 * The name of the slot to fill into.
 */
name: SlotKey
SlotFillProvider 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/slot-fill/index.tsx
import { Provider as SlotFillProvider } from "@wordpress/components";
Component: ../packages/components/src/slot-fill/index.tsx::Provider (react-component-meta)
/**
 * The children elements.
 */
children: ReactNode

/**
 * Whether to pass slots to the parent provider if existent.
 */
passthrough?: boolean | undefined = false

Snackbar

components-snackbar · ../packages/components/src/snackbar/stories/index.story.tsx
A Snackbar displays a succinct message that is cleared out after a small delay. It can also offer the user options, like viewing a published post. But these options should also be available elsewhere in the UI. ```jsx const MySnackbarNotice = () => ( <Snackbar>Post published successfully.</Snackbar> ); ```
Prop types (react-component-meta) 11 prop types
Component: ../packages/components/src/snackbar/index.tsx::default
Props:
/**
 * An array of action objects. Each member object should contain:
 * 
 * - `label`: `string` containing the text of the button/link
 * - `url`: `string` OR `onClick`: `( event: SyntheticEvent ) => void` to specify
 *    what the action does.
 * 
 * The default appearance of an action button is inferred based on whether
 * `url` or `onClick` are provided, rendering the button as a link if
 * appropriate. If both props are provided, `url` takes precedence, and the
 * action button will render as an anchor tag.
 */
actions?: (Pick<NoticeAction, "label" | "onClick" | "url"> & { openInNewTab?: boolean | undefined; })[] = []

/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The displayed message of a notice. Also used as the spoken message for
 * assistive technology, unless `spokenMessage` is provided as an alternative message.
 */
children: ReactNode

/**
 * A CSS `class` to give to the wrapper element.
 */
className?: string

/**
 * Whether to require user action to dismiss the snackbar.
 * By default, this is dismissed on a timeout, without user interaction.
 */
explicitDismiss?: boolean | undefined = false

/**
 * The icon to render in the snackbar.
 */
icon?: ReactNode = null

/**
 * A ref to the list that contains the snackbar.
 */
listRef?: MutableRefObject<HTMLDivElement | null>

/**
 * A deprecated alternative to `onRemove`. This prop is kept for
 * compatibility reasons but should be avoided.
 */
onDismiss?: () => void = noop

/**
 * Function called when dismissing the notice
 */
onRemove?: () => void = noop

/**
 * A politeness level for the notice's spoken message. Should be provided as
 * one of the valid options for an `aria-live` attribute value.
 * 
 * A value of `'assertive'` is to be used for important, and usually
 * time-sensitive, information. It will interrupt anything else the screen
 * reader is announcing in that moment.
 * A value of `'polite'` is to be used for advisory information. It should
 * not interrupt what the screen reader is announcing in that moment
 * (the "speech queue") or interrupt the current task.
 * 
 * Note that this value should be considered a suggestion; assistive
 * technologies may override it based on internal heuristics.
 */
politeness?: "assertive" | "polite" = 'polite'

/**
 * Used to provide a custom spoken message in place of the `children` default.
 */
spokenMessage?: ReactNode = children
Imports
import { Icon, Snackbar } from "@wordpress/components";
Default story ok
const Default = ( {
	children,
	...props
} ) => {
	return <Snackbar { ...props }>{ children }</Snackbar>;
};
With Actions story ok
const WithActions = ( {
	children,
	...props
} ) => {
	return <Snackbar { ...props }>{ children }</Snackbar>;
};
With Icon story ok
const WithIcon = ( {
	children,
	...props
} ) => {
	return <Snackbar { ...props }>{ children }</Snackbar>;
};
With Explicit Dismiss story ok
const WithExplicitDismiss = ( {
	children,
	...props
} ) => {
	return <Snackbar { ...props }>{ children }</Snackbar>;
};
With Action And Explicit Dismiss story ok
const WithActionAndExplicitDismiss = ( {
	children,
	...props
} ) => {
	return <Snackbar { ...props }>{ children }</Snackbar>;
};

Spinner

components-spinner · ../packages/components/src/spinner/stories/index.story.tsx
`Spinner` is a component used to notify users that their action is being processed. ```jsx import { Spinner } from '@wordpress/components'; function Example() { return <Spinner />; } ```
Imports
import { Spinner } from "@wordpress/components";
Default story ok
const Default = () => {
    return <Spinner />;
};
Custom Size story ok
const CustomSize = () => {
    return <Spinner style={{ width: space( 20 ), height: space( 20 ) }} />;
};

Stack

design-system-components-stack · ../packages/ui/src/stack/stories/index.story.tsx
A flexible layout component using CSS Flexbox for consistent spacing and alignment. Built on design tokens for predictable spacing values.
Prop types (react-component-meta) 9 prop types
Component: ../packages/ui/src/stack/index.ts::Stack
Props:
/**
 * The alignment of the stack items along the cross axis.
 */
align?: AlignItems | undefined = 'initial'

/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * The direction of the stack.
 */
direction?: "-moz-initial" | "inherit" | "initial" | "revert" | "revert-layer" | "unset" | "row" | "column"

/**
 * The amount of space between each child element using design system tokens.
 */
gap?: any = undefined

/**
 * The alignment of the stack items along the main axis.
 */
justify?: JustifyContent | undefined = 'initial'

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

/**
 * Whether the stack items should wrap to the next line.
 */
wrap?: "-moz-initial" | "inherit" | "initial" | "revert" | "revert-layer" | "unset" | "wrap" | "nowrap"
Imports
import { Stack } from "@wordpress/ui";
Default story ok
const Default = () => <Stack gap="md">(<>
        <DemoBox />
        <DemoBox variant="lg" />
        <DemoBox />
        <DemoBox />
        <DemoBox variant="lg" />
        <DemoBox />
    </>)</Stack>;
Nested story ok
const Nested = () => <Stack align="center" justify="center">(<>
        <DemoBox variant="lg" />
        <Stack gap="lg">
            <DemoBox />
            <DemoBox />
        </Stack>
        <DemoBox variant="lg" />
        <Stack direction="column">
            <DemoBox />
            <DemoBox />
        </Stack>
        <DemoBox variant="lg" />
    </>)</Stack>;

Tabs.Root

design-system-components-tabs · ../packages/ui/src/tabs/stories/index.story.tsx
Groups the tabs and the corresponding panels. `Tabs` is a collection of React components that combine to render an [ARIA-compliant tabs pattern](https://www.w3.org/WAI/ARIA/apg/patterns/tabs/).
Prop types (react-component-meta) 8 prop types
Component: ../packages/ui/src/tabs/index.ts::Root
Props:
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * The default value. Use when the component is not controlled.
 * When the value is `null`, no Tab will be active.
 */
defaultValue?: any = 0

/**
 * Callback invoked when new value is being set.
 * 
 * The event `reason` is `'none'` for user-initiated changes, such as a click
 * or keyboard navigation; `'initial'` for the first automatic selection or
 * fallback in uncontrolled roots when `defaultValue` is omitted or
 * `undefined`, including when the implicit initial value is disabled or
 * missing; `'disabled'` for automatic fallback when the selected tab becomes
 * disabled in uncontrolled roots; or `'missing'` for automatic fallback when
 * the selected tab is removed, or when an explicit `defaultValue` never
 * matches a mounted tab in uncontrolled roots.
 * 
 * For automatic changes, the selected value can be `null` when no enabled Tab
 * is available as a fallback.
 * 
 * Automatic changes cannot be canceled; calling `eventDetails.cancel()` for
 * `'initial'`, `'disabled'`, or `'missing'` has no effect.
 */
onValueChange?: (value: any, eventDetails: TabsRootChangeEventDetails) => void

/**
 * The component orientation (layout flow direction).
 */
orientation?: "horizontal" | "vertical" = 'horizontal'

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

/**
 * The value of the currently active `Tab`. Use when the component is controlled.
 * When the value is `null`, no Tab will be active.
 */
value?: any
Imports
import { List, Panel, Root, Tab, Popup, Positioner, Trigger } from "@wordpress/ui";
Default story ok
const Default = () => <Tabs.Root defaultValue="tab1">(<>
        <Tabs.List>
            <Tabs.Tab value="tab1">Tab 1</Tabs.Tab>
            <Tabs.Tab value="tab2">Tab 2</Tabs.Tab>
            <Tabs.Tab value="tab3">Tab 3</Tabs.Tab>
        </Tabs.List>
        <Tabs.Panel value="tab1">
            <ThemedParagraph>Selected tab: Tab 1</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab2">
            <ThemedParagraph>Selected tab: Tab 2</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab3">
            <ThemedParagraph>Selected tab: Tab 3</ThemedParagraph>
        </Tabs.Panel>
    </>)</Tabs.Root>;
Minimal story ok
const Minimal = () => <Tabs.Root>(<>
        <Tabs.List variant="minimal">
            <Tabs.Tab value="tab1">Tab 1</Tabs.Tab>
            <Tabs.Tab value="tab2">Tab 2</Tabs.Tab>
            <Tabs.Tab value="tab3">Tab 3</Tabs.Tab>
        </Tabs.List>
        <Tabs.Panel value="tab1">
            <ThemedParagraph>Selected tab: Tab 1</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab2">
            <ThemedParagraph>Selected tab: Tab 2</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab3">
            <ThemedParagraph>Selected tab: Tab 3</ThemedParagraph>
        </Tabs.Panel>
    </>)</Tabs.Root>;
Size And Overflow Playground story ok
const SizeAndOverflowPlayground = function SizeAndOverflowPlayground( props ) {
    const [ fullWidth, setFullWidth ] = useState( false );
    return (
        <div>
            <div
                style={ {
                    maxWidth: '40rem',
                    marginBottom: '1rem',
                    color: 'var( --wpds-color-foreground-content-neutral )',
                } }
            >
                <p>
                    This story helps understand how the TabList component
                    behaves under different conditions. The container below
                    (with the dotted red border) can be horizontally
                    resized, and it has a bit of padding to be out of the
                    way of the TabList.
                </p>
                <p>
                    The button will toggle between full width (adding{ ' ' }
                    <code>width: 100%</code>) and the default width.
                </p>
                <p>Try the following:</p>
                <ul>
                    <li>
                        <strong>Small container</strong> that causes tabs to
                        overflow with scroll.
                    </li>
                    <li>
                        <strong>Large container</strong> that exceeds the
                        normal width of the tabs.
                        <ul>
                            <li>
                                <strong>
                                    With <code>width: 100%</code>
                                </strong>{ ' ' }
                                set on the TabList (tabs fill up the space).
                            </li>
                            <li>
                                <strong>
                                    Without <code>width: 100%</code>
                                </strong>{ ' ' }
                                (defaults to <code>auto</code>) set on the
                                TabList (tabs take up space proportional to
                                their content).
                            </li>
                        </ul>
                    </li>
                </ul>
            </div>
            <button
                style={ { marginBottom: '1rem' } }
                onClick={ () => setFullWidth( ! fullWidth ) }
            >
                { fullWidth
                    ? 'Remove width: 100% from TabList'
                    : 'Set width: 100% in TabList' }
            </button>
            <Tabs.Root
                { ...props }
                style={ {
                    ...props.style,
                    width: '20rem',
                    border: '2px dotted red',
                    padding: '1rem',
                    resize: 'horizontal',
                    overflow: 'auto',
                } }
            >
                <Tabs.List
                    style={ {
                        maxWidth: '100%',
                        width: fullWidth ? '100%' : undefined,
                    } }
                >
                    <Tabs.Tab value="tab1">
                        Label with multiple words
                    </Tabs.Tab>
                    <Tabs.Tab value="tab2">Short</Tabs.Tab>
                    <Tabs.Tab value="tab3">
                        Hippopotomonstrosesquippedaliophobia
                    </Tabs.Tab>
                    <Tabs.Tab value="tab4">Tab 4</Tabs.Tab>
                    <Tabs.Tab value="tab5">Tab 5</Tabs.Tab>
                </Tabs.List>

                <Tabs.Panel value="tab1">
                    <ThemedParagraph>Selected tab: Tab 1</ThemedParagraph>
                    <ThemedParagraph>
                        (Label with multiple words)
                    </ThemedParagraph>
                </Tabs.Panel>
                <Tabs.Panel value="tab2">
                    <ThemedParagraph>Selected tab: Tab 2</ThemedParagraph>
                    <ThemedParagraph>(Short)</ThemedParagraph>
                </Tabs.Panel>
                <Tabs.Panel value="tab3">
                    <ThemedParagraph>Selected tab: Tab 3</ThemedParagraph>
                    <ThemedParagraph>
                        (Hippopotomonstrosesquippedaliophobia)
                    </ThemedParagraph>
                </Tabs.Panel>
                <Tabs.Panel value="tab4">
                    <ThemedParagraph>Selected tab: Tab 4</ThemedParagraph>
                </Tabs.Panel>
                <Tabs.Panel value="tab5">
                    <ThemedParagraph>Selected tab: Tab 5</ThemedParagraph>
                </Tabs.Panel>
            </Tabs.Root>
        </div>
    );
};
Vertical story ok
const Vertical = () => <Tabs.Root
    orientation="vertical"
    style={{
        minWidth: '320px',
        display: 'grid',
        gridTemplateColumns: '120px 1fr',
        gap: '24px',
    }} />;
With Disabled Tab story ok
const WithDisabledTab = () => <Tabs.Root defaultValue="tab3">(<>
        <Tabs.List>
            <Tabs.Tab value="tab1" disabled>
                Tab 1
            </Tabs.Tab>
            <Tabs.Tab value="tab2">Tab 2</Tabs.Tab>
            <Tabs.Tab value="tab3">Tab 3</Tabs.Tab>
        </Tabs.List>
        <Tabs.Panel value="tab1">
            <ThemedParagraph>Selected tab: Tab 1</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab2">
            <ThemedParagraph>Selected tab: Tab 2</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab3">
            <ThemedParagraph>Selected tab: Tab 3</ThemedParagraph>
        </Tabs.Panel>
    </>)</Tabs.Root>;
With Tab Icons And Tooltips story ok
const WithTabIconsAndTooltips = () => <Tabs.Root>(<>
        <Tabs.List>
            { tabWithIconsData.map(
                ( { value, label, icon: Icon } ) => (
                    <Tooltip.Root key={ value }>
                        <Tooltip.Trigger
                            aria-label={ label }
                            render={ <Tabs.Tab value={ value } /> }
                        >
                            { /* TODO: potentially refactor with new Icon component */ }
                            <Icon
                                style={ {
                                    width: '20px',
                                    height: '20px',
                                } }
                            />
                        </Tooltip.Trigger>
                        <Tooltip.Popup
                            positioner={
                                <Tooltip.Positioner
                                    align="center"
                                    side="top"
                                />
                            }
                        >
                            { label }
                        </Tooltip.Popup>
                    </Tooltip.Root>
                )
            ) }
        </Tabs.List>
        { tabWithIconsData.map( ( { value, label } ) => (
            <Tabs.Panel value={ value } key={ value }>
                <ThemedParagraph>
                    Selected tab: { label }
                </ThemedParagraph>
            </Tabs.Panel>
        ) ) }
    </>)</Tabs.Root>;
With Panels Always Mounted story ok
const WithPanelsAlwaysMounted = () => <Tabs.Root>(<>
        <Tabs.List>
            <Tabs.Tab value="tab1">Tab 1</Tabs.Tab>
            <Tabs.Tab value="tab2">Tab 2</Tabs.Tab>
            <Tabs.Tab value="tab3">Tab 3</Tabs.Tab>
        </Tabs.List>
        <Tabs.Panel value="tab1" keepMounted>
            <ThemedParagraph>Selected tab: Tab 1</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab2" keepMounted>
            <ThemedParagraph>Selected tab: Tab 2</ThemedParagraph>
        </Tabs.Panel>
        <Tabs.Panel value="tab3" keepMounted>
            <ThemedParagraph>Selected tab: Tab 3</ThemedParagraph>
        </Tabs.Panel>
    </>)</Tabs.Root>;
With Non Focusable Panels story ok
const WithNonFocusablePanels = () => <Tabs.Root>(<>
        <Tabs.List>
            <Tabs.Tab value="tab1">Tab 1</Tabs.Tab>
            <Tabs.Tab value="tab2">Tab 2</Tabs.Tab>
            <Tabs.Tab value="tab3">Tab 3</Tabs.Tab>
        </Tabs.List>
        <Tabs.Panel value="tab1" tabIndex={ -1 }>
            <ThemedParagraph>Selected tab: Tab 1</ThemedParagraph>
            <ThemedParagraph>
                This tabpanel is not focusable, therefore tabbing into
                it will focus its first tabbable child.
            </ThemedParagraph>
            <button>Focus me</button>
        </Tabs.Panel>
        <Tabs.Panel value="tab2" tabIndex={ -1 }>
            <ThemedParagraph>Selected tab: Tab 2</ThemedParagraph>
            <ThemedParagraph>
                This tabpanel is not focusable, therefore tabbing into
                it will focus its first tabbable child.
            </ThemedParagraph>
            <button>Focus me</button>
        </Tabs.Panel>
        <Tabs.Panel value="tab3" tabIndex={ -1 }>
            <ThemedParagraph>Selected tab: Tab 3</ThemedParagraph>
            <ThemedParagraph>
                This tabpanel is not focusable, therefore tabbing into
                it will focus its first tabbable child.
            </ThemedParagraph>
            <button>Focus me</button>
        </Tabs.Panel>
    </>)</Tabs.Root>;
Tabs.List 7 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tabs/index.ts
Groups the individual tab buttons. `Tabs` is a collection of React components that combine to render an [ARIA-compliant tabs pattern](https://www.w3.org/WAI/ARIA/apg/patterns/tabs/).
import { List } from "@wordpress/ui";
Component: ../packages/ui/src/tabs/index.ts::List (react-component-meta)
/**
 * Whether to automatically change the active tab on arrow key focus.
 * Otherwise, tabs will be activated using <kbd>Enter</kbd> or <kbd>Space</kbd> key press.
 */
activateOnFocus?: boolean | undefined = false

/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Whether to loop keyboard focus back to the first item
 * when the end of the list is reached while using the arrow keys.
 */
loopFocus?: boolean | undefined = true

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

/**
 * The visual variant of the tab list.
 */
variant?: "default" | "minimal" = 'default'
Tabs.Tab 7 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tabs/index.ts
An individual interactive tab button that toggles the corresponding panel. `Tabs` is a collection of React components that combine to render an [ARIA-compliant tabs pattern](https://www.w3.org/WAI/ARIA/apg/patterns/tabs/).
import { Tab } from "@wordpress/ui";
Component: ../packages/ui/src/tabs/index.ts::Tab (react-component-meta)
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Whether the Tab is disabled.
 * 
 * If a first Tab on a `<Tabs.List>` is disabled, it won't initially be selected.
 * Instead, the next enabled Tab will be selected.
 * However, it does not work like this during server-side rendering, as it is not known
 * during pre-rendering which Tabs are disabled.
 * To work around it, ensure that `defaultValue` or `value` on `<Tabs.Root>` is set to an enabled Tab's value.
 */
disabled?: boolean | undefined

/**
 * Whether the component renders a native `<button>` element when replacing it
 * via the `render` prop.
 * Set to `false` if the rendered element is not a button (for example, `<div>`).
 */
nativeButton?: boolean | undefined = true

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

/**
 * The value of the Tab.
 */
value: any
Tabs.Panel 6 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tabs/index.ts
A panel displayed when the corresponding tab is active. `Tabs` is a collection of React components that combine to render an [ARIA-compliant tabs pattern](https://www.w3.org/WAI/ARIA/apg/patterns/tabs/).
import { Panel } from "@wordpress/ui";
Component: ../packages/ui/src/tabs/index.ts::Panel (react-component-meta)
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Whether to keep the HTML element in the DOM while the panel is hidden.
 */
keepMounted?: boolean | undefined = false

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

/**
 * The value of the TabPanel. It will be shown when the Tab with the corresponding value is active.
 */
value: any

Text

design-system-components-text · ../packages/ui/src/text/stories/index.story.tsx
A text component for rendering content with predefined typographic variants. Built on design tokens for consistent typography across the UI.
Prop types (react-component-meta) 5 prop types
Component: ../packages/ui/src/text/index.ts::Text
Props:
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

/**
 * The typographic variant to apply, controlling font family, size,
 * line height, and weight.
 */
variant?: "heading-2xl" | "heading-xl" | "heading-lg" | "heading-md" | "heading-sm" | "body-xl" | "body-lg" | "body-md" | "body-sm" = 'body-md'
Imports
import { Stack, Text } from "@wordpress/ui";
Default story ok
const Default = () => <Text variant="body-md">The quick brown fox jumps over the lazy dog.</Text>;
All Variants story ok
Important: Setting the `variant` prop to a `heading` variant will not automatically render a heading element. Use the `render` prop to render a heading element with the appropriate level.
const AllVariants = () => (
    <Stack
        direction="column"
        gap="lg"
        style={ { color: 'var(--wpds-color-foreground-content-neutral)' } }
    >
        { (
            [
                'heading-2xl',
                'heading-xl',
                'heading-lg',
                'heading-md',
                'heading-sm',
                'body-xl',
                'body-lg',
                'body-md',
                'body-sm',
            ] as const
         ).map( ( variant ) => (
            <Stack key={ variant } direction="column" gap="xs">
                <Text variant="heading-sm">{ variant }</Text>
                <Text variant={ variant }>
                    The quick brown fox jumps over the lazy dog.
                </Text>
            </Stack>
        ) ) }
    </Stack>
);
With Render Prop story ok
const WithRenderProp = () => (
    <Stack direction="column" gap="md">
        <Text variant="heading-2xl" render={ <h1 /> }>
            Page Title
        </Text>
        <Text variant="heading-xl" render={ <h2 /> }>
            Section Heading
        </Text>
        <Text variant="body-md" render={ <p /> }>
            A paragraph of body text rendered as a semantic paragraph
            element.
        </Text>
    </Stack>
);

TextareaControl

components-textareacontrol · ../packages/components/src/textarea-control/stories/index.story.tsx
TextareaControls are TextControls that allow for multiple lines of text, and wrap overflow text onto a new line. They are a fixed height and scroll vertically when the cursor reaches the bottom of the field. ```jsx import { TextareaControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyTextareaControl = () => { const [ text, setText ] = useState( '' ); return ( <TextareaControl label="Text" help="Enter some text" value={ text } onChange={ ( value ) => setText( value ) } /> ); }; ```
Prop types (react-component-meta) 7 prop types
Component: ../packages/components/src/textarea-control/index.tsx::default
Props:
/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * A function that receives the new value of the textarea each time it
 * changes.
 */
onChange: (value: string) => void

/**
 * The number of rows the textarea should contain.
 */
rows?: number = 4

/**
 * The current value of the textarea.
 */
value: string
Imports
import { TextareaControl } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ value, setValue ] = useState( '' );

    return (
        <TextareaControl
            label="Text"
            help="Enter some text"
            placeholder="Placeholder"
            value={ value }
            onChange={ ( v ) => {
				setValue( v );
				onChange( v );
			} } />
    );
};

TextControl

components-textcontrol · ../packages/components/src/text-control/stories/index.story.tsx
TextControl components let users enter and edit text. ```jsx import { TextControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyTextControl = () => { const [ className, setClassName ] = useState( '' ); return ( <TextControl label="Additional CSS Class" value={ className } onChange={ ( value ) => setClassName( value ) } /> ); }; ```
Prop types (react-component-meta) 9 prop types
Component: ../packages/components/src/text-control/index.tsx::default
Props:
/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

className?: string

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * A function that receives the value of the input.
 */
onChange: (value: string) => void

/**
 * Type of the input element to render. Defaults to "text".
 */
type?: "number" | "search" | "time" | "text" | "tel" | "url" | "email" | "date" | "datetime-local" | "password" = 'text'

/**
 * The current value of the input.
 */
value: string | number
Imports
import { TextControl } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ value, setValue ] = useState( '' );

    return (
        <TextControl
            placeholder="Placeholder"
            value={ value }
            onChange={ ( v ) => {
				setValue( v );
				onChange( v );
			} } />
    );
};
With Label And Help Text story ok
const WithLabelAndHelpText = () => {
    const [ value, setValue ] = useState( '' );

    return (
        <TextControl
            label="Label Text"
            help="Help text to explain the input."
            value={ value }
            onChange={ ( v ) => {
				setValue( v );
				onChange( v );
			} } />
    );
};

TextHighlight

components-texthighlight · ../packages/components/src/text-highlight/stories/index.story.tsx
Highlights occurrences of a given string within another string of text. Wraps each match with a `<mark>` tag which provides browser default styling. ```jsx import { TextHighlight } from '@wordpress/components'; const MyTextHighlight = () => ( <TextHighlight text="Why do we like Gutenberg? Because Gutenberg is the best!" highlight="Gutenberg" /> ); ```
Prop types (react-component-meta) 2 prop types
Component: ../packages/components/src/text-highlight/index.tsx::default
Props:
/**
 * The string to search for and highlight within the `text`. Case
 * insensitive. Multiple matches.
 */
highlight: string = ''

/**
 * The string of text to be tested for occurrences of then given
 * `highlight`.
 */
text: string = ''
Imports
import { TextHighlight } from "@wordpress/components";
Default story ok
const Default = () => {
    return (
        <TextHighlight
            text="We call the new editor Gutenberg. The entire editing experience has been rebuilt for media rich pages and posts."
            highlight="Gutenberg" />
    );
};

ToggleControl

components-togglecontrol · ../packages/components/src/toggle-control/stories/index.story.tsx
ToggleControl is used to generate a toggle user interface. ```jsx import { ToggleControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const MyToggleControl = () => { const [ value, setValue ] = useState( false ); return ( <ToggleControl label="Fixed Background" checked={ value } onChange={ () => setValue( ( state ) => ! state ) } /> ); }; ```
Prop types (react-component-meta) 7 prop types
Component: ../packages/components/src/toggle-control/index.tsx::default
Props:
/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * If checked is true the toggle will be checked. If checked is false the
 * toggle will be unchecked. If no value is passed the toggle will be
 * unchecked.
 */
checked?: boolean | undefined

className?: string

/**
 * If disabled is true the toggle will be disabled and apply the appropriate
 * styles.
 */
disabled?: boolean | undefined

help?: ReactNode | ((checked: boolean) => ReactNode)

/**
 * The label for the toggle.
 */
label: ReactNode

/**
 * A callback function invoked when the toggle is clicked.
 */
onChange: (value: boolean) => void
Imports
import { ToggleControl } from "@wordpress/components";
Default story ok
const Default = ( {
	onChange,
	...props
} ) => {
	const [ checked, setChecked ] = useState( true );
	return (
		<ToggleControl
			{ ...props }
			checked={ checked }
			onChange={ ( ...changeArgs ) => {
				setChecked( ...changeArgs );
				onChange( ...changeArgs );
			} }
		/>
	);
};
With Help Text story ok
const WithHelpText = ( {
	onChange,
	...props
} ) => {
	const [ checked, setChecked ] = useState( true );
	return (
		<ToggleControl
			{ ...props }
			checked={ checked }
			onChange={ ( ...changeArgs ) => {
				setChecked( ...changeArgs );
				onChange( ...changeArgs );
			} }
		/>
	);
};

ToggleGroupControl

components-togglegroupcontrol · ../packages/components/src/toggle-group-control/stories/index.story.tsx
`ToggleGroupControl` is a form component that lets users choose options represented in horizontal segments. To render options for this control use `ToggleGroupControlOption` component. This component is intended for selecting a single persistent value from a set of options, similar to a how a radio button group would work. If you simply want a toggle to switch between views, use a `TabPanel` instead. Only use this control when you know for sure the labels of items inside won't wrap. For items with longer labels, you can consider a `SelectControl` or a `CustomSelectControl` component instead. ```jsx import { __experimentalToggleGroupControl as ToggleGroupControl, __experimentalToggleGroupControlOption as ToggleGroupControlOption, } from '@wordpress/components'; function Example() { return ( <ToggleGroupControl label="my label" value="vertical" isBlock > <ToggleGroupControlOption value="horizontal" label="Horizontal" /> <ToggleGroupControlOption value="vertical" label="Vertical" /> </ToggleGroupControl> ); } ```
Prop types (react-component-meta) 13 prop types
Component: ../packages/components/src/toggle-group-control/index.ts::ToggleGroupControl
Props:
/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

/**
 * The options to render in the `ToggleGroupControl`, using either the `ToggleGroupControlOption` or
 * `ToggleGroupControlOptionIcon` components.
 */
children: ReactNode

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * Determines if segments should be rendered with equal widths.
 */
isAdaptiveWidth?: boolean | undefined = false

/**
 * Renders `ToggleGroupControl` as a (CSS) block element, spanning the entire width of
 * the available space. This is the recommended style when the options are text-based and not icons.
 */
isBlock?: boolean | undefined = false

/**
 * Whether an option can be deselected by clicking it again.
 */
isDeselectable?: boolean | undefined = false

/**
 * Label for the control.
 */
label: string

/**
 * Callback when a segment is selected.
 */
onChange?: (value: string | number | undefined) => void

/**
 * The size variant of the control.
 */
size?: "default" | "__unstable-large"

/**
 * The selected value.
 */
value?: string | number | undefined
Imports
import { ToggleGroupControl, ToggleGroupControlOption, ToggleGroupControlOptionIcon } from "@wordpress/components";
Default story ok
const Default = ( {
	onChange,
	...props
} ) => {
	const [ value, setValue ] =
		useState< ToggleGroupControlProps[ 'value' ] >();

	return (
		<ToggleGroupControl
			{ ...props }
			onChange={ ( ...changeArgs ) => {
				setValue( ...changeArgs );
				onChange?.( ...changeArgs );
			} }
			value={ value }
		/>
	);
};
With Tooltip story ok
A tooltip can be shown for each option by enabling the `showTooltip` prop. The `aria-label` will be used in the tooltip if provided. Otherwise, the `label` will be used.
const WithTooltip = ( {
	onChange,
	...props
} ) => {
	const [ value, setValue ] =
		useState< ToggleGroupControlProps[ 'value' ] >();

	return (
		<ToggleGroupControl
			{ ...props }
			onChange={ ( ...changeArgs ) => {
				setValue( ...changeArgs );
				onChange?.( ...changeArgs );
			} }
			value={ value }
		/>
	);
};
With Icons story ok
The `ToggleGroupControlOptionIcon` component can be used for icon options. A `label` is required on each option for accessibility, which will be shown in a tooltip.
const WithIcons = ( {
	onChange,
	...props
} ) => {
	const [ value, setValue ] =
		useState< ToggleGroupControlProps[ 'value' ] >();

	return (
		<ToggleGroupControl
			{ ...props }
			onChange={ ( ...changeArgs ) => {
				setValue( ...changeArgs );
				onChange?.( ...changeArgs );
			} }
			value={ value }
		/>
	);
};
Deselectable story ok
When the `isDeselectable` prop is true, the option can be deselected by clicking on it again.
const Deselectable = ( {
	onChange,
	...props
} ) => {
	const [ value, setValue ] =
		useState< ToggleGroupControlProps[ 'value' ] >();

	return (
		<ToggleGroupControl
			{ ...props }
			onChange={ ( ...changeArgs ) => {
				setValue( ...changeArgs );
				onChange?.( ...changeArgs );
			} }
			value={ value }
		/>
	);
};
ToggleGroupControlOption 3 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/toggle-group-control/index.ts
`ToggleGroupControlOption` is a form component and is meant to be used as a child of `ToggleGroupControl`. ```jsx import { __experimentalToggleGroupControl as ToggleGroupControl, __experimentalToggleGroupControlOption as ToggleGroupControlOption, } from '@wordpress/components'; function Example() { return ( <ToggleGroupControl label="my label" value="vertical" isBlock > <ToggleGroupControlOption value="horizontal" label="Horizontal" /> <ToggleGroupControlOption value="vertical" label="Vertical" /> </ToggleGroupControl> ); } ```
import { ToggleGroupControlOption } from "@wordpress/components";
Component: ../packages/components/src/toggle-group-control/index.ts::ToggleGroupControlOption (react-component-meta)
/**
 * Label for the option. If needed, the `aria-label` prop can be used in addition
 * to specify a different label for assistive technologies.
 */
label: string

/**
 * Whether to display a Tooltip for the control option. If set to `true`, the tooltip will
 * show the aria-label or the label prop text.
 */
showTooltip?: boolean | undefined = false

value: string | number
ToggleGroupControlOptionIcon 3 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/toggle-group-control/index.ts
`ToggleGroupControlOptionIcon` is a form component which is meant to be used as a child of `ToggleGroupControl` and displays an icon. ```jsx import { __experimentalToggleGroupControl as ToggleGroupControl, __experimentalToggleGroupControlOptionIcon as ToggleGroupControlOptionIcon, from '@wordpress/components'; import { formatLowercase, formatUppercase } from '@wordpress/icons'; function Example() { return ( <ToggleGroupControl> <ToggleGroupControlOptionIcon value="uppercase" label="Uppercase" icon={ formatUppercase } /> <ToggleGroupControlOptionIcon value="lowercase" label="Lowercase" icon={ formatLowercase } /> </ToggleGroupControl> ); } ```
import { ToggleGroupControlOptionIcon } from "@wordpress/components";
Component: ../packages/components/src/toggle-group-control/index.ts::ToggleGroupControlOptionIcon (react-component-meta)
/**
 * Icon displayed as the content of the option. Usually one of the icons from
 * the `@wordpress/icons` package, or a custom React `<svg>` icon.
 */
icon: Element

/**
 * The text to accessibly label the icon option. Will also be shown in a tooltip.
 */
label: string

value: string | number

Tooltip.Root

design-system-components-tooltip · ../packages/ui/src/tooltip/stories/index.story.tsx
`Tooltip` is used to visually show the label of an icon button, or other such interactive controls that don't have a visual text label. Tooltip popups are visual-only and not exposed to assistive technologies. The trigger's accessible name (e.g. `aria-label`) is the source of truth for screen reader users. Tooltips are not available on touch devices, and thus should not be used for infotips, descriptions, or dynamic status messages.
see: {@link https://wordpress.github.io/gutenberg/?path=/docs/design-system-components-tooltip-usage-guidelines--docs Usage Guidelines}see: {@link https://wordpress.github.io/gutenberg/?path=/docs/design-system-components-iconbutton--docs IconButton}
Prop types (react-component-meta) 2 prop types
Component: ../packages/ui/src/tooltip/index.ts::Root
Props:
/**
 * The content of the tooltip.
 * This can be a regular React node or a render function that receives the `payload` of the active trigger.
 */
children?: ReactNode | PayloadChildRenderFunction<unknown>

/**
 * Whether the tooltip is disabled.
 */
disabled?: boolean | undefined = false
Imports
import { Icon, Popup, Portal, Positioner, Provider, Root, Trigger } from "@wordpress/ui";
Default story ok
const Default = () => <Tooltip.Root>(<>
        <Tooltip.Trigger aria-label="Save">💾</Tooltip.Trigger>
        <Tooltip.Popup>Save</Tooltip.Popup>
    </>)</Tooltip.Root>;
Disabled story ok
The `disabled` prop prevents the tooltip from showing, and can be used to show the tooltip conditionally without rendering the underlying react component conditionally (which could cause reconciliation issues).
const Disabled = () => <Tooltip.Root disabled />;
Positioning story ok
Customize where the tooltip appears relative to the trigger by passing a `<Tooltip.Positioner />` element to `Tooltip.Popup`'s `positioner` prop. `Tooltip.Positioner` accepts `side`, `align`, `sideOffset`, and collision settings; when `positioner` is omitted, the tooltip uses the defaults (`side="top"`, `align="center"`, `sideOffset={ 4 }`).
const Positioning = () => (
    <div
        style={ {
            display: 'flex',
            gap: '2rem',
            padding: '4rem',
            justifyContent: 'center',
        } }
    >
        <Tooltip.Root>
            <Tooltip.Trigger aria-label="Up">⬆️</Tooltip.Trigger>
            <Tooltip.Popup positioner={ <Tooltip.Positioner side="top" /> }>
                Up
            </Tooltip.Popup>
        </Tooltip.Root>

        <Tooltip.Root>
            <Tooltip.Trigger aria-label="Forward">➡️</Tooltip.Trigger>
            <Tooltip.Popup
                positioner={ <Tooltip.Positioner side="right" /> }
            >
                Forward
            </Tooltip.Popup>
        </Tooltip.Root>

        <Tooltip.Root>
            <Tooltip.Trigger aria-label="Down">⬇️</Tooltip.Trigger>
            <Tooltip.Popup
                positioner={ <Tooltip.Positioner side="bottom" /> }
            >
                Down
            </Tooltip.Popup>
        </Tooltip.Root>

        <Tooltip.Root>
            <Tooltip.Trigger aria-label="Back">⬅️</Tooltip.Trigger>
            <Tooltip.Popup
                positioner={ <Tooltip.Positioner side="left" /> }
            >
                Back
            </Tooltip.Popup>
        </Tooltip.Root>
    </div>
);
With Custom Positioner story ok
Beyond `side`, `Tooltip.Positioner` accepts the rest of the positioner surface — `align`, `alignOffset`, `sideOffset`, collision settings, and more — for fine-grained placement.
const WithCustomPositioner = () => <Tooltip.Root>(<>
        <Tooltip.Trigger aria-label="Save">💾</Tooltip.Trigger>
        <Tooltip.Popup
            positioner={
                <Tooltip.Positioner
                    side="right"
                    align="start"
                    sideOffset={ 16 }
                />
            }
        >
            Save
        </Tooltip.Popup>
    </>)</Tooltip.Root>;
With Custom z-index story ok
Popovers in Gutenberg are managed with explicit z-index values, which can create situations where a tooltip renders below another popover when you want it above. The `--wp-ui-tooltip-z-index` CSS variable controls the z-index of the tooltip's positioner. Override it either: - **Globally**, by setting the variable on `:root` or `body` (raises every tooltip in the page), or - **Per instance**, by passing a `Tooltip.Portal` with a `style` (or `className`) to `Tooltip.Popup`'s `portal` prop. The variable cascades from the portal wrapper to everything rendered inside it. This story demonstrates the per-instance approach.
const WithCustomZIndex = () => <Tooltip.Root>(<>
        <Tooltip.Trigger aria-label="Save">💾</Tooltip.Trigger>
        <Tooltip.Popup
            portal={
                <Tooltip.Portal
                    style={ { '--wp-ui-tooltip-z-index': '9999' } }
                />
            }
        >
            Save
        </Tooltip.Popup>
    </>)</Tooltip.Root>;
With Provider story ok
Use `Tooltip.Provider` to control the delay before tooltips appear. This is useful when you have multiple tooltips and want them to share the same delay configuration.
const WithProvider = () => (
    <Tooltip.Provider delay={ 0 }>
        <div style={ { display: 'flex', gap: '1rem' } }>
            <Tooltip.Root>
                <Tooltip.Trigger aria-label="Bold">
                    <Icon icon={ formatBold } />
                </Tooltip.Trigger>
                <Tooltip.Popup>Bold</Tooltip.Popup>
            </Tooltip.Root>

            <Tooltip.Root>
                <Tooltip.Trigger aria-label="Italic">
                    <Icon icon={ formatItalic } />
                </Tooltip.Trigger>
                <Tooltip.Popup>Italic</Tooltip.Popup>
            </Tooltip.Root>
        </div>
    </Tooltip.Provider>
);
Tooltip.Provider 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tooltip/index.ts
import { Provider } from "@wordpress/ui";
Component: ../packages/ui/src/tooltip/index.ts::Provider (react-component-meta)
children?: ReactNode

/**
 * How long to wait before closing a tooltip. Specified in milliseconds.
 */
closeDelay?: number

/**
 * How long to wait before opening a tooltip. Specified in milliseconds.
 */
delay?: number

/**
 * Another tooltip will open instantly if the previous tooltip
 * is closed within this timeout. Specified in milliseconds.
 */
timeout?: number = 400
Tooltip.Trigger 4 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tooltip/index.ts
import { Trigger } from "@wordpress/ui";
Component: ../packages/ui/src/tooltip/index.ts::Trigger (react-component-meta)
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Tooltip.Popup 6 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tooltip/index.ts
import { Popup } from "@wordpress/ui";
Component: ../packages/ui/src/tooltip/index.ts::Popup (react-component-meta)
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Optional portal element, typically `<Tooltip.Portal />` with custom
 * `container`. When omitted, `Tooltip.Popup` uses `Tooltip.Portal` with
 * default props. Do not pass `children` on the portal element; they would
 * be ignored.
 */
portal?: ReactElement<Omit<PortalProps, "children">, string | JSXElementConstructor<any>>

/**
 * Optional positioner element, typically `<Tooltip.Positioner />` with
 * custom positioning props (`side`, `align`, `sideOffset`, collision
 * settings, etc.). When omitted, `Tooltip.Popup` uses `Tooltip.Positioner`
 * with default props. Do not pass `children` on the positioner element;
 * they would be ignored.
 */
positioner?: ReactElement<Omit<PositionerProps, "children">, string | JSXElementConstructor<any>>

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Tooltip.Positioner 15 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tooltip/index.ts
Used to apply custom positioning to `Tooltip`'s floating content.
import { Positioner } from "@wordpress/ui";
Component: ../packages/ui/src/tooltip/index.ts::Positioner (react-component-meta)
/**
 * How to align the popup relative to the specified side.
 */
align?: "center" | "end" | "start" = 'center'

/**
 * Additional offset along the alignment axis in pixels.
 * Also accepts a function that returns the offset to read the dimensions of the anchor
 * and positioner elements, along with its side and alignment.
 * 
 * The function takes a `data` object parameter with the following properties:
 * - `data.anchor`: the dimensions of the anchor element with properties `width` and `height`.
 * - `data.positioner`: the dimensions of the positioner element with properties `width` and `height`.
 * - `data.side`: which side of the anchor element the positioner is aligned against.
 * - `data.align`: how the positioner is aligned relative to the specified side.
 */
alignOffset?: number | OffsetFunction | undefined = 0

/**
 * An element to position the popup against.
 * By default, the popup will be positioned against the trigger.
 */
anchor?: Element | VirtualElement | RefObject<Element | null> | (() => Element | VirtualElement | null) | null | undefined

/**
 * Minimum distance to maintain between the arrow and the edges of the popup.
 * 
 * Use it to prevent the arrow element from hanging out of the rounded corners of a popup.
 */
arrowPadding?: number = 5

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Determines how to handle collisions when positioning the popup.
 * 
 * `side` controls overflow on the preferred placement axis (`top`/`bottom` or `left`/`right`):
 * - `'flip'`: keep the requested side when it fits; otherwise try the opposite side
 *   (`top` and `bottom`, or `left` and `right`).
 * - `'shift'`: never change side; keep the requested side and move the popup within
 *   the clipping boundary so it stays visible.
 * - `'none'`: do not correct side-axis overflow.
 * 
 * `align` controls overflow on the alignment axis (`start`/`center`/`end`):
 * - `'flip'`: keep side, but swap `start` and `end` when the requested alignment overflows.
 * - `'shift'`: keep side and requested alignment, then nudge the popup along the
 *   alignment axis to fit.
 * - `'none'`: do not correct alignment-axis overflow.
 * 
 * `fallbackAxisSide` controls fallback behavior on the perpendicular axis when the
 * preferred axis cannot fit:
 * - `'start'`: allow perpendicular fallback and try the logical start side first
 *   (`top` before `bottom`, or `left` before `right` in LTR).
 * - `'end'`: allow perpendicular fallback and try the logical end side first
 *   (`bottom` before `top`, or `right` before `left` in LTR).
 * - `'none'`: do not fallback to the perpendicular axis.
 * 
 * When `side` is `'shift'`, explicitly setting `align` only supports `'shift'` or `'none'`.
 * If `align` is omitted, it defaults to `'flip'`.
 */
collisionAvoidance?: CollisionAvoidance | undefined

/**
 * An element or a rectangle that delimits the area that the popup is confined to.
 */
collisionBoundary?: Boundary | undefined = 'clipping-ancestors'

/**
 * Additional space to maintain from the edge of the collision boundary.
 */
collisionPadding?: Padding | undefined = 5

/**
 * Whether to disable the popup from tracking any layout shift of its positioning anchor.
 */
disableAnchorTracking?: boolean | undefined = false

/**
 * Determines which CSS `position` property to use.
 */
positionMethod?: "fixed" | "absolute" = 'absolute'

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * Which side of the anchor element to align the popup against.
 * May automatically change to avoid collisions.
 */
side?: "left" | "right" | "bottom" | "top" | "inline-end" | "inline-start" = 'top'

/**
 * Distance between the anchor and the popup in pixels.
 * Also accepts a function that returns the distance to read the dimensions of the anchor
 * and positioner elements, along with its side and alignment.
 * 
 * The function takes a `data` object parameter with the following properties:
 * - `data.anchor`: the dimensions of the anchor element with properties `width` and `height`.
 * - `data.positioner`: the dimensions of the positioner element with properties `width` and `height`.
 * - `data.side`: which side of the anchor element the positioner is aligned against.
 * - `data.align`: how the positioner is aligned relative to the specified side.
 */
sideOffset?: number | OffsetFunction | undefined = 4

/**
 * Whether to maintain the popup in the viewport after
 * the anchor element was scrolled out of view.
 */
sticky?: boolean | undefined = false

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Tooltip.Portal 5 prop types
/home/runner/work/gutenberg/gutenberg/packages/ui/src/tooltip/index.ts
Used to apply custom portal behavior to `Tooltip`'s floating content. `container` defaults to the `@wordpress/ui` compat overlay slot.
import { Portal } from "@wordpress/ui";
Component: ../packages/ui/src/tooltip/index.ts::Portal (react-component-meta)
/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * A parent element to render the portal element into.
 */
container?: HTMLElement | ShadowRoot | RefObject<HTMLElement | ShadowRoot | null> | null | undefined

/**
 * Whether to keep the portal mounted in the DOM while the popup is hidden.
 */
keepMounted?: boolean | undefined = false

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties

TreeGrid

components-treegrid · ../packages/components/src/tree-grid/stories/index.story.tsx
`TreeGrid` is used to create a tree hierarchy. It is not a visually styled component, but instead helps with adding keyboard navigation and roving tab index behaviors to tree grid structures. A tree grid is a hierarchical 2 dimensional UI component, for example it could be used to implement a file system browser. A tree grid allows the user to navigate using arrow keys. Up/down to navigate vertically across rows, and left/right to navigate horizontally between focusables in a row. The `TreeGrid` renders both a `table` and `tbody` element, and is intended to be used with `TreeGridRow` (`tr`) and `TreeGridCell` (`td`) to build out a grid. ```jsx function TreeMenu() { return ( <TreeGrid> <TreeGridRow level={ 1 } positionInSet={ 1 } setSize={ 2 }> <TreeGridCell> { ( props ) => ( <Button onClick={ onSelect } { ...props }>Select</Button> ) } </TreeGridCell> <TreeGridCell> { ( props ) => ( <Button onClick={ onMove } { ...props }>Move</Button> ) } </TreeGridCell> </TreeGridRow> <TreeGridRow level={ 1 } positionInSet={ 2 } setSize={ 2 }> <TreeGridCell> { ( props ) => ( <Button onClick={ onSelect } { ...props }>Select</Button> ) } </TreeGridCell> <TreeGridCell> { ( props ) => ( <Button onClick={ onMove } { ...props }>Move</Button> ) } </TreeGridCell> </TreeGridRow> <TreeGridRow level={ 2 } positionInSet={ 1 } setSize={ 1 }> <TreeGridCell> { ( props ) => ( <Button onClick={ onSelect } { ...props }>Select</Button> ) } </TreeGridCell> <TreeGridCell> { ( props ) => ( <Button onClick={ onMove } { ...props }>Move</Button> ) } </TreeGridCell> </TreeGridRow> </TreeGrid> ); } ```
see: {@link https://www.w3.org/TR/wai-aria-practices/examples/treegrid/treegrid-1.html}
Prop types (react-component-meta) 5 prop types
Component: ../packages/components/src/tree-grid/index.tsx::default
Props:
/**
 * Label to use for the element with the `application` role.
 */
applicationAriaLabel?: string

/**
 * The children to be rendered in the tree grid.
 */
children: ReactNode

/**
 * Callback to fire when row is collapsed.
 */
onCollapseRow?: (row: HTMLElement) => void = () => {}

/**
 * Callback to fire when row is expanded.
 */
onExpandRow?: (row: HTMLElement) => void = () => {}

/**
 * Callback that fires when focus is shifted from one row to another via
 * the Up and Down keys. Callback is also fired on Home and End keys which
 * move focus from the beginning row to the end row.
 * 
 * The callback is passed the event, the start row element that the focus was on
 * originally, and the destination row element after the focus has moved.
 */
onFocusRow?: (event: KeyboardEvent<HTMLTableElement>, startRow: HTMLElement, destinationRow: HTMLElement) => void = () => {}
Imports
import { Button, InputControl, TreeGrid, TreeGridCell, TreeGridRow } from "@wordpress/components";
import { Fragment } from "@wordpress/element";
Default story ok
const Default = () => <TreeGrid onExpandRow={fn()} onCollapseRow={fn()} onFocusRow={fn()}><Rows items={ groceries } /></TreeGrid>;
TreeGridRow 5 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/tree-grid/index.tsx
`TreeGridRow` is used to create a tree hierarchy. It is not a visually styled component, but instead helps with adding keyboard navigation and roving tab index behaviors to tree grid structures.
see: {@link https://www.w3.org/TR/wai-aria-practices/examples/treegrid/treegrid-1.html}
import { TreeGridRow } from "@wordpress/components";
Component: ../packages/components/src/tree-grid/index.tsx::TreeGridRow (react-component-meta)
/**
 * The children to be rendered in the row.
 */
children: ReactNode

/**
 * An optional value that designates whether a row is expanded or collapsed.
 * Currently this value only sets the correct aria-expanded property on a row,
 * it has no other built-in behavior.
 * 
 * If there is a need to implement `aria-expanded` elsewhere in the row, cell,
 * or element within a cell, you may pass `isExpanded={ undefined }`.
 * In order for keyboard navigation to continue working, add the
 * `data-expanded` attribute with either `true`/`false`. This allows the
 * `TreeGrid` component to still manage keyboard interactions while allowing
 * the `aria-expanded` attribute to be placed elsewhere.
 */
isExpanded?: boolean | undefined

/**
 * An integer value designating the level in the hierarchical tree structure.
 * Counting starts at 1. A value of `1` indicates the root level of the structure.
 */
level: number

/**
 * An integer value that represents the position in the set.
 * A set is the count of elements at a specific level. Counting starts at 1.
 */
positionInSet: number

/**
 * An integer value that represents the total number of items in the set,
 * at this specific level of the hierarchy.
 */
setSize: number
TreeGridCell 2 prop types
/home/runner/work/gutenberg/gutenberg/packages/components/src/tree-grid/index.tsx
`TreeGridCell` is used to create a tree hierarchy. It is not a visually styled component, but instead helps with adding keyboard navigation and roving tab index behaviors to tree grid structures.
see: {@link https://www.w3.org/TR/wai-aria-practices/examples/treegrid/treegrid-1.html}
import { TreeGridCell } from "@wordpress/components";
Component: ../packages/components/src/tree-grid/index.tsx::TreeGridCell (react-component-meta)
/**
 * A render function that receives the props necessary to make it participate in the
 * roving tabindex. Any extra props will also be passed through to this function.
 * 
 * Props passed as an argument to the render prop must be passed to the child
 * focusable component/element within the cell. If a component is used, it must
 * correctly handle the `onFocus`, `tabIndex`, and `ref` props, passing these to the
 * element it renders. These props are used to handle the roving tabindex functionality
 * of the tree grid.
 * 
 * ```jsx
 * <TreeGridCell>
 * 	{ ( props ) => (
 * 		<Button onClick={ doSomething } { ...props }>
 * 			Do something
 * 		</Button>
 * 	) }
 * </TreeGridCell>
 * ```
 */
children?: (props: RovingTabIndexItemPassThruProps) => Element

/**
 * Render `children` without wrapping it in a `TreeGridItem` component.
 * This means that `children` will not participate in the roving tabindex.
 */
withoutGridItem?: false = false

TreeSelect

components-treeselect · ../packages/components/src/tree-select/stories/index.story.tsx
Generates a hierarchical select input. ```jsx import { useState } from 'react'; import { TreeSelect } from '@wordpress/components'; const MyTreeSelect = () => { const [ page, setPage ] = useState( 'p21' ); return ( <TreeSelect label="Parent page" noOptionLabel="No parent page" onChange={ ( newPage ) => setPage( newPage ) } selectedId={ page } tree={ [ { name: 'Page 1', id: 'p1', children: [ { name: 'Descend 1 of page 1', id: 'p11' }, { name: 'Descend 2 of page 1', id: 'p12' }, ], }, { name: 'Page 2', id: 'p2', children: [ { name: 'Descend 1 of page 2', id: 'p21', children: [ { name: 'Descend 1 of Descend 1 of page 2', id: 'p211', }, ], }, ], }, ] } /> ); } ```
Prop types (react-component-meta) 19 prop types
Component: ../packages/components/src/tree-select/index.tsx::default
Props:
/**
 * Deprecated. Use `__next40pxDefaultSize` instead.
 */
__next36pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Start opting into the new margin-free styles that will become the default in a future version.
 */
__nextHasNoMarginBottom?: boolean | undefined

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

/**
 * As an alternative to the `options` prop, `optgroup`s and `options` can be
 * passed in as `children` for more customizability.
 */
children?: ReactNode

/**
 * If true, the `input` will be disabled.
 */
disabled?: boolean | undefined = false

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * The position of the label.
 */
labelPosition?: "top" | "bottom" | "side" | "edge" = 'top'

/**
 * If this property is added, an option will be added with this label to represent empty selection.
 */
noOptionLabel?: string

/**
 * A function that receives the value of the new option that is being selected as input.
 */
onChange?: (value: string, extra?: { event?: ChangeEvent<HTMLSelectElement> | undefined; } | undefined) => void

/**
 * An array of option property objects to be rendered,
 * each with a `label` and `value` property, as well as any other
 * `<option>` attributes.
 */
options?: readonly ({ label: string; value: string; } & Omit<OptionHTMLAttributes<HTMLOptionElement>, "label" | "value">)[]

/**
 * Renders an element on the left side of the input.
 * 
 * By default, the prefix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlPrefixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlPrefixWrapper as InputControlPrefixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   prefix={<InputControlPrefixWrapper>@</InputControlPrefixWrapper>}
 * />
 * ```
 */
prefix?: ReactNode

/**
 * The id of the currently selected node.
 */
selectedId?: string

/**
 * Adjusts the size of the input.
 */
size?: "small" | "default" | "compact" | "__unstable-large" = 'default'

/**
 * Renders an element on the right side of the input.
 * 
 * By default, the suffix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlSuffixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlSuffixWrapper as InputControlSuffixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   suffix={<InputControlSuffixWrapper>%</InputControlSuffixWrapper>}
 * />
 * ```
 */
suffix?: ReactNode

/**
 * An array containing the tree objects with the possible nodes the user can select.
 */
tree?: Tree[] = []

/**
 * The style variant of the control.
 */
variant?: "default" | "minimal" = 'default'
Imports
import { TreeSelect } from "@wordpress/components";
Default story ok
const Default = ( props ) => {
	const [ selection, setSelection ] =
		useState< ComponentProps< typeof TreeSelect >[ 'selectedId' ] >();

	return (
		<TreeSelect
			{ ...props }
			onChange={ setSelection }
			selectedId={ selection }
		/>
	);
};

Truncate

components-truncate · ../packages/components/src/truncate/stories/index.story.tsx
`Truncate` is a typography primitive that trims text content. For almost all cases, it is recommended that `Text`, `Heading`, or `Subheading` is used to render text content. However,`Truncate` is available for custom implementations. ```jsx import { __experimentalTruncate as Truncate } from `@wordpress/components`; function Example() { return ( <Truncate> Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc ex neque, vulputate a diam et, luctus convallis lacus. Vestibulum ac mollis mi. Morbi id elementum massa. </Truncate> ); } ```
Prop types (react-component-meta) 6 prop types
Component: ../packages/components/src/truncate/index.ts::Truncate
Props:
/**
 * The HTML element or React component to render the component as.
 */
as?: "symbol" | "object" | "a" | "abbr" | "address" | "area" | "article" | "aside" | "audio" | "b" | "base" | "bdi" | "bdo" | "big" | "blockquote" | "body" | "br" | "button" | "canvas" | "caption" | "center" | "cite" | "code" | "col" | "colgroup" | "data" | "datalist" | "dd" | "del" | "details" | "dfn" | "dialog" | "div" | "dl" | "dt" | "em" | "embed" | "fieldset" | "figcaption" | "figure" | "footer" | "form" | "h1" | "h2" | "h3" | "h4" | "h5" | "h6" | "head" | "header" | "hgroup" | "hr" | "html" | "i" | "iframe" | "img" | "input" | "ins" | "kbd" | "keygen" | "label" | "legend" | "li" | "link" | "main" | "map" | "mark" | "menu" | "menuitem" | "meta" | "meter" | "nav" | "noindex" | "noscript" | "ol" | "optgroup" | "option" | "output" | "p" | "param" | "picture" | "pre" | "progress" | "q" | "rp" | "rt" | "ruby" | "s" | "samp" | "search" | "slot" | "script" | "section" | "select" | "small" | "source" | "span" | "strong" | "style" | "sub" | "summary" | "sup" | "table" | "template" | "tbody" | "td" | "textarea" | "tfoot" | "th" | "thead" | "time" | "title" | "tr" | "track" | "u" | "ul" | "var" | "video" | "wbr" | "webview" | "svg" | "animate" | "animateMotion" | "animateTransform" | "circle" | "clipPath" | "defs" | "desc" | "ellipse" | "feBlend" | "feColorMatrix" | "feComponentTransfer" | "feComposite" | "feConvolveMatrix" | "feDiffuseLighting" | "feDisplacementMap" | "feDistantLight" | "feDropShadow" | "feFlood" | "feFuncA" | "feFuncB" | "feFuncG" | "feFuncR" | "feGaussianBlur" | "feImage" | "feMerge" | "feMergeNode" | "feMorphology" | "feOffset" | "fePointLight" | "feSpecularLighting" | "feSpotLight" | "feTile" | "feTurbulence" | "filter" | "foreignObject" | "g" | "image" | "line" | "linearGradient" | "marker" | "mask" | "metadata" | "mpath" | "path" | "pattern" | "polygon" | "polyline" | "radialGradient" | "rect" | "set" | "stop" | "switch" | "text" | "textPath" | "tspan" | "use" | "view"

/**
 * The children elements.
 * 
 * Note: text truncation will be attempted only if the `children` are either
 * of type `string` or `number`. In any other scenarios, the component will
 * not attempt to truncate the text, and will pass through the `children`.
 */
children: ReactNode

/**
 * The ellipsis string when truncating the text by the `limit` prop's value.
 */
ellipsis?: string = '…'

/**
 * Determines where to truncate.  For example, we can truncate text right in
 * the middle. To do this, we need to set `ellipsizeMode` to `middle` and a
 * text `limit`.
 * 
 * * `auto`: Trims content at the end automatically without a `limit`.
 * * `head`: Trims content at the beginning. Requires a `limit`.
 * * `middle`: Trims content in the middle. Requires a `limit`.
 * * `tail`: Trims content at the end. Requires a `limit`.
 */
ellipsizeMode?: "head" | "none" | "middle" | "auto" | "tail" = 'auto'

/**
 * Determines the max number of characters to be displayed before the rest
 * of the text gets truncated. Requires `ellipsizeMode` to assume values
 * different from `auto` and `none`.
 */
limit?: number = 0

/**
 * Clamps the text content to the specified `numberOfLines`, adding an
 * ellipsis at the end. Note: this feature ignores the value of the
 * `ellipsis` prop and always displays the default `…` ellipsis.
 */
numberOfLines?: number = 0
Imports
import { Truncate } from "@wordpress/components";
Default story ok
const Default = () => {
    return <Truncate numberOfLines={2}>{defaultText}</Truncate>;
};
Truncate by character count story ok
const CharacterCount = () => {
    return <Truncate limit={23} ellipsizeMode="tail" ellipsis="[---]">{defaultText}</Truncate>;
};

UnitControl

components-unitcontrol · ../packages/components/src/unit-control/stories/index.story.tsx
`UnitControl` allows the user to set a numeric quantity as well as a unit (e.g. `px`). ```jsx import { __experimentalUnitControl as UnitControl } from '@wordpress/components'; import { useState } from '@wordpress/element'; const Example = () => { const [ value, setValue ] = useState( '10px' ); return <UnitControl onChange={ setValue } value={ value } />; }; ```
Prop types (react-component-meta) 38 prop types
Component: ../packages/components/src/unit-control/index.tsx::UnitControl
Props:
/**
 * Deprecated. Use `__next40pxDefaultSize` instead.
 */
__next36pxDefaultSize?: boolean | undefined = false

/**
 * Start opting into the larger default height that will become the default size in a future version.
 */
__next40pxDefaultSize?: boolean | undefined

/**
 * Do not throw a warning for the deprecated 36px default size.
 * For internal components of other components that already throw the warning.
 */
__shouldNotWarnDeprecated36pxSize?: boolean | undefined

__unstableInputWidth?: Width<string | number> | undefined

__unstableStateReducer?: StateReducer

/**
 * If true, the `input` will be disabled.
 */
disabled?: boolean | undefined = false

/**
 * If `true`, the unit `<select>` is hidden.
 */
disableUnits?: boolean | undefined = false

/**
 * Determines the drag axis.
 */
dragDirection?: "s" | "n" | "e" | "w" = 'n'

/**
 * If `isDragEnabled` is true, this controls the amount of `px` to have been dragged before
 * the drag gesture is actually triggered.
 */
dragThreshold?: number = 10

/**
 * Additional description for the control.
 * 
 * Only use for meaningful description or instructions for the control. An element containing the description will be programmatically associated to the BaseControl by the means of an `aria-describedby` attribute.
 */
help?: ReactNode

/**
 * If true, the default `input` HTML arrows will be hidden.
 */
hideHTMLArrows?: boolean | undefined = false

/**
 * If true, the label will only be visible to screen readers.
 */
hideLabelFromVision?: boolean | undefined = false

/**
 * If true, enables mouse drag gestures.
 */
isDragEnabled?: boolean | undefined = true

/**
 * If true, the `ENTER` key press is required in order to trigger an `onChange`.
 * If enabled, a change is also triggered when tabbing away (`onBlur`).
 */
isPressEnterToChange?: boolean | undefined = false

/**
 * If `true`, and the selected unit provides a `default` value, this value is set
 * when changing units.
 */
isResetValueOnUnitChange?: boolean | undefined = false

/**
 * If true, pressing `UP` or `DOWN` along with the `SHIFT` key will increment the
 * value by the `shiftStep` value.
 */
isShiftStepEnabled?: boolean | undefined = true

/**
 * Whether the control can be focused via keyboard navigation.
 */
isUnitSelectTabbable?: boolean | undefined = true

/**
 * If this property is added, a label will be generated using label property as the content.
 */
label?: ReactNode

/**
 * The position of the label.
 */
labelPosition?: "top" | "bottom" | "side" | "edge" = 'top'

/**
 * The maximum `value` allowed.
 */
max?: number = Infinity

/**
 * The minimum `value` allowed.
 */
min?: number = -Infinity

/**
 * Callback when either the quantity or the unit inputs lose focus.
 */
onBlur?: FocusEventHandler<HTMLInputElement> & FocusEventHandler<HTMLInputElement | HTMLSelectElement>

/**
 * A callback function invoked when the value is changed.
 * A function that receives the value of the input.
 */
onChange?: UnitControlOnChangeCallback & InputChangeCallback<{}>

onDrag?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragEnd?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

onDragStart?: (dragProps: Omit<FullGestureState<"drag">, "event"> & { event: unknown; }) => void

/**
 * Callback when either the quantity or the unit inputs gains focus.
 */
onFocus?: FocusEventHandler<HTMLInputElement> & FocusEventHandler<HTMLInputElement | HTMLSelectElement>

/**
 * Callback when the `unit` changes.
 */
onUnitChange?: UnitControlOnChangeCallback

onValidate?: (nextValue: string, event?: SyntheticEvent<HTMLInputElement, Event> | undefined) => void

/**
 * Renders an element on the left side of the input.
 * 
 * By default, the prefix is aligned with the edge of the input border, with no padding.
 * If you want to apply standard padding in accordance with the size variant, wrap the element in
 * the provided `<InputControlPrefixWrapper>` component.
 * 
 * ```jsx
 * import {
 *   __experimentalInputControl as InputControl,
 *   __experimentalInputControlPrefixWrapper as InputControlPrefixWrapper,
 * } from '@wordpress/components';
 * 
 * <InputControl
 *   prefix={<InputControlPrefixWrapper>@</InputControlPrefixWrapper>}
 * />
 * ```
 */
prefix?: ReactNode

/**
 * If `true` enforces a valid number within the control's min/max range.
 * If `false` allows an empty string as a valid value.
 */
required?: boolean | undefined = false

/**
 * Amount to increment by when the `SHIFT` key is held down. This shift value is
 * a multiplier to the `step` value. For example, if the `step` value is `5`,
 * and `shiftStep` is `10`, each jump would increment/decrement by `50`.
 */
shiftStep?: number = 10

/**
 * Adjusts the size of the input.
 */
size?: "small" | "default" | "compact" | "__unstable-large" = 'default'

/**
 * Optional multiplication factor in spin changes. i.e. A spin changes
 * by `spinFactor * step` (if `step` is "any", 1 is used instead).
 */
spinFactor?: number = 1

/**
 * Amount by which the `value` is changed when incrementing/decrementing.
 * It is also a factor in validation as `value` must be a multiple of `step`
 * (offset by `min`, if specified) to be valid. Accepts the special string value `any`
 * that voids the validation constraint and causes stepping actions to increment/decrement by `1`.
 */
step?: string | number | undefined = 1

/**
 * Current unit. _Note: this prop is deprecated. Instead, provide a unit with a value through the `value` prop._
 */
unit?: string

/**
 * Available units to select from.
 */
units?: WPUnitControlUnit[] = [
	allUnits.px,
	allUnits[ '%' ],
	allUnits.em,
	allUnits.rem,
	allUnits.vw,
	allUnits.vh,
]

/**
 * The value of the input.
 * Current value. If passed as a string, the current unit will be inferred from this value.
 * For example, a `value` of "50%" will set the current unit to `%`.
 */
value?: string | number | undefined
Imports
import { UnitControl } from "@wordpress/components";
Default story ok
const Default = () => {
    const [ value, setValue ] = useState< string | undefined >( '10px' );

    return (
        <UnitControl
            onUnitChange={fn()}
            onFocus={fn()}
            onBlur={fn()}
            label="Label"
            value={ value }
            onChange={ ( v, extra ) => {
				setValue( v );
				onChange?.( v, extra );
			} } />
    );
};
Press Enter To Change story ok
If the `isPressEnterToChange` prop is set to `true`, the `onChange` callback will not fire while a new value is typed in the input field (you can verify this behavior by inspecting the console's output).
const PressEnterToChange = () => {
    const [ value, setValue ] = useState< string | undefined >( '10px' );

    return (
        <UnitControl
            onUnitChange={fn()}
            onFocus={fn()}
            onBlur={fn()}
            isPressEnterToChange
            value={ value }
            onChange={ ( v, extra ) => {
				setValue( v );
				onChange?.( v, extra );
			} } />
    );
};
Tweaking The Number Input story ok
Most of `NumberControl`'s props can be passed to `UnitControl`, and they will affect its numeric input field.
const TweakingTheNumberInput = () => {
    const [ value, setValue ] = useState< string | undefined >( '10px' );

    return (
        <UnitControl
            onUnitChange={fn()}
            onFocus={fn()}
            onBlur={fn()}
            min={0}
            max={100}
            step="any"
            label="Custom label"
            value={ value }
            onChange={ ( v, extra ) => {
				setValue( v );
				onChange?.( v, extra );
			} } />
    );
};
With Single Unit story ok
When only one unit is available, the unit selection dropdown becomes static text.
const WithSingleUnit = () => {
    const [ value, setValue ] = useState< string | undefined >( '10px' );

    return (
        <UnitControl
            onUnitChange={fn()}
            onFocus={fn()}
            onBlur={fn()}
            units={CSS_UNITS.slice( 0, 1 )}
            value={ value }
            onChange={ ( v, extra ) => {
				setValue( v );
				onChange?.( v, extra );
			} } />
    );
};
With Custom Units story ok
It is possible to pass a custom list of units. Every time the unit changes, if the `isResetValueOnUnitChange` is set to `true`, the input's quantity is reset to the new unit's default value.
const WithCustomUnits = () => {
    const [ value, setValue ] = useState< string | undefined >( '80km' );

    return (
        <UnitControl
            onUnitChange={fn()}
            onFocus={fn()}
            onBlur={fn()}
            isResetValueOnUnitChange
            min={0}
            units={[
                {
                    value: 'km',
                    label: 'km',
                    default: 1,
                },
                {
                    value: 'mi',
                    label: 'mi',
                    default: 1,
                },
                {
                    value: 'm',
                    label: 'm',
                    default: 1000,
                },
                {
                    value: 'yd',
                    label: 'yd',
                    default: 1760,
                },
            ]}
            value={ value }
            onChange={ ( v, extra ) => {
				setValue( v );
				onChange?.( v, extra );
			} } />
    );
};

VisuallyHidden

design-system-components-visuallyhidden · ../packages/ui/src/visually-hidden/stories/index.story.tsx
Visually hides content while keeping it accessible to screen readers. Useful when providing context that's only meaningful to assistive technology. Renders a `<div>` by default. Use the `render` prop to swap the underlying element while preserving the visually-hidden behavior. ## Composing with other components When composing with another component that uses the `render` prop pattern, keep `VisuallyHidden` as the **host** (outer component) and pass the other component via `render`. This keeps the other component's HTML element and semantics intact, while `VisuallyHidden` only adds its hiding styles: ```jsx // OtherComponent keeps its semantic element (e.g. <h2>). <VisuallyHidden render={ <OtherComponent /> }> Accessible text </VisuallyHidden> ```
Prop types (react-component-meta) 4 prop types
Component: ../packages/ui/src/visually-hidden/index.ts::VisuallyHidden
Props:
/**
 * The content to be rendered inside the component.
 */
children?: ReactNode

/**
 * CSS class name to apply to the element.
 */
className?: string

/**
 * Replaces the component's default HTML element using a given React
 * element, or a function that returns a React element.
 */
render?: ComponentRenderFn<HTMLAttributesWithRef<any>> | ReactElement<Record<string, unknown>, string | JSXElementConstructor<any>> | undefined

/**
 * CSS style to apply to the element.
 */
style?: CSSProperties
Imports
import { VisuallyHidden } from "@wordpress/ui";
Default story ok
const Default = () => (
    <>
        <VisuallyHidden>This should not show.</VisuallyHidden>
        <div>
            This text will <VisuallyHidden>but not inline </VisuallyHidden>
            always show.
        </div>
    </>
);
With Custom Element story ok
Use the `render` prop to change the underlying HTML element. By default, `VisuallyHidden` renders a `<div>`. Here it renders a `<label>` instead, keeping the native label–input association while hiding the label text visually.
const WithCustomElement = function WithCustomElementStory() {
    const inputId = useId();
    return (
        <>
            { /* eslint-disable-next-line jsx-a11y/label-has-associated-control */ }
            <VisuallyHidden render={ <label htmlFor={ inputId } /> }>
                Accessible label
            </VisuallyHidden>
            <input
                id={ inputId }
                placeholder="This input has a visually hidden label"
            />
        </>
    );
};