@waveinno/ui 0.3.0 → 0.4.0
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/CHANGELOG.md +17 -0
- package/README.md +29 -11
- package/dist/components/brand/waveinno-logo.js +1 -1
- package/dist/components/charts/bar-list.js +1 -1
- package/dist/components/charts/heatmap.js +1 -1
- package/dist/components/patterns/activity-feed.js +1 -1
- package/dist/components/patterns/app-launcher.js +1 -1
- package/dist/components/patterns/data-table-edit.js +1 -1
- package/dist/components/patterns/data-table-filters.js +1 -1
- package/dist/components/patterns/data-table.js +1 -1
- package/dist/components/patterns/page-header.js +1 -1
- package/dist/components/patterns/page-hero.js +1 -1
- package/dist/components/patterns/stat-card.js +1 -1
- package/dist/components/patterns/timeline.js +1 -1
- package/dist/components/ui/alert.js +1 -1
- package/dist/components/ui/avatar.js +1 -1
- package/dist/components/ui/badge.js +1 -1
- package/dist/components/ui/button.js +1 -1
- package/dist/components/ui/checkbox.js +1 -1
- package/dist/components/ui/combobox.js +1 -1
- package/dist/components/ui/confirm-dialog.js +1 -1
- package/dist/components/ui/dialog.js +1 -1
- package/dist/components/ui/dropdown-menu.js +1 -1
- package/dist/components/ui/file-upload.js +1 -1
- package/dist/components/ui/kbd.js +1 -1
- package/dist/components/ui/menu.js +1 -1
- package/dist/components/ui/password-input.js +1 -1
- package/dist/components/ui/pin-input.js +1 -1
- package/dist/components/ui/popover.js +1 -1
- package/dist/components/ui/progress.js +1 -1
- package/dist/components/ui/radio-group.js +1 -1
- package/dist/components/ui/segmented.d.ts +1 -1
- package/dist/components/ui/segmented.js +1 -1
- package/dist/components/ui/sheet.js +1 -1
- package/dist/components/ui/slider.js +1 -1
- package/dist/components/ui/spinner.js +1 -1
- package/dist/components/ui/tabs.js +1 -1
- package/dist/components/ui/toast.js +1 -1
- package/dist/hooks/index.d.ts +1 -0
- package/dist/hooks/index.js +1 -1
- package/dist/hooks/use-router.d.ts +41 -0
- package/dist/hooks/use-router.js +1 -0
- package/dist/lib/index.d.ts +1 -0
- package/dist/lib/index.js +1 -1
- package/dist/lib/theme.d.ts +48 -0
- package/dist/lib/theme.js +7 -0
- package/dist/next/index.d.ts +6 -0
- package/dist/next/index.js +1 -0
- package/dist/shell/app-shell.js +1 -1
- package/dist/shell/app-switcher.js +1 -1
- package/dist/shell/command-palette.js +1 -1
- package/dist/shell/icon-rail.js +1 -1
- package/dist/shell/mobile-nav.js +1 -1
- package/dist/shell/module-sidebar.js +1 -1
- package/dist/shell/notifications.js +1 -1
- package/dist/shell/placeholder-screen.js +1 -1
- package/dist/shell/topbar.js +1 -1
- package/dist/shell/use-active.js +1 -1
- package/dist/shell/user-menu.js +1 -1
- package/dist/styles.css +18 -5
- package/package.json +11 -1
package/dist/lib/index.d.ts
CHANGED
package/dist/lib/index.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export*from"./currency.js";export*from"./format.js";export*from"./utils.js";export*from"./boot-script.js";
|
|
1
|
+
export*from"./currency.js";export*from"./format.js";export*from"./utils.js";export*from"./boot-script.js";export*from"./theme.js";
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* createTheme — a whole palette from one brand colour.
|
|
3
|
+
*
|
|
4
|
+
* Every component reads the semantic tokens in styles.css (`--primary`,
|
|
5
|
+
* `--brand-1`, `--r-card`, …), so a theme is nothing but new values for them.
|
|
6
|
+
* Give it the brand colour and it derives the rest in OKLCH, where "lighter"
|
|
7
|
+
* and "darker" look evenly lighter and darker across hues: the hover step, the
|
|
8
|
+
* soft tint, the brand gradient, the ink for dark panels, and a dark-mode set
|
|
9
|
+
* that stays readable on a near-black canvas. Radius and fonts ride along.
|
|
10
|
+
*
|
|
11
|
+
* const { css } = createTheme({ primary: "#0f9d7a", radius: "lg", fontSans: "Manrope" });
|
|
12
|
+
* // paste `css` after @import "@waveinno/ui/styles.css", or inject it at runtime.
|
|
13
|
+
*
|
|
14
|
+
* Framework-free: the docs' theme builder and a product's build script use the same function.
|
|
15
|
+
*/
|
|
16
|
+
export type ThemeRadius = "none" | "sm" | "md" | "lg" | "xl";
|
|
17
|
+
export interface ThemeOptions {
|
|
18
|
+
/** The brand colour: buttons, links, the chosen item. Hex, e.g. "#4f46e5". */
|
|
19
|
+
primary: string;
|
|
20
|
+
/** The two stops of the brand gradient. Default: drawn from `primary`. */
|
|
21
|
+
brand?: [string, string];
|
|
22
|
+
/** A second colour for charts and highlights. Default: `primary` turned a little round the wheel. */
|
|
23
|
+
accent?: string;
|
|
24
|
+
/** The deep colour of dark panels and value bubbles. Default: `primary` at night. */
|
|
25
|
+
ink?: string;
|
|
26
|
+
radius?: ThemeRadius;
|
|
27
|
+
/** Body font family name, e.g. "Manrope". Bangla falls back to Noto Sans Bengali. */
|
|
28
|
+
fontSans?: string;
|
|
29
|
+
/** Headings and big numbers. */
|
|
30
|
+
fontDisplay?: string;
|
|
31
|
+
fontMono?: string;
|
|
32
|
+
}
|
|
33
|
+
export interface CreatedTheme {
|
|
34
|
+
light: Record<string, string>;
|
|
35
|
+
dark: Record<string, string>;
|
|
36
|
+
/** `:root { … }` and `[data-theme="dark"] { … }`, ready to paste. */
|
|
37
|
+
css: string;
|
|
38
|
+
}
|
|
39
|
+
type Lch = {
|
|
40
|
+
l: number;
|
|
41
|
+
c: number;
|
|
42
|
+
h: number;
|
|
43
|
+
};
|
|
44
|
+
export declare function hexToOklch(hex: string): Lch;
|
|
45
|
+
/** Back to hex, lowering chroma (never hue or lightness) until it fits in sRGB. */
|
|
46
|
+
export declare function oklchToHex(lch: Lch): string;
|
|
47
|
+
export declare function createTheme(options: ThemeOptions): CreatedTheme;
|
|
48
|
+
export {};
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
const j=t=>t<=.04045?t/12.92:((t+.055)/1.055)**2.4,I=t=>t<=.0031308?12.92*t:1.055*t**.4166666666666667-.055;function y(t){let r=t.trim().replace(/^#/,"");r.length===3&&(r=[...r].map(e=>e+e).join(""));const n=parseInt(r.slice(0,6),16);if(Number.isNaN(n))throw new Error(`createTheme: "${t}" is not a hex colour`);return[n>>16&255,n>>8&255,n&255].map(e=>e/255)}function f(t){const[r,n,e]=y(t).map(j),i=Math.cbrt(.4122214708*r+.5363325363*n+.0514459929*e),a=Math.cbrt(.2119034982*r+.6806995451*n+.1073969566*e),c=Math.cbrt(.0883024619*r+.2817188376*n+.6299787005*e),m=.2104542553*i+.793617785*a-.0040720468*c,o=1.9779984951*i-2.428592205*a+.4505937099*c,l=.0259040371*i+.7827717662*a-.808675766*c;return{l:m,c:Math.hypot(o,l),h:(Math.atan2(l,o)*180/Math.PI+360)%360}}function M({l:t,c:r,h:n}){const e=r*Math.cos(n*Math.PI/180),i=r*Math.sin(n*Math.PI/180),a=(t+.3963377774*e+.2158037573*i)**3,c=(t-.1055613458*e-.0638541728*i)**3,m=(t-.0894841775*e-1.291485548*i)**3;return[4.0767416621*a-3.3077115913*c+.2309699292*m,-1.2684380046*a+2.6097574011*c-.3413193965*m,-.0041960863*a-.7034186147*c+1.707614701*m]}const k=t=>t.every(r=>r>=-5e-4&&r<=1.0005);function s(t){const r=Math.min(1,Math.max(0,t.l));let n=0,e=Math.max(0,t.c);if(!k(M({l:r,c:e,h:t.h}))){for(let a=0;a<24;a++){const c=(n+e)/2;k(M({l:r,c,h:t.h}))?n=c:e=c}e=n}return`#${M({l:r,c:e,h:t.h}).map(a=>Math.round(Math.min(1,Math.max(0,I(Math.min(1,Math.max(0,a)))))*255)).map(a=>a.toString(16).padStart(2,"0")).join("")}`}const b=(t,r)=>({l:t.l+(r.l??0),c:Math.max(0,t.c+(r.c??0)),h:(t.h+(r.h??0)+360)%360}),h=(t,r)=>({...t,...r}),d=(t,r)=>{const[n,e,i]=y(t).map(a=>Math.round(a*255));return`rgba(${n}, ${e}, ${i}, ${r})`},N={none:0,sm:.75,md:1,lg:1.4,xl:1.8},T='"Noto Sans Bengali"',p=t=>/^[\w-]+$/.test(t)?t:`"${t.replace(/"/g,"")}"`;function P(t){const r=f(t.primary),n=r.l>.62?h(r,{l:.58}):r.l<.32?h(r,{l:.38}):r,e=s(n),i=t.brand?.[0]??s(b(n,{l:-.04,c:.03,h:-10})),a=t.brand?.[1]??s(b(n,{l:.08,c:.02,h:28})),c=t.accent??s(b(n,{l:.02,h:32})),m=t.ink??s(h(n,{l:.2,c:Math.min(.09,n.c*.5)})),o={"--primary":e,"--primary-hover":s(b(n,{l:-.07})),"--primary-subtle":s(h(n,{l:.96,c:Math.min(.03,n.c*.25)})),"--primary-muted":s(h(n,{l:.87,c:Math.min(.08,n.c*.45)})),"--accent":c,"--info":e,"--info-subtle":s(h(n,{l:.96,c:Math.min(.03,n.c*.25)})),"--selected":s(h(n,{l:.955,c:Math.min(.035,n.c*.3)})),"--brand-1":i,"--brand-2":a,"--ink":m},l=h(n,{l:Math.max(.66,n.l+.1)}),g=s(l),x={"--primary":g,"--primary-hover":s(b(l,{l:.07})),"--primary-subtle":d(g,.16),"--primary-muted":d(s(b(l,{l:.12})),.38),"--accent":s(h(f(c),{l:Math.max(.7,f(c).l+.1)})),"--info":g,"--info-subtle":d(g,.14),"--selected":d(g,.16)};if(t.radius){const u=N[t.radius];o["--radius-scale"]=String(u),o["--r-ctl"]=`${Math.round(8*u)}px`,o["--r-card"]=`${Math.round(10*u)}px`,o["--r-dlg"]=`${Math.round(14*u)}px`}t.fontSans&&(o["--font-inter"]=`${p(t.fontSans)}, ${T}`),t.fontDisplay&&(o["--font-jakarta"]=`${p(t.fontDisplay)}, ${T}`),t.fontMono&&(o["--font-jetbrains"]=p(t.fontMono));const $=(u,L)=>`${u} {
|
|
2
|
+
${Object.entries(L).map(([R,S])=>` ${R}: ${S};`).join(`
|
|
3
|
+
`)}
|
|
4
|
+
}`;return{light:o,dark:x,css:`${$(":root",o)}
|
|
5
|
+
|
|
6
|
+
${$('[data-theme="dark"]',x)}
|
|
7
|
+
`}}export{P as createTheme,f as hexToOklch,s as oklchToHex};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use client";import{jsx as p}from"react/jsx-runtime";import t from"next/link";import{usePathname as o,useRouter as u}from"next/navigation";import*as a from"react";import{RouterProvider as n}from"../hooks/use-router.js";const i={Link:t,usePathname:()=>o()??"/",useNavigate:()=>{const e=u();return a.useCallback(r=>e.push(r),[e])}};function m({children:e}){return p(n,{adapter:i,children:e})}export{m as NextRouterProvider,i as nextRouter};
|
package/dist/shell/app-shell.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{jsx as e,jsxs as u}from"react/jsx-runtime";import{
|
|
1
|
+
"use client";import{jsx as e,jsxs as u}from"react/jsx-runtime";import{useRouterAdapter as g}from"../hooks/use-router.js";import*as a from"react";import{Toaster as R}from"../components/ui/toast.js";import{TooltipProvider as b}from"../components/ui/tooltip.js";import{useHotkey as S,useNumberHotkeys as N}from"../hooks/use-hotkey.js";import{useApp as d}from"../store/app-store.js";import{useUi as f}from"../store/ui-store.js";import{CommandPalette as P}from"./command-palette.js";import{ShellProvider as k}from"./config.js";import{IconRail as w}from"./icon-rail.js";import{MobileNav as x}from"./mobile-nav.js";import{ModuleSidebar as A}from"./module-sidebar.js";import{RecordDrawer as C}from"./record-drawer.js";import{Topbar as D}from"./topbar.js";import{useActive as F}from"./use-active.js";function V({config:t,children:r}){return e(k,{config:t,children:e(T,{children:r})})}function T({children:t}){const r=f(o=>o.hydrate),i=d(o=>o.hydrate),m=d(o=>o.syncFromRoute),h=f(o=>o.togglePanel),{navigate:l}=g(),{cfg:p,pathname:y,mod:n,rail:v}=F();a.useEffect(()=>{r(),i(p.apps.map(o=>o.id))},[r,i,p.apps]),a.useEffect(()=>{m(n.app)},[n.app,m]),S({key:"b",mod:!0},h);const s=v.order;return N(a.useCallback(o=>{const c=s[o];c&&l(c.href)},[s,l])),u(b,{delayDuration:400,skipDelayDuration:200,children:[u("div",{className:"shell-grid overflow-hidden",children:[e(w,{}),e(A,{}),e(D,{}),e("main",{id:"main",className:"col-start-3 col-end-4 row-start-2 overflow-y-auto px-4 pb-16 pt-5 sm:px-6",children:e("div",{className:"page-in mx-auto w-full max-w-[1600px]",children:t},y)})]}),e(C,{}),e(P,{}),e(x,{}),e(R,{})]})}export{V as AppShell};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{Fragment as _,jsx as t,jsxs as s}from"react/jsx-runtime";import{ArrowRight as E,Check as I,CornerDownLeft as R}from"lucide-react";import{
|
|
1
|
+
"use client";import{Fragment as _,jsx as t,jsxs as s}from"react/jsx-runtime";import{ArrowRight as E,Check as I,CornerDownLeft as R}from"lucide-react";import{useRouterAdapter as S}from"../hooks/use-router.js";import*as f from"react";import{WaveWordmark as T}from"../components/brand/logo.js";import{StatusBadge as K}from"../components/ui/badge.js";import{Button as B}from"../components/ui/button.js";import{Dialog as O,DialogContent as L,DialogDescription as H,DialogTitle as U}from"../components/ui/dialog.js";import{Tooltip as W}from"../components/ui/tooltip.js";import{useHotkey as q}from"../hooks/use-hotkey.js";import{cn as y}from"../lib/utils.js";import{useApp as F}from"../store/app-store.js";import{useUi as k}from"../store/ui-store.js";import{useActive as P}from"./use-active.js";function ae(){const i=k(e=>e.launcherOpen),l=k(e=>e.setLauncher),w=F(e=>e.setApp),{cfg:p,app:o}=P(),{navigate:D}=S(),r=p.apps,x=p.isEntitled??(()=>!0),c=Math.max(0,r.findIndex(e=>e.id===o.id)),[m,d]=f.useState(c),h=f.useRef(null);q({key:"k",mod:!0,shift:!0},()=>l(!i)),f.useEffect(()=>{i&&d(c)},[i,c]);const n=r[m]??r[c],b=p.modules.filter(e=>e.app===n.id&&x(e)),v=e=>{const a=r[e];a&&(w(a.id),l(!1),D(a.href))},A=e=>{e.key==="ArrowDown"?(e.preventDefault(),d(a=>Math.min(a+1,r.length-1))):e.key==="ArrowUp"?(e.preventDefault(),d(a=>Math.max(a-1,0))):e.key==="Enter"&&(e.preventDefault(),v(m))},z=o.icon,C=n.icon;return s(_,{children:[t(W,{label:"Switch app",shortcut:"\u2318\u21E7K",children:s(B,{variant:"secondary",size:"sm",onClick:()=>l(!0),className:"h-8 shrink-0 rounded-full pl-1.5","aria-label":`App: ${o.name}. Switch app`,children:[t("span",{className:"grid size-5 shrink-0 place-items-center rounded-full text-white",style:{background:o.tint},"aria-hidden":!0,children:t(z,{className:"size-3"})}),t("span",{className:"hidden max-w-[110px] truncate md:inline",children:o.name})]})}),t(O,{open:i,onOpenChange:l,children:s(L,{variant:"center",width:"max-w-[720px]",hideClose:!0,className:"overflow-hidden p-0",onKeyDown:A,onOpenAutoFocus:e=>{e.preventDefault(),h.current?.focus()},children:[t(U,{className:"sr-only",children:"Switch app"}),t(H,{className:"sr-only",children:"Choose which app to open. The rail carries that app\u2019s modules."}),s("div",{className:"grid h-[60dvh] max-h-[400px] grid-cols-1 md:h-[400px] md:grid-cols-[260px_minmax(0,1fr)]",children:[s("div",{className:"flex min-h-0 flex-col border-border bg-surface md:border-r",children:[t("div",{className:"shrink-0 border-b border-border px-4 pb-3 pt-3.5",children:t(T,{size:"sm",suffix:"Apps you can operate"})}),t("ul",{className:"min-h-0 flex-1 overflow-y-auto p-1.5 pb-3",children:r.map((e,a)=>{const M=e.icon,u=e.id===o.id,g=a===m;return t("li",{children:s("button",{type:"button",ref:u?h:void 0,onMouseMove:()=>d(a),onClick:()=>v(a),className:y("flex w-full cursor-pointer items-center gap-2.5 rounded-ctl px-2.5 py-2 text-left transition-colors",g?"bg-raised shadow-elev2":"hover:bg-hover"),children:[t("span",{className:"grid size-7 shrink-0 place-items-center rounded-[calc(7px*var(--radius-scale))] text-white",style:{background:e.tint},"aria-hidden":!0,children:t(M,{className:"size-3.5"})}),s("span",{className:"min-w-0 flex-1",children:[t("span",{className:y("block truncate text-[13px]",u?"font-semibold text-primary":"text-text"),children:e.name}),s("span",{className:"num block text-[11px] text-muted",children:[p.modules.filter(N=>N.app===e.id&&x(N)).length," modules"]})]}),u?t(I,{className:"size-3.5 shrink-0 text-primary"}):g?t(E,{className:"size-3.5 shrink-0 text-muted"}):null]})},e.id)})})]}),s("div",{className:"hidden min-h-0 flex-col md:flex",children:[s("div",{className:"flex shrink-0 items-start gap-3 border-b border-border px-5 py-4",children:[t("span",{className:"grid size-9 shrink-0 place-items-center rounded-ctl text-white",style:{background:n.tint},"aria-hidden":!0,children:t(C,{className:"size-4"})}),s("div",{className:"min-w-0 flex-1",children:[t("h2",{className:"disp text-[15px] font-semibold",children:n.name}),t("p",{className:"mt-0.5 text-xs text-muted",children:n.tagline})]}),n.status?t(K,{label:n.status.label,tone:n.status.tone}):null]}),s("div",{className:"min-h-0 flex-1 overflow-y-auto px-5 py-4",children:[s("div",{className:"ov mb-2.5",children:[b.length," modules"]}),t("ul",{className:"grid grid-cols-1 gap-x-4 gap-y-0.5 sm:grid-cols-2",children:b.map(e=>{const a=e.icon;return s("li",{className:"flex items-center gap-2.5 rounded-ctl px-1.5 py-1.5",children:[t(a,{className:"size-3.5 shrink-0 text-body"}),t("span",{className:"min-w-0 flex-1 truncate text-[13px] text-text",children:e.title})]},e.key)})})]})]})]}),s("div",{className:"flex items-center gap-4 border-t border-border bg-surface px-4 py-2 text-[11px] text-muted",children:[s("span",{className:"flex items-center gap-1",children:[t("kbd",{className:"rounded border border-border2 px-1",children:"\u2191"}),t("kbd",{className:"rounded border border-border2 px-1",children:"\u2193"})," navigate"]}),s("span",{className:"flex items-center gap-1",children:[t(R,{className:"size-3"})," open"]}),t("span",{className:"ml-auto hidden sm:inline",children:"Every screen stays in \u2318K"})]})]})})]})}export{ae as AppSwitcher};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{jsx as o,jsxs as a}from"react/jsx-runtime";import{CornerDownLeft as M,Moon as E,Search as I,Sparkles as
|
|
1
|
+
"use client";import{jsx as o,jsxs as a}from"react/jsx-runtime";import{CornerDownLeft as M,Moon as E,Search as I,Sparkles as A,Sun as R}from"lucide-react";import{useRouterAdapter as L}from"../hooks/use-router.js";import*as s from"react";import{Dialog as T,DialogContent as O,DialogTitle as z}from"../components/ui/dialog.js";import{useHotkey as C}from"../hooks/use-hotkey.js";import{cn as D}from"../lib/utils.js";import{useUi as h}from"../store/ui-store.js";import{useShell as $}from"./config.js";function Q(){const l=$(),i=h(e=>e.paletteOpen),c=h(e=>e.setPalette),g=h(e=>e.toggleTheme),x=h(e=>e.theme),{navigate:k}=L(),[d,v]=s.useState(""),[u,m]=s.useState(0),y=s.useRef(null);C({key:"k",mod:!0},()=>c(!i)),C({key:"/"},()=>c(!0));const b=s.useMemo(()=>{const e=[...l.commands??[]];e.push({id:"act-theme",label:x==="dark"?"Switch to light theme":"Switch to dark theme",group:"Actions",icon:x==="dark"?R:E,run:g});const n=l.isEntitled??(()=>!0);for(const t of l.modules.filter(n)){e.push({id:`mod-${t.key}`,label:t.title,hint:t.description,group:"Modules",icon:t.icon,href:t.href});for(const r of t.nav)r.kind==="item"&&e.push({id:`scr-${t.key}-${r.href}`,label:r.label,hint:t.title,group:"Screens",icon:t.icon,href:r.href})}return e},[l.commands,l.modules,l.isEntitled,x,g]),p=s.useMemo(()=>{const e=d.trim().toLowerCase(),n=e?b.filter(r=>r.label.toLowerCase().includes(e)||r.hint?.toLowerCase().includes(e)):b.filter(r=>r.group!=="Screens"),t=["Actions","AI","Screens","Modules","Records"];return n.slice().sort((r,f)=>t.indexOf(r.group)-t.indexOf(f.group)).slice(0,40)},[b,d]);s.useEffect(()=>m(0),[d]),s.useEffect(()=>{i||v("")},[i]);const N=s.useCallback(e=>{e&&(c(!1),e.run?e.run():e.href&&k(e.href))},[k,c]),S=e=>{e.key==="ArrowDown"?(e.preventDefault(),m(n=>Math.min(n+1,p.length-1))):e.key==="ArrowUp"?(e.preventDefault(),m(n=>Math.max(n-1,0))):e.key==="Enter"&&(e.preventDefault(),N(p[u]))};s.useEffect(()=>{y.current?.querySelector(`[data-index="${u}"]`)?.scrollIntoView({block:"nearest"})},[u]);let w="";return o(T,{open:i,onOpenChange:c,children:a(O,{variant:"center",width:"max-w-[580px]",hideClose:!0,className:"top-[14vh] translate-y-0 overflow-hidden p-0 shadow-elev3",onKeyDown:S,children:[o(z,{className:"sr-only",children:"Command palette"}),a("div",{className:"flex items-center gap-2.5 border-b border-border px-4",children:[o(I,{className:"size-4 shrink-0 text-muted"}),o("input",{autoFocus:!0,value:d,onChange:e=>v(e.target.value),placeholder:"Search screens, run an agent, or ask\u2026",className:"h-12 flex-1 bg-transparent text-sm text-text outline-none placeholder:text-placeholder"}),o("kbd",{className:"rounded border border-border2 px-1.5 text-[11px] text-muted",children:"esc"})]}),o("div",{ref:y,className:"max-h-[54vh] overflow-y-auto p-1.5",children:p.length===0?a("p",{className:"px-3 py-8 text-center text-[13px] text-muted",children:["Nothing matches \u201C",d,"\u201D."]}):p.map((e,n)=>{const t=e.icon,r=e.group!==w?e.group:null;w=e.group;const f=n===u;return a(s.Fragment,{children:[r?o("div",{className:"ov px-2.5 pb-1 pt-2.5",children:r}):null,a("button",{type:"button","data-index":n,onMouseMove:()=>m(n),onClick:()=>N(e),className:D("flex w-full cursor-pointer items-center gap-2.5 rounded-ctl px-2.5 py-2 text-left text-[13px] transition-colors",f?"bg-hover text-text":"text-body"),children:[t?o(t,{className:D("size-4 shrink-0",e.group==="AI"?"text-accent":"text-muted")}):null,o("span",{className:"flex-1 truncate",children:e.label}),e.hint?o("span",{className:"hidden max-w-[45%] truncate text-[11px] text-muted sm:inline",children:e.hint}):null,f?o(M,{className:"size-3.5 shrink-0 text-muted"}):null]})]},e.id)})}),a("div",{className:"flex items-center gap-4 border-t border-border bg-surface px-4 py-2 text-[11px] text-muted",children:[a("span",{className:"flex items-center gap-1",children:[o("kbd",{className:"rounded border border-border2 px-1",children:"\u2191"}),o("kbd",{className:"rounded border border-border2 px-1",children:"\u2193"})," navigate"]}),a("span",{className:"flex items-center gap-1",children:[o("kbd",{className:"rounded border border-border2 px-1",children:"\u21B5"})," open"]}),a("span",{className:"ml-auto flex items-center gap-1",children:[o(A,{className:"size-3 text-accent"})," agents run with a credit estimate first"]})]})]})})}export{Q as CommandPalette};
|
package/dist/shell/icon-rail.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{Fragment as W,jsx as e,jsxs as c}from"react/jsx-runtime";import
|
|
1
|
+
"use client";import{Fragment as W,jsx as e,jsxs as c}from"react/jsx-runtime";import*as i from"react";import{WaveMark as T}from"../components/brand/logo.js";import{CountBadge as $}from"../components/ui/badge.js";import{Tooltip as f}from"../components/ui/tooltip.js";import{RouterLink as x}from"../hooks/use-router.js";import{cn as v}from"../lib/utils.js";import{useUi as E}from"../store/ui-store.js";import{useActive as R}from"./use-active.js";function d({mod:l,active:r,index:n,visiting:t}){const u=l.icon;return e("li",{className:"relative w-full","data-active":r||void 0,children:e(f,{label:t?`${l.title} \u2014 outside this app`:l.title,shortcut:n<9?`Alt+${n+1}`:void 0,side:"right",children:c(x,{href:l.href,"aria-current":r?"page":void 0,className:v("relative mx-auto flex min-h-14 w-[60px] flex-col items-center justify-center gap-[3px] rounded-ctl px-0.5 py-1.5","transition-colors duration-150",r?"bg-primary-subtle text-primary":"text-muted hover:bg-hover hover:text-text"),children:[e(u,{className:"size-[19px]",strokeWidth:r?2.2:1.8}),e("span",{className:"w-full truncate px-0.5 text-center text-[10px] font-medium leading-3",children:l.label}),l.badge?e($,{value:l.badge,tone:l.badgeTone==="danger"?"danger":"neutral",className:"absolute right-1.5 top-1"}):null,t?e("span",{className:"absolute left-1.5 top-1.5 size-1.5 rounded-full bg-accent","aria-hidden":!0}):null]})})})}function C(){const{cfg:l,pathname:r,mod:n,app:t,rail:u}=R(),y=E(a=>a.setLauncher),N=t.icon,{modules:o,platform:k,visiting:p}=u,w=l.showAppSwitcher!==!1&&l.apps.length>1,h=i.useRef(null),[m,A]=i.useState(null),b=i.useRef(t.id),[L,I]=i.useState(!1);i.useLayoutEffect(()=>{const a=h.current?.querySelector('[data-active="true"]'),s=b.current===t.id;b.current=t.id,I(s),A(a?{y:a.offsetTop+10,h:a.offsetHeight-20}:null)},[r,t.id,o.length]);const g=c("span",{className:"relative block",children:[e(T,{}),e("span",{className:"absolute -bottom-1 -right-1 grid size-[17px] place-items-center rounded-full text-white ring-2 ring-surface",style:{background:t.tint},children:e(N,{className:"size-2.5"})})]});return c("nav",{ref:h,"data-shell-rail":"","aria-label":`${t.name} modules`,className:"rail-fade relative col-start-1 row-start-1 row-span-2 flex flex-col items-center gap-0.5 overflow-y-auto overflow-x-hidden border-r border-border bg-surface py-2",children:[m?e("span",{"aria-hidden":!0,className:v("pointer-events-none absolute left-0 top-0 w-[3px] rounded-r-[3px] bg-primary",L&&"transition-[transform,height] duration-[220ms] ease-wave"),style:{transform:`translateY(${m.y}px)`,height:m.h}}):null,w?e(f,{label:`WAVEINNO \xB7 ${t.name} \u2014 switch app`,shortcut:"\u2318\u21E7K",side:"right",children:e("button",{type:"button",onClick:()=>y(!0),"aria-label":`WAVEINNO, ${t.name}. Switch app`,className:"relative mb-3 shrink-0 cursor-pointer transition-transform duration-150 hover:scale-105",children:g})}):e(f,{label:`WAVEINNO \xB7 ${t.name}`,side:"right",children:e(x,{href:t.href,"aria-label":`WAVEINNO ${t.name} home`,className:"relative mb-3 shrink-0 transition-transform duration-150 hover:scale-105",children:g})}),e("ul",{className:"flex w-full flex-col items-center gap-0.5",children:o.map((a,s)=>e(d,{mod:a,index:s,active:a.key===n.key},a.key))}),p?c(W,{children:[e("span",{className:"my-1.5 h-px w-8 shrink-0 bg-border2","aria-hidden":!0}),e("ul",{className:"flex w-full flex-col items-center",children:e(d,{mod:p,index:o.length,active:!0,visiting:!0})})]}):null,e("div",{className:"min-h-6 flex-1"}),e("ul",{className:"flex w-full flex-col items-center gap-0.5 pb-1",children:k.map((a,s)=>e(d,{mod:a,index:o.length+(p?1:0)+s,active:a.key===n.key},a.key))})]})}export{C as IconRail};
|
package/dist/shell/mobile-nav.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{jsx as t,jsxs as s}from"react/jsx-runtime";import
|
|
1
|
+
"use client";import{jsx as t,jsxs as s}from"react/jsx-runtime";import*as k from"react";import{WaveWordmark as N}from"../components/brand/logo.js";import{CountBadge as y}from"../components/ui/badge.js";import{Sheet as w,SheetContent as A,SheetTitle as L}from"../components/ui/sheet.js";import{RouterLink as l}from"../hooks/use-router.js";import{cn as p}from"../lib/utils.js";import{useApp as S}from"../store/app-store.js";import{useUi as f}from"../store/ui-store.js";import{useActive as C}from"./use-active.js";function B(){const u=f(e=>e.mobileNavOpen),n=f(e=>e.setMobileNav),h=S(e=>e.setApp),{cfg:o,pathname:d,mod:b,app:c,rail:x,isEntitled:v}=C(),g=x.order;return k.useEffect(()=>{n(!1)},[d,n]),t(w,{open:u,onOpenChange:n,children:s(A,{side:"left",width:"w-[300px]",className:"lg:hidden",children:[s("div",{className:"shrink-0 border-b border-border px-4 py-3",children:[t(L,{asChild:!0,children:t(N,{size:"sm",suffix:c.name})}),o.scopeLabelled??o.scope?t("div",{className:"mt-2",children:o.scopeLabelled??o.scope}):null]}),o.apps.length>1&&o.showAppSwitcher!==!1?t("div",{className:"flex shrink-0 gap-1.5 overflow-x-auto border-b border-border px-3 py-2.5",children:o.apps.map(e=>{const a=e.icon,i=e.id===c.id,r=o.modules.find(m=>m.app===e.id&&v(m));return t(l,{href:r?.href??e.href,onClick:()=>h(e.id),"aria-label":e.name,"aria-current":i?"true":void 0,className:p("grid size-9 shrink-0 place-items-center rounded-ctl text-white transition-[box-shadow,transform] duration-150",i?"ring-2 ring-text ring-offset-2 ring-offset-raised":"opacity-90 hover:opacity-100"),style:{background:e.tint},children:t(a,{className:"size-4"})},e.id)})}):null,t("div",{className:"flex-1 overflow-y-auto p-2",children:g.map(e=>{const a=e.icon,i=e.key===b.key;return s("div",{children:[s(l,{href:e.href,className:p("flex h-item items-center gap-2.5 rounded-ctl px-2.5 text-[13px] transition-colors",i?"bg-primary-subtle font-medium text-primary":"text-body hover:bg-hover"),children:[t(a,{className:"size-4 shrink-0"}),t("span",{className:"flex-1 truncate",children:e.title}),e.badge?t(y,{value:e.badge,tone:e.badgeTone==="danger"?"danger":"neutral"}):null]}),i?t("ul",{className:"mb-2 ml-[26px] mt-0.5 border-l border-border pl-2",children:e.nav.filter(r=>r.kind==="item").map(r=>t("li",{children:s(l,{href:r.href,className:p("flex h-8 items-center gap-2 rounded-ctl px-2 text-[13px] transition-colors",d===r.href?"font-medium text-primary":"text-muted hover:bg-hover hover:text-text"),children:[t("span",{className:"flex-1 truncate",children:r.label}),r.count?t("span",{className:"num text-[11px]",children:r.count}):null]})},r.href))}):null]},e.key)})})]})})}export{B as MobileNav};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{jsx as a,jsxs as o}from"react/jsx-runtime";import
|
|
1
|
+
"use client";import{jsx as a,jsxs as o}from"react/jsx-runtime";import*as r from"react";import{RouterLink as d}from"../hooks/use-router.js";import{cn as i}from"../lib/utils.js";import{useActive as b}from"./use-active.js";function k(){const{pathname:c,mod:t,item:p}=b(),u=r.useRef(null),[s,f]=r.useState(null),m=r.useRef(t.key),[x,h]=r.useState(!1);return r.useLayoutEffect(()=>{const e=u.current?.querySelector('li[data-active="true"]'),n=m.current===t.key;m.current=t.key,h(n),f(e?{y:e.offsetTop,h:e.offsetHeight}:null)},[c,t.key]),o("nav",{"data-shell-panel":"","aria-label":`${t.title} sections`,className:"col-start-2 row-start-1 row-span-2 overflow-y-auto overflow-x-hidden border-r border-border bg-surface px-2.5 py-3",children:[a("h2",{className:"px-2.5 pb-2.5 pt-1.5 text-[13px] font-semibold leading-[18px] text-text",children:t.title}),o("ul",{ref:u,className:"relative",children:[s?a("li",{"aria-hidden":!0,className:i("pointer-events-none absolute inset-x-0 top-0 rounded-ctl bg-primary-subtle",x&&"transition-[transform,height] duration-[220ms] ease-wave"),style:{transform:`translateY(${s.y}px)`,height:s.h}}):null,t.nav.map((e,n)=>{if(e.kind==="group")return a("li",{className:"ov px-2.5 pb-1.5 pt-3.5",children:e.label},`g-${n}`);const l=p?.href===e.href;return a("li",{"data-active":l||void 0,children:o(d,{href:e.href,"aria-current":l?"page":void 0,className:i("relative mb-px flex h-item items-center gap-2.5 rounded-ctl px-2.5 text-[13px] transition-colors duration-150",l?"font-medium text-primary":"text-body hover:bg-hover hover:text-text"),children:[a("span",{className:"truncate",children:e.label}),e.count?a("span",{className:i("num ml-auto shrink-0 text-xs",l?"text-primary":e.hot?"font-semibold text-text":"text-muted"),children:e.count}):null]})},e.href)})]})]})}export{k as ModuleSidebar};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{jsx as e,jsxs as a}from"react/jsx-runtime";import{Bell as p}from"lucide-react";import
|
|
1
|
+
"use client";import{jsx as e,jsxs as a}from"react/jsx-runtime";import{Bell as p}from"lucide-react";import{Badge as m}from"../components/ui/badge.js";import{Button as n}from"../components/ui/button.js";import{Popover as c,PopoverContent as d,PopoverTrigger as x}from"../components/ui/popover.js";import{Tooltip as f}from"../components/ui/tooltip.js";import{RouterLink as s}from"../hooks/use-router.js";import{fmtRelative as u}from"../lib/format.js";import{useShell as N}from"./config.js";function C(){const o=N(),r=o.notifications??[],i=r.filter(t=>!t.read).length,l=o.now??new Date;return a(c,{onOpenChange:t=>t&&o.onNotificationsOpen?.(),children:[e(f,{label:"Notifications",children:e(x,{asChild:!0,children:a(n,{variant:"ghost",size:"icon",className:"relative","aria-label":`Notifications, ${i} unread`,children:[e(p,{}),i>0?e("span",{className:"num absolute right-[3px] top-[3px] grid h-4 min-w-4 place-items-center rounded-full bg-danger px-1 text-[10px] font-semibold leading-none text-white ring-2 ring-canvas","aria-hidden":!0,children:i>9?"9+":i}):null]})})}),a(d,{align:"end",className:"w-[380px] max-w-[calc(100vw-32px)] p-0",children:[a("div",{className:"flex items-center justify-between border-b border-border px-3.5 py-2.5",children:[e("span",{className:"text-[13px] font-semibold text-text",children:"Notifications"}),i>0&&o.onNotificationsRead?e(n,{variant:"link",size:"sm",className:"h-auto",onClick:()=>o.onNotificationsRead?.("all"),children:"Mark all read"}):null]}),r.length===0?e("p",{className:"px-3.5 py-8 text-center text-[13px] text-muted",children:"You are all caught up."}):e("ul",{className:"max-h-[420px] overflow-y-auto",children:r.map(t=>e("li",{children:a(s,{href:t.href,onClick:()=>!t.read&&o.onNotificationsRead?.([t.id]),className:"flex gap-2.5 border-b border-border px-3.5 py-3 transition-colors last:border-0 hover:bg-hover",children:[e(m,{tone:t.tone,className:"mt-0.5 h-[18px] px-1.5",children:e("span",{className:"sr-only",children:t.tone})}),a("div",{className:"min-w-0 flex-1",children:[e("p",{className:"text-[13px] font-medium leading-[18px] text-text",children:t.title}),e("p",{className:"mt-0.5 truncate text-xs text-muted",children:t.detail}),a("p",{className:"mt-1 text-[11px] text-muted",children:[u(t.at,l)," \xB7 ",t.source]})]}),t.read?null:e("span",{className:"mt-2 size-1.5 shrink-0 rounded-full bg-primary","aria-label":"unread"})]})},t.id))}),o.notificationsHref?e("div",{className:"border-t border-border px-3.5 py-2",children:e(s,{href:o.notificationsHref,className:"text-xs font-medium text-primary hover:underline",children:o.notificationsHrefLabel??"Open activity"})}):null]})]})}export{C as Notifications};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{Fragment as y,jsx as a,jsxs as t}from"react/jsx-runtime";import{ArrowRight as h,Check as x,Database as f}from"lucide-react";import
|
|
1
|
+
"use client";import{Fragment as y,jsx as a,jsxs as t}from"react/jsx-runtime";import{ArrowRight as h,Check as x,Database as f}from"lucide-react";import{PageHeader as g}from"../components/patterns/page-header.js";import{Card as m}from"../components/ui/card.js";import{RouterLink as u}from"../hooks/use-router.js";import{useShell as b}from"./config.js";import{moduleFromPath as N,navItemFromPath as v}from"./registry.js";function I({pathname:n,plannedIn:o}){const i=b(),s=N(i.modules,n),d=v(n,s),l=d?.label??s.title,r=i.apps.find(e=>e.id===s.app),c=s.nav.filter(e=>e.kind==="item").filter(e=>e.href!==d?.href).slice(0,6),p=["Navigation, breadcrumb and page header","Plan / role gating from the registry","Data table \u2014 sort, pin, resize, export","Record drawer and command palette","Empty, loading and error states"];return t(y,{children:[a(g,{crumbs:[...i.homeCrumb?[i.homeCrumb]:[],...r&&r.href!==i.homeCrumb?.href?[{label:r.name,href:r.href}]:[],{label:s.title,href:s.href},{label:l}],title:l,description:s.description}),t("div",{className:"grid grid-cols-1 items-start gap-3 lg:grid-cols-[minmax(0,1fr)_320px]",children:[a(m,{className:"px-6 py-8",children:t("div",{className:"flex items-start gap-3.5",children:[a("span",{className:"grid size-9 shrink-0 place-items-center rounded-ctl bg-hover text-muted","aria-hidden":!0,children:a(f,{className:"size-4"})}),t("div",{className:"min-w-0",children:[t("h2",{className:"text-[15px] font-semibold text-text",children:[l," is designed but not built yet"]}),t("p",{className:"mt-1.5 max-w-[60ch] text-[13px] leading-5 text-muted",children:["The screen is in the navigation registry and inherits the page template. Its data contract is in the API specification; the page ships with its milestone",o?` (${o})`:"","."]})]})]})}),t("div",{className:"space-y-3",children:[t(m,{children:[a("h3",{className:"text-[13px] font-semibold text-text",children:"Already wired"}),a("ul",{className:"mt-2.5 space-y-2",children:p.map(e=>t("li",{className:"flex items-start gap-2 text-[13px] text-body",children:[a(x,{className:"mt-0.5 size-3.5 shrink-0 text-success"}),e]},e))})]}),c.length?t(m,{children:[t("h3",{className:"text-[13px] font-semibold text-text",children:["Elsewhere in ",s.title]}),a("ul",{className:"-mx-1.5 mt-2",children:c.map(e=>e.kind==="item"?a("li",{children:t(u,{href:e.href,className:"flex items-center gap-2 rounded-ctl px-1.5 py-1.5 text-[13px] text-body transition-colors hover:bg-hover hover:text-text",children:[a("span",{className:"min-w-0 flex-1 truncate",children:e.label}),a(h,{className:"size-3 shrink-0 text-muted"})]})},e.href):null)})]}):null]})]})]})}export{I as PlaceholderScreen};
|
package/dist/shell/topbar.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{jsx as e,jsxs as o}from"react/jsx-runtime";import{Menu as x,PanelLeft as h,Search as p}from"lucide-react";import{WaveMark as f}from"../components/brand/logo.js";import{Button as
|
|
1
|
+
"use client";import{jsx as e,jsxs as o}from"react/jsx-runtime";import{Menu as x,PanelLeft as h,Search as p}from"lucide-react";import{WaveMark as f}from"../components/brand/logo.js";import{Button as n}from"../components/ui/button.js";import{Tooltip as g}from"../components/ui/tooltip.js";import{cn as v}from"../lib/utils.js";import{useUi as s}from"../store/ui-store.js";import{AppSwitcher as N}from"./app-switcher.js";import{Notifications as k}from"./notifications.js";import{UserMenu as w}from"./user-menu.js";import{useActive as z}from"./use-active.js";function I(){const m=s(a=>a.togglePanel),i=s(a=>a.setPalette),c=s(a=>a.setMobileNav),u=s(a=>a.setLauncher),{cfg:t,app:r}=z(),b=r.icon,l=t.showAppSwitcher!==!1&&t.apps.length>1,d=t.searchClearance==="wide";return e("header",{className:"col-start-3 col-end-4 row-start-1 flex border-b border-border bg-canvas px-4 sm:px-6",children:o("div",{className:"@container relative mx-auto flex w-full max-w-[1600px] items-center gap-2 sm:gap-2.5",children:[o("div",{className:"flex min-w-0 items-center gap-2",children:[e(g,{label:"Toggle panel",shortcut:"\u2318B",children:e(n,{variant:"ghost",size:"icon",onClick:m,className:"-ml-2.5 hidden lg:inline-flex","aria-label":"Toggle module panel",children:e(h,{})})}),e(n,{variant:"ghost",size:"icon",onClick:()=>c(!0),className:"-ml-2.5 lg:hidden","aria-label":"Open navigation",children:e(x,{})}),o("button",{type:"button",onClick:()=>l?u(!0):c(!0),"aria-label":`WAVEINNO, ${r.name}`,className:"flex min-w-0 shrink items-center gap-2 rounded-full py-1 pl-0.5 pr-2 transition-colors hover:bg-hover lg:hidden",children:[o("span",{className:"relative shrink-0",children:[e(f,{size:"sm"}),e("span",{className:"absolute -bottom-0.5 -right-0.5 grid size-[13px] place-items-center rounded-full text-white ring-2 ring-canvas",style:{background:r.tint},children:e(b,{className:"size-2"})})]}),e("span",{className:`disp truncate text-[13px] font-semibold text-text ${l?"md:hidden":""}`,children:r.name})]})]}),o("button",{type:"button",onClick:()=>i(!0),className:v("absolute left-1/2 top-1/2 hidden h-[38px] -translate-x-1/2 -translate-y-1/2 cursor-text items-center gap-2.5 rounded-full border border-border bg-surface px-[15px] text-left transition-[background-color,border-color,box-shadow] hover:border-border2 focus-visible:border-primary focus-visible:bg-raised focus-visible:shadow-elev2",d?"w-[clamp(260px,calc(100%-960px),560px)] @min-[1220px]:flex":"w-[clamp(260px,calc(100%-720px),560px)] @min-[980px]:flex"),children:[e(p,{className:"size-4 shrink-0 text-muted"}),e("span",{className:"flex-1 truncate text-sm text-placeholder",children:t.searchPlaceholder??"Search screens and records\u2026"}),e("kbd",{className:"hidden rounded-[calc(5px*var(--radius-scale))] border border-border2 px-1.5 text-[11px] font-medium text-muted md:inline",children:"\u2318K"})]}),o("div",{className:"ml-auto flex items-center gap-2 sm:gap-2.5",children:[e(n,{variant:"ghost",size:"icon",onClick:()=>i(!0),className:d?"@min-[1220px]:hidden":"@min-[980px]:hidden","aria-label":"Search",children:e(p,{})}),t.topbarExtra?e("div",{className:"hidden sm:block",children:t.topbarExtra}):null,t.scope?e("div",{className:"hidden sm:block",children:t.scope}):null,l?e("div",{className:"hidden md:block",children:e(N,{})}):null,e(k,{}),e(w,{})]})]})})}export{I as Topbar};
|
package/dist/shell/use-active.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{
|
|
1
|
+
"use client";import{useRouterAdapter as l}from"../hooks/use-router.js";import{useApp as u}from"../store/app-store.js";import{useShell as f}from"./config.js";import{moduleFromPath as h,navItemFromPath as v,railModules as A}from"./registry.js";function P(){const t=f(),{pathname:e}=l(),p=u(o=>o.appId),s=h(t.modules,e),r=v(e,s),m=o=>!!o&&t.apps.some(c=>c.id===o),a=s.app??(m(p)?p:t.apps[0].id),n=t.apps.find(o=>o.id===a)??t.apps[0],i=t.isEntitled??(()=>!0),d=A(t.modules,n.id,s.key,i);return{cfg:t,pathname:e,mod:s,item:r,app:n,rail:d,isEntitled:i}}export{P as useActive};
|
package/dist/shell/user-menu.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{Fragment as D,jsx as e,jsxs as t}from"react/jsx-runtime";import{LogOut as l}from"lucide-react";import
|
|
1
|
+
"use client";import{Fragment as D,jsx as e,jsxs as t}from"react/jsx-runtime";import{LogOut as l}from"lucide-react";import{Avatar as s}from"../components/ui/avatar.js";import{DropdownMenu as c,DropdownMenuContent as u,DropdownMenuItem as m,DropdownMenuLabel as d,DropdownMenuSeparator as a,DropdownMenuTrigger as x}from"../components/ui/dropdown-menu.js";import{RouterLink as g}from"../hooks/use-router.js";import{DensityPicker as f,ThemeToggle as w}from"./appearance-controls.js";import{useShell as v}from"./config.js";function L(){const{user:n,userLinks:r=[],onSignOut:p}=v();return t(c,{children:[e(x,{className:"shrink-0 cursor-pointer rounded-full","aria-label":"Account menu",children:e(s,{name:n.name,src:n.avatar})}),t(u,{align:"end",className:"w-72",children:[t("div",{className:"flex items-center gap-2.5 px-2.5 py-2.5",children:[e(s,{name:n.name,size:"lg"}),t("div",{className:"min-w-0",children:[e("p",{className:"truncate text-[13px] font-semibold text-text",children:n.name}),e("p",{className:"truncate text-[11px] text-muted",children:n.email})]})]}),t("div",{className:"mx-2.5 mb-1 rounded-ctl bg-hover px-2.5 py-2",children:[e("p",{className:"ov",children:"Signed in as"}),e("p",{className:"mt-0.5 text-xs text-text",children:n.role}),n.context?e("p",{className:"mt-0.5 text-[11px] text-muted",children:n.context}):null]}),e(a,{}),e(d,{children:"Appearance"}),t("div",{className:"flex items-center justify-between gap-2 px-2.5 py-1.5",onClick:o=>o.stopPropagation(),children:[e("span",{className:"text-[13px] text-body",children:"Theme"}),e(w,{})]}),t("div",{className:"flex items-center justify-between gap-2 px-2.5 pb-2 pt-1",onClick:o=>o.stopPropagation(),children:[e("span",{className:"text-[13px] text-body",children:"Density"}),e(f,{compact:!0})]}),r.length?e(a,{}):null,r.map(o=>{const i=o.icon;return e(m,{asChild:!0,children:t(g,{href:o.href,children:[e(i,{}),o.label]})},o.href)}),p?t(D,{children:[e(a,{}),t(m,{danger:!0,onSelect:p,children:[e(l,{}),"Sign out"]})]}):null]})]})}export{L as UserMenu};
|
package/dist/styles.css
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
/* @waveinno/ui — import after tailwindcss:
|
|
3
3
|
@import "tailwindcss";
|
|
4
4
|
@import "@waveinno/ui/styles.css";
|
|
5
|
-
@source "<path to node_modules>/@waveinno/ui/
|
|
5
|
+
@source "<path to node_modules>/@waveinno/ui/dist";
|
|
6
6
|
The consumer owns the Tailwind entry so it controls @source and plugins. */
|
|
7
7
|
|
|
8
8
|
/* ══════════════════════════════════════════════════════════════════════════
|
|
@@ -37,6 +37,12 @@
|
|
|
37
37
|
--primary-subtle: #eef2ff;
|
|
38
38
|
--primary-muted: #c7d2fe;
|
|
39
39
|
--accent: #7c3aed;
|
|
40
|
+
/* The brand gradient, royal to violet (the logo's own), and the ink that
|
|
41
|
+
dark panels, value bubbles and command menus are drawn in. A theme that
|
|
42
|
+
changes these changes every gradient, glow and ink surface with them. */
|
|
43
|
+
--brand-1: #1f45ea;
|
|
44
|
+
--brand-2: #7560fd;
|
|
45
|
+
--ink: #140d33;
|
|
40
46
|
|
|
41
47
|
/* ── intent ── */
|
|
42
48
|
--success: #009767;
|
|
@@ -53,10 +59,14 @@
|
|
|
53
59
|
--elev3: 0 16px 48px rgba(5, 8, 22, 0.16);
|
|
54
60
|
--lit: 0 0 #0000;
|
|
55
61
|
|
|
56
|
-
/* ── radius ──
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
62
|
+
/* ── radius ──
|
|
63
|
+
One scale for every corner: the three named radii and each component's
|
|
64
|
+
own (written as calc(Npx * var(--radius-scale))). 0 is square, 1 the
|
|
65
|
+
WAVEINNO default, 1.8 very round. Pills stay pills. */
|
|
66
|
+
--radius-scale: 1;
|
|
67
|
+
--r-ctl: calc(8px * var(--radius-scale));
|
|
68
|
+
--r-card: calc(10px * var(--radius-scale));
|
|
69
|
+
--r-dlg: calc(14px * var(--radius-scale));
|
|
60
70
|
|
|
61
71
|
/* ── shell geometry ── */
|
|
62
72
|
--rail: 72px;
|
|
@@ -171,6 +181,9 @@
|
|
|
171
181
|
--color-primary-subtle: var(--primary-subtle);
|
|
172
182
|
--color-primary-muted: var(--primary-muted);
|
|
173
183
|
--color-accent: var(--accent);
|
|
184
|
+
--color-brand-1: var(--brand-1);
|
|
185
|
+
--color-brand-2: var(--brand-2);
|
|
186
|
+
--color-ink: var(--ink);
|
|
174
187
|
|
|
175
188
|
--color-success: var(--success);
|
|
176
189
|
--color-success-subtle: var(--success-subtle);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@waveinno/ui",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.4.0",
|
|
4
4
|
"description": "WAVEINNO design system — tokens, shell, primitives and patterns shared by every WAVEINNO product",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"waveinno",
|
|
@@ -29,6 +29,11 @@
|
|
|
29
29
|
"import": "./dist/index.js",
|
|
30
30
|
"default": "./dist/index.js"
|
|
31
31
|
},
|
|
32
|
+
"./next": {
|
|
33
|
+
"types": "./dist/next/index.d.ts",
|
|
34
|
+
"import": "./dist/next/index.js",
|
|
35
|
+
"default": "./dist/next/index.js"
|
|
36
|
+
},
|
|
32
37
|
"./styles.css": "./dist/styles.css",
|
|
33
38
|
"./package.json": "./package.json",
|
|
34
39
|
"./brand/*": "./dist/brand/*"
|
|
@@ -87,6 +92,11 @@
|
|
|
87
92
|
"react-dom": ">=19",
|
|
88
93
|
"tailwindcss": ">=4"
|
|
89
94
|
},
|
|
95
|
+
"peerDependenciesMeta": {
|
|
96
|
+
"next": {
|
|
97
|
+
"optional": true
|
|
98
|
+
}
|
|
99
|
+
},
|
|
90
100
|
"devDependencies": {
|
|
91
101
|
"@types/node": "^26.6.2",
|
|
92
102
|
"@types/react": "^19.3.0",
|