@nebutra/ui 0.2.1 → 0.2.3

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.
Files changed (56) hide show
  1. package/LICENSE +21 -676
  2. package/README.md +81 -86
  3. package/dist/agent/index.d.ts +119 -0
  4. package/dist/agent/index.js +135 -0
  5. package/dist/agent/index.js.map +1 -0
  6. package/dist/canonical-Drca5UMj.d.ts +4309 -0
  7. package/dist/components/index.d.ts +51 -56
  8. package/dist/components/index.js +1696 -1203
  9. package/dist/components/index.js.map +1 -1
  10. package/dist/hooks/index.d.ts +62 -15
  11. package/dist/hooks/index.js +56 -34
  12. package/dist/hooks/index.js.map +1 -1
  13. package/dist/index-CKLIGfiU.d.ts +19 -0
  14. package/dist/index-Dg4jRJV2.d.ts +57 -0
  15. package/dist/layout/index.d.ts +7 -3
  16. package/dist/layout/index.js +525 -542
  17. package/dist/layout/index.js.map +1 -1
  18. package/dist/layouts/index.d.ts +80 -2
  19. package/dist/layouts/index.js +32 -19
  20. package/dist/layouts/index.js.map +1 -1
  21. package/dist/patterns/index.d.ts +131 -5
  22. package/dist/patterns/index.js +1594 -806
  23. package/dist/patterns/index.js.map +1 -1
  24. package/dist/primitives/canonical.d.ts +25 -0
  25. package/dist/primitives/canonical.js +12269 -0
  26. package/dist/primitives/canonical.js.map +1 -0
  27. package/dist/primitives/index.d.ts +694 -3544
  28. package/dist/primitives/index.js +8994 -6583
  29. package/dist/primitives/index.js.map +1 -1
  30. package/dist/shared/animation/css/index.d.ts +1 -0
  31. package/dist/shared/animation/css/index.js +14 -0
  32. package/dist/shared/animation/css/index.js.map +1 -0
  33. package/dist/shared/animation/index.d.ts +6 -0
  34. package/dist/shared/animation/index.js +272 -0
  35. package/dist/shared/animation/index.js.map +1 -0
  36. package/dist/shared/animation/motion/index.d.ts +4 -0
  37. package/dist/shared/animation/motion/index.js +205 -0
  38. package/dist/shared/animation/motion/index.js.map +1 -0
  39. package/dist/styles/brand-override.css +11 -11
  40. package/dist/tailwind.preset.d.ts +10 -10
  41. package/dist/tailwind.preset.js +7 -4
  42. package/dist/tailwind.preset.js.map +1 -1
  43. package/dist/theme/index.d.ts +2 -2
  44. package/dist/tokens-EAC6uPem.d.ts +302 -0
  45. package/dist/typography/fonts.css +51 -37
  46. package/dist/typography/index.d.ts +27 -27
  47. package/dist/typography/index.js +24 -4
  48. package/dist/typography/index.js.map +1 -1
  49. package/dist/utils/index.d.ts +66 -14
  50. package/dist/utils/index.js +53 -10
  51. package/dist/utils/index.js.map +1 -1
  52. package/package.json +56 -14
  53. package/src/styles/brand-override.css +61 -0
  54. package/src/styles/preset.css +29 -0
  55. package/src/styles/sources.css +37 -0
  56. package/src/typography/fonts.css +124 -0
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/utils/cn.ts","../../src/utils/brand-colors.ts","../../src/utils/index.ts"],"names":[],"mappings":";;;;AAGO,SAAS,MAAM,MAAA,EAAsB;AAC1C,EAAA,OAAO,OAAA,CAAQ,IAAA,CAAK,MAAM,CAAC,CAAA;AAC7B;;;ACQO,IAAM,cAAA,GAAiB;AAAA,EAC5B,OAAA,EAAS,SAAA;AAAA;AAAA,EACT,MAAA,EAAQ,SAAA;AAAA;AAAA,EACR,QAAA,EAAU,SAAA;AAAA;AAAA,EACV,WAAA,EAAa,SAAA;AAAA;AAAA,EACb,QAAA,EAAU;AAAA;AACZ;AAOO,SAAS,UAAA,CAAW,MAAc,QAAA,EAA0B;AACjE,EAAA,IAAI,OAAO,MAAA,KAAW,WAAA,IAAe,OAAO,aAAa,WAAA,EAAa;AACpE,IAAA,OAAO,QAAA;AAAA,EACT;AACA,EAAA,MAAM,KAAA,GAAQ,iBAAiB,QAAA,CAAS,eAAe,EAAE,gBAAA,CAAiB,IAAI,EAAE,IAAA,EAAK;AACrF,EAAA,OAAO,KAAA,IAAS,QAAA;AAClB;AAGO,SAAS,eAAA,GAA0B;AACxC,EAAA,OAAO,UAAA,CAAW,iBAAA,EAAmB,cAAA,CAAe,OAAO,CAAA;AAC7D;AAGO,SAAS,cAAA,GAAyB;AACvC,EAAA,OAAO,UAAA,CAAW,gBAAA,EAAkB,cAAA,CAAe,MAAM,CAAA;AAC3D;AAGO,SAAS,gBAAA,GAA2B;AACzC,EAAA,OAAO,UAAA,CAAW,kBAAA,EAAoB,cAAA,CAAe,QAAQ,CAAA;AAC/D;;;AClCO,IAAM,WAAA,GAAc;AAAA,EACzB,EAAA,EAAI,CAAA;AAAA,EACJ,EAAA,EAAI,GAAA;AAAA,EACJ,EAAA,EAAI,GAAA;AAAA,EACJ,EAAA,EAAI,IAAA;AAAA,EACJ,EAAA,EAAI;AACN;AAOO,SAAS,eAAe,UAAA,EAAiC;AAC9D,EAAA,IAAI,OAAO,MAAA,KAAW,WAAA,EAAa,OAAO,IAAA;AAC1C,EAAA,OAAO,MAAA,CAAO,UAAA,IAAc,WAAA,CAAY,UAAU,CAAA;AACpD","file":"index.js","sourcesContent":["import { type ClassValue, clsx } from \"clsx\";\nimport { twMerge } from \"tailwind-merge\";\n\nexport function cn(...inputs: ClassValue[]) {\n return twMerge(clsx(inputs));\n}\n","/**\n * Brand Color Utilities\n *\n * Resolves Nebutra brand CSS variables at runtime for components that\n * require raw hex values (e.g. WebGL shaders, Canvas APIs, animation libraries\n * that can't consume `var(--token)` strings directly).\n *\n * Components that accept CSS color strings (inline styles, gradients, SVG)\n * should prefer `var(--brand-primary)` / `var(--brand-accent)` directly\n * instead of calling these helpers.\n */\n\n/** SSR / no-DOM fallbacks — only used when `window` is unavailable. */\nexport const BRAND_FALLBACK = {\n primary: \"#0033FE\", // nebutra-blue-500\n accent: \"#0BF1C3\", // nebutra-cyan-500\n tertiary: \"#5c7cfa\", // nebutra-blue-400\n primaryDark: \"#002ad4\", // nebutra-blue-600\n backDark: \"#000830\", // nebutra-blue-950\n} as const;\n\n/**\n * Read a CSS variable from :root and return its trimmed value.\n * Falls back to `fallback` in SSR/no-DOM environments or when the var\n * is unresolved (empty string).\n */\nexport function readCssVar(name: string, fallback: string): string {\n if (typeof window === \"undefined\" || typeof document === \"undefined\") {\n return fallback;\n }\n const value = getComputedStyle(document.documentElement).getPropertyValue(name).trim();\n return value || fallback;\n}\n\n/** Resolve `--brand-primary` to a hex/color string (with SSR fallback). */\nexport function getBrandPrimary(): string {\n return readCssVar(\"--brand-primary\", BRAND_FALLBACK.primary);\n}\n\n/** Resolve `--brand-accent` to a hex/color string (with SSR fallback). */\nexport function getBrandAccent(): string {\n return readCssVar(\"--brand-accent\", BRAND_FALLBACK.accent);\n}\n\n/** Resolve `--brand-tertiary` to a hex/color string (with SSR fallback). */\nexport function getBrandTertiary(): string {\n return readCssVar(\"--brand-tertiary\", BRAND_FALLBACK.tertiary);\n}\n","/**\n * Utility Functions\n */\n\n/**\n * Merge class names — canonical implementation from ./cn.ts\n * Uses twMerge(clsx(...)) to correctly resolve Tailwind class conflicts.\n */\nexport { cn } from \"./cn\";\n\n/**\n * Breakpoint values (matches Primer)\n */\nexport const BREAKPOINTS = {\n xs: 0,\n sm: 544,\n md: 768,\n lg: 1012,\n xl: 1280,\n} as const;\n\nexport type Breakpoint = keyof typeof BREAKPOINTS;\n\n/**\n * Check if viewport is at or above breakpoint\n */\nexport function isBreakpointUp(breakpoint: Breakpoint): boolean {\n if (typeof window === \"undefined\") return true;\n return window.innerWidth >= BREAKPOINTS[breakpoint];\n}\n\nexport {\n BRAND_FALLBACK,\n getBrandAccent,\n getBrandPrimary,\n getBrandTertiary,\n readCssVar,\n} from \"./brand-colors\";\n"]}
1
+ {"version":3,"sources":["../../src/utils/cn.ts","../../src/utils/primitive-props.ts","../../src/utils/brand-colors.ts","../../src/utils/index.ts"],"names":[],"mappings":"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","file":"index.js","sourcesContent":["import { type ClassValue, clsx } from \"clsx\";\nimport { twMerge } from \"tailwind-merge\";\n\nexport function cn(...inputs: ClassValue[]) {\n return twMerge(clsx(inputs));\n}\n","import type * as React from \"react\";\n\n/**\n * Base UI (and some Radix peers) type `style` as CSSProperties | state-function.\n * Token merge helpers only need the plain object branch — drop functions so DTS\n * builds stay green across monorepo and standalone package mirrors.\n * Returns `{}` (never undefined) so spreads stay exactOptionalPropertyTypes-safe.\n */\nexport function asPlainStyle(style: unknown): React.CSSProperties {\n if (style == null || typeof style === \"function\") return {};\n return style as React.CSSProperties;\n}\n\nexport type PrimitiveProps<T> = React.PropsWithChildren<T & { className?: string | undefined }>;\n\nexport type PrimitiveComponent<TElement, TProps> = React.ForwardRefExoticComponent<\n PrimitiveProps<TProps> & React.RefAttributes<TElement>\n>;\n\n/**\n * Resolve the HTMLElement type for a given intrinsic element tag.\n */\ntype ElementForTag<E extends keyof React.JSX.IntrinsicElements> = E extends \"button\"\n ? HTMLButtonElement\n : E extends \"span\"\n ? HTMLSpanElement\n : E extends \"img\"\n ? HTMLImageElement\n : E extends \"label\"\n ? HTMLLabelElement\n : E extends \"input\"\n ? HTMLInputElement\n : E extends \"a\"\n ? HTMLAnchorElement\n : E extends \"p\"\n ? HTMLParagraphElement\n : E extends \"h1\" | \"h2\" | \"h3\" | \"h4\" | \"h5\" | \"h6\"\n ? HTMLHeadingElement\n : HTMLElement;\n\n/**\n * Workaround for Radix UI types not resolving HTML element props (className,\n * children, etc.) with React 19 + exactOptionalPropertyTypes.\n *\n * The optional second type parameter `Extra` allows preserving Radix-specific\n * props (e.g. `asChild`, `align`, `sideOffset`) that are not standard HTML attrs.\n *\n * Usage:\n * const Header = withHtmlProps<\"h3\">(AccordionPrimitive.Header);\n * const Trigger = withHtmlProps<\"button\", { asChild?: boolean }>(DialogPrimitive.Trigger);\n * const Content = withHtmlProps<\"div\", { align?: string; sideOffset?: number }>(PopoverPrimitive.Content);\n */\n\nexport function withHtmlProps<E extends keyof React.JSX.IntrinsicElements, Extra = object>(\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n Component: any,\n): React.ForwardRefExoticComponent<\n React.ComponentPropsWithoutRef<E> & Extra & React.RefAttributes<ElementForTag<E>>\n> {\n return Component;\n}\n","/**\n * Runtime color resolution for APIs that cannot consume CSS variables\n * (Canvas, WebGL, some animation libs).\n *\n * Layers (do not mix):\n * - Product action / CTA: getProductPrimary() → semantic `--primary` (roles.action)\n * - Brand mark / AI badge / logo tint: getBrandMark() → `--brand-mark` (roles.brand)\n * - VI lock (print / legal assets): getBrandPrimary() → `--brand-primary` hex\n *\n * Prefer CSS / Tailwind in components:\n * - `bg-primary` for CTAs\n * - `bg-brand-mark` / `text-brand-mark` for Logo/AI badge (see recipe.css)\n *\n * @see packages/design/ARCHITECTURE.md\n * @see packages/design/tokens/recipe.css\n */\n\n/** SSR fallbacks when document is unavailable */\nexport const BRAND_FALLBACK = {\n /** VI 云毓蓝 — identity only */\n primary: \"#0033FE\",\n accent: \"#0BF1C3\",\n tertiary: \"#5c7cfa\",\n primaryDark: \"#002ad4\",\n backDark: \"#000830\",\n /** Soft product action (matches themes/light --primary ≈ #254bfa) */\n productPrimary: \"#254bfa\",\n /**\n * Brand mark fallback (= product action when factory brand has action≡brand).\n * Skins may diverge (e.g. Linear purple action + indigo mark).\n */\n brandMark: \"#254bfa\",\n brandMarkForeground: \"#ffffff\",\n} as const;\n\n/**\n * Read a CSS variable from :root and return its trimmed value.\n */\nexport function readCssVar(name: string, fallback: string): string {\n if (typeof window === \"undefined\" || typeof document === \"undefined\") {\n return fallback;\n }\n const value = getComputedStyle(document.documentElement).getPropertyValue(name).trim();\n return value || fallback;\n}\n\n/** Turn HSL channel triple or full color into a CSS color string. */\nfunction asCssColor(value: string, fallback: string): string {\n const v = value.trim() || fallback;\n if (\n v.startsWith(\"#\") ||\n v.startsWith(\"rgb\") ||\n v.startsWith(\"hsl\") ||\n v.startsWith(\"oklch\") ||\n v.startsWith(\"color(\")\n ) {\n return v;\n }\n // shadcn-style \"228 85% 56%\"\n return `hsl(${v})`;\n}\n\n/**\n * Product action color — follows the active skin (`--primary`).\n * Use for shaders/canvas that must match buttons/CTAs.\n */\nexport function getProductPrimary(): string {\n return asCssColor(readCssVar(\"--primary\", \"228 85% 56%\"), BRAND_FALLBACK.productPrimary);\n}\n\n/** VI lock color — legal / print lockups only (not product chrome). */\nexport function getBrandPrimary(): string {\n return asCssVarColor(\"--brand-primary\", BRAND_FALLBACK.primary);\n}\n\n/**\n * Product brand-mark (roles.brand) — Logo tile, AI badge, identity chips.\n * Never use for default CTA (that is getProductPrimary / --primary).\n */\nexport function getBrandMark(): string {\n const raw = readCssVar(\"--brand-mark\", \"228 85% 56%\");\n // Factory recipe defaults `--brand-mark: var(--primary)` — resolve to action color.\n if (/var\\(\\s*--primary\\s*\\)/u.test(raw)) {\n return getProductPrimary();\n }\n return asCssColor(raw, BRAND_FALLBACK.brandMark);\n}\n\n/** Foreground on brand-mark surfaces. */\nexport function getBrandMarkForeground(): string {\n const raw = readCssVar(\"--brand-mark-foreground\", \"0 0% 100%\");\n if (/var\\(\\s*--primary-foreground\\s*\\)/u.test(raw)) {\n return asCssColor(\n readCssVar(\"--primary-foreground\", \"0 0% 100%\"),\n BRAND_FALLBACK.brandMarkForeground,\n );\n }\n return asCssColor(raw, BRAND_FALLBACK.brandMarkForeground);\n}\n\nfunction asCssVarColor(name: string, fallback: string): string {\n return asCssColor(readCssVar(name, fallback), fallback);\n}\n\nexport function getBrandAccent(): string {\n return asCssVarColor(\"--brand-accent\", BRAND_FALLBACK.accent);\n}\n\nexport function getBrandTertiary(): string {\n return asCssVarColor(\"--brand-tertiary\", BRAND_FALLBACK.tertiary);\n}\n","/**\n * Utility Functions\n */\n\n/**\n * Merge class names — canonical implementation from ./cn.ts\n * Uses twMerge(clsx(...)) to correctly resolve Tailwind class conflicts.\n */\nexport { cn } from \"./cn\";\nexport { asPlainStyle, withHtmlProps, type PrimitiveProps, type PrimitiveComponent } from \"./primitive-props\";\n\n/**\n * Breakpoint values (matches Primer)\n */\nexport const BREAKPOINTS = {\n xs: 0,\n sm: 544,\n md: 768,\n lg: 1012,\n xl: 1280,\n} as const;\n\nexport type Breakpoint = keyof typeof BREAKPOINTS;\n\n/**\n * Check if viewport is at or above breakpoint\n */\nexport function isBreakpointUp(breakpoint: Breakpoint): boolean {\n if (typeof window === \"undefined\") return true;\n return window.innerWidth >= BREAKPOINTS[breakpoint];\n}\n\nexport {\n BRAND_FALLBACK,\n getBrandAccent,\n getBrandMark,\n getBrandMarkForeground,\n getBrandPrimary,\n getBrandTertiary,\n getProductPrimary,\n readCssVar,\n} from \"./brand-colors\";\n"]}
package/package.json CHANGED
@@ -1,11 +1,13 @@
1
1
  {
2
2
  "name": "@nebutra/ui",
3
- "version": "0.2.1",
4
- "description": "Unified UI component library — Lobe UI + Radix + HeroUI + layout components",
3
+ "version": "0.2.3",
4
+ "description": "Nebutra design-system UI primitives, patterns, layouts, and token-integrated components",
5
5
  "private": false,
6
6
  "license": "MIT",
7
7
  "type": "module",
8
- "sideEffects": false,
8
+ "sideEffects": [
9
+ "**/*.css"
10
+ ],
9
11
  "exports": {
10
12
  ".": {
11
13
  "types": "./dist/index.d.ts",
@@ -27,6 +29,10 @@
27
29
  "types": "./dist/icons/index.d.ts",
28
30
  "import": "./dist/icons/index.js"
29
31
  },
32
+ "./agent": {
33
+ "types": "./dist/agent/index.d.ts",
34
+ "import": "./dist/agent/index.js"
35
+ },
30
36
  "./theme": {
31
37
  "types": "./dist/theme/index.d.ts",
32
38
  "import": "./dist/theme/index.js"
@@ -35,6 +41,10 @@
35
41
  "types": "./dist/primitives/index.d.ts",
36
42
  "import": "./dist/primitives/index.js"
37
43
  },
44
+ "./primitives/canonical": {
45
+ "types": "./dist/primitives/canonical.d.ts",
46
+ "import": "./dist/primitives/canonical.js"
47
+ },
38
48
  "./patterns": {
39
49
  "types": "./dist/patterns/index.d.ts",
40
50
  "import": "./dist/patterns/index.js"
@@ -43,11 +53,26 @@
43
53
  "types": "./dist/typography/index.d.ts",
44
54
  "import": "./dist/typography/index.js"
45
55
  },
46
- "./typography/fonts.css": "./dist/typography/fonts.css",
56
+ "./typography/fonts.css": "./src/typography/fonts.css",
57
+ "./styles/sources.css": "./src/styles/sources.css",
58
+ "./styles/preset.css": "./src/styles/preset.css",
59
+ "./styles.css": "./src/styles/preset.css",
47
60
  "./hooks": {
48
61
  "types": "./dist/hooks/index.d.ts",
49
62
  "import": "./dist/hooks/index.js"
50
63
  },
64
+ "./shared/animation": {
65
+ "types": "./dist/shared/animation/index.d.ts",
66
+ "import": "./dist/shared/animation/index.js"
67
+ },
68
+ "./shared/animation/css": {
69
+ "types": "./dist/shared/animation/css/index.d.ts",
70
+ "import": "./dist/shared/animation/css/index.js"
71
+ },
72
+ "./shared/animation/motion": {
73
+ "types": "./dist/shared/animation/motion/index.d.ts",
74
+ "import": "./dist/shared/animation/motion/index.js"
75
+ },
51
76
  "./utils": {
52
77
  "types": "./dist/utils/index.d.ts",
53
78
  "import": "./dist/utils/index.js"
@@ -59,6 +84,8 @@
59
84
  },
60
85
  "files": [
61
86
  "dist",
87
+ "src/styles",
88
+ "src/typography/fonts.css",
62
89
  "README.md"
63
90
  ],
64
91
  "dependencies": {
@@ -68,11 +95,13 @@
68
95
  "@lobehub/fluent-emoji": "^4.1.0",
69
96
  "@lobehub/icons": "^5.0.1",
70
97
  "@lobehub/ui": "^5.4.0",
71
- "@xyflow/react": "^12.10.2",
72
98
  "@number-flow/react": "^0.5.5",
73
99
  "@paper-design/shaders-react": "^0.0.71",
74
100
  "@phosphor-icons/react": "^2.1.10",
75
101
  "@react-types/shared": "^3.33.1",
102
+ "@tanstack/react-table": "^8.21.3",
103
+ "@tanstack/react-virtual": "^3.13.24",
104
+ "@xyflow/react": "^12.10.2",
76
105
  "antd": "^6.3.1",
77
106
  "antd-style": "^4.1.0",
78
107
  "canvas-confetti": "^1.9.4",
@@ -85,7 +114,6 @@
85
114
  "embla-carousel-react": "^8.6.0",
86
115
  "framer-motion": "^12.35.0",
87
116
  "input-otp": "^1.4.2",
88
- "motion": "^12.35.0",
89
117
  "piri": "^1.3.2",
90
118
  "react": "^19.2.4",
91
119
  "react-ascii-text": "*",
@@ -94,24 +122,26 @@
94
122
  "react-markdown": "^10.1.0",
95
123
  "react-resizable-panels": "^4.7.1",
96
124
  "react-syntax-highlighter": "^16.1.1",
97
- "remark-gfm": "^4.0.1",
98
125
  "react-tweet": "^3.3.0",
99
126
  "react-use-measure": "^2.1.7",
100
127
  "recharts": "^3.7.0",
128
+ "remark-gfm": "^4.0.1",
101
129
  "rough-notation": "^0.5.1",
102
130
  "sonner": "^2.0.7",
103
131
  "streamdown": "^2.5.0",
104
132
  "tailwind-merge": "^3.5.0",
105
133
  "usehooks-ts": "^3.1.1",
106
134
  "vaul": "^1.1.2",
107
- "@nebutra/brand": "0.1.1",
108
- "@nebutra/graph-model": "0.2.1",
109
- "@nebutra/icons": "0.1.1",
110
- "@nebutra/tokens": "0.1.1"
135
+ "@nebutra/tokens": "0.1.3",
136
+ "@nebutra/icons": "0.1.2",
137
+ "@nebutra/graph-model": "0.2.3",
138
+ "@nebutra/brand": "0.1.2"
111
139
  },
112
140
  "peerDependencies": {
113
141
  "@clerk/nextjs": ">=5.0.0",
142
+ "driver.js": "^1.4.0",
114
143
  "next": ">=14.0.0",
144
+ "next-intl": "^4.12.0",
115
145
  "react": ">=19.0.0",
116
146
  "react-dom": ">=19.0.0"
117
147
  },
@@ -119,11 +149,18 @@
119
149
  "@clerk/nextjs": {
120
150
  "optional": true
121
151
  },
152
+ "driver.js": {
153
+ "optional": true
154
+ },
122
155
  "next": {
123
156
  "optional": true
157
+ },
158
+ "next-intl": {
159
+ "optional": true
124
160
  }
125
161
  },
126
162
  "devDependencies": {
163
+ "@storybook/react": "8.6.17",
127
164
  "@storybook/test": "^8.6.17",
128
165
  "@testing-library/jest-dom": "^6.9.1",
129
166
  "@testing-library/react": "^16.3.2",
@@ -132,14 +169,17 @@
132
169
  "@types/react": "^19.2.14",
133
170
  "@types/react-syntax-highlighter": "^15.5.13",
134
171
  "@types/three": "^0.183.1",
172
+ "@vitejs/plugin-react-swc": "^4.3.1",
173
+ "driver.js": "^1.4.0",
135
174
  "next": "^16.2.6",
175
+ "next-intl": "^4.12.0",
136
176
  "storybook": "^8.6.17",
137
- "@vitejs/plugin-react": "^4.3.4",
138
177
  "tsup": "^8.5.1",
139
178
  "tsx": "^4.21.0",
140
179
  "typescript": "^5.9.3",
141
180
  "vitest": "^4.0.18",
142
- "@nebutra/design-tokens": "0.1.1"
181
+ "jsdom": "^29.1.1",
182
+ "@nebutra/design-tokens": "0.1.2"
143
183
  },
144
184
  "homepage": "https://github.com/Nebutra/Nebutra-Sailor/tree/main/packages/design/ui#readme",
145
185
  "repository": {
@@ -157,11 +197,13 @@
157
197
  "@react-three/fiber": "^9.5.0",
158
198
  "three": "^0.183.2"
159
199
  },
200
+ "main": "./dist/index.js",
201
+ "types": "./dist/index.d.ts",
160
202
  "scripts": {
161
203
  "test": "vitest run",
162
204
  "typecheck": "tsc --noEmit",
163
205
  "build:registry": "tsx scripts/build-registry.ts",
164
- "build": "NODE_OPTIONS='--max-old-space-size=6144' tsup && tsx scripts/build-registry.ts",
206
+ "build": "NODE_OPTIONS='--max-old-space-size=6144' tsup",
165
207
  "dev": "tsup --watch"
166
208
  }
167
209
  }
@@ -0,0 +1,61 @@
1
+ /**
2
+ * brand-override.css — Custom Brand Configuration (legacy scale remap)
3
+ *
4
+ * Prefer the skin surface for product chrome:
5
+ * @import "@nebutra/tokens/skins/<name>.css";
6
+ * @see packages/design/tokens/skins/README.md
7
+ *
8
+ * This file remaps the **blue scale** only (residual `bg-blue-9` call sites).
9
+ * New code should use semantic tokens (`bg-primary`, `border-border`).
10
+ *
11
+ * Drop into globals.css after tokens if you still need scale remapping:
12
+ * @import "@nebutra/ui/styles/brand-override.css";
13
+ *
14
+ * ────────────────────────────────────────────────────────────
15
+ * HOW THE CASCADE WORKS
16
+ *
17
+ * 1. You define: --your-primary-* (11 steps)
18
+ * 2. System maps: --blue-9 → --your-primary-500 (solid fill)
19
+ * --blue-3 → --your-primary-200 (component bg)
20
+ * 3. Residual blue-N utilities follow your brand; semantic CSS still wins
21
+ * for Button / Input that already use --primary.
22
+ * ────────────────────────────────────────────────────────────
23
+ */
24
+
25
+ :root {
26
+ /* ══════════════════════════════════════════════════════════
27
+ PRIMARY BRAND COLOR — replace #0033FE with your primary
28
+ ════════════════════════════════════════════════════════ */
29
+ --nebutra-blue-50: #f0f4ff; /* lightest tint — backgrounds */
30
+ --nebutra-blue-100: #dbe4ff;
31
+ --nebutra-blue-200: #bac8ff;
32
+ --nebutra-blue-300: #91a7ff;
33
+ --nebutra-blue-400: #5c7cfa;
34
+ --nebutra-blue-500: #0033fe; /* ← YOUR PRIMARY COLOR HERE */
35
+ --nebutra-blue-600: #002ad4;
36
+ --nebutra-blue-700: #0021ab;
37
+ --nebutra-blue-800: #001882;
38
+ --nebutra-blue-900: #000f59;
39
+ --nebutra-blue-950: #000830; /* darkest — text */
40
+
41
+ /* ══════════════════════════════════════════════════════════
42
+ SECONDARY ACCENT COLOR — replace #0BF1C3 with your accent
43
+ ════════════════════════════════════════════════════════ */
44
+ --nebutra-cyan-50: #e6fff8; /* lightest tint */
45
+ --nebutra-cyan-100: #b3ffec;
46
+ --nebutra-cyan-200: #80ffe0;
47
+ --nebutra-cyan-300: #4dfcd4;
48
+ --nebutra-cyan-400: #1af7c8;
49
+ --nebutra-cyan-500: #0bf1c3; /* ← YOUR ACCENT COLOR HERE */
50
+ --nebutra-cyan-600: #09c9a3;
51
+ --nebutra-cyan-700: #07a183;
52
+ --nebutra-cyan-800: #057963;
53
+ --nebutra-cyan-900: #035143;
54
+ --nebutra-cyan-950: #012923; /* darkest */
55
+
56
+ /* ══════════════════════════════════════════════════════════
57
+ OPTIONAL: Brand name tokens (used in metadata / docs only)
58
+ ════════════════════════════════════════════════════════ */
59
+ /* --brand-name: "Your Brand"; */
60
+ /* --brand-domain: "yourbrand.com"; */
61
+ }
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Full design-system CSS entry for product apps (Tailwind v4).
3
+ *
4
+ * Architecture: packages/design/ARCHITECTURE.md
5
+ *
6
+ * One import wires:
7
+ * 1. Tailwind
8
+ * 2. @nebutra/tokens (semantic CSS variables + @theme) ← skin surface
9
+ * 3. Source scan so UI CVA classes are generated
10
+ * 4. Typography CSS variables
11
+ * 5. dark variant
12
+ *
13
+ * Simple apps:
14
+ * @import "@nebutra/ui/styles/preset.css";
15
+ *
16
+ * Complex apps (fumadocs, katex first):
17
+ * @import "tailwindcss";
18
+ * @import "…third-party…";
19
+ * @import "@nebutra/tokens/styles.css";
20
+ * @import "@nebutra/ui/styles/sources.css";
21
+ */
22
+
23
+ @import "tailwindcss";
24
+ @import "@nebutra/tokens/styles.css";
25
+ @import "@nebutra/tokens/recipe.css";
26
+ @import "./sources.css";
27
+ @import "../typography/fonts.css";
28
+
29
+ @custom-variant dark (&:is(.dark *));
@@ -0,0 +1,37 @@
1
+ /**
2
+ * Tailwind v4 source registration for @nebutra/ui (+ icons).
3
+ *
4
+ * WHY THIS FILE EXISTS
5
+ * --------------------
6
+ * UI primitives style themselves with CVA *utility class strings*, not a
7
+ * prebuilt component CSS sheet. Under Tailwind v4 those utilities only exist
8
+ * in an app’s bundle if the app’s CSS pipeline *scans* this package.
9
+ *
10
+ * Best practice: the design-system package owns the scan paths.
11
+ * Apps import this file once — they never hardcode monorepo-relative @source.
12
+ *
13
+ * Usage (after @import "tailwindcss"):
14
+ * @import "@nebutra/ui/styles/sources.css";
15
+ *
16
+ * Or use the full preset:
17
+ * @import "@nebutra/ui/styles/preset.css";
18
+ *
19
+ * Paths are relative to THIS file so resolution is stable in workspace
20
+ * and when resolved through node_modules/@nebutra/ui.
21
+ */
22
+
23
+ /* All CVA / className strings under the UI package */
24
+ @source "../**/*.{ts,tsx,js,jsx}";
25
+
26
+ /* Icon components often appear in class strings next to UI primitives */
27
+ @source "../../../icons/src/**/*.{ts,tsx,js,jsx}";
28
+
29
+ /*
30
+ * @nebutra/i18n ships rendered components (locale-switcher, market-locale-picker),
31
+ * so its class strings need compiling too. Without this the utilities silently
32
+ * do not exist: the locale switcher asked for `bg-neutral-1` to opt out of the
33
+ * translucent popover surface and got nothing, so the DS default `bg-popover/95`
34
+ * kept winning and the panel stayed see-through — a fix that was correct in the
35
+ * source and absent from the stylesheet.
36
+ */
37
+ @source "../../../../platform/i18n/src/**/*.{ts,tsx,js,jsx}";
@@ -0,0 +1,124 @@
1
+ /**
2
+ * Font rules — the typography BEHAVIOUR layer (which element gets which stack).
3
+ * The STACKS themselves are owned by @nebutra/tokens, generated from
4
+ * packages/design/design-tokens/tokens/core.json → fontFamily.*.
5
+ *
6
+ * Font loading (Next.js apps): each app's layout.tsx applies the loader classes
7
+ * GeistSans → --font-geist-sans (variable, 100–900) Latin + numerals
8
+ * GeistMono → --font-geist-mono (variable, 100–900) code
9
+ * cjkFontClassName → --font-vivo-sans-sc (@nebutra/fonts/next/cjk) CJK
10
+ * and the token stacks reference those variables in that order, so Geist keeps
11
+ * Latin and only CJK falls through to vivo Sans SC.
12
+ *
13
+ * IMPORT ORDER MATTERS: this file must come AFTER @nebutra/tokens/styles.css
14
+ * (see ../styles/preset.css). It used to re-declare --font-sans / --font-heading /
15
+ * --font-mono here as Geist-only literals; being the later import, those copies
16
+ * won, and the CJK half of every token stack was silently discarded. Declare
17
+ * stacks in the tokens, never here.
18
+ */
19
+
20
+ /* ============================================
21
+ CSS Custom Properties — derived aliases only
22
+ ============================================ */
23
+
24
+ :root {
25
+ /* Legacy alias for the body/UI stack — the stack lives in the tokens. */
26
+ --font-primary: var(--font-sans);
27
+
28
+ /* CJK — appended as a fallback on the rules below (see the note there). The
29
+ token already leads with the self-hosted face; the system families repeat
30
+ here so this alias still degrades on its own. */
31
+ --font-cjk:
32
+ var(--font-cn), "Noto Sans SC", "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", sans-serif;
33
+
34
+ /* Not a token: no Nebutra surface uses a serif, this exists for shadcn parity. */
35
+ --font-serif: Georgia, Cambria, "Times New Roman", Times, serif;
36
+ }
37
+
38
+ /* ============================================
39
+ Font Smoothing & Rendering
40
+ ============================================ */
41
+
42
+ html {
43
+ -webkit-font-smoothing: antialiased;
44
+ -moz-osx-font-smoothing: grayscale;
45
+ text-rendering: optimizeLegibility;
46
+ font-feature-settings:
47
+ "calt" 1,
48
+ "liga" 1;
49
+ /* Variable-font polish: */
50
+ /* - font-synthesis: none → forbid faux-bold / faux-italic synthesis;
51
+ variable fonts already ship every weight/style, synthesised faces
52
+ look fuzzy at sub-pixel boundaries.
53
+ - font-optical-sizing: auto → tells the engine to use the opsz axis
54
+ on fonts that ship one (Geist Sans, Geist Mono, Inter, Playfair),
55
+ so glyphs are rendered with weights tuned to their display size
56
+ instead of being scaled uniformly. */
57
+ font-synthesis: none;
58
+ font-optical-sizing: auto;
59
+ }
60
+
61
+ /* ============================================
62
+ Base Typography
63
+ ============================================ */
64
+
65
+ body {
66
+ /* Font precedence in ONE place: explicit user choice (--user-ui-font) →
67
+ active theme/DESIGN font (--font-sans) → default; the CJK stack is always
68
+ appended as a fallback so Chinese/Japanese/Korean glyphs render regardless
69
+ of the (often Latin-only) theme font. This replaces a blanket :lang(zh)
70
+ override that used to discard the theme font entirely. */
71
+ font-family: var(--user-ui-font, var(--font-sans)), var(--font-cjk);
72
+ /* An explicit user size (--user-ui-font-size) wins; otherwise the active
73
+ theme/DESIGN type-scale (--text-base); otherwise the 1rem default. This is
74
+ backward-compatible — with neither var set it resolves to exactly 1rem.
75
+ (Previously this was a hardcoded 1rem that, being unlayered, silently
76
+ overrode the app's --user-ui-font-size font-size control.) */
77
+ font-size: var(--user-ui-font-size, var(--text-base, 1rem));
78
+ line-height: 1.5;
79
+ font-weight: 400;
80
+ }
81
+
82
+ /* Headings */
83
+ h1,
84
+ h2,
85
+ h3,
86
+ h4,
87
+ h5,
88
+ h6 {
89
+ font-family: var(--font-heading), var(--font-cjk);
90
+ /* Theme/DESIGN can lighten headings via fontWeight.heading; default 600. */
91
+ font-weight: var(--font-weight-heading, 600);
92
+ line-height: 1.25;
93
+ }
94
+
95
+ /* Code */
96
+ code,
97
+ kbd,
98
+ pre,
99
+ samp {
100
+ font-family: var(--user-code-font, var(--font-mono)), var(--font-cjk);
101
+ }
102
+
103
+ /* ============================================
104
+ Font Feature Settings
105
+ ============================================ */
106
+
107
+ /* Enable tabular figures for numbers in tables */
108
+ .tabular-nums {
109
+ font-feature-settings: "tnum" 1;
110
+ }
111
+
112
+ /* Enable case-sensitive forms for all-caps text */
113
+ .case-sensitive {
114
+ font-feature-settings: "case" 1;
115
+ }
116
+
117
+ /* ============================================
118
+ CJK Support
119
+ ============================================ */
120
+
121
+ /* No blanket :lang(zh) font-family override here. The CJK stack is appended as
122
+ a fallback on the body / heading / code rules above, so the active theme or
123
+ DESIGN.md font drives Latin text on every locale while CJK glyphs still fall
124
+ back to --font-cjk. (A blanket override would discard the theme font.) */