/* global React, ReactDOM */ const { useState, useEffect, useRef, useCallback } = React; const BOOKING_URL = "https://calendly.com/littlestarparty1"; const PHONE = "619-617-4905"; const PHONE_TEL = "+16196174905"; /* ============================================================ Active promo — set PROMO_ACTIVE to false to hide everything ============================================================ */ const PROMO_ACTIVE = true; const PROMO = { badge: "☀️ SUMMER SPECIAL", headline: "Summer Special — book now & get 2 extra girls added FREE, any party date", sub: "Limited time — but your party can be any date you want.", short: "SUMMER SPECIAL — 2 extra girls FREE, book now!", shortMobile: "2 extra girls FREE!", expires: "Summer Special · limited time", }; /* ============================================================ Package data ============================================================ */ const PACKAGES = [ { id: "star", name: "STAR", tagline: "the essentials", price: 849, deposit: 249, duration: "1.5 hours", capacity: "Birthday girl + 7 friends", extra: "$55 / extra guest", color: "#ff6fb3", bg: "assets/photo-star.jpg", bgPos: "center 18%", short: [ "1.5 hrs of party bus fun", "Makeup + rhinestone face gems", "Hair extension clips + glitter spray", "Mini manicures", "Pink carpet runway show", "Freestyle dance party", "Birthday tiara, sash + goody bag", ], glam: [ "Makeup with rhinestone face gems", "Colorful hair extension clips", "Glitter hairspray", "Mini manicures", "Temporary tattoos for kids", ], experience: [ "1.5 hours of party bus fun", "Pink carpet runway show", "Freestyle dance party", "Music + LED party lights", ], birthdayGirl: [ "Birthday tiara + sash", "Deluxe goody bag", ], }, { id: "popstar", name: "POP STAR", tagline: "for the squad", price: 799, deposit: 249, duration: "1.5 hours", capacity: "Birthday girl + 14 friends (15 total)", extra: "$35 / extra guest · buses fit 20–25", color: "#e91e80", bg: "assets/photo-popstar.jpg", bgPos: "center 25%", isLimited: true, short: [ "Built for bigger groups (15+)", "Birthday girl gets the full glam treatment", "Friends enjoy the experience — no glam services", "Sing-along mic for everyone", "Dance party + LED lights + games", "Pink carpet photo moments", "VIP treatment for birthday girl", ], glam: [ "👑 Glam is for the birthday girl only:", "Soft glam makeup + rhinestone face gems", "Clip-in hair extensions", "Glitter hairspray", "Mini manicure", "Temporary tattoos", ], experience: [ "1.5 hours of party bus fun for all the girls", "Dance party with music + LED lights", "Sing-along mic — every girl gets to perform", "Pink carpet photo moments for the whole group", "Hostess-led games + interaction", "Music-video-style atmosphere", "✨ Superstar entrance for the birthday girl", ], birthdayGirl: [ "Full glam (only birthday girl)", "Birthday tiara + sash", "Deluxe birthday-girl goodie bag", "Superstar pink-carpet entrance", ], footnote: "How can we do 15 girls for $799? Only the birthday girl gets the glam services (mani, face gems, hair extensions) — her friends come for the experience: the dancing, the mic, the lights, the games. Perfect for dance teams, cheer squads, classmates & larger birthday groups.", }, { id: "vip", name: "VIP", tagline: "the full glam", price: 1299, deposit: 449, duration: "2 hours", capacity: "Birthday girl + 9 friends", extra: "$99 / extra guest", color: "#b8186b", bg: "assets/photo-vip.jpg", bgPos: "center 15%", featured: true, short: [ "2 full hours of party bus fun", "Spa robes for all girls", "Full makeup + face gems", "Hair extensions + glitter spray", "Mini manicures + tattoos", "Superstar entrance + sing-along mic", "Deluxe goody bags + tiara gift", ], glam: [ "Spa robes for all girls", "Makeup with rhinestone face gems", "Colorful hair extension clips", "Glitter hairspray", "Mini manicures", "Temporary tattoos for kids", ], experience: [ "2 hours of party bus fun", "Pink carpet runway show", "Freestyle dance party", "Superstar entrance for birthday girl", "Sing-along mic experience (1 mic)", ], birthdayGirl: [ "VIP wristbands + lanyards for all girls", "Tiara + sash", "Deluxe goody bags for all girls", "Flower headband, fancy gloves, feather boa + heart sunglasses gift", ], }, { id: "ultimate", name: "ULTIMATE VIP", tagline: "the full show", price: 1699, deposit: 599, duration: "2 hours", capacity: "Birthday girl + 11 friends", extra: "$125 / extra guest", color: "#5a0a39", bg: "assets/photo-ultimate.jpg", bgPos: "center 22%", short: [ "Choose a theme (K-pop, princess, etc.)", "Spa robes + mask + cucumber eyes", "Full glam + clip-in braids", "Themed decor + themed music", "Sing-along mic (every girl)", "Superstar entrance", "Themed deluxe goody bags", ], glam: [ "Spa robes for all girls", "Spa mask + cucumber eye patches", "Makeup with rhinestone face gems", "Colorful clip-in hair braids", "Glitter hairspray", "Mini manicures", "Temporary tattoos for kids", ], experience: [ "2 hours of party bus fun", "Theme of your choice (K-pop, princess, etc.)", "Themed decor + themed music experience", "Pink carpet runway show", "Freestyle dance party", "Superstar entrance for birthday girl", "Sing-along mic — every girl gets one", ], birthdayGirl: [ "VIP wristbands + lanyards for all girls", "Tiara + sash", "Themed deluxe goody bags for all girls", "Flower headband, fancy gloves, feather boa + heart sunglasses gift", ], }, ]; const ADDONS = [ { name: "Superstar entrance", price: "$99 · the lift moment", icon: "star", highlight: true, blurb: "Music drops, the crowd quiets — and the birthday girl rises into view on her own private platform like a Hollywood headliner. Her favorite song plays, her friends cheer her up, then everyone runs onto the bus to dance with her. Included free in VIP + Ultimate VIP." }, { name: "Birthday squad robes", price: "$30 each", icon: "spa", image: "assets/addon-robes.jpg", blurb: "Pink satin robes with gold glitter — \"Birthday Princess\" for her, \"Birthday Squad\" for the crew. Included free in VIP + Ultimate VIP." }, { name: "Spa mask + cucumber eyes", price: "$10 / girl", icon: "spa", image: "assets/addon-spa.jpg", blurb: "Included free in Ultimate VIP." }, { name: "Sing-along mic experience", price: "$10 / girl", icon: "mic", blurb: "Every girl gets her own microphone for the full party — duets, solos, lip-sync battles. (Included free in POP STAR, VIP & Ultimate VIP.)" }, { name: "Clip-in braids", price: "$10 each", icon: "braid", image: "assets/addon-braids.jpg", blurb: "Included free in Ultimate VIP." }, { name: "Mermaid face gems", price: "$10 each", icon: "gem", image: "assets/addon-gems.jpg" }, { name: "Feather fringe boas", price: "$10 each", icon: "boa", image: "assets/addon-boas.jpg" }, { name: "Flower headbands", price: "$5 each", icon: "flower", image: "assets/addon-flowers.jpg" }, { name: "Fancy gloves", price: "$5 each", icon: "glove", image: "assets/addon-gloves.jpg" }, { name: "Heart-shaped sunglasses", price: "$3.50 each", icon: "heart", image: "assets/addon-sunglasses.jpg" }, { name: "Themed party decor upgrade", price: "$300 extra", icon: "disco", blurb: "Included free in Ultimate VIP." }, ]; const FAQ = [ { q: "Does the bus drive around with the girls on it?", a: "Nope — the bus does NOT move with the girls on board. We park at your designated location (your driveway, a park, a venue — wherever you choose) and the entire party happens right there while the bus is parked. Think of it as a private studio on wheels: pink leather seats, disco lights, mirrors, a stage and a sing-along mic. The girls are safe, parents can come and go, and you don't have to worry about anyone riding around.", }, { q: "Where do you serve and is there a travel fee?", a: "We're based at the Palomar Transit Center in Chula Vista and serve all of San Diego, Orange County (Newport to Long Beach), Temecula, Murrieta and Corona. Travel fees start at $49 for 0–30 miles and tier up by distance — check the Travel section above to find your city. Travel fees are added to your final invoice on top of the package price.", }, { q: "How does it work — do you drive the kids around?", a: "The party bus parks right in your driveway (or wherever you'd like) and the whole experience happens inside while it's parked. No driving required — it's a private studio on wheels with disco lights, pink leather seats, a sing-along mic, mirrors, and everything they need to feel like total stars.", }, { q: "What ages is this for?", a: "Our happiest little stars are usually 5–12, but we've hosted everyone from 4-year-old princess parties to tween dance-team celebrations. We tailor the energy to the age group.", }, { q: "How long is each experience?", a: "STAR + POP STAR = 1.5 hours of pure magic. VIP + ULTIMATE VIP = 2 full hours so there's time for the spa + the full glam treatment + the pink-carpet show.", }, { q: "Can boys come too?", a: "Yes — boys are welcome at no extra charge and don't count against your headcount. Since most boys come along for the dance-party energy, they typically don't take part in the glam services (makeup, mani, hair). Everyone has a blast either way.", }, { q: "What does the deposit cover and when is the rest due?", a: "The deposit locks in your date — $249 for the STAR and POP STAR packages, $449 for VIP, and $599 for Ultimate VIP. The remaining balance is due the Monday before the event. Dates fill up fast — especially spring + summer weekends — so book early!", }, { q: "Can I add my own theme or decor?", a: "Yes! The Ultimate VIP includes a custom theme of your choice. For the other packages, themed decor is a $300 add-on. K-pop, princess, mermaid, Taylor — bring us the vibe and we'll bring it to life.", }, ]; const REVIEWS = [ { quote: "My daughter literally cried when it was over because she didn't want it to end. The hostess made every single girl feel like the main character. Worth every penny.", name: "Maria L.", meta: "Carlsbad · 9th birthday", initial: "M", }, { quote: "The bus pulled up and 12 girls SCREAMED. The makeup, the spa robes, the pink carpet — they thought they were on a TV show. Best party we've ever thrown.", name: "Jessica T.", meta: "Newport Beach · 7th birthday", initial: "J", }, { quote: "I'm a party planner and Little Stars is now my go-to recommendation. The setup is gorgeous, the team is professional, and the kids leave glowing. Five stars.", name: "Andrea R.", meta: "Temecula · group party", initial: "A", }, ]; const TRAVEL_TIERS = [ { id: "z1", fee: 49, range: "0–30 miles", label: "In our backyard", cities: [ "Chula Vista", "National City", "Bonita", "Imperial Beach", "San Diego (Downtown)", "Hillcrest", "Mission Valley", "Mission Hills", "Coronado", "La Jolla", "Pacific Beach", "Ocean Beach", "Point Loma", "El Cajon", "La Mesa", "Lemon Grove", "Santee", "Spring Valley", ], }, { id: "z2", fee: 79, range: "31–50 miles", label: "Close to home", cities: [ "Poway", "Del Mar", "Solana Beach", "Encinitas", "Cardiff", "Rancho Santa Fe", "Rancho Bernardo", "Scripps Ranch", "Mira Mesa", "Carmel Valley", "Sorrento Valley", "San Marcos", "Escondido", "Carlsbad", "Ramona", ], }, { id: "z3", fee: 125, range: "51–70 miles", label: "A little further", cities: [ "Oceanside", "Vista", "Fallbrook", "Bonsall", "Valley Center", "San Clemente", "Dana Point", ], }, { id: "z4", fee: 175, range: "71–90 miles", label: "Worth the drive", cities: [ "Temecula", "Murrieta", "Laguna Niguel", "Laguna Beach", "Aliso Viejo", "Mission Viejo", "Lake Forest", "Irvine", "Costa Mesa", "Newport Beach", ], }, { id: "z5", fee: "239+", range: "91+ miles", label: "Special trip (custom quote)", cities: [ "Anaheim", "Santa Ana", "Orange", "Huntington Beach", "Fullerton", "Long Beach", "Corona", ], }, ]; /* ============================================================ Icons ============================================================ */ const Star = ({ size = 24, fill = "currentColor" }) => ( ); const Sparkle = ({ size = 20 }) => ( ); const PlayIcon = () => ( ); const ArrowRight = ({ size = 16 }) => ( ); const Crown = ({ size = 24 }) => ( ); const MutedIcon = () => ( ); const UnmutedIcon = () => ( ); const AddonIcon = ({ kind }) => { const props = { width: 28, height: 28, viewBox: "0 0 24 24", fill: "currentColor", xmlns: "http://www.w3.org/2000/svg" }; switch (kind) { case "spa": return ; case "mic": return ; case "flower": return ; case "glove": return ; case "disco": return ; case "boa": return ; case "gem": return ; case "braid": return ; case "heart": return ; default: return null; } }; /* ============================================================ Promo Announcement Bar ============================================================ */ function PromoBar() { if (!PROMO_ACTIVE) return null; return (
{[0, 1, 2].map((i) => ( {PROMO.badge} 🎉 {PROMO.headline}. Tap to book → ))}
); } /* ============================================================ Nav ============================================================ */ function Nav() { return ( ); } /* ============================================================ Hero ============================================================ */ function Hero() { const videoRef = useRef(null); const [muted, setMuted] = useState(true); const toggleMute = () => { if (videoRef.current) { videoRef.current.muted = !videoRef.current.muted; setMuted(videoRef.current.muted); } }; return (
Booking dates year-round · up to 12 months out

Birthdays
become core memories
she'll never forget.

A private, neon-lit celebration where she sings, dances, glams up and feels like the star of the day. The bus parks at your location and the entire party happens inside — pink carpet, disco lights, sing-along mic and her best friends.

Book her party See packages
{PROMO_ACTIVE ? ( ☀️ SUMMER SPECIAL Book now & get 2 extra girls FREE — limited time, but your party can be any date → ) : null}
★★★★★ 200+ happy birthdays
San Diego · OC · Temecula
); } /* ============================================================ Trust strip ============================================================ */ function TrustStrip() { const items = [ { icon: "★", text: "Rated 5/5 by parents" }, { icon: "🚌", text: "Private studio on wheels" }, { icon: "✨", text: "Pulls into your driveway" }, { icon: "📍", text: "San Diego · OC · Temecula" }, { icon: "🎂", text: "Ages 5–12 (we flex it)" }, ]; return (
{items.map((it, i) => (
{it.icon} {it.text}
))}
); } /* ============================================================ How it works ============================================================ */ function HowItWorks() { const steps = [ { n: "01", t: "Pick her vibe", p: "Choose from four packages — from a sweet glam session to a themed pop-star show. Customize with add-ons to make it hers.", video: "assets/video-3.mp4", }, { n: "02", t: "We pull up", p: "Our pink party bus parks in your driveway. Pink carpet rolls out. Disco lights on. She makes her superstar entrance to cheers.", video: "assets/video-2.mp4", }, { n: "03", t: "She's the star", p: "Glam, spa, sing-along, dance — our hostess runs the entire experience while you actually get to enjoy the party.", video: "assets/video-5.mp4", }, ]; // Auto-play videos when in view const ref = useRef(null); useEffect(() => { const obs = new IntersectionObserver((entries) => { entries.forEach((e) => { const v = e.target; if (e.isIntersecting) v.play().catch(() => {}); else v.pause(); }); }, { threshold: 0.3 }); ref.current?.querySelectorAll("video").forEach((v) => obs.observe(v)); return () => obs.disconnect(); }, []); return (
The experience

Not just a party.
A core memory.

Three simple steps. Zero stress for you. All sparkle for her.

{steps.map((s, i) => (
))}
); } /* ============================================================ Mid-page promo band (keeps the offer visible while scrolling) ============================================================ */ function PromoBand() { if (!PROMO_ACTIVE) return null; return (
🎉
Summer Special — book now & get 2 extra girls added FREE
Limited time — your party can be any date, even months away.
Book now →
); } /* ============================================================ Packages ============================================================ */ function Packages({ onSelect }) { return (
Four ways to celebrate

Choose her package

Every package includes a hostess, the pink carpet entrance and all the magic. Pick the one that fits her crew.

{PACKAGES.map((p) => (
{p.featured ?
MOST POPULAR
: null}
the {p.name}
$ {p.price.toLocaleString()}
{PROMO_ACTIVE ? (
🎉
+2 girls FREE Summer Special · book now
) : null}
{p.duration} · {p.capacity}
${p.deposit} deposit to reserve your date
    {p.short.slice(0, 5).map((f, i) => (
  • {f}
  • ))}
Book this
))}
); } /* ============================================================ Package Modal ============================================================ */ function PackageModal({ pkg, onClose }) { useEffect(() => { const onEsc = (e) => { if (e.key === "Escape") onClose(); }; document.addEventListener("keydown", onEsc); document.body.style.overflow = "hidden"; return () => { document.removeEventListener("keydown", onEsc); document.body.style.overflow = ""; }; }, [onClose]); if (!pkg) return null; return (
e.stopPropagation()}>
{pkg.tagline}
{pkg.isLimited ? (
✨ LIMITED TIME
) : null}

The {pkg.name} package

${pkg.price} {pkg.duration} · {pkg.capacity} · {pkg.extra}
${pkg.deposit} deposit reserves your date · remaining balance due the Monday before the event
The experience
    {pkg.experience.map((it, i) =>
  • {it}
  • )}
Glam treatment
    {pkg.glam.map((it, i) =>
  • {it}
  • )}
For the birthday girl
    {pkg.birthdayGirl.map((it, i) =>
  • {it}
  • )}
Capacity
  • {pkg.capacity}
  • {pkg.extra}
  • {pkg.duration} total
{pkg.footnote ? (

✨ {pkg.footnote}

) : null}
Book the {pkg.name} package Call us
); } /* ============================================================ Superstar Entrance Section ============================================================ */ function SuperstarEntrance() { const videoRef = useRef(null); const [muted, setMuted] = useState(true); const toggleMute = () => { if (videoRef.current) { videoRef.current.muted = !videoRef.current.muted; setMuted(videoRef.current.muted); } }; return (
✦ SIGNATURE MOMENT ✦

The Superstar
entrance.

Music drops. The crowd quiets. And the birthday girl rises into view on her own private platform — like a Hollywood headliner stepping onto her own stage. Her favorite song plays, her friends cheer, then everyone runs onto the bus to dance with her.

It's the moment parents tell us about for years. The one the girls re-watch on their phones a hundred times. The core memory.

FREE Included with VIP & Ultimate VIP packages
+$99 Add to STAR or POP STAR as an upgrade
); } /* ============================================================ Video reel (gallery) ============================================================ */ function Reel() { const cards = [ { src: "assets/video-hero.mp4", label: "Inside the bus" }, { src: "assets/video-2.mp4", label: "Pink carpet entrance" }, { src: "assets/video-3.mp4", label: "Glam time" }, { src: "assets/video-4.mp4", label: "Sing-along mic" }, { src: "assets/video-5.mp4", label: "Dance party" }, { src: "assets/video-6.mp4", label: "Spa squad" }, ]; const trackRef = useRef(null); // Auto-play videos when in view useEffect(() => { const obs = new IntersectionObserver((entries) => { entries.forEach((e) => { const v = e.target; if (e.isIntersecting) v.play().catch(() => {}); else v.pause(); }); }, { threshold: 0.4 }); trackRef.current?.querySelectorAll("video").forEach((v) => obs.observe(v)); return () => obs.disconnect(); }, []); return ( ); } /* ============================================================ Travel Fees ============================================================ */ function TravelFees() { const [query, setQuery] = useState(""); const q = query.trim().toLowerCase(); const isFiltering = q.length > 0; // Find matched tier(s) const matched = isFiltering ? TRAVEL_TIERS .map((t) => ({ ...t, cities: t.cities.filter((c) => c.toLowerCase().includes(q)), })) .filter((t) => t.cities.length > 0) : TRAVEL_TIERS; const anyMatch = isFiltering && matched.length > 0; return (
Travel fees

We come to you.

We leave from the Palomar Transit Center in Chula Vista — travel fees are tiered by driving distance and added to your final invoice. Find your city below or just give us a call.

setQuery(e.target.value)} /> {isFiltering ? ( ) : null}
{isFiltering && !anyMatch ? (

We don't have "{query}" in our quick list — but that doesn't mean we can't come!

Call us for a quote
) : null}
{matched.map((t) => (
$ {t.fee}
{t.label}
{t.range}
{t.cities.map((c, i) => ( {isFiltering ? ( ) : c} ))}
))}
Travel fees are added to your final invoice — they're separate from your package price and deposit. The Monday-before-the-event balance includes any travel fee for your zone.

Don't see your city? No worries — we travel beyond this list all the time. Give us a call at {PHONE} and we'll send you a custom quote.
); } function Highlight({ text, q }) { const idx = text.toLowerCase().indexOf(q); if (idx < 0) return text; return ( <> {text.slice(0, idx)} {text.slice(idx, idx + q.length)} {text.slice(idx + q.length)} ); } /* ============================================================ Add-ons ============================================================ */ function Addons() { return (
Make it extra

Sparkly add-ons

Stack any of these onto any package to make her day even more "her."

{ADDONS.map((a, i) => (
{a.image ? (
) : (
)}

{a.name}

{a.price}
{a.blurb ?

{a.blurb}

: null}
))}
); } /* ============================================================ Social TikTok strip ============================================================ */ function Social() { const tiles = [ "tt-01.png","tt-02.png","tt-03.png","tt-04.png","tt-05.png","tt-06.png", "tt-07.png","tt-08.png","tt-09.png","tt-10.png","tt-11.png","tt-12.png", ]; return (
From our feed

@lilstarsparties

Instagram TikTok
{tiles.map((t, i) => ( ))}
); } /* ============================================================ Reviews ============================================================ */ function Reviews() { return (
Parents are talking

The reviews are in.

Here's what moms and dads tell us after the bus pulls away.

{REVIEWS.map((r, i) => (
★★★★★
"{r.quote}"
{r.initial}
{r.name}
{r.meta}
))}
); } /* ============================================================ FAQ ============================================================ */ function FaqSection() { const [open, setOpen] = useState(0); return (
The fine print

Common questions

{FAQ.map((f, i) => (
{f.a}
))}
); } /* ============================================================ Contact Form ============================================================ */ const FORMSPREE_ENDPOINT = "https://formspree.io/f/mojblyyr"; function ContactSection() { const [status, setStatus] = useState("idle"); // idle, submitting, success, error const [errorMsg, setErrorMsg] = useState(""); const formRef = useRef(null); const handleSubmit = async (e) => { e.preventDefault(); setStatus("submitting"); setErrorMsg(""); const form = formRef.current; const formData = new FormData(form); try { const response = await fetch(FORMSPREE_ENDPOINT, { method: "POST", body: formData, headers: { Accept: "application/json" }, }); if (response.ok) { setStatus("success"); form.reset(); } else { const data = await response.json().catch(() => ({})); setErrorMsg(data?.error || "Something went wrong. Please call us at " + PHONE + "."); setStatus("error"); } } catch (err) { setErrorMsg("Couldn't send. Check your connection or call us at " + PHONE + "."); setStatus("error"); } }; return (
Get in touch

Have a question?
Let's chat.

Not ready to book yet? Send us a note and we'll get back to you within 24 hours. Tell us what you're thinking and we'll help you plan her perfect day.

Call us
{PHONE}
Service area
San Diego · OC · Temecula
{status === "success" ? (

Got it! 💖

Thanks for reaching out. We'll get back to you within 24 hours.

) : (
{status === "error" ? (
{errorMsg}
) : null}
{/* Honeypot for spam */} {/* Subject line in your inbox */}

Or just call us at {PHONE}. We're real humans!

)}
); } /* ============================================================ Booking CTA ============================================================ */ function BookingCta() { return (

Popular dates fill up fast
book her party early.

Lock in any date — up to 12 months out — with a deposit starting at $249. Takes 90 seconds.

Book on the calendar
or talk to a real human → 📞 {PHONE} 💬 Text us ✉️ Email us
); } /* ============================================================ Footer ============================================================ */ function Footer() { return ( ); } /* ============================================================ Sticky Mobile CTA ============================================================ */ function StickyMobileCTA() { const [show, setShow] = useState(false); useEffect(() => { const onScroll = () => setShow(window.scrollY > 600); onScroll(); window.addEventListener("scroll", onScroll, { passive: true }); return () => window.removeEventListener("scroll", onScroll); }, []); if (!show) return null; return (
Ready to book her party?
Takes 90 seconds · From $249 deposit
Book
); } /* ============================================================ Floating "Talk to a real human" widget ============================================================ */ function FloatingChat() { const [open, setOpen] = useState(false); const [teased, setTeased] = useState(false); useEffect(() => { // Auto-tease after 12 seconds (show the bubble briefly) const t = setTimeout(() => { const dismissed = localStorage.getItem("ls_chat_dismissed"); if (!dismissed) setTeased(true); }, 12000); return () => clearTimeout(t); }, []); const handleOpen = () => { setOpen(true); setTeased(false); }; const handleClose = () => { setOpen(false); localStorage.setItem("ls_chat_dismissed", "1"); }; const handleDismissTease = (e) => { e.stopPropagation(); setTeased(false); localStorage.setItem("ls_chat_dismissed", "1"); }; return ( <> {teased && !open ? (
Hi mama! 💖
Got questions? Text or call us — we usually answer in 5 min ✨
) : null} {open ? (
Little Stars
Little Stars Party Bus
Typically replies in 5 min
Hi mama! 👋 Got a question about a package, a date, or pricing? Pick the easiest way to reach us — we're real humans and we'll get back to you fast!
Text us
{PHONE}
Call us
{PHONE}
Email us
info@littlestarspartybus.com
Book now
Pick a date — 90 sec
✨ Real humans · No bots · Mon–Sat 9am–8pm
) : null} ); } /* ============================================================ App ============================================================ */ function App() { const [activePkg, setActivePkg] = useState(null); return ( <>