@mikenotthepope/substrateui 0.1.1 → 0.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -3271,30 +3271,58 @@ import * as React40 from "react";
3271
3271
  // components/ThemeProvider.tsx
3272
3272
  import { createContext as createContext3, useContext as useContext3, useEffect, useState as useState2, useCallback, useMemo as useMemo2 } from "react";
3273
3273
  import { jsx as jsx43 } from "react/jsx-runtime";
3274
+ var VALID_THEMES = ["light", "dark", "system"];
3275
+ var COLOR_THEMES = ["blue", "plum", "plum-trio"];
3274
3276
  var ThemeContext = createContext3(void 0);
3275
3277
  var STORAGE_KEY = "substrateui-theme";
3278
+ var COLOR_STORAGE_KEY = "substrateui-color-theme";
3276
3279
  function getSystemTheme() {
3277
3280
  if (typeof window === "undefined") return "light";
3278
3281
  return window.matchMedia("(prefers-color-scheme: dark)").matches ? "dark" : "light";
3279
3282
  }
3283
+ function readStoredTheme(key, fallback) {
3284
+ if (typeof window === "undefined") return fallback;
3285
+ const stored = localStorage.getItem(key);
3286
+ return VALID_THEMES.includes(stored) ? stored : fallback;
3287
+ }
3288
+ function readStoredColorTheme(key, fallback) {
3289
+ if (typeof window === "undefined") return fallback;
3290
+ const stored = localStorage.getItem(key);
3291
+ return COLOR_THEMES.includes(stored != null ? stored : "") ? stored : fallback;
3292
+ }
3280
3293
  function applyClass(resolved) {
3281
3294
  document.documentElement.classList.remove("light", "dark");
3282
3295
  document.documentElement.classList.add(resolved);
3283
3296
  }
3297
+ function applyColorTheme(colorTheme) {
3298
+ for (const t of COLOR_THEMES) {
3299
+ document.documentElement.classList.remove(`theme-${t}`);
3300
+ }
3301
+ if (colorTheme !== "blue") {
3302
+ document.documentElement.classList.add(`theme-${colorTheme}`);
3303
+ }
3304
+ }
3284
3305
  function ThemeProvider({
3285
3306
  children,
3286
3307
  defaultTheme = "system",
3287
- storageKey = STORAGE_KEY
3308
+ defaultColorTheme = "blue",
3309
+ storageKey = STORAGE_KEY,
3310
+ colorStorageKey = COLOR_STORAGE_KEY
3288
3311
  }) {
3289
- const [theme, setThemeState] = useState2(() => {
3290
- if (typeof window === "undefined") return defaultTheme;
3291
- return localStorage.getItem(storageKey) || defaultTheme;
3292
- });
3312
+ const [theme, setThemeState] = useState2(
3313
+ () => readStoredTheme(storageKey, defaultTheme)
3314
+ );
3315
+ const [colorTheme, setColorThemeState] = useState2(
3316
+ () => readStoredColorTheme(colorStorageKey, defaultColorTheme)
3317
+ );
3293
3318
  const [systemTheme, setSystemTheme] = useState2(getSystemTheme);
3294
3319
  const resolvedTheme = theme === "system" ? systemTheme : theme;
3295
3320
  useEffect(() => {
3296
3321
  applyClass(resolvedTheme);
3297
3322
  }, [resolvedTheme]);
3323
+ useEffect(() => {
3324
+ applyColorTheme(colorTheme);
3325
+ }, [colorTheme]);
3298
3326
  useEffect(() => {
3299
3327
  const mq = window.matchMedia("(prefers-color-scheme: dark)");
3300
3328
  const handler = (e) => {
@@ -3303,6 +3331,23 @@ function ThemeProvider({
3303
3331
  mq.addEventListener("change", handler);
3304
3332
  return () => mq.removeEventListener("change", handler);
3305
3333
  }, []);
3334
+ useEffect(() => {
3335
+ const handler = (e) => {
3336
+ var _a;
3337
+ if (e.key === storageKey) {
3338
+ setThemeState(
3339
+ VALID_THEMES.includes(e.newValue) ? e.newValue : defaultTheme
3340
+ );
3341
+ }
3342
+ if (e.key === colorStorageKey) {
3343
+ setColorThemeState(
3344
+ COLOR_THEMES.includes((_a = e.newValue) != null ? _a : "") ? e.newValue : defaultColorTheme
3345
+ );
3346
+ }
3347
+ };
3348
+ window.addEventListener("storage", handler);
3349
+ return () => window.removeEventListener("storage", handler);
3350
+ }, [storageKey, colorStorageKey, defaultTheme, defaultColorTheme]);
3306
3351
  const setTheme = useCallback(
3307
3352
  (newTheme) => {
3308
3353
  localStorage.setItem(storageKey, newTheme);
@@ -3310,9 +3355,16 @@ function ThemeProvider({
3310
3355
  },
3311
3356
  [storageKey]
3312
3357
  );
3358
+ const setColorTheme = useCallback(
3359
+ (newColorTheme) => {
3360
+ localStorage.setItem(colorStorageKey, newColorTheme);
3361
+ setColorThemeState(newColorTheme);
3362
+ },
3363
+ [colorStorageKey]
3364
+ );
3313
3365
  const value = useMemo2(
3314
- () => ({ theme, resolvedTheme, setTheme }),
3315
- [theme, resolvedTheme, setTheme]
3366
+ () => ({ theme, resolvedTheme, setTheme, colorTheme, setColorTheme, colorThemes: COLOR_THEMES }),
3367
+ [theme, resolvedTheme, setTheme, colorTheme, setColorTheme]
3316
3368
  );
3317
3369
  return /* @__PURE__ */ jsx43(ThemeContext.Provider, { value, children });
3318
3370
  }
@@ -5836,6 +5888,83 @@ function ThemeToggle(_a) {
5836
5888
  );
5837
5889
  }
5838
5890
 
5891
+ // components/ColorThemeToggle.tsx
5892
+ import { useSyncExternalStore as useSyncExternalStore2 } from "react";
5893
+ import { jsx as jsx65, jsxs as jsxs33 } from "react/jsx-runtime";
5894
+ var subscribe2 = () => () => {
5895
+ };
5896
+ var getSnapshot2 = () => true;
5897
+ var getServerSnapshot2 = () => false;
5898
+ var COLOR_SWATCHES = {
5899
+ blue: "#5294FF",
5900
+ plum: "#B254CF",
5901
+ "plum-trio": "#B254CF"
5902
+ };
5903
+ var COLOR_LABELS = {
5904
+ blue: "Blue",
5905
+ plum: "Plum",
5906
+ "plum-trio": "Plum Trio"
5907
+ };
5908
+ function ColorThemeToggle(_a) {
5909
+ var _b = _a, {
5910
+ variant = "ghost",
5911
+ size = "md",
5912
+ className
5913
+ } = _b, props = __objRest(_b, [
5914
+ "variant",
5915
+ "size",
5916
+ "className"
5917
+ ]);
5918
+ const { colorTheme, setColorTheme, colorThemes } = useTheme();
5919
+ const mounted = useSyncExternalStore2(subscribe2, getSnapshot2, getServerSnapshot2);
5920
+ return /* @__PURE__ */ jsxs33(DropdownMenuComponent, { children: [
5921
+ /* @__PURE__ */ jsx65(DropdownMenuComponent.Trigger, { asChild: true, children: /* @__PURE__ */ jsx65(
5922
+ IconButton,
5923
+ __spreadProps(__spreadValues({
5924
+ variant,
5925
+ size,
5926
+ className,
5927
+ "aria-label": mounted ? `Color theme: ${colorTheme}` : "Color theme"
5928
+ }, props), {
5929
+ children: /* @__PURE__ */ jsx65(
5930
+ "span",
5931
+ {
5932
+ className: "block w-4 h-4 border-2 border-border",
5933
+ style: {
5934
+ backgroundColor: mounted ? COLOR_SWATCHES[colorTheme] : void 0,
5935
+ borderRadius: "var(--radius, 0)"
5936
+ }
5937
+ }
5938
+ )
5939
+ })
5940
+ ) }),
5941
+ /* @__PURE__ */ jsxs33(DropdownMenuComponent.Content, { align: "end", children: [
5942
+ /* @__PURE__ */ jsx65(DropdownMenuComponent.Label, { children: "Color Theme" }),
5943
+ /* @__PURE__ */ jsx65(DropdownMenuComponent.Separator, {}),
5944
+ /* @__PURE__ */ jsx65(
5945
+ DropdownMenuComponent.RadioGroup,
5946
+ {
5947
+ value: colorTheme,
5948
+ onValueChange: (v) => setColorTheme(v),
5949
+ children: colorThemes.map((theme) => /* @__PURE__ */ jsxs33(DropdownMenuComponent.RadioItem, { value: theme, children: [
5950
+ /* @__PURE__ */ jsx65(
5951
+ "span",
5952
+ {
5953
+ className: "inline-block w-3 h-3 border border-border mr-1",
5954
+ style: {
5955
+ backgroundColor: COLOR_SWATCHES[theme],
5956
+ borderRadius: "var(--radius, 0)"
5957
+ }
5958
+ }
5959
+ ),
5960
+ COLOR_LABELS[theme]
5961
+ ] }, theme))
5962
+ }
5963
+ )
5964
+ ] })
5965
+ ] });
5966
+ }
5967
+
5839
5968
  // lib/create-theme.ts
5840
5969
  function createTheme(name, config) {
5841
5970
  const declarations = [];
@@ -5876,7 +6005,7 @@ ${declarations.join("\n")}
5876
6005
  }
5877
6006
 
5878
6007
  // components/landing/Hero.tsx
5879
- import { jsx as jsx65, jsxs as jsxs33 } from "react/jsx-runtime";
6008
+ import { jsx as jsx66, jsxs as jsxs34 } from "react/jsx-runtime";
5880
6009
  function Hero({
5881
6010
  badge,
5882
6011
  title,
@@ -5886,14 +6015,14 @@ function Hero({
5886
6015
  className,
5887
6016
  align = "center"
5888
6017
  }) {
5889
- return /* @__PURE__ */ jsx65(
6018
+ return /* @__PURE__ */ jsx66(
5890
6019
  "section",
5891
6020
  {
5892
6021
  className: cn(
5893
6022
  "w-full border-b-2 bg-background",
5894
6023
  className
5895
6024
  ),
5896
- children: /* @__PURE__ */ jsxs33(
6025
+ children: /* @__PURE__ */ jsxs34(
5897
6026
  "div",
5898
6027
  {
5899
6028
  className: cn(
@@ -5902,10 +6031,10 @@ function Hero({
5902
6031
  align === "left" && "items-start text-left"
5903
6032
  ),
5904
6033
  children: [
5905
- badge && /* @__PURE__ */ jsx65("div", { children: badge }),
5906
- /* @__PURE__ */ jsx65("h1", { className: "font-head text-4xl sm:text-5xl lg:text-6xl max-w-4xl", children: title }),
5907
- subtitle && /* @__PURE__ */ jsx65("p", { className: "font-sans text-lg lg:text-xl text-muted-foreground max-w-2xl", children: subtitle }),
5908
- actions && /* @__PURE__ */ jsx65("div", { className: "flex flex-wrap gap-3 mt-2", children: actions }),
6034
+ badge && /* @__PURE__ */ jsx66("div", { children: badge }),
6035
+ /* @__PURE__ */ jsx66("h1", { className: "font-head text-4xl sm:text-5xl lg:text-6xl max-w-4xl", children: title }),
6036
+ subtitle && /* @__PURE__ */ jsx66("p", { className: "font-sans text-lg lg:text-xl text-muted-foreground max-w-2xl", children: subtitle }),
6037
+ actions && /* @__PURE__ */ jsx66("div", { className: "flex flex-wrap gap-3 mt-2", children: actions }),
5909
6038
  children
5910
6039
  ]
5911
6040
  }
@@ -5916,7 +6045,7 @@ function Hero({
5916
6045
 
5917
6046
  // components/landing/Section.tsx
5918
6047
  import { cva as cva20 } from "class-variance-authority";
5919
- import { jsx as jsx66, jsxs as jsxs34 } from "react/jsx-runtime";
6048
+ import { jsx as jsx67, jsxs as jsxs35 } from "react/jsx-runtime";
5920
6049
  var sectionVariants = cva20("w-full py-16 lg:py-24 scroll-mt-[120px]", {
5921
6050
  variants: {
5922
6051
  background: {
@@ -5946,13 +6075,13 @@ function Section(_a) {
5946
6075
  "background",
5947
6076
  "align"
5948
6077
  ]);
5949
- return /* @__PURE__ */ jsx66(
6078
+ return /* @__PURE__ */ jsx67(
5950
6079
  "section",
5951
6080
  __spreadProps(__spreadValues({
5952
6081
  className: cn(sectionVariants({ background }), className)
5953
6082
  }, props), {
5954
- children: /* @__PURE__ */ jsxs34("div", { className: "mx-auto max-w-6xl px-4", children: [
5955
- (title || subtitle) && /* @__PURE__ */ jsxs34(
6083
+ children: /* @__PURE__ */ jsxs35("div", { className: "mx-auto max-w-6xl px-4", children: [
6084
+ (title || subtitle) && /* @__PURE__ */ jsxs35(
5956
6085
  "div",
5957
6086
  {
5958
6087
  className: cn(
@@ -5961,8 +6090,8 @@ function Section(_a) {
5961
6090
  align === "left" && "text-left"
5962
6091
  ),
5963
6092
  children: [
5964
- title && /* @__PURE__ */ jsx66("h2", { className: "font-head text-3xl lg:text-4xl mb-3", children: title }),
5965
- subtitle && /* @__PURE__ */ jsx66("p", { className: "font-sans text-lg text-muted-foreground max-w-2xl mx-auto", children: subtitle })
6093
+ title && /* @__PURE__ */ jsx67("h2", { className: "font-head text-3xl lg:text-4xl mb-3", children: title }),
6094
+ subtitle && /* @__PURE__ */ jsx67("p", { className: "font-sans text-lg text-muted-foreground max-w-2xl mx-auto", children: subtitle })
5966
6095
  ]
5967
6096
  }
5968
6097
  ),
@@ -5973,7 +6102,7 @@ function Section(_a) {
5973
6102
  }
5974
6103
 
5975
6104
  // components/landing/Footer.tsx
5976
- import { jsx as jsx67, jsxs as jsxs35 } from "react/jsx-runtime";
6105
+ import { jsx as jsx68, jsxs as jsxs36 } from "react/jsx-runtime";
5977
6106
  function Footer({
5978
6107
  brand,
5979
6108
  tagline,
@@ -5981,15 +6110,15 @@ function Footer({
5981
6110
  bottom,
5982
6111
  className
5983
6112
  }) {
5984
- return /* @__PURE__ */ jsx67("footer", { className: cn("w-full border-t-2 bg-background", className), children: /* @__PURE__ */ jsxs35("div", { className: "mx-auto max-w-6xl px-4 py-12 lg:py-16", children: [
5985
- /* @__PURE__ */ jsxs35("div", { className: "grid gap-8 lg:grid-cols-[1.5fr_repeat(auto-fit,1fr)]", children: [
5986
- /* @__PURE__ */ jsxs35("div", { className: "max-w-xs", children: [
5987
- /* @__PURE__ */ jsx67("div", { className: "font-head text-2xl mb-2", children: brand }),
5988
- tagline && /* @__PURE__ */ jsx67("p", { className: "font-sans text-sm text-muted-foreground", children: tagline })
6113
+ return /* @__PURE__ */ jsx68("footer", { className: cn("w-full border-t-2 bg-background", className), children: /* @__PURE__ */ jsxs36("div", { className: "mx-auto max-w-6xl px-4 py-12 lg:py-16", children: [
6114
+ /* @__PURE__ */ jsxs36("div", { className: "grid gap-8 lg:grid-cols-[1.5fr_repeat(auto-fit,1fr)]", children: [
6115
+ /* @__PURE__ */ jsxs36("div", { className: "max-w-xs", children: [
6116
+ /* @__PURE__ */ jsx68("div", { className: "font-head text-2xl mb-2", children: brand }),
6117
+ tagline && /* @__PURE__ */ jsx68("p", { className: "font-sans text-sm text-muted-foreground", children: tagline })
5989
6118
  ] }),
5990
- groups.length > 0 && /* @__PURE__ */ jsx67("div", { className: "grid gap-8 sm:grid-cols-2 lg:grid-cols-3 col-span-full lg:col-span-1", children: groups.map((group) => /* @__PURE__ */ jsxs35("div", { children: [
5991
- /* @__PURE__ */ jsx67("h4", { className: "font-head text-sm uppercase mb-3", children: group.title }),
5992
- /* @__PURE__ */ jsx67("ul", { className: "flex flex-col gap-2", children: group.links.map((link) => /* @__PURE__ */ jsx67("li", { children: /* @__PURE__ */ jsx67(
6119
+ groups.length > 0 && /* @__PURE__ */ jsx68("div", { className: "grid gap-8 sm:grid-cols-2 lg:grid-cols-3 col-span-full lg:col-span-1", children: groups.map((group) => /* @__PURE__ */ jsxs36("div", { children: [
6120
+ /* @__PURE__ */ jsx68("h4", { className: "font-head text-sm uppercase mb-3", children: group.title }),
6121
+ /* @__PURE__ */ jsx68("ul", { className: "flex flex-col gap-2", children: group.links.map((link) => /* @__PURE__ */ jsx68("li", { children: /* @__PURE__ */ jsx68(
5993
6122
  "a",
5994
6123
  {
5995
6124
  href: link.href,
@@ -5999,21 +6128,21 @@ function Footer({
5999
6128
  ) }, link.label)) })
6000
6129
  ] }, group.title)) })
6001
6130
  ] }),
6002
- bottom && /* @__PURE__ */ jsx67("div", { className: "mt-12 pt-6 border-t-2 font-sans text-sm text-muted-foreground", children: bottom })
6131
+ bottom && /* @__PURE__ */ jsx68("div", { className: "mt-12 pt-6 border-t-2 font-sans text-sm text-muted-foreground", children: bottom })
6003
6132
  ] }) });
6004
6133
  }
6005
6134
 
6006
6135
  // components/landing/PricingTable.tsx
6007
- import { jsx as jsx68, jsxs as jsxs36 } from "react/jsx-runtime";
6136
+ import { jsx as jsx69, jsxs as jsxs37 } from "react/jsx-runtime";
6008
6137
  function PricingTable({ tiers, className }) {
6009
- return /* @__PURE__ */ jsx68(
6138
+ return /* @__PURE__ */ jsx69(
6010
6139
  "div",
6011
6140
  {
6012
6141
  className: cn(
6013
6142
  "grid gap-6 sm:grid-cols-2 lg:grid-cols-3",
6014
6143
  className
6015
6144
  ),
6016
- children: tiers.map((tier) => /* @__PURE__ */ jsxs36(
6145
+ children: tiers.map((tier) => /* @__PURE__ */ jsxs37(
6017
6146
  "div",
6018
6147
  {
6019
6148
  className: cn(
@@ -6021,15 +6150,15 @@ function PricingTable({ tiers, className }) {
6021
6150
  tier.highlighted ? "shadow-lg border-primary ring-2 ring-primary scale-[1.02]" : "shadow-md"
6022
6151
  ),
6023
6152
  children: [
6024
- /* @__PURE__ */ jsxs36("div", { className: "p-6 border-b-2", children: [
6025
- /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between mb-2", children: [
6026
- /* @__PURE__ */ jsx68("h3", { className: "font-head text-xl", children: tier.name }),
6153
+ /* @__PURE__ */ jsxs37("div", { className: "p-6 border-b-2", children: [
6154
+ /* @__PURE__ */ jsxs37("div", { className: "flex items-center justify-between mb-2", children: [
6155
+ /* @__PURE__ */ jsx69("h3", { className: "font-head text-xl", children: tier.name }),
6027
6156
  tier.badge
6028
6157
  ] }),
6029
- /* @__PURE__ */ jsx68("div", { className: "font-head text-4xl mb-1", children: tier.price }),
6030
- tier.description && /* @__PURE__ */ jsx68("p", { className: "font-sans text-sm text-muted-foreground", children: tier.description })
6158
+ /* @__PURE__ */ jsx69("div", { className: "font-head text-4xl mb-1", children: tier.price }),
6159
+ tier.description && /* @__PURE__ */ jsx69("p", { className: "font-sans text-sm text-muted-foreground", children: tier.description })
6031
6160
  ] }),
6032
- /* @__PURE__ */ jsx68("div", { className: "p-6 flex-1", children: /* @__PURE__ */ jsx68("ul", { className: "flex flex-col gap-3", children: tier.features.map((feature) => /* @__PURE__ */ jsxs36(
6161
+ /* @__PURE__ */ jsx69("div", { className: "p-6 flex-1", children: /* @__PURE__ */ jsx69("ul", { className: "flex flex-col gap-3", children: tier.features.map((feature) => /* @__PURE__ */ jsxs37(
6033
6162
  "li",
6034
6163
  {
6035
6164
  className: cn(
@@ -6037,7 +6166,7 @@ function PricingTable({ tiers, className }) {
6037
6166
  !feature.included && "text-muted-foreground line-through"
6038
6167
  ),
6039
6168
  children: [
6040
- /* @__PURE__ */ jsx68(
6169
+ /* @__PURE__ */ jsx69(
6041
6170
  "span",
6042
6171
  {
6043
6172
  className: cn(
@@ -6052,7 +6181,7 @@ function PricingTable({ tiers, className }) {
6052
6181
  },
6053
6182
  feature.text
6054
6183
  )) }) }),
6055
- /* @__PURE__ */ jsx68("div", { className: "p-6 border-t-2", children: tier.cta })
6184
+ /* @__PURE__ */ jsx69("div", { className: "p-6 border-t-2", children: tier.cta })
6056
6185
  ]
6057
6186
  },
6058
6187
  tier.name
@@ -6062,7 +6191,7 @@ function PricingTable({ tiers, className }) {
6062
6191
  }
6063
6192
 
6064
6193
  // components/landing/FeatureSection.tsx
6065
- import { jsx as jsx69, jsxs as jsxs37 } from "react/jsx-runtime";
6194
+ import { jsx as jsx70, jsxs as jsxs38 } from "react/jsx-runtime";
6066
6195
  var columnClasses2 = {
6067
6196
  2: "grid gap-6 sm:grid-cols-2",
6068
6197
  3: "grid gap-6 sm:grid-cols-2 lg:grid-cols-3",
@@ -6073,14 +6202,14 @@ function FeatureSection({
6073
6202
  columns = 3,
6074
6203
  className
6075
6204
  }) {
6076
- return /* @__PURE__ */ jsx69("div", { className: cn(columnClasses2[columns], className), children: features.map((feature) => /* @__PURE__ */ jsxs37(
6205
+ return /* @__PURE__ */ jsx70("div", { className: cn(columnClasses2[columns], className), children: features.map((feature) => /* @__PURE__ */ jsxs38(
6077
6206
  "div",
6078
6207
  {
6079
6208
  className: "border-2 p-6 bg-card shadow-md",
6080
6209
  children: [
6081
- feature.icon && /* @__PURE__ */ jsx69("div", { className: "mb-4 inline-flex items-center justify-center h-12 w-12 border-2 bg-primary text-primary-foreground shadow-sm", children: feature.icon }),
6082
- /* @__PURE__ */ jsx69("h3", { className: "font-head text-lg mb-2", children: feature.title }),
6083
- /* @__PURE__ */ jsx69("p", { className: "font-sans text-sm text-muted-foreground", children: feature.description })
6210
+ feature.icon && /* @__PURE__ */ jsx70("div", { className: "mb-4 inline-flex items-center justify-center h-12 w-12 border-2 bg-primary text-primary-foreground shadow-sm", children: feature.icon }),
6211
+ /* @__PURE__ */ jsx70("h3", { className: "font-head text-lg mb-2", children: feature.title }),
6212
+ /* @__PURE__ */ jsx70("p", { className: "font-sans text-sm text-muted-foreground", children: feature.description })
6084
6213
  ]
6085
6214
  },
6086
6215
  feature.title
@@ -6088,7 +6217,7 @@ function FeatureSection({
6088
6217
  }
6089
6218
 
6090
6219
  // components/landing/Testimonial.tsx
6091
- import { jsx as jsx70, jsxs as jsxs38 } from "react/jsx-runtime";
6220
+ import { jsx as jsx71, jsxs as jsxs39 } from "react/jsx-runtime";
6092
6221
  var columnClasses3 = {
6093
6222
  1: "grid gap-6 max-w-2xl mx-auto",
6094
6223
  2: "grid gap-6 sm:grid-cols-2",
@@ -6099,21 +6228,21 @@ function Testimonial({
6099
6228
  columns = 3,
6100
6229
  className
6101
6230
  }) {
6102
- return /* @__PURE__ */ jsx70("div", { className: cn(columnClasses3[columns], className), children: testimonials.map((t) => /* @__PURE__ */ jsxs38(
6231
+ return /* @__PURE__ */ jsx71("div", { className: cn(columnClasses3[columns], className), children: testimonials.map((t) => /* @__PURE__ */ jsxs39(
6103
6232
  "div",
6104
6233
  {
6105
6234
  className: "border-2 p-6 bg-card shadow-md flex flex-col",
6106
6235
  children: [
6107
- /* @__PURE__ */ jsxs38("blockquote", { className: "font-sans text-sm leading-relaxed flex-1 mb-6", children: [
6236
+ /* @__PURE__ */ jsxs39("blockquote", { className: "font-sans text-sm leading-relaxed flex-1 mb-6", children: [
6108
6237
  "\u201C",
6109
6238
  t.quote,
6110
6239
  "\u201D"
6111
6240
  ] }),
6112
- /* @__PURE__ */ jsxs38("div", { className: "flex items-center gap-3 border-t-2 pt-4", children: [
6113
- t.avatar && /* @__PURE__ */ jsx70("div", { className: "h-10 w-10 shrink-0 border-2 overflow-hidden", children: t.avatar }),
6114
- /* @__PURE__ */ jsxs38("div", { children: [
6115
- /* @__PURE__ */ jsx70("p", { className: "font-head text-sm", children: t.name }),
6116
- (t.role || t.company) && /* @__PURE__ */ jsx70("p", { className: "font-sans text-xs text-muted-foreground", children: [t.role, t.company].filter(Boolean).join(", ") })
6241
+ /* @__PURE__ */ jsxs39("div", { className: "flex items-center gap-3 border-t-2 pt-4", children: [
6242
+ t.avatar && /* @__PURE__ */ jsx71("div", { className: "h-10 w-10 shrink-0 border-2 overflow-hidden", children: t.avatar }),
6243
+ /* @__PURE__ */ jsxs39("div", { children: [
6244
+ /* @__PURE__ */ jsx71("p", { className: "font-head text-sm", children: t.name }),
6245
+ (t.role || t.company) && /* @__PURE__ */ jsx71("p", { className: "font-sans text-xs text-muted-foreground", children: [t.role, t.company].filter(Boolean).join(", ") })
6117
6246
  ] })
6118
6247
  ] })
6119
6248
  ]
@@ -6123,9 +6252,9 @@ function Testimonial({
6123
6252
  }
6124
6253
 
6125
6254
  // components/landing/LogoCloud.tsx
6126
- import { jsx as jsx71 } from "react/jsx-runtime";
6255
+ import { jsx as jsx72 } from "react/jsx-runtime";
6127
6256
  function LogoCloud({ children, className }) {
6128
- return /* @__PURE__ */ jsx71(
6257
+ return /* @__PURE__ */ jsx72(
6129
6258
  "div",
6130
6259
  {
6131
6260
  className: cn(
@@ -6138,24 +6267,24 @@ function LogoCloud({ children, className }) {
6138
6267
  }
6139
6268
 
6140
6269
  // components/landing/CTABanner.tsx
6141
- import { jsx as jsx72, jsxs as jsxs39 } from "react/jsx-runtime";
6270
+ import { jsx as jsx73, jsxs as jsxs40 } from "react/jsx-runtime";
6142
6271
  function CTABanner({
6143
6272
  title,
6144
6273
  subtitle,
6145
6274
  actions,
6146
6275
  className
6147
6276
  }) {
6148
- return /* @__PURE__ */ jsx72(
6277
+ return /* @__PURE__ */ jsx73(
6149
6278
  "section",
6150
6279
  {
6151
6280
  className: cn(
6152
6281
  "w-full border-y-2 bg-primary text-primary-foreground",
6153
6282
  className
6154
6283
  ),
6155
- children: /* @__PURE__ */ jsxs39("div", { className: "mx-auto max-w-6xl px-4 py-16 lg:py-20 flex flex-col items-center text-center gap-4", children: [
6156
- /* @__PURE__ */ jsx72("h2", { className: "font-head text-3xl lg:text-4xl", children: title }),
6157
- subtitle && /* @__PURE__ */ jsx72("p", { className: "font-sans text-lg max-w-xl", children: subtitle }),
6158
- actions && /* @__PURE__ */ jsx72("div", { className: "flex flex-wrap gap-3 mt-2", children: actions })
6284
+ children: /* @__PURE__ */ jsxs40("div", { className: "mx-auto max-w-6xl px-4 py-16 lg:py-20 flex flex-col items-center text-center gap-4", children: [
6285
+ /* @__PURE__ */ jsx73("h2", { className: "font-head text-3xl lg:text-4xl", children: title }),
6286
+ subtitle && /* @__PURE__ */ jsx73("p", { className: "font-sans text-lg max-w-xl", children: subtitle }),
6287
+ actions && /* @__PURE__ */ jsx73("div", { className: "flex flex-wrap gap-3 mt-2", children: actions })
6159
6288
  ] })
6160
6289
  }
6161
6290
  );
@@ -6164,20 +6293,20 @@ function CTABanner({
6164
6293
  // components/landing/FAQ.tsx
6165
6294
  import * as React60 from "react";
6166
6295
  import { ChevronDown as ChevronDown6 } from "lucide-react";
6167
- import { jsx as jsx73, jsxs as jsxs40 } from "react/jsx-runtime";
6296
+ import { jsx as jsx74, jsxs as jsxs41 } from "react/jsx-runtime";
6168
6297
  function FAQ({ items, className }) {
6169
6298
  const [openIndex, setOpenIndex] = React60.useState(null);
6170
- return /* @__PURE__ */ jsx73("div", { className: cn("w-full max-w-3xl mx-auto", className), children: items.map((item, i) => {
6299
+ return /* @__PURE__ */ jsx74("div", { className: cn("w-full max-w-3xl mx-auto", className), children: items.map((item, i) => {
6171
6300
  const isOpen = openIndex === i;
6172
- return /* @__PURE__ */ jsxs40("div", { className: "border-2 border-b-0 last:border-b-2", children: [
6173
- /* @__PURE__ */ jsxs40(
6301
+ return /* @__PURE__ */ jsxs41("div", { className: "border-2 border-b-0 last:border-b-2", children: [
6302
+ /* @__PURE__ */ jsxs41(
6174
6303
  "button",
6175
6304
  {
6176
6305
  onClick: () => setOpenIndex(isOpen ? null : i),
6177
6306
  className: "w-full flex items-center justify-between p-4 text-left cursor-pointer hover:bg-accent/30 transition-colors",
6178
6307
  children: [
6179
- /* @__PURE__ */ jsx73("span", { className: "font-head text-sm pr-4", children: item.question }),
6180
- /* @__PURE__ */ jsx73(
6308
+ /* @__PURE__ */ jsx74("span", { className: "font-head text-sm pr-4", children: item.question }),
6309
+ /* @__PURE__ */ jsx74(
6181
6310
  ChevronDown6,
6182
6311
  {
6183
6312
  className: cn(
@@ -6189,24 +6318,24 @@ function FAQ({ items, className }) {
6189
6318
  ]
6190
6319
  }
6191
6320
  ),
6192
- isOpen && /* @__PURE__ */ jsx73("div", { className: "px-4 pb-4 font-sans text-sm text-muted-foreground", children: item.answer })
6321
+ isOpen && /* @__PURE__ */ jsx74("div", { className: "px-4 pb-4 font-sans text-sm text-muted-foreground", children: item.answer })
6193
6322
  ] }, i);
6194
6323
  }) });
6195
6324
  }
6196
6325
 
6197
6326
  // components/landing/StatsBar.tsx
6198
- import { jsx as jsx74, jsxs as jsxs41 } from "react/jsx-runtime";
6327
+ import { jsx as jsx75, jsxs as jsxs42 } from "react/jsx-runtime";
6199
6328
  function StatsBar({ stats, className }) {
6200
- return /* @__PURE__ */ jsx74(
6329
+ return /* @__PURE__ */ jsx75(
6201
6330
  "div",
6202
6331
  {
6203
6332
  className: cn(
6204
6333
  "w-full border-y-2 bg-card",
6205
6334
  className
6206
6335
  ),
6207
- children: /* @__PURE__ */ jsx74("div", { className: "mx-auto max-w-6xl px-4 py-10 grid grid-cols-2 lg:grid-cols-4 gap-8", children: stats.map((stat) => /* @__PURE__ */ jsxs41("div", { className: "text-center", children: [
6208
- /* @__PURE__ */ jsx74("div", { className: "font-head text-3xl lg:text-4xl mb-1", children: stat.value }),
6209
- /* @__PURE__ */ jsx74("div", { className: "font-sans text-sm text-muted-foreground uppercase", children: stat.label })
6336
+ children: /* @__PURE__ */ jsx75("div", { className: "mx-auto max-w-6xl px-4 py-10 grid grid-cols-2 lg:grid-cols-4 gap-8", children: stats.map((stat) => /* @__PURE__ */ jsxs42("div", { className: "text-center", children: [
6337
+ /* @__PURE__ */ jsx75("div", { className: "font-head text-3xl lg:text-4xl mb-1", children: stat.value }),
6338
+ /* @__PURE__ */ jsx75("div", { className: "font-sans text-sm text-muted-foreground uppercase", children: stat.label })
6210
6339
  ] }, stat.label)) })
6211
6340
  }
6212
6341
  );
@@ -6215,37 +6344,39 @@ function StatsBar({ stats, className }) {
6215
6344
  // components/landing/AnnouncementBanner.tsx
6216
6345
  import * as React61 from "react";
6217
6346
  import { X as X4 } from "lucide-react";
6218
- import { jsx as jsx75, jsxs as jsxs42 } from "react/jsx-runtime";
6347
+ import { jsx as jsx76, jsxs as jsxs43 } from "react/jsx-runtime";
6219
6348
  function AnnouncementBanner({
6220
6349
  children,
6221
6350
  dismissible = true,
6222
6351
  className
6223
6352
  }) {
6224
- const [visible, setVisible] = React61.useState(() => {
6225
- if (typeof window === "undefined") return true;
6226
- return sessionStorage.getItem("announcement-dismissed") !== "true";
6227
- });
6353
+ const [visible, setVisible] = React61.useState(true);
6354
+ React61.useEffect(() => {
6355
+ if (sessionStorage.getItem("announcement-dismissed") === "true") {
6356
+ setVisible(false);
6357
+ }
6358
+ }, []);
6228
6359
  const handleDismiss = () => {
6229
6360
  setVisible(false);
6230
6361
  sessionStorage.setItem("announcement-dismissed", "true");
6231
6362
  };
6232
6363
  if (!visible) return null;
6233
- return /* @__PURE__ */ jsx75(
6364
+ return /* @__PURE__ */ jsx76(
6234
6365
  "div",
6235
6366
  {
6236
6367
  className: cn(
6237
6368
  "w-full bg-primary text-primary-foreground border-b-2",
6238
6369
  className
6239
6370
  ),
6240
- children: /* @__PURE__ */ jsxs42("div", { className: "mx-auto max-w-6xl px-4 py-2 flex items-center justify-center gap-3", children: [
6241
- /* @__PURE__ */ jsx75("p", { className: "font-sans text-sm text-center flex-1", children }),
6242
- dismissible && /* @__PURE__ */ jsx75(
6371
+ children: /* @__PURE__ */ jsxs43("div", { className: "mx-auto max-w-6xl px-4 py-2 flex items-center justify-center gap-3", children: [
6372
+ /* @__PURE__ */ jsx76("p", { className: "font-sans text-sm text-center flex-1", children }),
6373
+ dismissible && /* @__PURE__ */ jsx76(
6243
6374
  "button",
6244
6375
  {
6245
6376
  onClick: handleDismiss,
6246
6377
  className: "shrink-0 p-2 min-w-[44px] min-h-[44px] inline-flex items-center justify-center hover:bg-foreground/10 transition-colors cursor-pointer",
6247
6378
  "aria-label": "Dismiss",
6248
- children: /* @__PURE__ */ jsx75(X4, { className: "h-4 w-4" })
6379
+ children: /* @__PURE__ */ jsx76(X4, { className: "h-4 w-4" })
6249
6380
  }
6250
6381
  )
6251
6382
  ] })
@@ -6254,7 +6385,7 @@ function AnnouncementBanner({
6254
6385
  }
6255
6386
 
6256
6387
  // components/landing/NewsletterSignup.tsx
6257
- import { jsx as jsx76, jsxs as jsxs43 } from "react/jsx-runtime";
6388
+ import { jsx as jsx77, jsxs as jsxs44 } from "react/jsx-runtime";
6258
6389
  function NewsletterSignup({
6259
6390
  title = "Stay in the loop",
6260
6391
  subtitle,
@@ -6262,16 +6393,16 @@ function NewsletterSignup({
6262
6393
  buttonLabel = "Subscribe",
6263
6394
  className
6264
6395
  }) {
6265
- return /* @__PURE__ */ jsxs43("div", { className: cn("w-full max-w-md mx-auto", className), children: [
6266
- title && /* @__PURE__ */ jsx76("h3", { className: "font-head text-xl mb-2 text-center", children: title }),
6267
- subtitle && /* @__PURE__ */ jsx76("p", { className: "font-sans text-sm text-muted-foreground text-center mb-4", children: subtitle }),
6268
- /* @__PURE__ */ jsxs43(
6396
+ return /* @__PURE__ */ jsxs44("div", { className: cn("w-full max-w-md mx-auto", className), children: [
6397
+ title && /* @__PURE__ */ jsx77("h3", { className: "font-head text-xl mb-2 text-center", children: title }),
6398
+ subtitle && /* @__PURE__ */ jsx77("p", { className: "font-sans text-sm text-muted-foreground text-center mb-4", children: subtitle }),
6399
+ /* @__PURE__ */ jsxs44(
6269
6400
  "form",
6270
6401
  {
6271
6402
  onSubmit: (e) => e.preventDefault(),
6272
6403
  className: "flex gap-2",
6273
6404
  children: [
6274
- /* @__PURE__ */ jsx76(
6405
+ /* @__PURE__ */ jsx77(
6275
6406
  "input",
6276
6407
  {
6277
6408
  type: "email",
@@ -6280,7 +6411,7 @@ function NewsletterSignup({
6280
6411
  required: true
6281
6412
  }
6282
6413
  ),
6283
- /* @__PURE__ */ jsx76(
6414
+ /* @__PURE__ */ jsx77(
6284
6415
  "button",
6285
6416
  {
6286
6417
  type: "submit",
@@ -6310,6 +6441,7 @@ export {
6310
6441
  ChartComponent as Chart,
6311
6442
  Checkbox,
6312
6443
  CollapsibleComponent as Collapsible,
6444
+ ColorThemeToggle,
6313
6445
  ComboboxComponent as Combobox,
6314
6446
  CommandComponent as Command,
6315
6447
  Container,