@the-portland-company/shell 0.65.1 → 0.66.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.
@@ -2214,8 +2214,8 @@ function NavSidebar({
2214
2214
  };
2215
2215
  const activeFn = nav.isActive ?? isNavItemActive;
2216
2216
  const ModeIcon = mode?.icon;
2217
- const orgBg = org?.brandColor || ORG_PILL_DEFAULT;
2218
2217
  const orgLogoSrc = resolveOrgLogoUrl(org?.logoUrl);
2218
+ const orgGradient = org?.brandColor ? `linear-gradient(to right, ${org.brandColor}, ${org.brandColorSecondary || org.brandColor})` : "linear-gradient(to right, #007BFF, #A54B7A, #E63946)";
2219
2219
  const activeGroupKey = react.useMemo(() => {
2220
2220
  for (let i = 0; i < nav.items.length; i++) {
2221
2221
  const item = nav.items[i];
@@ -2311,29 +2311,33 @@ function NavSidebar({
2311
2311
  ),
2312
2312
  /* @__PURE__ */ jsxRuntime.jsx("span", { className: "sr-only", children: "Loading organization" })
2313
2313
  ] }) : org.organizations && org.organizations.length > 0 && org.onSwitch ? /* @__PURE__ */ jsxRuntime.jsxs("details", { "data-nav-details": true, className: "group relative", children: [
2314
- /* @__PURE__ */ jsxRuntime.jsxs("summary", { className: "flex w-full cursor-pointer list-none items-center justify-between gap-2 rounded-md border border-[color:var(--line)] bg-[color:var(--panel-elevated)] px-2.5 py-2 text-left text-[color:var(--foreground)] shadow-sm transition hover:bg-[color:var(--panel)] [&::-webkit-details-marker]:hidden", children: [
2315
- /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex min-w-0 items-center gap-2.5", children: [
2316
- /* @__PURE__ */ jsxRuntime.jsx(
2317
- "span",
2314
+ /* @__PURE__ */ jsxRuntime.jsxs("summary", { className: "flex w-full cursor-pointer list-none flex-col overflow-hidden rounded-[5px] border border-[color:var(--line)] bg-[color:var(--panel-elevated)] text-left text-[color:var(--foreground)] shadow-sm transition hover:bg-[color:var(--panel)] [&::-webkit-details-marker]:hidden", children: [
2315
+ /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "relative flex h-[70px] w-full items-center justify-center bg-white px-3", children: [
2316
+ orgLogoSrc ? /* @__PURE__ */ jsxRuntime.jsx("img", { src: orgLogoSrc, alt: "", className: "max-h-[70px] max-w-full object-contain" }) : org.canUploadLogo ? /* @__PURE__ */ jsxRuntime.jsx(
2317
+ "a",
2318
2318
  {
2319
- style: { backgroundColor: orgBg },
2320
- className: "flex h-7 w-7 shrink-0 items-center justify-center overflow-hidden rounded-full text-[11px] font-bold text-white",
2321
- children: orgLogoSrc ? /* @__PURE__ */ jsxRuntime.jsx("img", { src: orgLogoSrc, alt: "", className: "h-full w-full object-cover" }) : (org.name ?? "Org").slice(0, 2).toUpperCase()
2319
+ href: org.uploadLogoHref ?? "#",
2320
+ onClick: (e) => e.stopPropagation(),
2321
+ className: "text-xs font-semibold text-[color:var(--color-accent)] underline",
2322
+ children: "Upload logo"
2322
2323
  }
2323
- ),
2324
+ ) : /* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-sm font-semibold text-neutral-800", children: org.name ?? "Organization" }),
2325
+ /* @__PURE__ */ jsxRuntime.jsx("span", { "aria-hidden": true, className: "absolute inset-x-0 bottom-0 h-[3px]", style: { backgroundImage: orgGradient } })
2326
+ ] }),
2327
+ /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex w-full min-w-0 items-center justify-between gap-2 px-2.5 py-2", children: [
2324
2328
  /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex min-w-0 flex-col", children: [
2325
2329
  /* @__PURE__ */ jsxRuntime.jsx(
2326
2330
  "span",
2327
2331
  {
2328
2332
  title: org.name ?? void 0,
2329
- className: "truncate text-sm font-semibold",
2333
+ className: "truncate text-[13px] font-semibold",
2330
2334
  children: org.name ?? "No organizations"
2331
2335
  }
2332
2336
  ),
2333
2337
  org.id && !org.loading ? /* @__PURE__ */ jsxRuntime.jsx(OrgIdCopyButton, { id: org.id }) : null
2334
- ] })
2335
- ] }),
2336
- /* @__PURE__ */ jsxRuntime.jsx(ChevronDown, {})
2338
+ ] }),
2339
+ /* @__PURE__ */ jsxRuntime.jsx(ChevronDown, {})
2340
+ ] })
2337
2341
  ] }),
2338
2342
  /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "absolute left-0 right-0 z-40 mt-1 max-h-[min(60vh,520px)] overflow-y-auto rounded-xl border border-[color:var(--line)] bg-[color:var(--panel-elevated)] py-1 shadow-[var(--shadow-soft)]", children: [
2339
2343
  shouldShowOrgFilter(org.organizations.length) ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "sticky top-0 z-10 bg-[color:var(--panel-elevated)] px-2 pb-1 pt-1", children: /* @__PURE__ */ jsxRuntime.jsx(
@@ -2403,60 +2407,76 @@ function NavSidebar({
2403
2407
  {
2404
2408
  type: "button",
2405
2409
  onClick: org.onClick,
2406
- className: "flex w-full items-center justify-between gap-2 rounded-md border border-[color:var(--line)] bg-[color:var(--panel-elevated)] px-2.5 py-2 text-left text-[color:var(--foreground)] shadow-sm transition hover:bg-[color:var(--panel)]",
2410
+ className: "flex w-full flex-col overflow-hidden rounded-[5px] border border-[color:var(--line)] bg-[color:var(--panel-elevated)] text-left text-[color:var(--foreground)] shadow-sm transition hover:bg-[color:var(--panel)]",
2407
2411
  children: [
2408
- /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex min-w-0 items-center gap-2.5", children: [
2409
- /* @__PURE__ */ jsxRuntime.jsx(
2410
- "span",
2412
+ /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "relative flex h-[70px] w-full items-center justify-center bg-white px-3", children: [
2413
+ orgLogoSrc ? /* @__PURE__ */ jsxRuntime.jsx("img", { src: orgLogoSrc, alt: "", className: "max-h-[70px] max-w-full object-contain" }) : org.canUploadLogo ? /* @__PURE__ */ jsxRuntime.jsx(
2414
+ "a",
2411
2415
  {
2412
- style: { backgroundColor: orgBg },
2413
- className: "flex h-7 w-7 shrink-0 items-center justify-center overflow-hidden rounded-full text-[11px] font-bold text-white",
2414
- children: orgLogoSrc ? /* @__PURE__ */ jsxRuntime.jsx("img", { src: orgLogoSrc, alt: "", className: "h-full w-full object-cover" }) : (org.name ?? "Org").slice(0, 2).toUpperCase()
2416
+ href: org.uploadLogoHref ?? "#",
2417
+ onClick: (e) => e.stopPropagation(),
2418
+ className: "text-xs font-semibold text-[color:var(--color-accent)] underline",
2419
+ children: "Upload logo"
2415
2420
  }
2416
- ),
2421
+ ) : /* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-sm font-semibold text-neutral-800", children: org.name ?? "Organization" }),
2422
+ /* @__PURE__ */ jsxRuntime.jsx("span", { "aria-hidden": true, className: "absolute inset-x-0 bottom-0 h-[3px]", style: { backgroundImage: orgGradient } })
2423
+ ] }),
2424
+ /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex w-full min-w-0 items-center justify-between gap-2 px-2.5 py-2", children: [
2417
2425
  /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex min-w-0 flex-col", children: [
2418
2426
  /* @__PURE__ */ jsxRuntime.jsx(
2419
2427
  "span",
2420
2428
  {
2421
2429
  title: org.name ?? void 0,
2422
- className: "truncate text-sm font-semibold",
2430
+ className: "truncate text-[13px] font-semibold",
2423
2431
  children: org.name ?? "No organizations"
2424
2432
  }
2425
2433
  ),
2426
2434
  org.id && !org.loading ? /* @__PURE__ */ jsxRuntime.jsx(OrgIdCopyButton, { id: org.id }) : null
2427
- ] })
2428
- ] }),
2429
- /* @__PURE__ */ jsxRuntime.jsx(ChevronDown, {})
2435
+ ] }),
2436
+ /* @__PURE__ */ jsxRuntime.jsx(ChevronDown, {})
2437
+ ] })
2430
2438
  ]
2431
2439
  }
2432
2440
  )
2433
2441
  ] }) : null,
2434
2442
  mode ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "mb-4", children: [
2435
- /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center justify-center gap-2 rounded-md bg-[color:var(--panel-elevated)] p-1", children: (mode.options && mode.options.length > 0 ? mode.options : [{ id: mode.label, label: mode.label, icon: ModeIcon }]).map(
2436
- (opt) => {
2437
- const selected = opt.label === mode.label;
2438
- const OptIcon = opt.icon;
2439
- return /* @__PURE__ */ jsxRuntime.jsx(
2440
- "button",
2441
- {
2442
- type: "button",
2443
- title: opt.label,
2444
- "aria-label": opt.label,
2445
- "aria-current": selected ? "true" : void 0,
2446
- onClick: () => {
2447
- if (!selected) mode.onSelect?.(opt.id);
2448
- },
2449
- disabled: !mode.onSelect && !selected,
2450
- className: [
2451
- "flex h-9 flex-1 items-center justify-center rounded transition",
2452
- selected ? "bg-[color:var(--mode-accent,var(--color-accent))] text-[color:var(--mode-on-accent,white)] shadow-sm" : "text-[color:var(--sidebar-text-muted,var(--muted))] hover:bg-[color:var(--panel)] hover:text-[color:var(--sidebar-text,var(--foreground))]"
2453
- ].join(" "),
2454
- children: OptIcon ? /* @__PURE__ */ jsxRuntime.jsx(OptIcon, { size: 16, className: "shrink-0" }) : null
2455
- },
2456
- opt.id
2457
- );
2443
+ /* @__PURE__ */ jsxRuntime.jsx(
2444
+ "div",
2445
+ {
2446
+ role: "radiogroup",
2447
+ "aria-label": "Mode",
2448
+ className: "flex items-center justify-start gap-0.5 rounded-lg border border-[color:var(--border-inverse,var(--line))] bg-[color:var(--mode-track-bg,var(--panel-elevated))] p-[3px]",
2449
+ children: (mode.options && mode.options.length > 0 ? mode.options : [{ id: mode.label, label: mode.label, icon: ModeIcon }]).map(
2450
+ (opt) => {
2451
+ const selected = opt.label === mode.label;
2452
+ const OptIcon = opt.icon;
2453
+ const available = opt.available ?? true;
2454
+ const title = !available ? opt.unavailableTooltip ?? `${opt.label} isn't active for this organization.` : opt.label;
2455
+ return /* @__PURE__ */ jsxRuntime.jsx(
2456
+ "button",
2457
+ {
2458
+ type: "button",
2459
+ role: "radio",
2460
+ title,
2461
+ "aria-label": title,
2462
+ "aria-checked": selected,
2463
+ "aria-current": selected ? "true" : void 0,
2464
+ onClick: () => {
2465
+ if (available && !selected) mode.onSelect?.(opt.id);
2466
+ },
2467
+ disabled: !available,
2468
+ className: [
2469
+ "flex h-9 items-center justify-center rounded px-[9px] py-[6px] transition",
2470
+ !available ? "cursor-not-allowed text-[color:var(--sidebar-text-muted,var(--muted))] opacity-35" : selected ? "bg-[color:var(--mode-accent,var(--color-accent))] text-[color:var(--mode-on-accent,white)] shadow-sm" : "text-[color:var(--sidebar-text-muted,var(--muted))] hover:bg-white/5 hover:text-[color:var(--sidebar-text,var(--foreground))]"
2471
+ ].join(" "),
2472
+ children: OptIcon ? /* @__PURE__ */ jsxRuntime.jsx(OptIcon, { size: 15, className: "shrink-0" }) : null
2473
+ },
2474
+ opt.id
2475
+ );
2476
+ }
2477
+ )
2458
2478
  }
2459
- ) }),
2479
+ ),
2460
2480
  /* @__PURE__ */ jsxRuntime.jsx("p", { className: "mt-1.5 text-center text-[11px] font-semibold uppercase tracking-[0.08em] text-[color:var(--sidebar-text-muted,var(--muted))]", children: mode.label })
2461
2481
  ] }) : null,
2462
2482
  /* @__PURE__ */ jsxRuntime.jsxs("nav", { className: "flex flex-col gap-1", children: [