Refactor Admin UI / Breadcrumbs to use DS components and design tokens#77012
Refactor Admin UI / Breadcrumbs to use DS components and design tokens#77012jameskoster wants to merge 9 commits intotrunkfrom
Conversation
| li:not(:last-child)::after { | ||
| content: "/"; | ||
| margin: 0 var(--wpds-dimension-gap-sm); | ||
| color: var(--wpds-color-stroke-surface-neutral); |
There was a problem hiding this comment.
I figure this is okay as the separator is a decorative element and the list structure conveys meaning to assistive tech. I appreciate it's a bit of a gray area though. Thoughts welcome.
There was a problem hiding this comment.
Does this affect hover styles and general click area of the item, though?
|
The following accounts have interacted with this PR and/or linked issues. I will continue to update these lists as activity occurs. You can also manually ask me to refresh this list by adding the If you're merging code through a pull request on GitHub, copy and paste the following into the bottom of the merge commit message. To understand the WordPress project's expectations around crediting contributors, please review the Contributor Attribution page in the Core Handbook. |
| const ALLOWLIST = { | ||
| '@wordpress/ui': { | ||
| allowed: [ 'Badge', 'Stack' ], | ||
| allowed: [ 'Badge', 'Link', 'Stack', 'Text' ], |
There was a problem hiding this comment.
If this needs to be handled separately I understand :)
There was a problem hiding this comment.
Just flagging that Text is now allowed, and I guess Link may soon allowed too?
|
Size Change: +145 B (0%) Total Size: 7.74 MB 📦 View Changed
ℹ️ View Unchanged
|
|
Flaky tests detected in 4710a2f. 🔍 Workflow run URL: https://github.com/WordPress/gutenberg/actions/runs/24247473882
|
| font-size: var(--wpds-font-size-lg); | ||
| font-weight: var(--wpds-font-weight-medium); | ||
| line-height: var(--wpds-font-line-height-lg); |
There was a problem hiding this comment.
My assumption would be we'd not want to be overriding any of these anymore if we're using Text component? Do font-size and line-height not work for what we want?
There was a problem hiding this comment.
Text is only used for the last item in the trail. These styles are to ensure the Links size and line-height match. Though I suppose we could replace nav with a Text instance that renders as nav, then remove these styles. I'll try that :)
There was a problem hiding this comment.
Yep, these styles are here from earlier work to make the title + breadcrumbs consistent with CSS, since Text wasn't ready to use yet. Now that Text is safe, we should update Text across the admin-ui to ensure consistency.
Worth updating also the title to use Text either in this PR or separately; happy to follow-up with separate PR if you'd prefer.
aduth
left a comment
There was a problem hiding this comment.
This looks like it's in pretty good shape, but needs a rebase to remove the pieces that have been addressed separately for allowlisting Text usage and handling jsx-a11y/heading-has-content.
| </Link> | ||
| ) : ( | ||
| <Heading level={ 1 } truncate> | ||
| /* eslint-disable jsx-a11y/heading-has-content */ |
There was a problem hiding this comment.
We can remove this after rebase, since this was addressed via #77073.
| li:not(:last-child)::after { | ||
| content: "/"; | ||
| margin: 0 variables.$grid-unit-10; | ||
| // @TODO: Remove truncation styles once `Text` supports truncation natively. |
There was a problem hiding this comment.
I can help write an issue for this, but what do we think this'll look like? A truncate prop like what we had with the @wordpress/components's Text component?
There was a problem hiding this comment.
Yes I think so, potentially with a numberOfLines (or equivalent) option as well.
Refactor breadcrumb links to compose the UI Link with the router Link via the render prop, adopting design-system styling. Replace the base-styles spacing variable with a design token and add Link to the eslint allowlist for @wordpress/ui. Made-with: Cursor
Made-with: Cursor
Replace HStack and Heading from @wordpress/components with Stack and Text from @wordpress/ui. Add Text to the eslint allowlist for @wordpress/ui. Made-with: Cursor
Made-with: Cursor
Use an outer Text with body-lg on the nav element so links and separators inherit typography via CSS. The inner Text with heading-lg on the h1 overrides for the current item. Removes manual font declarations from the stylesheet. Made-with: Cursor
b1af8da to
c950341
Compare
No longer needed after #77073. Made-with: Cursor
| as="ul" | ||
| <Text | ||
| variant="body-lg" | ||
| render={ <nav /> } |
There was a problem hiding this comment.
While this technically works, it feels a bit unusual. My preference would be to apply Text where needed, ie. on the single Link instances eg
<Text
variant="body-lg"
render={
<Link
tone="neutral"
render={ <RouterLink to={ item.to } /> }
/>
}
>
{ item.label }
</Text>There was a problem hiding this comment.
Hah, I had the same thought but Cursor convinced me:
- Less repetition — one Text instance vs. one per item.
- No extra DOM nodes — approach B adds a wrapper around every link, which adds noise and could affect inline layout.
I guess these are very minor points though, so happy to go this way if y'all prefer.
There was a problem hiding this comment.
I still lean towards my suggested approach (which was your initial instinct) and push back to cursor:
- re. repetition, this code mostly runs in a loop anyway, and could be abstracted to an internal
BreadcrumbsItemcomponent anyway - re. extra DOM nodes — I'm not sure Opus is right here. I'd expect only a single dom node anyway
| overflow: hidden; | ||
| text-overflow: ellipsis; | ||
| white-space: nowrap; | ||
| margin: 0; |
There was a problem hiding this comment.
If we use Text as for my previous suggestion, we may not need margin: 0
Wrap each Link in Text with body-lg via nested render props (Text → Link → RouterLink) rather than using an outer Text on the nav element. Remove the h1 margin override. Made-with: Cursor
What
Refactors the Breadcrumbs component to use
Link,Stack, andTextfrom@wordpress/uiinstead ofHStack,Heading, and the unstyled routerLink. Replaces the@wordpress/base-stylesspacing variable with a design token and addsLinkandTextto the@wordpress/uiESLint allowlist. Makes some small style adjustments.Why
The Breadcrumbs component was relying on experimental components from
@wordpress/components(__experimentalHStack,__experimentalHeading) and an unstyled router link. Migrating to@wordpress/uicomponents aligns breadcrumbs with the design system, giving links consistent interactive styling via theneutraltone and typography viaTextvariants. It also resolves a longstanding TODO in the stylesheet about adopting theTextcomponent.How
Link(for styling) with the routerLink(for navigation) using therenderprop. Usestone="neutral"for breadcrumb-appropriate link styling.HStackwithStack direction="row", rendered as a<ul>via therenderprop.HeadingwithText variant="heading-lg", rendered as an<h1>via therenderprop. Truncation is handled via a CSS class untilTextsupports it natively.@wordpress/base-stylesimport andh1override. Replaces the Sass spacing variable with--wpds-dimension-gap-sm. Uses a subdued color for the decorative "/" separator.LinkandTextto theuse-recommended-componentsallowlist for@wordpress/ui, with corresponding test updates.Before
After
Use of AI Tools
Created with Cursor & Claude Opus 4.6