@orangecheck/design 0.24.0 → 0.26.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/dist/index.mjs CHANGED
@@ -4,7 +4,7 @@ import * as React2 from 'react';
4
4
  import { createContext, useState, useRef, useEffect, useCallback, useMemo, useContext, Fragment as Fragment$1, useId } from 'react';
5
5
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
6
6
  import { useTheme } from 'next-themes';
7
- import { ChevronDown, Plus, Palette, Check, Sun, Moon, Monitor, CheckIcon, CircleIcon, X, XIcon, AlertTriangle, Pencil, ChevronLeft, ChevronRight, ChevronDownIcon, ChevronUpIcon, Maximize2, Copy, HelpCircle, Boxes, CornerDownLeft, Loader2, Menu } from 'lucide-react';
7
+ import { ChevronDown, Plus, Palette, Check, Sun, Moon, Monitor, Waves, Pause, CheckIcon, CircleIcon, X, XIcon, AlertTriangle, Pencil, ChevronLeft, ChevronRight, ChevronDownIcon, ChevronUpIcon, Maximize2, Copy, HelpCircle, Boxes, CornerDownLeft, Loader2, Menu } from 'lucide-react';
8
8
  import { Slot } from '@radix-ui/react-slot';
9
9
  import { cva } from 'class-variance-authority';
10
10
  import * as LabelPrimitive from '@radix-ui/react-label';
@@ -73,13 +73,18 @@ function resolveTheme(id) {
73
73
  return isKnownTheme(id) ? id : DEFAULT_OC_THEME;
74
74
  }
75
75
  var OC_SKIN_COOKIE = "oc_skin";
76
+ var OC_MOTION_COOKIE = "oc_motion";
76
77
  var BLOBS = [1, 2, 3, 4, 5];
77
78
  function OcAurora({ intensity, className }) {
78
79
  const style = intensity == null ? void 0 : { "--oc-aurora-intensity": String(intensity) };
79
- return /* @__PURE__ */ jsx("div", { className: cn("oc-aurora", className), style, "aria-hidden": "true", children: BLOBS.map((n) => /* @__PURE__ */ jsx("div", { className: `oc-aurora__blob oc-aurora__blob-${n}` }, n)) });
80
+ return /* @__PURE__ */ jsxs("div", { className: cn("oc-aurora", className), style, "aria-hidden": "true", children: [
81
+ BLOBS.map((n) => /* @__PURE__ */ jsx("div", { className: `oc-aurora__blob oc-aurora__blob-${n}` }, n)),
82
+ /* @__PURE__ */ jsx("div", { className: "oc-aurora__grain" })
83
+ ] });
80
84
  }
81
85
  var ONE_YEAR = 60 * 60 * 24 * 365;
82
86
  var ATTR = "data-oc-theme";
87
+ var MOTION_ATTR = "data-oc-motion";
83
88
  function readSkinCookie() {
84
89
  if (typeof document === "undefined") return null;
85
90
  const prefix = `${OC_SKIN_COOKIE}=`;
@@ -111,6 +116,38 @@ function applyAttr(skin) {
111
116
  if (typeof document === "undefined") return;
112
117
  document.documentElement.setAttribute(ATTR, skin);
113
118
  }
119
+ function readMotionCookie() {
120
+ if (typeof document === "undefined") return null;
121
+ const prefix = `${OC_MOTION_COOKIE}=`;
122
+ for (const part of document.cookie.split(";")) {
123
+ const trimmed = part.trim();
124
+ if (trimmed.startsWith(prefix)) {
125
+ const v = decodeURIComponent(trimmed.slice(prefix.length));
126
+ return v === "off" ? "off" : v === "on" ? "on" : null;
127
+ }
128
+ }
129
+ return null;
130
+ }
131
+ function writeMotionCookie(value) {
132
+ if (typeof document === "undefined") return;
133
+ const isLocal = location.hostname === "localhost" || location.hostname === "127.0.0.1";
134
+ const parts = [
135
+ `${OC_MOTION_COOKIE}=${encodeURIComponent(value)}`,
136
+ "Path=/",
137
+ `Max-Age=${ONE_YEAR}`,
138
+ "SameSite=Lax"
139
+ ];
140
+ if (!isLocal) {
141
+ parts.push("Domain=.ochk.io");
142
+ parts.push("Secure");
143
+ }
144
+ document.cookie = parts.join("; ");
145
+ }
146
+ function applyMotionAttr(motion) {
147
+ if (typeof document === "undefined") return;
148
+ if (motion === "off") document.documentElement.setAttribute(MOTION_ATTR, "off");
149
+ else document.documentElement.removeAttribute(MOTION_ATTR);
150
+ }
114
151
  function applySkinChrome(skin) {
115
152
  if (typeof window === "undefined") return;
116
153
  if (typeof window.__ocApplySkinChrome === "function") {
@@ -127,6 +164,7 @@ function OcThemeProvider({
127
164
  aurora = true
128
165
  }) {
129
166
  const [skin, setSkinState] = useState(() => resolveTheme(defaultSkin));
167
+ const [motion, setMotionState] = useState("on");
130
168
  const hydratedRef = useRef(false);
131
169
  useEffect(() => {
132
170
  if (hydratedRef.current) return;
@@ -135,6 +173,9 @@ function OcThemeProvider({
135
173
  applyAttr(fromCookie);
136
174
  applySkinChrome(fromCookie);
137
175
  setSkinState(fromCookie);
176
+ const motionCookie = readMotionCookie() ?? "on";
177
+ applyMotionAttr(motionCookie);
178
+ setMotionState(motionCookie);
138
179
  }, [defaultSkin]);
139
180
  useEffect(() => {
140
181
  function sync() {
@@ -144,6 +185,11 @@ function OcThemeProvider({
144
185
  applySkinChrome(fromCookie);
145
186
  setSkinState(fromCookie);
146
187
  }
188
+ const motionCookie = readMotionCookie() ?? "on";
189
+ if (motionCookie !== motion) {
190
+ applyMotionAttr(motionCookie);
191
+ setMotionState(motionCookie);
192
+ }
147
193
  }
148
194
  window.addEventListener("focus", sync);
149
195
  document.addEventListener("visibilitychange", sync);
@@ -151,7 +197,7 @@ function OcThemeProvider({
151
197
  window.removeEventListener("focus", sync);
152
198
  document.removeEventListener("visibilitychange", sync);
153
199
  };
154
- }, [skin]);
200
+ }, [skin, motion]);
155
201
  const setSkin = useCallback((id) => {
156
202
  const next = resolveTheme(id);
157
203
  applyAttr(next);
@@ -159,9 +205,15 @@ function OcThemeProvider({
159
205
  writeSkinCookie(next);
160
206
  setSkinState(next);
161
207
  }, []);
208
+ const setMotion = useCallback((value2) => {
209
+ const next = value2 === "off" ? "off" : "on";
210
+ applyMotionAttr(next);
211
+ writeMotionCookie(next);
212
+ setMotionState(next);
213
+ }, []);
162
214
  const value = useMemo(
163
- () => ({ skin, setSkin, themes: OC_THEMES }),
164
- [skin, setSkin]
215
+ () => ({ skin, setSkin, themes: OC_THEMES, motion, setMotion }),
216
+ [skin, setSkin, motion, setMotion]
165
217
  );
166
218
  return /* @__PURE__ */ jsxs(OcSkinContext.Provider, { value, children: [
167
219
  aurora !== false && /* @__PURE__ */ jsx(OcAurora, { intensity: typeof aurora === "object" ? aurora.intensity : void 0 }),
@@ -175,9 +227,13 @@ function useOcSkin() {
175
227
  }
176
228
  return ctx;
177
229
  }
230
+ function useOcMotion() {
231
+ const { motion, setMotion } = useOcSkin();
232
+ return { motion, setMotion };
233
+ }
178
234
  function getOcThemeInitScript(defaultSkin = DEFAULT_OC_THEME) {
179
235
  const accents = Object.fromEntries(OC_THEMES.map((t) => [t.id, t.accent]));
180
- return `(function(){var ACC=${JSON.stringify(accents)},DEF=${JSON.stringify(defaultSkin)},ORIG=${JSON.stringify(OC_DEFAULT_ACCENT)},fav=null;function acc(s){return ACC[s]||ACC[DEF]||ORIG;}window.__ocApplySkinChrome=function(s){try{var a=acc(s);var meta=document.querySelector('meta[name="theme-color"]');if(meta){meta.setAttribute('content',a);}var link=document.querySelector('link[rel~="icon"][type="image/svg+xml"]');if(!link){return;}var paint=function(svg){link.setAttribute('href','data:image/svg+xml,'+encodeURIComponent(svg.split(ORIG).join(a)));};if(fav!=null){paint(fav);return;}var h=link.getAttribute('href');if(!h||h.indexOf('data:')===0){return;}fetch(h).then(function(r){return r.text();}).then(function(svg){fav=svg;paint(svg);}).catch(function(){});}catch(e){}};try{var m=document.cookie.match(/(?:^|; )${OC_SKIN_COOKIE}=([^;]*)/);var s=m?decodeURIComponent(m[1]):DEF;if(!s){s=DEF;}document.documentElement.setAttribute('${ATTR}',s);window.__ocApplySkinChrome(s);}catch(e){document.documentElement.setAttribute('${ATTR}',DEF);}})();`;
236
+ return `(function(){var ACC=${JSON.stringify(accents)},DEF=${JSON.stringify(defaultSkin)},ORIG=${JSON.stringify(OC_DEFAULT_ACCENT)},fav=null;function acc(s){return ACC[s]||ACC[DEF]||ORIG;}window.__ocApplySkinChrome=function(s){try{var a=acc(s);var meta=document.querySelector('meta[name="theme-color"]');if(meta){meta.setAttribute('content',a);}var link=document.querySelector('link[rel~="icon"][type="image/svg+xml"]');if(!link){return;}var paint=function(svg){link.setAttribute('href','data:image/svg+xml,'+encodeURIComponent(svg.split(ORIG).join(a)));};if(fav!=null){paint(fav);return;}var h=link.getAttribute('href');if(!h||h.indexOf('data:')===0){return;}fetch(h).then(function(r){return r.text();}).then(function(svg){fav=svg;paint(svg);}).catch(function(){});}catch(e){}};try{var m=document.cookie.match(/(?:^|; )${OC_SKIN_COOKIE}=([^;]*)/);var s=m?decodeURIComponent(m[1]):DEF;if(!s){s=DEF;}document.documentElement.setAttribute('${ATTR}',s);window.__ocApplySkinChrome(s);}catch(e){document.documentElement.setAttribute('${ATTR}',DEF);}try{var mm=document.cookie.match(/(?:^|; )${OC_MOTION_COOKIE}=([^;]*)/);if(mm&&decodeURIComponent(mm[1])==='off'){document.documentElement.setAttribute('${MOTION_ATTR}','off');}}catch(e){}})();`;
181
237
  }
182
238
  var COOKIE = "oc_theme";
183
239
  var ALLOWED = /* @__PURE__ */ new Set(["light", "dark", "system"]);
@@ -312,10 +368,12 @@ var MODES = [
312
368
  ];
313
369
  function AppearanceControls({ className }) {
314
370
  const { skin, setSkin, themes } = useOcSkin();
371
+ const { motion, setMotion } = useOcMotion();
315
372
  const { theme, setTheme } = useTheme();
316
373
  const [mounted, setMounted] = useState(false);
317
374
  useEffect(() => setMounted(true), []);
318
375
  const activeMode = mounted ? theme ?? "system" : null;
376
+ const activeMotion = mounted ? motion : null;
319
377
  return /* @__PURE__ */ jsxs("div", { className, children: [
320
378
  /* @__PURE__ */ jsx("div", { className: "label-mono text-muted-foreground px-3 pt-3 pb-2", children: "mode" }),
321
379
  /* @__PURE__ */ jsx("div", { className: "grid grid-cols-3 gap-1 px-2 pb-2", children: MODES.map(({ id, label, Icon: Icon2 }) => {
@@ -362,6 +420,32 @@ function AppearanceControls({ className }) {
362
420
  ]
363
421
  }
364
422
  ) }, t.id);
423
+ }) }),
424
+ /* @__PURE__ */ jsx("div", { className: "label-mono text-muted-foreground border-t px-3 pt-3 pb-2", children: "ambient motion" }),
425
+ /* @__PURE__ */ jsx("div", { className: "grid grid-cols-2 gap-1 px-2 pb-3", children: [
426
+ { id: "on", label: "on", Icon: Waves },
427
+ { id: "off", label: "off", Icon: Pause }
428
+ ].map(({ id, label, Icon: Icon2 }) => {
429
+ const active = activeMotion === id;
430
+ return /* @__PURE__ */ jsxs(
431
+ "button",
432
+ {
433
+ type: "button",
434
+ role: "menuitemradio",
435
+ "aria-checked": active,
436
+ "aria-label": id === "off" ? "pause ambient motion" : "ambient motion on",
437
+ onClick: () => setMotion(id),
438
+ className: cn(
439
+ "flex flex-col items-center gap-1 rounded-md border py-2 text-[11px] transition-colors",
440
+ active ? "border-primary text-foreground bg-accent" : "border-transparent text-muted-foreground hover:bg-accent hover:text-accent-foreground"
441
+ ),
442
+ children: [
443
+ /* @__PURE__ */ jsx(Icon2, { className: "size-4", "aria-hidden": true }),
444
+ label
445
+ ]
446
+ },
447
+ id
448
+ );
365
449
  }) })
366
450
  ] });
367
451
  }
@@ -4894,6 +4978,9 @@ function OcFamilyFooter({
4894
4978
  columns = [],
4895
4979
  family,
4896
4980
  legalBase = "https://ochk.io",
4981
+ legalCopyright,
4982
+ legalLinks,
4983
+ builtWith,
4897
4984
  className
4898
4985
  }) {
4899
4986
  const familyCols = [];
@@ -4907,6 +4994,13 @@ function OcFamilyFooter({
4907
4994
  const grid = GRID[allColumns.length] ?? GRID[3];
4908
4995
  const year = (/* @__PURE__ */ new Date()).getFullYear();
4909
4996
  const legal = (path) => `${legalBase}${path}`;
4997
+ const links = legalLinks ?? [
4998
+ { href: legal("/privacy"), label: "privacy" },
4999
+ { href: legal("/terms"), label: "terms" },
5000
+ { href: legal("/security"), label: "security" },
5001
+ { href: legal("/trademark"), label: "trademarks" },
5002
+ { href: legal("/contact"), label: "contact" }
5003
+ ];
4910
5004
  return /* @__PURE__ */ jsx("footer", { className: cn("border-t", className), children: /* @__PURE__ */ jsxs("div", { className: "container py-10 sm:py-12 md:py-16", children: [
4911
5005
  /* @__PURE__ */ jsxs("div", { className: cn("grid gap-8 sm:grid-cols-2 sm:gap-10", grid), children: [
4912
5006
  /* @__PURE__ */ jsxs("div", { children: [
@@ -4920,61 +5014,29 @@ function OcFamilyFooter({
4920
5014
  allColumns.map((column) => /* @__PURE__ */ jsx(FooterColumnView, { column }, column.label))
4921
5015
  ] }),
4922
5016
  /* @__PURE__ */ jsxs("div", { className: "mt-10 flex flex-col items-start justify-between gap-3 border-t pt-6 font-mono text-[11px] tracking-widest uppercase sm:flex-row sm:items-center", children: [
4923
- /* @__PURE__ */ jsxs("span", { className: "text-muted-foreground", children: [
5017
+ /* @__PURE__ */ jsx("span", { className: "text-muted-foreground", children: legalCopyright ?? /* @__PURE__ */ jsxs(Fragment, { children: [
4924
5018
  "\xA9 ",
4925
5019
  year,
4926
5020
  " orangecheck \xB7 mit + cc-by-4.0"
4927
- ] }),
4928
- /* @__PURE__ */ jsxs("div", { className: "text-muted-foreground/80 flex flex-wrap items-center gap-x-4 gap-y-1", children: [
4929
- /* @__PURE__ */ jsx(
4930
- "a",
4931
- {
4932
- href: legal("/privacy"),
4933
- className: "hover:text-foreground transition-colors",
4934
- children: "privacy"
4935
- }
4936
- ),
4937
- /* @__PURE__ */ jsx(
4938
- "a",
4939
- {
4940
- href: legal("/terms"),
4941
- className: "hover:text-foreground transition-colors",
4942
- children: "terms"
4943
- }
4944
- ),
4945
- /* @__PURE__ */ jsx(
4946
- "a",
4947
- {
4948
- href: legal("/security"),
4949
- className: "hover:text-foreground transition-colors",
4950
- children: "security"
4951
- }
4952
- ),
4953
- /* @__PURE__ */ jsx(
4954
- "a",
4955
- {
4956
- href: legal("/trademark"),
4957
- className: "hover:text-foreground transition-colors",
4958
- children: "trademarks"
4959
- }
4960
- ),
4961
- /* @__PURE__ */ jsx(
4962
- "a",
4963
- {
4964
- href: legal("/contact"),
4965
- className: "hover:text-foreground transition-colors",
4966
- children: "contact"
4967
- }
4968
- )
4969
- ] }),
5021
+ ] }) }),
5022
+ /* @__PURE__ */ jsx("div", { className: "text-muted-foreground/80 flex flex-wrap items-center gap-x-4 gap-y-1", children: links.map((link) => /* @__PURE__ */ jsx(
5023
+ "a",
5024
+ {
5025
+ href: link.href,
5026
+ ...link.external ? { target: "_blank", rel: "noreferrer" } : {},
5027
+ className: "hover:text-foreground transition-colors",
5028
+ children: link.label
5029
+ },
5030
+ link.label
5031
+ )) }),
4970
5032
  /* @__PURE__ */ jsxs("span", { className: "text-muted-foreground inline-flex items-center gap-1.5", children: [
4971
5033
  /* @__PURE__ */ jsx("span", { className: "text-primary text-[13px] leading-none", children: "\u20BF" }),
4972
- /* @__PURE__ */ jsx("span", { children: "built with bitcoin" })
5034
+ /* @__PURE__ */ jsx("span", { children: builtWith ?? "built with bitcoin" })
4973
5035
  ] })
4974
5036
  ] })
4975
5037
  ] }) });
4976
5038
  }
4977
5039
 
4978
- export { AccentList, AccentNote, Accordion, AccordionContent, AccordionItem, AccordionTrigger, Alert, AlertDescription, AlertTitle, AlertWithAction, AlertWithCountdown, AppShell, AppearanceControls, Badge, Bar, BitcoinAddress, BrandBand, Button, Callout, Card, CheckList, Checkbox, ComparisonTable, ConfirmHost, CopyButton, DEFAULT_OC_THEME, DataRow, DefinitionList, Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, EcosystemSwitcher, EmailCapture, EmptyState, ErrorBoundary, FAMILY_PROPERTIES, Faq, FeatureCard, HelpHint, IconBadge, Input, Label, LayoutSubHeader, MarketingHeading, Modal, NumberedStep, OC_DEFAULT_ACCENT, OC_SKIN_COOKIE, OC_THEMES, OcAccountMenu, OcAccountMenuView, OcAppBar, OcAppearanceMenu, OcAurora, OcDashboardHub, OcDashboardShell, OcFamilyFooter, OcLogoDropdown, OcPrimaryNav, OcThemeBridge, OcThemePicker, OcThemeProvider, Pagination, Panel, Popover, PopoverAnchor, PopoverContent, PopoverTrigger, PromptHost, QrCode, REFERENCE_BTC_USD, RadioGroup, RadioGroupItem, SITE_STATE_LABEL, SatsAmount, Section, SectionHeader, Select, SelectContent, SelectGroup, SelectItem, SelectLabel, SelectScrollDownButton, SelectScrollUpButton, SelectSeparator, SelectTrigger, SelectValue, Separator, Sheet, SheetClose, SheetContent, SheetDescription, SheetFooter, SheetHeader, SheetOverlay, SheetPortal, SheetTitle, SheetTrigger, Skeleton, Sparkline, StatBlock, StatCard, StatGrid, StatTile, StatusPill, StepList, Surface, Switch, Tabs, TabsContent, TabsList, TabsTrigger, Textarea, ThemeToggle, ThemeToggleLink, Toaster, Tooltip, TwoToneHeading, VerifiedChip, Working, WorkingPanel, accentFor, asOf, badgeVariants, buttonVariants, cn, confirm, explorerUrl, findFamilyProperty, formatSats, formatSatsCompact, getOcThemeInitScript, iconBadgeVariants, isKnownTheme, makeStatusPill, priceBoth, prompt, relativeTime, resolveTheme, satsToUsd, shortenAddress, surfaceVariants, usdToSats, useOcSkin, useSpotPrice };
5040
+ export { AccentList, AccentNote, Accordion, AccordionContent, AccordionItem, AccordionTrigger, Alert, AlertDescription, AlertTitle, AlertWithAction, AlertWithCountdown, AppShell, AppearanceControls, Badge, Bar, BitcoinAddress, BrandBand, Button, Callout, Card, CheckList, Checkbox, ComparisonTable, ConfirmHost, CopyButton, DEFAULT_OC_THEME, DataRow, DefinitionList, Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, EcosystemSwitcher, EmailCapture, EmptyState, ErrorBoundary, FAMILY_PROPERTIES, Faq, FeatureCard, HelpHint, IconBadge, Input, Label, LayoutSubHeader, MarketingHeading, Modal, NumberedStep, OC_DEFAULT_ACCENT, OC_MOTION_COOKIE, OC_SKIN_COOKIE, OC_THEMES, OcAccountMenu, OcAccountMenuView, OcAppBar, OcAppearanceMenu, OcAurora, OcDashboardHub, OcDashboardShell, OcFamilyFooter, OcLogoDropdown, OcPrimaryNav, OcThemeBridge, OcThemePicker, OcThemeProvider, Pagination, Panel, Popover, PopoverAnchor, PopoverContent, PopoverTrigger, PromptHost, QrCode, REFERENCE_BTC_USD, RadioGroup, RadioGroupItem, SITE_STATE_LABEL, SatsAmount, Section, SectionHeader, Select, SelectContent, SelectGroup, SelectItem, SelectLabel, SelectScrollDownButton, SelectScrollUpButton, SelectSeparator, SelectTrigger, SelectValue, Separator, Sheet, SheetClose, SheetContent, SheetDescription, SheetFooter, SheetHeader, SheetOverlay, SheetPortal, SheetTitle, SheetTrigger, Skeleton, Sparkline, StatBlock, StatCard, StatGrid, StatTile, StatusPill, StepList, Surface, Switch, Tabs, TabsContent, TabsList, TabsTrigger, Textarea, ThemeToggle, ThemeToggleLink, Toaster, Tooltip, TwoToneHeading, VerifiedChip, Working, WorkingPanel, accentFor, asOf, badgeVariants, buttonVariants, cn, confirm, explorerUrl, findFamilyProperty, formatSats, formatSatsCompact, getOcThemeInitScript, iconBadgeVariants, isKnownTheme, makeStatusPill, priceBoth, prompt, relativeTime, resolveTheme, satsToUsd, shortenAddress, surfaceVariants, usdToSats, useOcMotion, useOcSkin, useSpotPrice };
4979
5041
  //# sourceMappingURL=index.mjs.map
4980
5042
  //# sourceMappingURL=index.mjs.map