Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .sync/dep-parity.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"$note": "Upstream's pinned versions for every dependency both trees declare in the SAME section, snapshotted at `cursor`. The sync ports deltas, which is correct per commit and lets a one-time divergence become permanent: once a version is off upstream's line, every later `chore(deps)` batch skips it, because those ports bump only where this fork already matched upstream's pre-image. `prettier` sat at ^3.8.4 against upstream's ^3.9.6 for that reason, through four ported batches, until this file was written. Section-aware on purpose: 18 packages are declared on both sides but in different sections — the whole `@tiptap/*` family is a peer `^3` upstream and a dependency `^3.29.2` here, and `ai` is a peer there and a devDependency here. Those are structural divergences, not drift, and comparing a peer range against a dependency range says nothing. They are absent from this file by construction rather than by omission. Guarded by `test/utils/dep-parity.spec.ts`. Refresh with `node .sync/dep-parity.mjs <path-to-nuxt-ui-mirror> [cursor]`, which preserves `exceptions`.",
"cursor": "be58f3f5ebbd0dee23d9b345b45a7c51d1225b8b",
"cursor": "a7f26a320535da1fbe77a7066e53386423da4d3a",
"manifests": {
"package.json": {
"dependencies": {
Expand Down
31 changes: 31 additions & 0 deletions .sync/log/a7f26a320535da1fbe77a7066e53386423da4d3a.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# No-op: docs(showcase): add brusnika-lms.com

**Upstream:** `a7f26a320535da1fbe77a7066e53386423da4d3a` (nuxt/ui, #6863)
**Decision:** no-op — upstream curates its own gallery

## Upstream change

Four lines in `docs/content/showcase.yml` and one screenshot: a site built with
Nuxt UI joins their showcase, with `screenshotOptions.cookies` set so the
screenshotter gets past the consent banner.

```diff
+ - name: Brusnika.LMS
+ url: https://brusnika-lms.com/
+ screenshotOptions:
+ cookies: ['cookie-consent=accepted']
```

## b24ui

This fork has its own `docs/content/showcase.yml` listing sites built with
Bitrix24 UI, so an entry naming a Nuxt UI site is content, not code. Same call
as `d0cfc2b1`, `78cc1ce5`, `cf5f15e3`, `2beb2345` and `a630c943`, which the
ledger already records as no-ops for the same reason.

The one showcase commit that was **not** a no-op is `f6d188bd` — it changed the
schema (`screenshotOptions`), and the schema is shared. This one uses that field
rather than introducing it, so there is nothing structural left to take:
`screenshotOptions` is already supported here.

Recorded rather than skipped silently so the next porter does not re-derive it.
97 changes: 97 additions & 0 deletions .sync/log/d4f2ca02322cd9ad5b2c2fe235aa445f88042997.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
# Port: fix(theme): replace deprecated bare tailwind aliases

**Upstream:** `d4f2ca02322cd9ad5b2c2fe235aa445f88042997` (nuxt/ui, #6865)
**Decision:** port — adapted; one of the two renames is not value-preserving here

## Upstream change

Tailwind v4 keeps the v3 bare spellings working as deprecated aliases. Upstream
replaces the two it still used with the current names:

- `backdrop-blur` → `backdrop-blur-sm` — `chat-prompt.ts`, `content/content-toc.ts`,
`header.ts`, `table.ts` (×4)
- `rounded` → `rounded-sm` — `input-date.ts`, `input-time.ts`

Six theme files, eleven snapshot files, no behaviour change on their side.

## Why the second rename cannot be copied

The bare aliases are **hardcoded**; the named ones read a theme variable. Compiled
with this repo's own Tailwind (4.3.3) through `@tailwindcss/postcss`:

```
.backdrop-blur => --tw-backdrop-blur: blur(8px);
.backdrop-blur-sm => --tw-backdrop-blur: blur(var(--blur-sm));
.rounded => border-radius: 0.25rem;
.rounded-sm => border-radius: var(--radius-sm);
.rounded-2xs => border-radius: var(--radius-2xs);
```

So each rename is value-preserving only if the variable still holds the v3
default — which is true upstream and **half true here**:

- `--blur-sm` is Tailwind's own `8px`; this fork does not override the blur
scale (no `--blur-*` anywhere in `src/`). `backdrop-blur` → `backdrop-blur-sm`
is exact.
- `--radius-sm` is **8px here**, not `0.25rem`. `src/runtime/air-design-tokens/tw-style/radius.css`
replaces the whole radius scale with the Air design system's, and its `sm` step
is 8px. Taking upstream's line verbatim would silently double the corner radius
on every InputDate and InputTime segment.

The same file defines `--radius-2xs: 4px`, which is what bare `rounded` emits, so
**`rounded-2xs`** is the value-preserving name in this fork. It is also the
radius the design system already assigns to fields: `007_b24_global.css` sets
`--ui-field-border-radius: var(--ui-border-radius-2xs)`, and
`--ui-border-radius-2xs` is `4px` as well.

This is a deprecation cleanup, not a design change, so the value is what is being
preserved — not the class name.

## b24ui port

Applied to every bare occurrence in the fork, which is more than upstream's set
because two of the files are fork-local:

| file | change | n |
| --- | --- | --- |
| `src/theme/header.ts` | `backdrop-blur` → `-sm` | 1 |
| `src/theme/table.ts` | `backdrop-blur` → `-sm` | 4 |
| `src/theme/table-wrapper.ts` | `backdrop-blur` → `-sm` | 6 |
| `src/theme/input-date.ts` | `rounded` → `rounded-2xs` | 1 |
| `src/theme/input-time.ts` | `rounded` → `rounded-2xs` | 1 |

`table-wrapper.ts` has no upstream counterpart; one of its six is inside a
commented-out line, changed with the rest so the comment does not read as a
different rule than the three live ones around it.

Two docs examples carried the same aliases and are fixed here too —
`ScrollAreaExternalScrollExample.vue` (`backdrop-blur`) and
`useConfettiCustomPlaceExample.vue` (`rounded`). Leaving them means the next
sweep rediscovers them.

**`chat-prompt.ts` and `content/content-toc.ts` need nothing**: neither of our
copies contains `backdrop-blur` at all.

## What was deliberately not touched

The sweep that found the above also lists `ring` and `outline-none`, and neither
belongs in this commit:

- Bare `ring` is **not deprecated in v4** — it is the current 1px utility.
`.ring` and `.ring-1` compile to the identical declaration (verified in the
same probe). The v3→v4 note about `ring` → `ring-3` is about the default width
changing, which this fork already lives with.
- `outline-none` in v4 is a real utility meaning `outline-style: none`; it is
`outline-hidden` that replaced v3's meaning. Our ~50 `focus:outline-none` are a
separate question about intent, not an alias rename, and upstream's commit does
not touch them either.

## Verify

- **Compiled, not assumed.** The table above comes from compiling a probe
stylesheet with this repo's Tailwind and reading the emitted declarations, then
from the generated docs CSS: `--blur-sm:8px` and `--radius-sm:8px` are what the
site actually ships.
- **Snapshots: 814 lines removed, 814 added, and after normalising the two
renamed tokens, zero lines differ.** The churn is the rename and nothing else.
- Gauntlet (`CI=true`): `lint` · `typecheck` · `test` · `build` · `docs:generate`.
47 changes: 47 additions & 0 deletions .sync/log/e2a253ec9496efa5ac3c7b9635ccf20a3458a704.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
# Port: docs(header): prevent focus on toggle button animations

**Upstream:** `e2a253ec9496efa5ac3c7b9635ccf20a3458a704` (nuxt/ui)
**Decision:** port — one of two files exists here

## Upstream change

Six lines across two docs files. The three `motion.line` elements that draw the
animated hamburger icon carried `class="outline-none"`; they now carry
`tabindex="-1"` instead.

```diff
- class="outline-none"
+ tabindex="-1"
```

The two are not variants of one another. `outline-none` suppresses the focus
ring while leaving the element in the tab order — the lines stayed focusable and
the only evidence of it disappeared. `tabindex="-1"` takes them out of the tab
order, which is the actual intent: an SVG line inside a button is decoration, and
tabbing to it strands the reader on something with no behaviour and now, with the
outline gone, no visible position either.

## b24ui port

**One of the two files exists here.** Upstream changes
`docs/app/components/content/HeaderToggleButton.vue` and
`docs/app/components/content/examples/header/HeaderToggleAnimatedExample.vue`;
this fork has only the second. There is no `HeaderToggleButton.vue` under
`docs/app/components/content/` and no other component wrapping the same icon —
checked by searching for `motion-v` across `docs/app`, `playgrounds` and `src`,
which returns exactly two files: this example and `src/runtime/components/prose/Img.vue`,
whose `Motion`/`AnimatePresence` usage has no `outline-none` and no focusable
children to fix.

**The example is structurally identical to upstream's**, down to the
`:variants` / `:animate` / `:custom` triple and the `1 / 2 / 3` custom indices,
so the swap is upstream's verbatim on all three elements.

## Verify

Checked in the built output rather than the source. The example is served to the
header page as `/api/component-example/headerToggleAnimatedExample.json`
(there is no standalone `/examples/header-toggle-animated-example/` route for
this one): after `docs:generate` that payload carries **three** `tabindex="-1"`
and **zero** `outline-none`, and no other attribute on the three `<line>`
elements moved.
20 changes: 19 additions & 1 deletion .sync/nuxt-ui.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"upstream": "nuxt/ui",
"branch": "v4",
"cursor": "be58f3f5ebbd0dee23d9b345b45a7c51d1225b8b",
"cursor": "a7f26a320535da1fbe77a7066e53386423da4d3a",
"_cursor_note": "cursor = last upstream commit ported into b24ui. The sync is manual by decision: one commit at a time, oldest-first, each with a `.sync/log/<sha>.md` journal and an entry in `processed`. There is no dispatcher, no porter workflow and no kill-switch — `.sync/PORTING.md` is the whole procedure. `processed` is maintained per port (backfilled #68-#72 on 2026-06-09).",
"processed": {
"2799fa6f2b25ce3eb15e050f3ef7c57d0d9a2fdb": {
Expand Down Expand Up @@ -1583,6 +1583,24 @@
"b24ui_sha": "fc562bcefd685fd8f5fe0ace4d99293a46359c16",
"decision": "port",
"summary": "docs(table): pin TanStack Table links to v8 (nuxt/ui #6864) — PORT, applies in full minus a page we lack. Upstream rewrites every tanstack.com/table/latest to /table/v8 because latest now resolves to a major the documented API no longer matches, widens two labels to name the version, and corrects one link: the column-pinning section pointed at the row-pinning API. Applies here for the same reason, checked not assumed — this fork depends on @tanstack/vue-table ^8.21.3, so every latest link documents an API our Table does not implement. 18 links across two files: docs/content/docs/2.components/table.md (17) and skills/b24-ui-nuxt/references/recipes/data-tables.md (1); both labels widened as upstream did. We inherit the mislabelled link too — our line 523 in 'With column pinning' read '[Pinning APIs](…/features/row-pinning)' and is now '[Column Pinning APIs](…/features/column-pinning)'. Worth noting because it is a content error rather than a version pin, and a sweep of latest -> v8 alone would have carried it forward. Not applicable: docs/content/docs/1.getting-started/3.migration/2.v3.md — our migration directory holds only 1.v2.md, this fork has no v3 migration page. Verified with lint, test and docs:generate; documentation only, zero /table/latest remain and 18 /table/v8."
},
"e2a253ec9496efa5ac3c7b9635ccf20a3458a704": {
"pr": "pending-merge",
"b24ui_sha": "pending-merge",
"decision": "port",
"summary": "docs(header): prevent focus on toggle button animations (nuxt/ui) — PORT of the half that exists here. Upstream swaps class=\"outline-none\" for tabindex=\"-1\" on the three motion.line elements of the animated hamburger icon, in two files. The two attributes are not variants of each other: outline-none hides the focus ring and leaves the element in the tab order, so the lines stayed focusable and the only evidence of it disappeared; tabindex=\"-1\" removes them from it, which is the intent — an SVG line inside a button is decoration. Only docs/app/components/content/examples/header/HeaderToggleAnimatedExample.vue exists in this fork; there is no HeaderToggleButton.vue under docs/app/components/content/, and searching for motion-v across docs/app, playgrounds and src returns exactly two files — this example and src/runtime/components/prose/Img.vue, whose Motion usage has neither outline-none nor focusable children. The example is structurally identical to upstream's down to the :variants/:animate/:custom triple and the 1/2/3 indices, so the swap is verbatim on all three elements."
},
"d4f2ca02322cd9ad5b2c2fe235aa445f88042997": {
"pr": "pending-merge",
"b24ui_sha": "pending-merge",
"decision": "port",
"summary": "fix(theme): replace deprecated bare tailwind aliases (nuxt/ui #6865) — PORT, adapted: one of the two renames is not value-preserving in this fork. Tailwind v4 keeps the v3 bare spellings as deprecated aliases and upstream replaces the two it used — backdrop-blur -> backdrop-blur-sm and rounded -> rounded-sm — across six theme files. The catch is that the bare aliases are hardcoded while the named ones read a theme variable. Compiled with this repo's own Tailwind 4.3.3: .backdrop-blur emits blur(8px), .backdrop-blur-sm emits blur(var(--blur-sm)); .rounded emits 0.25rem, .rounded-sm emits var(--radius-sm). --blur-sm is Tailwind's own 8px and this fork does not override the blur scale, so the first rename is exact. --radius-sm is 8px here: src/runtime/air-design-tokens/tw-style/radius.css replaces the whole radius scale with the Air design system's, so taking upstream's line verbatim would have doubled the corner radius on every InputDate and InputTime segment. The same file defines --radius-2xs: 4px, which is what bare rounded emits, so rounded-2xs is the value-preserving name — and it matches the design system's own field radius, --ui-field-border-radius: var(--ui-border-radius-2xs), also 4px. A deprecation cleanup preserves the value, not the class name. Applied to every bare occurrence in the fork, which is a larger set than upstream's because two files are fork-local: header.ts (1), table.ts (4), table-wrapper.ts (6, one inside a commented line, changed with the rest so the comment does not read as a different rule), input-date.ts (1), input-time.ts (1), plus two docs examples carrying the same aliases (ScrollAreaExternalScrollExample, useConfettiCustomPlaceExample). chat-prompt.ts and content/content-toc.ts need nothing — neither of our copies contains backdrop-blur. Deliberately not touched: bare `ring`, which is not deprecated in v4 (.ring and .ring-1 compile identically, verified in the same probe), and outline-none, which in v4 is a real utility meaning outline-style: none — upstream's commit does not touch either. Verified by compiling a probe stylesheet and reading the emitted declarations rather than by trusting the upgrade guide, and by the generated docs CSS, where --blur-sm:8px and --radius-sm:8px are what the site ships; snapshots moved 814 lines removed / 814 added, and after normalising the two renamed tokens zero lines differ."
},
"a7f26a320535da1fbe77a7066e53386423da4d3a": {
"pr": "pending-merge",
"b24ui_sha": "pending-merge",
"decision": "no-op",
"summary": "docs(showcase): add brusnika-lms.com (nuxt/ui #6863) — NO-OP: four lines in docs/content/showcase.yml plus a screenshot, adding a site built with Nuxt UI to their gallery. This fork keeps its own showcase.yml listing sites built with Bitrix24 UI, so the entry is content, not code. Same call as d0cfc2b1, 78cc1ce5, cf5f15e3, 2beb2345 and a630c943. The one showcase commit that was not a no-op is f6d188bd, which introduced the screenshotOptions field — shared schema. This commit uses that field rather than introducing it, and screenshotOptions is already supported here (docs/modules/showcase.ts and docs/content.config.ts both carry it), so nothing structural is left to take."
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ const variants: { [k: string]: VariantType | ((custom: unknown) => VariantType)
:variants="variants"
:animate="open ? 'close' : 'normal'"
:custom="1"
class="outline-none"
tabindex="-1"
/>
<motion.line
x1="4"
Expand All @@ -107,7 +107,7 @@ const variants: { [k: string]: VariantType | ((custom: unknown) => VariantType)
:variants="variants"
:animate="open ? 'close' : 'normal'"
:custom="2"
class="outline-none"
tabindex="-1"
/>
<motion.line
x1="4"
Expand All @@ -117,7 +117,7 @@ const variants: { [k: string]: VariantType | ((custom: unknown) => VariantType)
:variants="variants"
:animate="open ? 'close' : 'normal'"
:custom="3"
class="outline-none"
tabindex="-1"
/>
</svg>
</B24Button>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ function scrollToStart() {
<div :class="isHorizontal && 'flex'">
<div
ref="title"
class="z-10 flex gap-4 bg-elevated/50 backdrop-blur"
class="z-10 flex gap-4 bg-elevated/50 backdrop-blur-sm"
:class="isHorizontal
? 'sticky start-0 w-72 shrink-0 flex-col justify-center p-6 border-e border-muted'
: 'sticky top-0 items-end justify-between px-6 py-4 border-b border-muted'"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ function fireAtPlace(): void {
<div class="relative mt-sm2 mb-4 w-full">
<canvas
ref="myCanvas"
class="m-auto h-64 w-1/2 rounded backdrop-blur-md bg-(--ui-color-design-outline-na-bg) border-1 border-(--ui-color-design-outline-na-stroke)"
class="m-auto h-64 w-1/2 rounded-2xs backdrop-blur-md bg-(--ui-color-design-outline-na-bg) border-1 border-(--ui-color-design-outline-na-stroke)"
/>
</div>
</div>
Expand Down
2 changes: 1 addition & 1 deletion src/theme/header.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
*/
export default {
slots: {
root: 'bg-(--ui-color-bg-content-primary)/75 backdrop-blur border-b border-(--ui-color-divider-default) h-(--b24ui-header-height) sticky top-0 z-50',
root: 'bg-(--ui-color-bg-content-primary)/75 backdrop-blur-sm border-b border-(--ui-color-divider-default) h-(--b24ui-header-height) sticky top-0 z-50',
container: 'flex items-center justify-between gap-3 h-full',
left: 'lg:flex-1 flex items-center gap-1.5',
center: 'hidden lg:flex',
Expand Down
2 changes: 1 addition & 1 deletion src/theme/input-date.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ export default () => {
'style-blurred-bg-input'
].join(' '),
segment: [
'rounded',
'rounded-2xs',
'text-center',
'outline-hidden',
'text-(--ui-color-base-1)',
Expand Down
2 changes: 1 addition & 1 deletion src/theme/input-time.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ export default () => {
'style-blurred-bg-input'
].join(' '),
segment: [
'rounded',
'rounded-2xs',
'text-center',
'outline-hidden',
'text-(--ui-color-base-1)',
Expand Down
Loading