Bob AI: Add countdown timer overlay to hero image
This commit is contained in:
@@ -1,30 +1,89 @@
|
||||
// AUTO-GENERATED by per-section-migrate. Edit freely — Bob will treat this
|
||||
// file as the canonical source for the "home" section.
|
||||
/* eslint-disable */
|
||||
// @ts-nocheck — generated by catalog-eject; runtime-correct but TS strict-mode false-positives on inlined catalog body
|
||||
import Button from "@/components/ui/Button";
|
||||
import HeroBackgroundSlot from "@/components/ui/HeroBackgroundSlot";
|
||||
import TextAnimation from "@/components/ui/TextAnimation";
|
||||
import ImageOrVideo from "@/components/ui/ImageOrVideo";
|
||||
import ScrollReveal from "@/components/ui/ScrollReveal";
|
||||
import React from "react";
|
||||
import AvatarGroup from "@/components/ui/AvatarGroup";
|
||||
|
||||
import React from 'react';
|
||||
import HeroBillboard from '@/components/sections/hero/HeroBillboard';
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
type HeroBillboardProps = {
|
||||
tag?: string;
|
||||
title: string;
|
||||
description: string;
|
||||
primaryButton: { text: string; href: string };
|
||||
secondaryButton: { text: string; href: string };
|
||||
avatarsSrc?: string[];
|
||||
avatarsLabel?: string;
|
||||
} & ({ imageSrc: string; videoSrc?: never } | { videoSrc: string; imageSrc?: never });
|
||||
|
||||
const HomeInline = () => {
|
||||
const [timeLeft, setTimeLeft] = React.useState(300);
|
||||
|
||||
React.useEffect(() => {
|
||||
const timer = setInterval(() => {
|
||||
setTimeLeft((prev) => (prev > 0 ? prev - 1 : 0));
|
||||
}, 1000);
|
||||
return () => clearInterval(timer);
|
||||
}, []);
|
||||
|
||||
const minutes = Math.floor(timeLeft / 60);
|
||||
const seconds = timeLeft % 60;
|
||||
const formattedTime = `${minutes.toString().padStart(2, '0')}:${seconds.toString().padStart(2, '0')}`;
|
||||
|
||||
export default function HomeSection(): React.JSX.Element {
|
||||
return (
|
||||
<div id="home" data-section="home">
|
||||
<SectionErrorBoundary name="home">
|
||||
<HeroBillboard
|
||||
title="Your Daily Dose of Artisan Freshness"
|
||||
description="Artisan breads, pastries, and custom cakes crafted with premium ingredients. Order online or visit us today."
|
||||
primaryButton={{
|
||||
text: "Order Now",
|
||||
href: "#contact",
|
||||
}}
|
||||
secondaryButton={{
|
||||
text: "Our Menu",
|
||||
href: "#products",
|
||||
}}
|
||||
imageSrc="http://img.b2bpic.net/free-photo/top-view-mix-breads-cookies-with-brown-sugar-cubes_23-2148695485.jpg"
|
||||
avatarsLabel="Trusted by 1000+ customers"
|
||||
avatarsSrc={["https://i.pravatar.cc/150?img=1","https://i.pravatar.cc/150?img=2","https://i.pravatar.cc/150?img=3","https://i.pravatar.cc/150?img=4","https://i.pravatar.cc/150?img=5"]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
<section aria-label="Hero section" className="relative pt-25 pb-20 md:pt-30">
|
||||
<HeroBackgroundSlot />
|
||||
<div className="flex flex-col gap-12 md:gap-15 w-content-width mx-auto">
|
||||
<div className="flex flex-col items-center gap-3 text-center">
|
||||
{["https://i.pravatar.cc/150?img=1","https://i.pravatar.cc/150?img=2","https://i.pravatar.cc/150?img=3","https://i.pravatar.cc/150?img=4","https://i.pravatar.cc/150?img=5"] && ["https://i.pravatar.cc/150?img=1","https://i.pravatar.cc/150?img=2","https://i.pravatar.cc/150?img=3","https://i.pravatar.cc/150?img=4","https://i.pravatar.cc/150?img=5"].length > 0 ? (
|
||||
<AvatarGroup avatarsSrc={["https://i.pravatar.cc/150?img=1","https://i.pravatar.cc/150?img=2","https://i.pravatar.cc/150?img=3","https://i.pravatar.cc/150?img=4","https://i.pravatar.cc/150?img=5"]} label={"Trusted by 1000+ customers"} className="mb-1" />
|
||||
) : undefined ? (
|
||||
<div className="px-3 py-1 mb-1 text-sm card rounded w-fit">
|
||||
<p>{undefined}</p>
|
||||
</div>
|
||||
) : null}
|
||||
|
||||
<TextAnimation
|
||||
text={"Your Daily Dose of Artisan Freshness"}
|
||||
variant="fade-blur"
|
||||
gradientText={true}
|
||||
tag="h1"
|
||||
className="md:max-w-8/10 text-7xl 2xl:text-8xl leading-[1.15] font-semibold text-center text-balance"
|
||||
/>
|
||||
|
||||
<TextAnimation
|
||||
text={"Artisan breads, pastries, and custom cakes crafted with premium ingredients. Order online or visit us today."}
|
||||
variant="fade-blur"
|
||||
gradientText={false}
|
||||
tag="p"
|
||||
className="md:max-w-7/10 text-lg md:text-xl leading-snug text-balance"
|
||||
/>
|
||||
|
||||
<div className="flex flex-wrap justify-center gap-3 mt-2 md:mt-3">
|
||||
<Button text={{"text":"Order Now","href":"#contact"}.text} href={{"text":"Order Now","href":"#contact"}.href} variant="primary"/>
|
||||
<Button text={{"text":"Our Menu","href":"#products"}.text} href={{"text":"Our Menu","href":"#products"}.href} variant="secondary" animationDelay={0.1} />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<ScrollReveal variant="slide-up" delay={0.2} className="w-full p-2 xl:p-3 2xl:p-4 card rounded overflow-hidden relative">
|
||||
<ImageOrVideo imageSrc={"http://img.b2bpic.net/free-photo/top-view-mix-breads-cookies-with-brown-sugar-cubes_23-2148695485.jpg"} className="aspect-4/5 md:aspect-video" />
|
||||
<div className="absolute top-6 right-6 bg-background/90 backdrop-blur-md px-4 py-2 rounded-full shadow-lg flex items-center gap-3 border border-border z-10">
|
||||
<span className="text-sm font-medium text-foreground">Opt in for today's discount!</span>
|
||||
<span className="text-sm font-bold text-primary-cta">{formattedTime}</span>
|
||||
<Button text="Claim" href="#contact" variant="primary" className="!py-1 !px-3 !text-xs !h-auto" />
|
||||
</div>
|
||||
</ScrollReveal>
|
||||
</div>
|
||||
</section>
|
||||
);
|
||||
};
|
||||
|
||||
export default function HomeSection() {
|
||||
return (
|
||||
<div data-webild-section="home" id="home">
|
||||
<HomeInline />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user