@retinalabsllc/zairusjs 0.2.0 → 0.2.1

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.d.mts CHANGED
@@ -353,4 +353,32 @@ interface PortfolioHeroProps {
353
353
  }
354
354
  declare const PortfolioHero: React.FC<PortfolioHeroProps>;
355
355
 
356
- export { AITranscriptionFeature, type AITranscriptionFeatureProps, AppBento2, type AppBento2Props, type BentoFeature, type BoardMember, type CompanyDetails, type DocumentSectionData, type EmailContact, Faq, type FaqItem, type FaqProps, FeatureScroll, type FeatureScrollProps, Footer, type FooterColumn, type FooterLink, type FooterProps, Header, type HeaderLink, type HeaderProps, HeroSection, type HeroSectionProps, ManagedBoardBlock, type ManagedBoardBlockProps, ManagedContactBlock, type ManagedContactBlockProps, ManagedDocument, type ManagedDocumentProps, ManagedNewsletterSplitBlock, type ManagedNewsletterSplitBlockProps, ManagedNotFoundBlock, type ManagedNotFoundBlockProps, ManagedPricingBlock, type ManagedPricingBlockProps, ManagedProjectsBlock, type ManagedProjectsBlockProps, ManagedToaster, NumberInput, type NumberInputProps, PageSpinner, type PageSpinnerProps, type PlatformFeatureItem, PlatformFeatures, type PlatformFeaturesProps, PortfolioHero, type PortfolioHeroProps, type PricingFeature, type PricingPlan, type ProjectItem, type ScrollFeature, type SocialContact, type SocialLink, TextInput, type TextInputProps, ThreeDButton, type ThreeDButtonProps };
356
+ interface ProductHeroProps {
357
+ badgeText?: string;
358
+ titlePrefix: React.ReactNode;
359
+ highlightText: string;
360
+ subtitle?: string;
361
+ ctaText?: string;
362
+ ctaHref?: string;
363
+ secondaryCtaText?: string;
364
+ secondaryCtaHref?: string;
365
+ /** Array of exactly 3 images for the carousel (Mandatory) */
366
+ images: string[];
367
+ }
368
+ declare const ProductHero: React.FC<ProductHeroProps>;
369
+
370
+ interface GifFeatureCardProps {
371
+ /** The URL path to your .gif file */
372
+ gifSrc: string;
373
+ /** The main heading text displayed at the bottom left */
374
+ title?: React.ReactNode;
375
+ /** The secondary description text displayed below the title */
376
+ subtitle?: React.ReactNode;
377
+ /** Alt text for accessibility */
378
+ alt?: string;
379
+ /** Optional override for aspect ratio or height (defaults to aspect-video) */
380
+ className?: string;
381
+ }
382
+ declare const GifFeatureCard: React.FC<GifFeatureCardProps>;
383
+
384
+ export { AITranscriptionFeature, type AITranscriptionFeatureProps, AppBento2, type AppBento2Props, type BentoFeature, type BoardMember, type CompanyDetails, type DocumentSectionData, type EmailContact, Faq, type FaqItem, type FaqProps, FeatureScroll, type FeatureScrollProps, Footer, type FooterColumn, type FooterLink, type FooterProps, GifFeatureCard, type GifFeatureCardProps, Header, type HeaderLink, type HeaderProps, HeroSection, type HeroSectionProps, ManagedBoardBlock, type ManagedBoardBlockProps, ManagedContactBlock, type ManagedContactBlockProps, ManagedDocument, type ManagedDocumentProps, ManagedNewsletterSplitBlock, type ManagedNewsletterSplitBlockProps, ManagedNotFoundBlock, type ManagedNotFoundBlockProps, ManagedPricingBlock, type ManagedPricingBlockProps, ManagedProjectsBlock, type ManagedProjectsBlockProps, ManagedToaster, NumberInput, type NumberInputProps, PageSpinner, type PageSpinnerProps, type PlatformFeatureItem, PlatformFeatures, type PlatformFeaturesProps, PortfolioHero, type PortfolioHeroProps, type PricingFeature, type PricingPlan, ProductHero, type ProductHeroProps, type ProjectItem, type ScrollFeature, type SocialContact, type SocialLink, TextInput, type TextInputProps, ThreeDButton, type ThreeDButtonProps };
package/dist/index.d.ts CHANGED
@@ -353,4 +353,32 @@ interface PortfolioHeroProps {
353
353
  }
354
354
  declare const PortfolioHero: React.FC<PortfolioHeroProps>;
355
355
 
356
- export { AITranscriptionFeature, type AITranscriptionFeatureProps, AppBento2, type AppBento2Props, type BentoFeature, type BoardMember, type CompanyDetails, type DocumentSectionData, type EmailContact, Faq, type FaqItem, type FaqProps, FeatureScroll, type FeatureScrollProps, Footer, type FooterColumn, type FooterLink, type FooterProps, Header, type HeaderLink, type HeaderProps, HeroSection, type HeroSectionProps, ManagedBoardBlock, type ManagedBoardBlockProps, ManagedContactBlock, type ManagedContactBlockProps, ManagedDocument, type ManagedDocumentProps, ManagedNewsletterSplitBlock, type ManagedNewsletterSplitBlockProps, ManagedNotFoundBlock, type ManagedNotFoundBlockProps, ManagedPricingBlock, type ManagedPricingBlockProps, ManagedProjectsBlock, type ManagedProjectsBlockProps, ManagedToaster, NumberInput, type NumberInputProps, PageSpinner, type PageSpinnerProps, type PlatformFeatureItem, PlatformFeatures, type PlatformFeaturesProps, PortfolioHero, type PortfolioHeroProps, type PricingFeature, type PricingPlan, type ProjectItem, type ScrollFeature, type SocialContact, type SocialLink, TextInput, type TextInputProps, ThreeDButton, type ThreeDButtonProps };
356
+ interface ProductHeroProps {
357
+ badgeText?: string;
358
+ titlePrefix: React.ReactNode;
359
+ highlightText: string;
360
+ subtitle?: string;
361
+ ctaText?: string;
362
+ ctaHref?: string;
363
+ secondaryCtaText?: string;
364
+ secondaryCtaHref?: string;
365
+ /** Array of exactly 3 images for the carousel (Mandatory) */
366
+ images: string[];
367
+ }
368
+ declare const ProductHero: React.FC<ProductHeroProps>;
369
+
370
+ interface GifFeatureCardProps {
371
+ /** The URL path to your .gif file */
372
+ gifSrc: string;
373
+ /** The main heading text displayed at the bottom left */
374
+ title?: React.ReactNode;
375
+ /** The secondary description text displayed below the title */
376
+ subtitle?: React.ReactNode;
377
+ /** Alt text for accessibility */
378
+ alt?: string;
379
+ /** Optional override for aspect ratio or height (defaults to aspect-video) */
380
+ className?: string;
381
+ }
382
+ declare const GifFeatureCard: React.FC<GifFeatureCardProps>;
383
+
384
+ export { AITranscriptionFeature, type AITranscriptionFeatureProps, AppBento2, type AppBento2Props, type BentoFeature, type BoardMember, type CompanyDetails, type DocumentSectionData, type EmailContact, Faq, type FaqItem, type FaqProps, FeatureScroll, type FeatureScrollProps, Footer, type FooterColumn, type FooterLink, type FooterProps, GifFeatureCard, type GifFeatureCardProps, Header, type HeaderLink, type HeaderProps, HeroSection, type HeroSectionProps, ManagedBoardBlock, type ManagedBoardBlockProps, ManagedContactBlock, type ManagedContactBlockProps, ManagedDocument, type ManagedDocumentProps, ManagedNewsletterSplitBlock, type ManagedNewsletterSplitBlockProps, ManagedNotFoundBlock, type ManagedNotFoundBlockProps, ManagedPricingBlock, type ManagedPricingBlockProps, ManagedProjectsBlock, type ManagedProjectsBlockProps, ManagedToaster, NumberInput, type NumberInputProps, PageSpinner, type PageSpinnerProps, type PlatformFeatureItem, PlatformFeatures, type PlatformFeaturesProps, PortfolioHero, type PortfolioHeroProps, type PricingFeature, type PricingPlan, ProductHero, type ProductHeroProps, type ProjectItem, type ScrollFeature, type SocialContact, type SocialLink, TextInput, type TextInputProps, ThreeDButton, type ThreeDButtonProps };
package/dist/index.js CHANGED
@@ -36,6 +36,7 @@ __export(index_exports, {
36
36
  Faq: () => Faq,
37
37
  FeatureScroll: () => FeatureScroll,
38
38
  Footer: () => Footer,
39
+ GifFeatureCard: () => GifFeatureCard,
39
40
  Header: () => Header,
40
41
  HeroSection: () => HeroSection,
41
42
  ManagedBoardBlock: () => ManagedBoardBlock,
@@ -50,6 +51,7 @@ __export(index_exports, {
50
51
  PageSpinner: () => PageSpinner,
51
52
  PlatformFeatures: () => PlatformFeatures,
52
53
  PortfolioHero: () => PortfolioHero,
54
+ ProductHero: () => ProductHero,
53
55
  TextInput: () => TextInput,
54
56
  ThreeDButton: () => ThreeDButton
55
57
  });
@@ -431,7 +433,7 @@ var FeatureScroll = ({ tagline, headline, features }) => {
431
433
  scrollRef.current.scrollBy({ left: scrollAmount, behavior: "smooth" });
432
434
  }
433
435
  };
434
- return /* @__PURE__ */ import_react10.default.createElement("section", { className: "py-24 w-full flex justify-center relative z-10 overflow-hidden" }, /* @__PURE__ */ import_react10.default.createElement("div", { className: "max-w-6xl w-full flex flex-col px-4 md:px-8" }, /* @__PURE__ */ import_react10.default.createElement("div", { className: "flex flex-col md:flex-row md:items-end justify-between gap-6 mb-12" }, /* @__PURE__ */ import_react10.default.createElement("div", { className: "relative z-10 text-left" }, /* @__PURE__ */ import_react10.default.createElement("span", { className: "text-[10px] tracking-[0.4em] text-neutral-500 block mb-4" }, tagline), /* @__PURE__ */ import_react10.default.createElement("h2", { className: "text-3xl md:text-5xl tracking-tight text-black leading-[1.05]" }, headline)), /* @__PURE__ */ import_react10.default.createElement("div", { className: "hidden md:flex items-center gap-3" }, /* @__PURE__ */ import_react10.default.createElement(
436
+ return /* @__PURE__ */ import_react10.default.createElement("section", { className: "py-24 w-full flex justify-center relative z-10 overflow-hidden" }, /* @__PURE__ */ import_react10.default.createElement("div", { className: "max-w-6xl w-full flex flex-col px-4 md:px-8" }, /* @__PURE__ */ import_react10.default.createElement("div", { className: "flex flex-col md:flex-row md:items-end justify-between gap-6 mb-12" }, /* @__PURE__ */ import_react10.default.createElement("div", { className: "relative z-10 text-left" }, /* @__PURE__ */ import_react10.default.createElement("span", { className: "text-[10px] tracking-[0.4em] text-neutral-500 block mb-4" }, tagline), /* @__PURE__ */ import_react10.default.createElement("h2", { className: "text-3xl font-serif md:text-5xl tracking-tight text-black leading-[1.05]" }, headline)), /* @__PURE__ */ import_react10.default.createElement("div", { className: "hidden md:flex items-center gap-3" }, /* @__PURE__ */ import_react10.default.createElement(
435
437
  "button",
436
438
  {
437
439
  onClick: () => scroll("left"),
@@ -1027,6 +1029,134 @@ var PortfolioHero = ({
1027
1029
  ))
1028
1030
  ));
1029
1031
  };
1032
+
1033
+ // src/components/ProductHero.tsx
1034
+ var import_react31 = __toESM(require("react"));
1035
+ var import_link9 = __toESM(require("next/link"));
1036
+ var import_image8 = __toESM(require("next/image"));
1037
+ var ProductHero = ({
1038
+ badgeText,
1039
+ titlePrefix,
1040
+ highlightText,
1041
+ subtitle,
1042
+ ctaText,
1043
+ ctaHref,
1044
+ secondaryCtaText,
1045
+ secondaryCtaHref,
1046
+ images
1047
+ }) => {
1048
+ const [currentIndex, setCurrentIndex] = (0, import_react31.useState)(0);
1049
+ const nextSlide = (0, import_react31.useCallback)(() => {
1050
+ setCurrentIndex((prev) => (prev + 1) % images.length);
1051
+ }, [images.length]);
1052
+ const prevSlide = (0, import_react31.useCallback)(() => {
1053
+ setCurrentIndex((prev) => (prev - 1 + images.length) % images.length);
1054
+ }, [images.length]);
1055
+ (0, import_react31.useEffect)(() => {
1056
+ const timer = setInterval(() => {
1057
+ nextSlide();
1058
+ }, 5e3);
1059
+ return () => clearInterval(timer);
1060
+ }, [nextSlide]);
1061
+ const getCarouselClasses = (idx) => {
1062
+ const diff = (idx - currentIndex + images.length) % images.length;
1063
+ if (diff === 0) {
1064
+ return "translate-x-0 scale-100 opacity-100 z-30 pointer-events-auto shadow-2xl";
1065
+ }
1066
+ if (diff === 1 || diff < 0 && diff === -2) {
1067
+ return "translate-x-[40%] sm:translate-x-[35%] scale-90 opacity-30 z-20 cursor-pointer hover:opacity-50";
1068
+ }
1069
+ if (diff === images.length - 1 || diff === -1) {
1070
+ return "-translate-x-[40%] sm:-translate-x-[35%] scale-90 opacity-30 z-20 cursor-pointer hover:opacity-50";
1071
+ }
1072
+ return "opacity-0 z-0 scale-75 pointer-events-none";
1073
+ };
1074
+ return /* @__PURE__ */ import_react31.default.createElement("section", { className: "relative pt-32 sm:pt-40 pb-0 flex flex-col items-center overflow-hidden w-full bg-[#f5f5f5]" }, /* @__PURE__ */ import_react31.default.createElement(
1075
+ "div",
1076
+ {
1077
+ className: "absolute inset-0 w-full h-full pointer-events-none z-0 bg-linear-to-b from-white via-white to-[#f5f5f5]"
1078
+ }
1079
+ ), /* @__PURE__ */ import_react31.default.createElement(
1080
+ "div",
1081
+ {
1082
+ className: "absolute inset-0 w-full h-full pointer-events-none z-0 opacity-[0.3] mix-blend-overlay",
1083
+ style: {
1084
+ backgroundImage: `url("data:image/svg+xml,%3Csvg viewBox='0 0 200 200' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='noiseFilter'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23noiseFilter)'/%3E%3C/svg%3E")`
1085
+ }
1086
+ }
1087
+ ), /* @__PURE__ */ import_react31.default.createElement("div", { className: "relative max-w-5xl mx-auto px-4 sm:px-6 w-full flex flex-col items-center text-center z-10" }, badgeText && /* @__PURE__ */ import_react31.default.createElement("div", { className: "inline-flex items-center gap-1.5 mb-6 px-4 py-1.5 rounded-full bg-neutral-100 border border-neutral-200 backdrop-blur-md shadow-xs" }, /* @__PURE__ */ import_react31.default.createElement("span", { className: "text-[10px] tracking-[0.4em] text-neutral-600 uppercase font-medium" }, badgeText)), /* @__PURE__ */ import_react31.default.createElement("h1", { className: "text-[40px] md:text-5xl lg:text-7xl text-black tracking-tight leading-[1.05] max-w-4xl mb-4" }, titlePrefix, " ", /* @__PURE__ */ import_react31.default.createElement("span", { className: "bg-linear-to-r from-[#043324] to-[#21a473] bg-clip-text text-transparent font-serif italic pr-2" }, highlightText)), subtitle && /* @__PURE__ */ import_react31.default.createElement("p", { className: "text-[13px] md:text-[16px] text-neutral-600 max-w-xl mx-auto mb-10 font-light leading-relaxed" }, subtitle), /* @__PURE__ */ import_react31.default.createElement("div", { className: "flex flex-col sm:flex-row gap-4 justify-center items-center w-full px-2 sm:px-0 mx-auto mb-12 relative z-30" }, ctaText && ctaHref && /* @__PURE__ */ import_react31.default.createElement("div", { className: "w-full sm:w-60 flex justify-center *:w-full" }, /* @__PURE__ */ import_react31.default.createElement(ThreeDButton, { href: ctaHref }, ctaText)), secondaryCtaText && secondaryCtaHref && /* @__PURE__ */ import_react31.default.createElement(
1088
+ import_link9.default,
1089
+ {
1090
+ href: secondaryCtaHref,
1091
+ className: "w-full sm:w-60 inline-flex items-center justify-center text-[12px] tracking-widest rounded-full px-8 py-2.5 bg-white text-black border border-neutral-200 transition-colors hover:bg-neutral-50 outline-none shadow-sm"
1092
+ },
1093
+ secondaryCtaText
1094
+ )), /* @__PURE__ */ import_react31.default.createElement("div", { className: "relative w-full max-w-4xl mx-auto px-2 sm:px-6 mt-8 z-20" }, /* @__PURE__ */ import_react31.default.createElement("div", { className: "relative w-full aspect-4/3 md:aspect-video flex items-center justify-center" }, /* @__PURE__ */ import_react31.default.createElement("button", { onClick: prevSlide, className: "absolute left-0 sm:-left-12 z-40 p-2 text-neutral-400 hover:text-black transition-colors outline-none", "aria-label": "Previous image" }, /* @__PURE__ */ import_react31.default.createElement("svg", { width: "24", height: "24", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" }, /* @__PURE__ */ import_react31.default.createElement("path", { d: "M15 18l-6-6 6-6" }))), /* @__PURE__ */ import_react31.default.createElement("button", { onClick: nextSlide, className: "absolute right-0 sm:-right-12 z-40 p-2 text-neutral-400 hover:text-black transition-colors outline-none", "aria-label": "Next image" }, /* @__PURE__ */ import_react31.default.createElement("svg", { width: "24", height: "24", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" }, /* @__PURE__ */ import_react31.default.createElement("path", { d: "M9 18l6-6-6-6" }))), images.map((src, idx) => /* @__PURE__ */ import_react31.default.createElement(
1095
+ "div",
1096
+ {
1097
+ key: idx,
1098
+ onClick: () => {
1099
+ if (currentIndex !== idx) setCurrentIndex(idx);
1100
+ },
1101
+ className: `absolute inset-0 transition-all duration-700 ease-out transform ${getCarouselClasses(idx)}`
1102
+ },
1103
+ /* @__PURE__ */ import_react31.default.createElement("div", { className: "relative w-full h-full rounded-2xl overflow-hidden shadow-xl" }, /* @__PURE__ */ import_react31.default.createElement(
1104
+ import_image8.default,
1105
+ {
1106
+ src,
1107
+ alt: `Product Overview ${idx + 1}`,
1108
+ fill: true,
1109
+ sizes: "(max-width: 768px) 100vw, 800px",
1110
+ className: "object-cover object-center select-none",
1111
+ priority: idx === 0
1112
+ }
1113
+ ))
1114
+ )), /* @__PURE__ */ import_react31.default.createElement("div", { className: "absolute inset-x-0 bottom-0 h-1/3 sm:h-1/2 bg-linear-to-t from-[#f5f5f5] to-transparent z-40 pointer-events-none" })))));
1115
+ };
1116
+
1117
+ // src/components/GifFeatureCard.tsx
1118
+ var import_react32 = __toESM(require("react"));
1119
+ var import_image9 = __toESM(require("next/image"));
1120
+ var import_react33 = require("@hugeicons/react");
1121
+ var import_core_free_icons7 = require("@hugeicons/core-free-icons");
1122
+ var GifFeatureCard = ({
1123
+ gifSrc,
1124
+ title,
1125
+ subtitle,
1126
+ alt = "Feature animation",
1127
+ className = "aspect-video"
1128
+ }) => {
1129
+ const [isLoading, setIsLoading] = (0, import_react32.useState)(true);
1130
+ return /* @__PURE__ */ import_react32.default.createElement("div", { className: `relative w-full bg-black overflow-hidden shadow-2xl ${className}` }, isLoading && /* @__PURE__ */ import_react32.default.createElement("div", { className: "absolute inset-0 flex items-center justify-center z-20 bg-black" }, /* @__PURE__ */ import_react32.default.createElement(
1131
+ import_react33.HugeiconsIcon,
1132
+ {
1133
+ icon: import_core_free_icons7.Loading03Icon,
1134
+ size: 32,
1135
+ className: "animate-spin text-white"
1136
+ }
1137
+ )), /* @__PURE__ */ import_react32.default.createElement(
1138
+ "div",
1139
+ {
1140
+ className: `absolute inset-0 z-0 transition-all duration-1000 ease-out ${isLoading ? "scale-105 blur-2xl opacity-0" : "scale-100 blur-0 opacity-100"}`
1141
+ },
1142
+ /* @__PURE__ */ import_react32.default.createElement(
1143
+ import_image9.default,
1144
+ {
1145
+ src: gifSrc,
1146
+ alt,
1147
+ fill: true,
1148
+ unoptimized: true,
1149
+ onLoad: () => setIsLoading(false),
1150
+ className: "object-cover object-center pointer-events-none"
1151
+ }
1152
+ )
1153
+ ), /* @__PURE__ */ import_react32.default.createElement(
1154
+ "div",
1155
+ {
1156
+ className: "absolute inset-x-0 bottom-0 h-1/2 sm:h-2/3 bg-linear-to-t from-black/95 via-black/40 to-transparent z-10 pointer-events-none transition-opacity duration-700"
1157
+ }
1158
+ ), /* @__PURE__ */ import_react32.default.createElement("div", { className: "absolute inset-x-0 bottom-0 p-6 sm:p-8 z-30 flex flex-col justify-end text-left pointer-events-none" }, title && /* @__PURE__ */ import_react32.default.createElement("h3", { className: "text-xl sm:text-2xl md:text-3xl font-medium text-white tracking-tight mb-2 sm:mb-3 drop-shadow-md" }, title), subtitle && /* @__PURE__ */ import_react32.default.createElement("p", { className: "text-[13px] sm:text-[15px] leading-relaxed text-neutral-300 max-w-2xl drop-shadow-sm" }, subtitle)));
1159
+ };
1030
1160
  // Annotate the CommonJS export names for ESM import in node:
1031
1161
  0 && (module.exports = {
1032
1162
  AITranscriptionFeature,
@@ -1034,6 +1164,7 @@ var PortfolioHero = ({
1034
1164
  Faq,
1035
1165
  FeatureScroll,
1036
1166
  Footer,
1167
+ GifFeatureCard,
1037
1168
  Header,
1038
1169
  HeroSection,
1039
1170
  ManagedBoardBlock,
@@ -1048,6 +1179,7 @@ var PortfolioHero = ({
1048
1179
  PageSpinner,
1049
1180
  PlatformFeatures,
1050
1181
  PortfolioHero,
1182
+ ProductHero,
1051
1183
  TextInput,
1052
1184
  ThreeDButton
1053
1185
  });
package/dist/index.mjs CHANGED
@@ -376,7 +376,7 @@ var FeatureScroll = ({ tagline, headline, features }) => {
376
376
  scrollRef.current.scrollBy({ left: scrollAmount, behavior: "smooth" });
377
377
  }
378
378
  };
379
- return /* @__PURE__ */ React7.createElement("section", { className: "py-24 w-full flex justify-center relative z-10 overflow-hidden" }, /* @__PURE__ */ React7.createElement("div", { className: "max-w-6xl w-full flex flex-col px-4 md:px-8" }, /* @__PURE__ */ React7.createElement("div", { className: "flex flex-col md:flex-row md:items-end justify-between gap-6 mb-12" }, /* @__PURE__ */ React7.createElement("div", { className: "relative z-10 text-left" }, /* @__PURE__ */ React7.createElement("span", { className: "text-[10px] tracking-[0.4em] text-neutral-500 block mb-4" }, tagline), /* @__PURE__ */ React7.createElement("h2", { className: "text-3xl md:text-5xl tracking-tight text-black leading-[1.05]" }, headline)), /* @__PURE__ */ React7.createElement("div", { className: "hidden md:flex items-center gap-3" }, /* @__PURE__ */ React7.createElement(
379
+ return /* @__PURE__ */ React7.createElement("section", { className: "py-24 w-full flex justify-center relative z-10 overflow-hidden" }, /* @__PURE__ */ React7.createElement("div", { className: "max-w-6xl w-full flex flex-col px-4 md:px-8" }, /* @__PURE__ */ React7.createElement("div", { className: "flex flex-col md:flex-row md:items-end justify-between gap-6 mb-12" }, /* @__PURE__ */ React7.createElement("div", { className: "relative z-10 text-left" }, /* @__PURE__ */ React7.createElement("span", { className: "text-[10px] tracking-[0.4em] text-neutral-500 block mb-4" }, tagline), /* @__PURE__ */ React7.createElement("h2", { className: "text-3xl font-serif md:text-5xl tracking-tight text-black leading-[1.05]" }, headline)), /* @__PURE__ */ React7.createElement("div", { className: "hidden md:flex items-center gap-3" }, /* @__PURE__ */ React7.createElement(
380
380
  "button",
381
381
  {
382
382
  onClick: () => scroll("left"),
@@ -972,12 +972,141 @@ var PortfolioHero = ({
972
972
  ))
973
973
  ));
974
974
  };
975
+
976
+ // src/components/ProductHero.tsx
977
+ import React21, { useState as useState6, useEffect as useEffect4, useCallback } from "react";
978
+ import Link9 from "next/link";
979
+ import Image8 from "next/image";
980
+ var ProductHero = ({
981
+ badgeText,
982
+ titlePrefix,
983
+ highlightText,
984
+ subtitle,
985
+ ctaText,
986
+ ctaHref,
987
+ secondaryCtaText,
988
+ secondaryCtaHref,
989
+ images
990
+ }) => {
991
+ const [currentIndex, setCurrentIndex] = useState6(0);
992
+ const nextSlide = useCallback(() => {
993
+ setCurrentIndex((prev) => (prev + 1) % images.length);
994
+ }, [images.length]);
995
+ const prevSlide = useCallback(() => {
996
+ setCurrentIndex((prev) => (prev - 1 + images.length) % images.length);
997
+ }, [images.length]);
998
+ useEffect4(() => {
999
+ const timer = setInterval(() => {
1000
+ nextSlide();
1001
+ }, 5e3);
1002
+ return () => clearInterval(timer);
1003
+ }, [nextSlide]);
1004
+ const getCarouselClasses = (idx) => {
1005
+ const diff = (idx - currentIndex + images.length) % images.length;
1006
+ if (diff === 0) {
1007
+ return "translate-x-0 scale-100 opacity-100 z-30 pointer-events-auto shadow-2xl";
1008
+ }
1009
+ if (diff === 1 || diff < 0 && diff === -2) {
1010
+ return "translate-x-[40%] sm:translate-x-[35%] scale-90 opacity-30 z-20 cursor-pointer hover:opacity-50";
1011
+ }
1012
+ if (diff === images.length - 1 || diff === -1) {
1013
+ return "-translate-x-[40%] sm:-translate-x-[35%] scale-90 opacity-30 z-20 cursor-pointer hover:opacity-50";
1014
+ }
1015
+ return "opacity-0 z-0 scale-75 pointer-events-none";
1016
+ };
1017
+ return /* @__PURE__ */ React21.createElement("section", { className: "relative pt-32 sm:pt-40 pb-0 flex flex-col items-center overflow-hidden w-full bg-[#f5f5f5]" }, /* @__PURE__ */ React21.createElement(
1018
+ "div",
1019
+ {
1020
+ className: "absolute inset-0 w-full h-full pointer-events-none z-0 bg-linear-to-b from-white via-white to-[#f5f5f5]"
1021
+ }
1022
+ ), /* @__PURE__ */ React21.createElement(
1023
+ "div",
1024
+ {
1025
+ className: "absolute inset-0 w-full h-full pointer-events-none z-0 opacity-[0.3] mix-blend-overlay",
1026
+ style: {
1027
+ backgroundImage: `url("data:image/svg+xml,%3Csvg viewBox='0 0 200 200' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='noiseFilter'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23noiseFilter)'/%3E%3C/svg%3E")`
1028
+ }
1029
+ }
1030
+ ), /* @__PURE__ */ React21.createElement("div", { className: "relative max-w-5xl mx-auto px-4 sm:px-6 w-full flex flex-col items-center text-center z-10" }, badgeText && /* @__PURE__ */ React21.createElement("div", { className: "inline-flex items-center gap-1.5 mb-6 px-4 py-1.5 rounded-full bg-neutral-100 border border-neutral-200 backdrop-blur-md shadow-xs" }, /* @__PURE__ */ React21.createElement("span", { className: "text-[10px] tracking-[0.4em] text-neutral-600 uppercase font-medium" }, badgeText)), /* @__PURE__ */ React21.createElement("h1", { className: "text-[40px] md:text-5xl lg:text-7xl text-black tracking-tight leading-[1.05] max-w-4xl mb-4" }, titlePrefix, " ", /* @__PURE__ */ React21.createElement("span", { className: "bg-linear-to-r from-[#043324] to-[#21a473] bg-clip-text text-transparent font-serif italic pr-2" }, highlightText)), subtitle && /* @__PURE__ */ React21.createElement("p", { className: "text-[13px] md:text-[16px] text-neutral-600 max-w-xl mx-auto mb-10 font-light leading-relaxed" }, subtitle), /* @__PURE__ */ React21.createElement("div", { className: "flex flex-col sm:flex-row gap-4 justify-center items-center w-full px-2 sm:px-0 mx-auto mb-12 relative z-30" }, ctaText && ctaHref && /* @__PURE__ */ React21.createElement("div", { className: "w-full sm:w-60 flex justify-center *:w-full" }, /* @__PURE__ */ React21.createElement(ThreeDButton, { href: ctaHref }, ctaText)), secondaryCtaText && secondaryCtaHref && /* @__PURE__ */ React21.createElement(
1031
+ Link9,
1032
+ {
1033
+ href: secondaryCtaHref,
1034
+ className: "w-full sm:w-60 inline-flex items-center justify-center text-[12px] tracking-widest rounded-full px-8 py-2.5 bg-white text-black border border-neutral-200 transition-colors hover:bg-neutral-50 outline-none shadow-sm"
1035
+ },
1036
+ secondaryCtaText
1037
+ )), /* @__PURE__ */ React21.createElement("div", { className: "relative w-full max-w-4xl mx-auto px-2 sm:px-6 mt-8 z-20" }, /* @__PURE__ */ React21.createElement("div", { className: "relative w-full aspect-4/3 md:aspect-video flex items-center justify-center" }, /* @__PURE__ */ React21.createElement("button", { onClick: prevSlide, className: "absolute left-0 sm:-left-12 z-40 p-2 text-neutral-400 hover:text-black transition-colors outline-none", "aria-label": "Previous image" }, /* @__PURE__ */ React21.createElement("svg", { width: "24", height: "24", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" }, /* @__PURE__ */ React21.createElement("path", { d: "M15 18l-6-6 6-6" }))), /* @__PURE__ */ React21.createElement("button", { onClick: nextSlide, className: "absolute right-0 sm:-right-12 z-40 p-2 text-neutral-400 hover:text-black transition-colors outline-none", "aria-label": "Next image" }, /* @__PURE__ */ React21.createElement("svg", { width: "24", height: "24", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" }, /* @__PURE__ */ React21.createElement("path", { d: "M9 18l6-6-6-6" }))), images.map((src, idx) => /* @__PURE__ */ React21.createElement(
1038
+ "div",
1039
+ {
1040
+ key: idx,
1041
+ onClick: () => {
1042
+ if (currentIndex !== idx) setCurrentIndex(idx);
1043
+ },
1044
+ className: `absolute inset-0 transition-all duration-700 ease-out transform ${getCarouselClasses(idx)}`
1045
+ },
1046
+ /* @__PURE__ */ React21.createElement("div", { className: "relative w-full h-full rounded-2xl overflow-hidden shadow-xl" }, /* @__PURE__ */ React21.createElement(
1047
+ Image8,
1048
+ {
1049
+ src,
1050
+ alt: `Product Overview ${idx + 1}`,
1051
+ fill: true,
1052
+ sizes: "(max-width: 768px) 100vw, 800px",
1053
+ className: "object-cover object-center select-none",
1054
+ priority: idx === 0
1055
+ }
1056
+ ))
1057
+ )), /* @__PURE__ */ React21.createElement("div", { className: "absolute inset-x-0 bottom-0 h-1/3 sm:h-1/2 bg-linear-to-t from-[#f5f5f5] to-transparent z-40 pointer-events-none" })))));
1058
+ };
1059
+
1060
+ // src/components/GifFeatureCard.tsx
1061
+ import React22, { useState as useState7 } from "react";
1062
+ import Image9 from "next/image";
1063
+ import { HugeiconsIcon as HugeiconsIcon11 } from "@hugeicons/react";
1064
+ import { Loading03Icon as Loading03Icon4 } from "@hugeicons/core-free-icons";
1065
+ var GifFeatureCard = ({
1066
+ gifSrc,
1067
+ title,
1068
+ subtitle,
1069
+ alt = "Feature animation",
1070
+ className = "aspect-video"
1071
+ }) => {
1072
+ const [isLoading, setIsLoading] = useState7(true);
1073
+ return /* @__PURE__ */ React22.createElement("div", { className: `relative w-full bg-black overflow-hidden shadow-2xl ${className}` }, isLoading && /* @__PURE__ */ React22.createElement("div", { className: "absolute inset-0 flex items-center justify-center z-20 bg-black" }, /* @__PURE__ */ React22.createElement(
1074
+ HugeiconsIcon11,
1075
+ {
1076
+ icon: Loading03Icon4,
1077
+ size: 32,
1078
+ className: "animate-spin text-white"
1079
+ }
1080
+ )), /* @__PURE__ */ React22.createElement(
1081
+ "div",
1082
+ {
1083
+ className: `absolute inset-0 z-0 transition-all duration-1000 ease-out ${isLoading ? "scale-105 blur-2xl opacity-0" : "scale-100 blur-0 opacity-100"}`
1084
+ },
1085
+ /* @__PURE__ */ React22.createElement(
1086
+ Image9,
1087
+ {
1088
+ src: gifSrc,
1089
+ alt,
1090
+ fill: true,
1091
+ unoptimized: true,
1092
+ onLoad: () => setIsLoading(false),
1093
+ className: "object-cover object-center pointer-events-none"
1094
+ }
1095
+ )
1096
+ ), /* @__PURE__ */ React22.createElement(
1097
+ "div",
1098
+ {
1099
+ className: "absolute inset-x-0 bottom-0 h-1/2 sm:h-2/3 bg-linear-to-t from-black/95 via-black/40 to-transparent z-10 pointer-events-none transition-opacity duration-700"
1100
+ }
1101
+ ), /* @__PURE__ */ React22.createElement("div", { className: "absolute inset-x-0 bottom-0 p-6 sm:p-8 z-30 flex flex-col justify-end text-left pointer-events-none" }, title && /* @__PURE__ */ React22.createElement("h3", { className: "text-xl sm:text-2xl md:text-3xl font-medium text-white tracking-tight mb-2 sm:mb-3 drop-shadow-md" }, title), subtitle && /* @__PURE__ */ React22.createElement("p", { className: "text-[13px] sm:text-[15px] leading-relaxed text-neutral-300 max-w-2xl drop-shadow-sm" }, subtitle)));
1102
+ };
975
1103
  export {
976
1104
  AITranscriptionFeature,
977
1105
  AppBento2,
978
1106
  Faq,
979
1107
  FeatureScroll,
980
1108
  Footer,
1109
+ GifFeatureCard,
981
1110
  Header,
982
1111
  HeroSection,
983
1112
  ManagedBoardBlock,
@@ -992,6 +1121,7 @@ export {
992
1121
  PageSpinner,
993
1122
  PlatformFeatures,
994
1123
  PortfolioHero,
1124
+ ProductHero,
995
1125
  TextInput,
996
1126
  ThreeDButton
997
1127
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@retinalabsllc/zairusjs",
3
- "version": "0.2.0",
3
+ "version": "0.2.1",
4
4
  "description": "A perceptive, Ai data driven Next.js UI component library.",
5
5
  "author": "Retina Labs Company",
6
6
  "license": "MIT",
@@ -39,7 +39,7 @@
39
39
  "dependencies": {
40
40
  "@hugeicons/core-free-icons": "^1.1.0",
41
41
  "@hugeicons/react": "^1.1.1",
42
- "@retinalabsllc/zairusjs": "^0.1.5",
42
+ "@retinalabsllc/zairusjs": "0.2.0",
43
43
  "clsx": "^2.1.1",
44
44
  "react-hot-toast": "^2.6.0",
45
45
  "tailwind-merge": "^3.6.0",