Skip to content

Commit 73cae03

Browse files
committed
toolbar: move ToolbarToggle composition to components (ui parts don't author render={<X/>})
ToolbarToggle (ui) rendered <Toolbar.Button render={<Toggle/>}/> — authoring a render-prop to compose a second Base UI behavior is composition, which belongs in components. The ready-made now composes the styled ui ToolbarButton + Toggle (and reads density from the Toolbar context); the ui-tier story inlines that same ToolbarButton+Toggle directly (a ui story never imports from components).
1 parent c73cba7 commit 73cae03

4 files changed

Lines changed: 57 additions & 64 deletions

File tree

Lines changed: 22 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,37 @@
1+
import { Toggle } from "@base-ui/react/toggle";
2+
import type { Toggle as BaseToggleTypes } from "@base-ui/react/toggle";
13
import * as React from "react";
24

3-
import {
4-
ToolbarToggle as ToolbarToggleElement,
5-
type ToolbarToggleProps as ToolbarToggleElementProps,
6-
type ToolbarDensity,
7-
} from "../../ui/toolbar";
5+
import { ToolbarButton as ToolbarButtonElement, type ToolbarDensity } from "../../ui/toolbar";
86
import { ToolbarDensityContext } from "./toolbar-context";
97

108
export type ToolbarToggleProps<Value extends string = string> = Omit<
11-
ToolbarToggleElementProps<Value>,
12-
"density"
9+
BaseToggleTypes.Props<Value>,
10+
"className" | "style"
1311
> & {
1412
/** Density override; defaults to the surrounding `Toolbar`'s density. */
1513
density?: ToolbarDensity;
14+
/** Accessible name for the icon toggle. */
15+
"aria-label": string;
1616
};
1717

18-
/** A toolbar formatting toggle that takes its `density` from the surrounding `Toolbar` via context. */
18+
/**
19+
* A two-state toolbar button for formatting toggles like bold or italic. Composes the styled
20+
* `ToolbarButton` with `Toggle` behavior, and takes its `density` from the surrounding `Toolbar`
21+
* via context.
22+
*/
1923
export function ToolbarToggle<Value extends string = string>({
24+
render,
2025
density,
21-
...props
26+
"aria-label": ariaLabel,
27+
...toggleProps
2228
}: ToolbarToggleProps<Value>) {
2329
const toolbarDensity = React.useContext(ToolbarDensityContext);
24-
return <ToolbarToggleElement density={density ?? toolbarDensity} {...props} />;
30+
return (
31+
<ToolbarButtonElement
32+
density={density ?? toolbarDensity}
33+
aria-label={ariaLabel}
34+
render={<Toggle render={render} {...toggleProps} />}
35+
/>
36+
);
2537
}

packages/propel/src/ui/toolbar/index.tsx

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,5 @@ export * from "./toolbar-menu-trigger-label";
66
export * from "./toolbar-group";
77
export * from "./toolbar-item-icon";
88
export * from "./toolbar-separator";
9-
export * from "./toolbar-toggle";
109
export * from "./toolbar-toggle-group";
1110
export { type ToolbarDensity, type ToolbarElevation } from "./variants";

packages/propel/src/ui/toolbar/toolbar-toggle.tsx

Lines changed: 0 additions & 29 deletions
This file was deleted.

packages/propel/src/ui/toolbar/toolbar.stories.tsx

Lines changed: 35 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { Toggle } from "@base-ui/react/toggle";
12
import type { Meta, StoryObj } from "@storybook/react-vite";
23
import {
34
AlignCenter,
@@ -22,7 +23,6 @@ import {
2223
ToolbarGroup,
2324
ToolbarItemIcon,
2425
ToolbarSeparator,
25-
ToolbarToggle,
2626
ToolbarToggleGroup,
2727
} from "./index";
2828

@@ -36,7 +36,6 @@ const meta = {
3636
ToolbarGroup,
3737
ToolbarButton,
3838
ToolbarItemIcon,
39-
ToolbarToggle,
4039
ToolbarToggleGroup,
4140
ToolbarSeparator,
4241
ToolbarMenuTriggerButton,
@@ -65,44 +64,56 @@ export const Default: Story = {
6564
</ToolbarMenuTriggerButton>
6665
<ToolbarSeparator />
6766
<ToolbarGroup aria-label="Text formatting">
68-
<ToolbarToggle density={args.density} aria-label="Bold">
67+
<ToolbarButton density={args.density} aria-label="Bold" render={<Toggle />}>
6968
<ToolbarItemIcon>
7069
<Bold />
7170
</ToolbarItemIcon>
72-
</ToolbarToggle>
73-
<ToolbarToggle density={args.density} aria-label="Italic">
71+
</ToolbarButton>
72+
<ToolbarButton density={args.density} aria-label="Italic" render={<Toggle />}>
7473
<ToolbarItemIcon>
7574
<Italic />
7675
</ToolbarItemIcon>
77-
</ToolbarToggle>
78-
<ToolbarToggle density={args.density} aria-label="Underline">
76+
</ToolbarButton>
77+
<ToolbarButton density={args.density} aria-label="Underline" render={<Toggle />}>
7978
<ToolbarItemIcon>
8079
<Underline />
8180
</ToolbarItemIcon>
82-
</ToolbarToggle>
83-
<ToolbarToggle density={args.density} aria-label="Strikethrough">
81+
</ToolbarButton>
82+
<ToolbarButton density={args.density} aria-label="Strikethrough" render={<Toggle />}>
8483
<ToolbarItemIcon>
8584
<Strikethrough />
8685
</ToolbarItemIcon>
87-
</ToolbarToggle>
86+
</ToolbarButton>
8887
</ToolbarGroup>
8988
<ToolbarSeparator />
9089
<ToolbarToggleGroup aria-label="Text alignment" defaultValue={["left"]}>
91-
<ToolbarToggle density={args.density} value="left" aria-label="Align left">
90+
<ToolbarButton
91+
density={args.density}
92+
aria-label="Align left"
93+
render={<Toggle value="left" />}
94+
>
9295
<ToolbarItemIcon>
9396
<AlignLeft />
9497
</ToolbarItemIcon>
95-
</ToolbarToggle>
96-
<ToolbarToggle density={args.density} value="center" aria-label="Align center">
98+
</ToolbarButton>
99+
<ToolbarButton
100+
density={args.density}
101+
aria-label="Align center"
102+
render={<Toggle value="center" />}
103+
>
97104
<ToolbarItemIcon>
98105
<AlignCenter />
99106
</ToolbarItemIcon>
100-
</ToolbarToggle>
101-
<ToolbarToggle density={args.density} value="right" aria-label="Align right">
107+
</ToolbarButton>
108+
<ToolbarButton
109+
density={args.density}
110+
aria-label="Align right"
111+
render={<Toggle value="right" />}
112+
>
102113
<ToolbarItemIcon>
103114
<AlignRight />
104115
</ToolbarItemIcon>
105-
</ToolbarToggle>
116+
</ToolbarButton>
106117
</ToolbarToggleGroup>
107118
<ToolbarSeparator />
108119
<ToolbarButton density={args.density} aria-label="Insert link">
@@ -137,16 +148,16 @@ export const Elevations: Story = {
137148
<div className="flex flex-col gap-6">
138149
{(["raised", "flat"] as const).map((elevation) => (
139150
<Toolbar key={elevation} {...args} elevation={elevation}>
140-
<ToolbarToggle density={args.density} aria-label="Bold">
151+
<ToolbarButton density={args.density} aria-label="Bold" render={<Toggle />}>
141152
<ToolbarItemIcon>
142153
<Bold />
143154
</ToolbarItemIcon>
144-
</ToolbarToggle>
145-
<ToolbarToggle density={args.density} aria-label="Italic">
155+
</ToolbarButton>
156+
<ToolbarButton density={args.density} aria-label="Italic" render={<Toggle />}>
146157
<ToolbarItemIcon>
147158
<Italic />
148159
</ToolbarItemIcon>
149-
</ToolbarToggle>
160+
</ToolbarButton>
150161
<ToolbarSeparator />
151162
<ToolbarButton density={args.density} aria-label="Insert link">
152163
<ToolbarItemIcon>
@@ -169,16 +180,16 @@ export const Densities: Story = {
169180
<div className="flex flex-col gap-6">
170181
{(["compact", "comfortable"] as const).map((density) => (
171182
<Toolbar key={density} {...args} density={density}>
172-
<ToolbarToggle density={density} aria-label="Bold">
183+
<ToolbarButton density={density} aria-label="Bold" render={<Toggle />}>
173184
<ToolbarItemIcon>
174185
<Bold />
175186
</ToolbarItemIcon>
176-
</ToolbarToggle>
177-
<ToolbarToggle density={density} aria-label="Italic">
187+
</ToolbarButton>
188+
<ToolbarButton density={density} aria-label="Italic" render={<Toggle />}>
178189
<ToolbarItemIcon>
179190
<Italic />
180191
</ToolbarItemIcon>
181-
</ToolbarToggle>
192+
</ToolbarButton>
182193
<ToolbarSeparator />
183194
<ToolbarButton density={density} aria-label="Insert link">
184195
<ToolbarItemIcon>

0 commit comments

Comments
 (0)