@godxjp/ui 33.25.0 → 33.25.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/agent/START-HERE.md +1 -1
- package/agent/index.json +2 -2
- package/agent/llms.txt +3 -3
- package/dist/components/layout/affix.js +38 -9
- package/dist/contracts/measurement.json +1 -1
- package/dist/styles/layers.json +1 -1
- package/dist/styles/layout.css +24 -0
- package/dist/styles/precompiled/base.css +1 -1
- package/dist/styles/precompiled/layout.css +1 -1
- package/dist/styles.css +1 -1
- package/package.json +2 -2
package/agent/START-HERE.md
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
You are about to write code against a design system you did not author. This file is the whole
|
|
4
4
|
contract. Read it before you write JSX.
|
|
5
5
|
|
|
6
|
-
**This catalog describes `@godxjp/ui` 33.25.
|
|
6
|
+
**This catalog describes `@godxjp/ui` 33.25.2.** If the project you are editing has a different
|
|
7
7
|
version in its `package.json`, read the pinned catalog for THAT version instead
|
|
8
8
|
(`…/v<their-version>/agent/…`). A catalog newer than the installed package describes props that do
|
|
9
9
|
not exist yet; older, and it hides props that do. Neither failure announces itself.
|
package/agent/index.json
CHANGED
|
@@ -54,7 +54,7 @@
|
|
|
54
54
|
"note": "Pin to the tag that matches the @godxjp/ui version you installed. A catalog newer than your package describes props you do not have; older, and it hides props you do.",
|
|
55
55
|
"read": {
|
|
56
56
|
"live": "https://raw.githubusercontent.com/godx-jp/godxjp-ui/main/agent/index.json",
|
|
57
|
-
"pinned": "https://raw.githubusercontent.com/godx-jp/godxjp-ui/v33.25.
|
|
57
|
+
"pinned": "https://raw.githubusercontent.com/godx-jp/godxjp-ui/v33.25.2/agent/index.json"
|
|
58
58
|
},
|
|
59
59
|
"source": "mcp/src/data — the same data @godxjp/ui-mcp serves — plus the foundation and semantic token tiers, read from src/tokens/*.css",
|
|
60
60
|
"start": "https://raw.githubusercontent.com/godx-jp/godxjp-ui/main/agent/START-HERE.md",
|
|
@@ -68,5 +68,5 @@
|
|
|
68
68
|
"foundation": "the seeds a consumer is invited to set — --primary, --background, --radius",
|
|
69
69
|
"semantic": "named roles that follow the seeds — --ring, --text-link, --overlay-background"
|
|
70
70
|
},
|
|
71
|
-
"version": "33.25.
|
|
71
|
+
"version": "33.25.2"
|
|
72
72
|
}
|
package/agent/llms.txt
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
# @godxjp/ui
|
|
2
2
|
|
|
3
3
|
> A Japanese-enterprise React design system: 212 components, 3203 design tokens,
|
|
4
|
-
> 44 cardinal rules. This file is the entry point for AI agents. Catalog version 33.25.
|
|
4
|
+
> 44 cardinal rules. This file is the entry point for AI agents. Catalog version 33.25.2.
|
|
5
5
|
|
|
6
6
|
If your client can run a process, do not read these files — run the MCP server instead
|
|
7
|
-
(`npx @godxjp/ui-mcp@33.25.
|
|
7
|
+
(`npx @godxjp/ui-mcp@33.25.2`). It is searchable and version-locked. These files exist for agents
|
|
8
8
|
that can only fetch URLs.
|
|
9
9
|
|
|
10
10
|
## Start
|
|
@@ -27,7 +27,7 @@ that can only fetch URLs.
|
|
|
27
27
|
## Pinning
|
|
28
28
|
|
|
29
29
|
Every URL above tracks `main`. To pin to the release a project actually installed, swap `main` for
|
|
30
|
-
the tag: `.../godx-jp/godxjp-ui/v33.25.
|
|
30
|
+
the tag: `.../godx-jp/godxjp-ui/v33.25.2/agent/...`. A catalog that does not match the installed
|
|
31
31
|
package describes props that are absent, or hides props that are present, and says nothing either way.
|
|
32
32
|
|
|
33
33
|
Pinned catalogs only exist for releases whose tag actually contains `agent/`. If `…/v<version>/agent/index.json` returns 404, that release predates this catalog: read `…/main/…` instead and compare `index.json` → `version` against the package you have, so you at least know which way it drifted.
|
|
@@ -67,9 +67,12 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
67
67
|
assumeInView: true
|
|
68
68
|
});
|
|
69
69
|
const [rendered, setRendered] = React.useState(true);
|
|
70
|
-
const
|
|
70
|
+
const [sticky, setSticky] = React.useState(false);
|
|
71
|
+
const [stuck, setStuck] = React.useState(false);
|
|
72
|
+
const affixed = (sticky ? stuck : !inView) && rendered;
|
|
71
73
|
const [box, setBox] = React.useState(null);
|
|
72
74
|
const [targetInset, setTargetInset] = React.useState(0);
|
|
75
|
+
const [room, setRoom] = React.useState(null);
|
|
73
76
|
const measure = React.useCallback(() => {
|
|
74
77
|
const root = rootRef.current;
|
|
75
78
|
const content = contentRef.current;
|
|
@@ -77,17 +80,40 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
77
80
|
setRendered(isRendered(root));
|
|
78
81
|
const rootRect = root.getBoundingClientRect();
|
|
79
82
|
const contentRect = content.getBoundingClientRect();
|
|
83
|
+
const blockSize = content.scrollHeight > content.clientHeight + 1 ? content.scrollHeight : contentRect.height;
|
|
80
84
|
setBox(
|
|
81
|
-
(previous) => previous && previous.inline === rootRect.width && previous.block ===
|
|
85
|
+
(previous) => previous && previous.inline === rootRect.width && previous.block === blockSize ? previous : { inline: rootRect.width, block: blockSize }
|
|
82
86
|
);
|
|
83
87
|
const rect = targetElement?.getBoundingClientRect();
|
|
84
88
|
const blockEl = fixedContainingBlock(content);
|
|
89
|
+
const sentinelRect = sentinelRef.current?.getBoundingClientRect();
|
|
90
|
+
const insetStart = sentinelRect ? rootRect.top - sentinelRect.top : 0;
|
|
91
|
+
const insetEnd = sentinelRect ? sentinelRect.bottom - rootRect.bottom : 0;
|
|
92
|
+
const visibleTop = Math.max(rect ? rect.top : 0, 0);
|
|
93
|
+
const visibleBottom = Math.min(rect ? rect.bottom : window.innerHeight, window.innerHeight);
|
|
94
|
+
const line = pinToEnd ? visibleBottom - insetEnd : (rect ? rect.top : 0) + insetStart;
|
|
95
|
+
const parent = root.parentElement;
|
|
96
|
+
const nextSticky = blockEl !== null && blockEl === targetElement && parent !== null && parent.getBoundingClientRect().height > rootRect.height + 1;
|
|
97
|
+
setSticky((previous) => previous === nextSticky ? previous : nextSticky);
|
|
98
|
+
if (nextSticky) {
|
|
99
|
+
const atLine = Math.abs((pinToEnd ? rootRect.bottom : rootRect.top) - line) < 1;
|
|
100
|
+
const nextStuck = atLine && (targetElement?.scrollTop ?? 0) > 0;
|
|
101
|
+
setStuck((previous) => previous === nextStuck ? previous : nextStuck);
|
|
102
|
+
setTargetInset((previous) => previous === 0 ? previous : 0);
|
|
103
|
+
}
|
|
85
104
|
const block = blockEl?.getBoundingClientRect();
|
|
86
105
|
const viewportInset = rect ? pinToEnd ? window.innerHeight - rect.bottom : rect.top : 0;
|
|
87
106
|
const blockOffset = block ? pinToEnd ? window.innerHeight - (block.bottom + ((blockEl?.scrollHeight ?? 0) - (blockEl?.clientHeight ?? 0) - (blockEl?.scrollTop ?? 0))) : block.top - (blockEl?.scrollTop ?? 0) : 0;
|
|
88
107
|
const next = viewportInset - blockOffset;
|
|
89
|
-
setTargetInset((previous) => previous === next ? previous : next);
|
|
90
|
-
|
|
108
|
+
if (!nextSticky) setTargetInset((previous) => previous === next ? previous : next);
|
|
109
|
+
if (!affixed && !nextSticky) {
|
|
110
|
+
setRoom((previous) => previous === null ? previous : null);
|
|
111
|
+
return;
|
|
112
|
+
}
|
|
113
|
+
const nextRoom = Math.max(0, Math.floor(pinToEnd ? line - visibleTop : visibleBottom - line));
|
|
114
|
+
const clamp = blockSize > nextRoom ? nextRoom : null;
|
|
115
|
+
setRoom((previous) => previous === clamp ? previous : clamp);
|
|
116
|
+
}, [affixed, pinToEnd, targetElement]);
|
|
91
117
|
React.useLayoutEffect(() => {
|
|
92
118
|
measure();
|
|
93
119
|
}, [measure, affixed, children]);
|
|
@@ -106,7 +132,7 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
106
132
|
};
|
|
107
133
|
}, [measure, targetElement]);
|
|
108
134
|
React.useEffect(() => {
|
|
109
|
-
if (!affixed || typeof window === "undefined") return void 0;
|
|
135
|
+
if (!affixed && !sticky || typeof window === "undefined") return void 0;
|
|
110
136
|
let frame = null;
|
|
111
137
|
const onScroll = () => {
|
|
112
138
|
if (frame !== null) return;
|
|
@@ -122,7 +148,7 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
122
148
|
window.removeEventListener("resize", onScroll);
|
|
123
149
|
if (frame !== null) window.cancelAnimationFrame(frame);
|
|
124
150
|
};
|
|
125
|
-
}, [affixed, targetElement, measure]);
|
|
151
|
+
}, [affixed, sticky, targetElement, measure]);
|
|
126
152
|
React.useEffect(() => {
|
|
127
153
|
const content = contentRef.current;
|
|
128
154
|
if (pinToEnd || !affixed || !content || typeof document === "undefined") return void 0;
|
|
@@ -151,8 +177,9 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
151
177
|
const style = {
|
|
152
178
|
...offsetBlockStart === void 0 ? void 0 : { "--affix-inset-block-start": `${offsetBlockStart}px` },
|
|
153
179
|
...offsetBlockEnd === void 0 ? void 0 : { "--affix-inset-block-end": `${offsetBlockEnd}px` },
|
|
154
|
-
...targetInset === 0 ? void 0 : { "--affix-target-inset": `${targetInset}px` },
|
|
155
|
-
|
|
180
|
+
...sticky || targetInset === 0 ? void 0 : { "--affix-target-inset": `${targetInset}px` },
|
|
181
|
+
...!sticky && affixed && box ? { "--affix-content-inline-size": `${box.inline}px` } : void 0,
|
|
182
|
+
...(affixed || sticky) && room !== null ? { "--affix-content-max-block-size": `${room}px` } : void 0
|
|
156
183
|
};
|
|
157
184
|
return /* @__PURE__ */ jsxs(
|
|
158
185
|
"div",
|
|
@@ -165,6 +192,7 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
165
192
|
id,
|
|
166
193
|
"data-slot": "affix",
|
|
167
194
|
"data-affixed": affixed ? "" : void 0,
|
|
195
|
+
"data-pin": sticky ? pinToEnd ? "sticky-end" : "sticky-start" : void 0,
|
|
168
196
|
className: cn("ui-affix", className),
|
|
169
197
|
style,
|
|
170
198
|
...rest,
|
|
@@ -179,7 +207,7 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
179
207
|
className: "ui-affix-sentinel"
|
|
180
208
|
}
|
|
181
209
|
),
|
|
182
|
-
affixed && box ? /* @__PURE__ */ jsx(
|
|
210
|
+
affixed && box && !sticky ? /* @__PURE__ */ jsx(
|
|
183
211
|
"div",
|
|
184
212
|
{
|
|
185
213
|
"data-slot": "affix-placeholder",
|
|
@@ -194,6 +222,7 @@ const Affix = React.forwardRef(function Affix2({
|
|
|
194
222
|
ref: contentRef,
|
|
195
223
|
"data-slot": "affix-content",
|
|
196
224
|
"data-edge": pinToEnd ? "block-end" : "block-start",
|
|
225
|
+
"data-clamped": (affixed || sticky) && room !== null ? "" : void 0,
|
|
197
226
|
"data-affixed": affixed ? "" : void 0,
|
|
198
227
|
className: "ui-affix-content",
|
|
199
228
|
children
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$comment": "AUTO-GENERATED by scripts/gen-measurement-contract.mjs — do not edit. Read this instead of guessing: docs/MEASUREMENT-CONTRACT.md.",
|
|
3
|
-
"version": "33.25.
|
|
3
|
+
"version": "33.25.2",
|
|
4
4
|
"targetSize": {
|
|
5
5
|
"standard": "WCAG 2.2 SC 2.5.8 Target Size (Minimum), level AA — 24×24 CSS px",
|
|
6
6
|
"min": 24,
|
package/dist/styles/layers.json
CHANGED
package/dist/styles/layout.css
CHANGED
|
@@ -2515,6 +2515,30 @@
|
|
|
2515
2515
|
inline-size: var(--affix-content-inline-size, auto);
|
|
2516
2516
|
}
|
|
2517
2517
|
|
|
2518
|
+
.ui-affix-content[data-affixed][data-clamped],
|
|
2519
|
+
.ui-affix[data-pin] > .ui-affix-content[data-clamped] {
|
|
2520
|
+
max-block-size: var(--affix-content-max-block-size, none);
|
|
2521
|
+
overflow-y: auto;
|
|
2522
|
+
overscroll-behavior: contain;
|
|
2523
|
+
}
|
|
2524
|
+
|
|
2525
|
+
.ui-affix[data-pin="sticky-start"] {
|
|
2526
|
+
position: sticky;
|
|
2527
|
+
inset-block-start: var(--affix-inset-block-start);
|
|
2528
|
+
z-index: var(--sticky-z-index);
|
|
2529
|
+
}
|
|
2530
|
+
|
|
2531
|
+
.ui-affix[data-pin="sticky-end"] {
|
|
2532
|
+
position: sticky;
|
|
2533
|
+
inset-block-end: var(--affix-inset-block-end);
|
|
2534
|
+
z-index: var(--sticky-z-index);
|
|
2535
|
+
}
|
|
2536
|
+
|
|
2537
|
+
.ui-affix[data-pin] > .ui-affix-content[data-affixed] {
|
|
2538
|
+
position: static;
|
|
2539
|
+
inline-size: auto;
|
|
2540
|
+
}
|
|
2541
|
+
|
|
2518
2542
|
.ui-affix-content[data-affixed][data-edge="block-start"] {
|
|
2519
2543
|
inset-block-start: calc(var(--affix-target-inset, 0px) + var(--affix-inset-block-start));
|
|
2520
2544
|
}
|