Compare commits
3 Commits
version_1_
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
| fcd25a7954 | |||
|
|
61f1ed4dc8 | ||
| 6e15cfb67b |
@@ -1,269 +1,33 @@
|
||||
import AboutTextSplit from '@/components/sections/about/AboutTextSplit';
|
||||
import ContactCta from '@/components/sections/contact/ContactCta';
|
||||
import FeaturesDetailedCards from '@/components/sections/features/FeaturesDetailedCards';
|
||||
import FeaturesRevealCardsBento from '@/components/sections/features/FeaturesRevealCardsBento';
|
||||
import HeroTiltedCards from '@/components/sections/hero/HeroTiltedCards';
|
||||
import MetricsIconCards from '@/components/sections/metrics/MetricsIconCards';
|
||||
import TestimonialQuoteCards from '@/components/sections/testimonial/TestimonialQuoteCards';
|
||||
import { Award, CheckCircle, Star } from "lucide-react";
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
// AUTO-GENERATED shell by per-section-migrate.
|
||||
// Section bodies live in ./<PageBase>/sections/<X>.tsx. Edit the section
|
||||
// files directly. Non-block content (wrappers, non-inlinable sections) is
|
||||
// preserved inline; extracted section blocks become <XSection/> refs.
|
||||
|
||||
export default function HomePage() {
|
||||
import React from 'react';
|
||||
import HeroSection from './HomePage/sections/Hero';
|
||||
import AboutSection from './HomePage/sections/About';
|
||||
import ServicesSection from './HomePage/sections/Services';
|
||||
import ProcessSection from './HomePage/sections/Process';
|
||||
import MetricsSection from './HomePage/sections/Metrics';
|
||||
import ReviewsSection from './HomePage/sections/Reviews';
|
||||
import ContactSection from './HomePage/sections/Contact';
|
||||
|
||||
export default function HomePage(): React.JSX.Element {
|
||||
return (
|
||||
<>
|
||||
<div id="hero" data-section="hero">
|
||||
<SectionErrorBoundary name="hero">
|
||||
<HeroTiltedCards
|
||||
tag="Trusted Residential Excellence"
|
||||
title="Plumbing Crafted with Dignity"
|
||||
description="We treat your $2M home like our own. Professional, clean, and reliable plumbing services for the discerning homeowner."
|
||||
primaryButton={{
|
||||
text: "Schedule Quote",
|
||||
href: "#contact",
|
||||
}}
|
||||
secondaryButton={{
|
||||
text: "Our Services",
|
||||
href: "#services",
|
||||
}}
|
||||
items={[
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/plumbing-professional-doing-his-job_23-2150721571.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/interior-design-neoclassical-style-with-furnishings-decor_23-2151199306.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/interior-modern-bathroom-with-window-overlooking-city_169016-26703.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/steel-faucet-interior-modern-bathroom-with-window_169016-26704.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/small-bathroom-space-with-modern-style-furniture_23-2150864624.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
<>
|
||||
<HeroSection />
|
||||
|
||||
<div id="about" data-section="about">
|
||||
<SectionErrorBoundary name="about">
|
||||
<AboutTextSplit
|
||||
title="The G&M Standard"
|
||||
descriptions={[
|
||||
"We founded G&M on a simple premise: professional plumbing shouldn't be stressful. We combine technical expertise with the respect and courtesy your home deserves.",
|
||||
"Our team of master plumbers represents the pinnacle of the trade, combining years of field experience with rigorous training. We follow a strict protocol: arrive on time, treat the home with care, and execute flawless, lasting repairs.",
|
||||
"Your home is your most valuable asset. We ensure every job—from a simple washer replacement to a complex boiler installation—is completed with craftsman-grade precision and unmatched integrity.",
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
<AboutSection />
|
||||
|
||||
<div id="services" data-section="services">
|
||||
<SectionErrorBoundary name="services">
|
||||
<FeaturesDetailedCards
|
||||
tag="Our Expertise"
|
||||
title="Professional Plumbing Solutions"
|
||||
description="Comprehensive, craftsman-grade solutions tailored for luxury residential needs."
|
||||
items={[
|
||||
{
|
||||
title: "Precision Pipe Repair",
|
||||
description: "Expert solutions for aging or damaged lines, ensuring structural integrity.",
|
||||
tags: [
|
||||
"Reliable",
|
||||
"Craftsman",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/closeup-shot-metal-wrenches-wooden-surface_181624-19856.jpg?_wi=1",
|
||||
},
|
||||
{
|
||||
title: "Drain & Sewer Care",
|
||||
description: "High-tech diagnostics and non-invasive clearing for modern plumbing needs.",
|
||||
tags: [
|
||||
"Tech-enabled",
|
||||
"Clean",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/plumber-man_1368-949.jpg",
|
||||
},
|
||||
{
|
||||
title: "Boiler & Heating",
|
||||
description: "Efficient installation and maintenance for luxury residential boilers.",
|
||||
tags: [
|
||||
"Efficient",
|
||||
"Comfort",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/medium-shot-black-man-working_23-2149546192.jpg",
|
||||
},
|
||||
{
|
||||
title: "Luxury Fixture Install",
|
||||
description: "Professional mounting of designer hardware and high-end faucets.",
|
||||
tags: [
|
||||
"Designer",
|
||||
"Precise",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/steel-faucet-interior-modern-bathroom-with-window_169016-26975.jpg",
|
||||
},
|
||||
{
|
||||
title: "Kitchen Plumbing",
|
||||
description: "Refined installation for modern gourmet kitchens and sink systems.",
|
||||
tags: [
|
||||
"Gourmet",
|
||||
"Seamless",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/man-drying-glass-with-kitchen-towel-by-black-faucet-drying-dishes_169016-69554.jpg",
|
||||
},
|
||||
{
|
||||
title: "Leak Diagnostics",
|
||||
description: "Advanced non-destructive testing for hidden plumbing issues.",
|
||||
tags: [
|
||||
"Advanced",
|
||||
"Thorough",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/female-mechanic-removing-tool-from-tool-box_1170-1228.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
<ServicesSection />
|
||||
|
||||
<div id="process" data-section="process">
|
||||
<SectionErrorBoundary name="process">
|
||||
<FeaturesRevealCardsBento
|
||||
tag="How We Work"
|
||||
title="The G&M Experience"
|
||||
description="Seamless, transparent, and respectful service at every turn."
|
||||
items={[
|
||||
{
|
||||
title: "Digital Quote",
|
||||
description: "Request a quote online; transparent pricing from the start.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/white-kitchen-sink-faucet_58702-1832.jpg",
|
||||
},
|
||||
{
|
||||
title: "Prep Protocols",
|
||||
description: "We arrive on-time with floor protection and clean uniforms.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/sanitary-equipment_93675-132393.jpg",
|
||||
},
|
||||
{
|
||||
title: "Master Plumbing",
|
||||
description: "Top-tier craftsmanship using the highest quality materials.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/authentic-woman-using-handheld-mixer_158595-5630.jpg",
|
||||
},
|
||||
{
|
||||
title: "Clean Execution",
|
||||
description: "We leave your space cleaner than we found it, every time.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/high-angle-man-cleaning-sink_23-2149535089.jpg",
|
||||
},
|
||||
{
|
||||
title: "Quality Audit",
|
||||
description: "Final check against our internal standards of excellence.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/side-view-man-working-as-plumber_23-2150746307.jpg",
|
||||
},
|
||||
{
|
||||
title: "Lifetime Support",
|
||||
description: "We stand by our work; call anytime with follow-up questions.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/copy-space-mechanical-tools_23-2148557958.jpg",
|
||||
},
|
||||
{
|
||||
title: "Feedback Loop",
|
||||
description: "Help us improve by sharing your experience post-service.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/tools-hardware-set_23-2151979300.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
<ProcessSection />
|
||||
|
||||
<div id="metrics" data-section="metrics">
|
||||
<SectionErrorBoundary name="metrics">
|
||||
<MetricsIconCards
|
||||
tag="Our Impact"
|
||||
title="Precision by the Numbers"
|
||||
description="Measured results through professional service standards."
|
||||
metrics={[
|
||||
{
|
||||
icon: CheckCircle,
|
||||
title: "Successful Jobs",
|
||||
value: "12,000+",
|
||||
},
|
||||
{
|
||||
icon: Award,
|
||||
title: "Master Certifications",
|
||||
value: "45",
|
||||
},
|
||||
{
|
||||
icon: Star,
|
||||
title: "Average Rating",
|
||||
value: "5.0",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
<MetricsSection />
|
||||
|
||||
<div id="reviews" data-section="reviews">
|
||||
<SectionErrorBoundary name="reviews">
|
||||
<TestimonialQuoteCards
|
||||
tag="Client Stories"
|
||||
title="Earned Trust, Not Claimed"
|
||||
description="See why top homeowners choose our plumbing services."
|
||||
testimonials={[
|
||||
{
|
||||
name: "Jonathan Reed",
|
||||
role: "Homeowner",
|
||||
quote: "Finally, a plumbing service that understands the level of care required in a luxury home. Impeccable work.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/amazing-laughing-redhead-young-lady-standing-cafe_171337-15271.jpg",
|
||||
},
|
||||
{
|
||||
name: "Sarah Miller",
|
||||
role: "Interior Designer",
|
||||
quote: "I trust G&M with all my client installations. They are punctual, clean, and masterfully thorough.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/happy-business-woman-resting-couch_23-2148095785.jpg",
|
||||
},
|
||||
{
|
||||
name: "David Thorne",
|
||||
role: "Property Manager",
|
||||
quote: "Rare to find such professionalism in the trades. Honest, transparent, and technically elite.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/old-man-posing-living-room_23-2148441065.jpg",
|
||||
},
|
||||
{
|
||||
name: "Elena Vance",
|
||||
role: "Estate Owner",
|
||||
quote: "The only plumber I'll call now. They arrive on time, respect the property, and get it right the first time.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/collaboration-two-carpenters-building_329181-15617.jpg",
|
||||
},
|
||||
{
|
||||
name: "Marcus Chen",
|
||||
role: "Homeowner",
|
||||
quote: "Craftsmanship at its finest. They handled our bathroom renovation flawlessly.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/portrait-man-smiling-camera_23-2148238839.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
<ReviewsSection />
|
||||
|
||||
<div id="contact" data-section="contact">
|
||||
<SectionErrorBoundary name="contact">
|
||||
<ContactCta
|
||||
tag="Get Started"
|
||||
text="Experience the G&M difference for your home. Schedule a professional quote today."
|
||||
primaryButton={{
|
||||
text: "Call Now",
|
||||
href: "tel:5550123456",
|
||||
}}
|
||||
secondaryButton={{
|
||||
text: "Online Quote",
|
||||
href: "#",
|
||||
}}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
<ContactSection />
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
23
src/pages/HomePage/sections/About.tsx
Normal file
23
src/pages/HomePage/sections/About.tsx
Normal file
@@ -0,0 +1,23 @@
|
||||
// AUTO-GENERATED by per-section-migrate. Edit freely — Bob will treat this
|
||||
// file as the canonical source for the "about" section.
|
||||
|
||||
import React from 'react';
|
||||
import AboutTextSplit from '@/components/sections/about/AboutTextSplit';
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
|
||||
export default function AboutSection(): React.JSX.Element {
|
||||
return (
|
||||
<div id="about" data-section="about">
|
||||
<SectionErrorBoundary name="about">
|
||||
<AboutTextSplit
|
||||
title="The G&M Standard"
|
||||
descriptions={[
|
||||
"We founded G&M on a simple premise: professional plumbing shouldn't be stressful. We combine technical expertise with the respect and courtesy your home deserves.",
|
||||
"Our team of master plumbers represents the pinnacle of the trade, combining years of field experience with rigorous training. We follow a strict protocol: arrive on time, treat the home with care, and execute flawless, lasting repairs.",
|
||||
"Your home is your most valuable asset. We ensure every job—from a simple washer replacement to a complex boiler installation—is completed with craftsman-grade precision and unmatched integrity.",
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
98
src/pages/HomePage/sections/Contact.tsx
Normal file
98
src/pages/HomePage/sections/Contact.tsx
Normal file
@@ -0,0 +1,98 @@
|
||||
/* eslint-disable */
|
||||
// @ts-nocheck — generated by catalog-eject; runtime-correct but TS strict-mode false-positives on inlined catalog body
|
||||
import ScrollReveal from "@/components/ui/ScrollReveal";
|
||||
import TextAnimation from "@/components/ui/TextAnimation";
|
||||
import Button from "@/components/ui/Button";
|
||||
import { MapPin, Phone, Clock, Map } from "lucide-react";
|
||||
|
||||
const primaryButton = {
|
||||
text: "Call Now",
|
||||
href: "tel:5550123456"
|
||||
};
|
||||
const secondaryButton = {
|
||||
text: "Online Quote",
|
||||
href: "#"
|
||||
};
|
||||
|
||||
const ContactInline = () => {
|
||||
return (
|
||||
<section aria-label="Contact section" className="py-20">
|
||||
<div className="w-content-width mx-auto">
|
||||
<ScrollReveal variant="slide-up">
|
||||
<div className="grid grid-cols-1 lg:grid-cols-2 gap-12 py-16 px-8 md:px-12 rounded card">
|
||||
<div className="flex flex-col items-start gap-6 justify-center">
|
||||
<div className="px-3 py-1 text-sm bg-background rounded w-fit">
|
||||
<p>{"Get Started"}</p>
|
||||
</div>
|
||||
|
||||
<TextAnimation
|
||||
text={"Experience the G&M difference for your home. Schedule a professional quote today."}
|
||||
variant="fade-blur"
|
||||
gradientText={true}
|
||||
tag="h2"
|
||||
className="text-4xl md:text-5xl leading-[1.15] font-semibold text-balance"
|
||||
/>
|
||||
|
||||
<div className="flex flex-wrap gap-3 mt-4">
|
||||
<Button text={primaryButton.text} href={primaryButton.href} variant="primary" />
|
||||
<Button text={secondaryButton.text} href={secondaryButton.href} variant="secondary" animationDelay={0.1} />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="flex flex-col gap-8 lg:pl-12 lg:border-l border-foreground/10 justify-center">
|
||||
<div className="flex items-start gap-4">
|
||||
<div className="p-3 rounded-full bg-background text-primary-cta shrink-0">
|
||||
<MapPin className="w-6 h-6" />
|
||||
</div>
|
||||
<div>
|
||||
<h3 className="text-lg font-semibold text-foreground mb-1">Address</h3>
|
||||
<p className="text-muted-foreground">105 Southeast Pkwy Ste 113<br/>Franklin, TN 37064</p>
|
||||
<p className="text-sm text-muted-foreground mt-1">Floor 1 · Southeast Business Center</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="flex items-start gap-4">
|
||||
<div className="p-3 rounded-full bg-background text-primary-cta shrink-0">
|
||||
<Phone className="w-6 h-6" />
|
||||
</div>
|
||||
<div>
|
||||
<h3 className="text-lg font-semibold text-foreground mb-1">Phone</h3>
|
||||
<p className="text-muted-foreground">(615) 599-6770</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="flex items-start gap-4">
|
||||
<div className="p-3 rounded-full bg-background text-primary-cta shrink-0">
|
||||
<Clock className="w-6 h-6" />
|
||||
</div>
|
||||
<div>
|
||||
<h3 className="text-lg font-semibold text-foreground mb-1">Hours</h3>
|
||||
<p className="text-muted-foreground">Mon - Fri: 7 AM – 4 PM</p>
|
||||
<p className="text-muted-foreground">Sat - Sun: Closed</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="flex items-start gap-4">
|
||||
<div className="p-3 rounded-full bg-background text-primary-cta shrink-0">
|
||||
<Map className="w-6 h-6" />
|
||||
</div>
|
||||
<div>
|
||||
<h3 className="text-lg font-semibold text-foreground mb-1">Location Reference</h3>
|
||||
<p className="text-muted-foreground">V4VG+X4 Franklin, Tennessee</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</ScrollReveal>
|
||||
</div>
|
||||
</section>
|
||||
);
|
||||
};
|
||||
|
||||
export default function ContactSection() {
|
||||
return (
|
||||
<div data-webild-section="contact" id="contact">
|
||||
<ContactInline />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
45
src/pages/HomePage/sections/Hero.tsx
Normal file
45
src/pages/HomePage/sections/Hero.tsx
Normal file
@@ -0,0 +1,45 @@
|
||||
// AUTO-GENERATED by per-section-migrate. Edit freely — Bob will treat this
|
||||
// file as the canonical source for the "hero" section.
|
||||
|
||||
import React from 'react';
|
||||
import HeroTiltedCards from '@/components/sections/hero/HeroTiltedCards';
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
|
||||
export default function HeroSection(): React.JSX.Element {
|
||||
return (
|
||||
<div id="hero" data-section="hero">
|
||||
<SectionErrorBoundary name="hero">
|
||||
<HeroTiltedCards
|
||||
tag="Trusted Residential Excellence"
|
||||
title="Plumbing Crafted with Dignity"
|
||||
description="We treat your $2M home like our own. Professional, clean, and reliable plumbing services for the discerning homeowner."
|
||||
primaryButton={{
|
||||
text: "Schedule Quote",
|
||||
href: "#contact",
|
||||
}}
|
||||
secondaryButton={{
|
||||
text: "Our Services",
|
||||
href: "#services",
|
||||
}}
|
||||
items={[
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/plumbing-professional-doing-his-job_23-2150721571.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/interior-design-neoclassical-style-with-furnishings-decor_23-2151199306.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/interior-modern-bathroom-with-window-overlooking-city_169016-26703.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/steel-faucet-interior-modern-bathroom-with-window_169016-26704.jpg",
|
||||
},
|
||||
{
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/small-bathroom-space-with-modern-style-furniture_23-2150864624.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
38
src/pages/HomePage/sections/Metrics.tsx
Normal file
38
src/pages/HomePage/sections/Metrics.tsx
Normal file
@@ -0,0 +1,38 @@
|
||||
// AUTO-GENERATED by per-section-migrate. Edit freely — Bob will treat this
|
||||
// file as the canonical source for the "metrics" section.
|
||||
|
||||
import React from 'react';
|
||||
import MetricsIconCards from '@/components/sections/metrics/MetricsIconCards';
|
||||
import { Award, CheckCircle, Star } from "lucide-react";
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
|
||||
export default function MetricsSection(): React.JSX.Element {
|
||||
return (
|
||||
<div id="metrics" data-section="metrics">
|
||||
<SectionErrorBoundary name="metrics">
|
||||
<MetricsIconCards
|
||||
tag="Our Impact"
|
||||
title="Precision by the Numbers"
|
||||
description="Measured results through professional service standards."
|
||||
metrics={[
|
||||
{
|
||||
icon: CheckCircle,
|
||||
title: "Successful Jobs",
|
||||
value: "12,000+",
|
||||
},
|
||||
{
|
||||
icon: Award,
|
||||
title: "Master Certifications",
|
||||
value: "45",
|
||||
},
|
||||
{
|
||||
icon: Star,
|
||||
title: "Average Rating",
|
||||
value: "5.0",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
64
src/pages/HomePage/sections/Process.tsx
Normal file
64
src/pages/HomePage/sections/Process.tsx
Normal file
@@ -0,0 +1,64 @@
|
||||
// AUTO-GENERATED by per-section-migrate. Edit freely — Bob will treat this
|
||||
// file as the canonical source for the "process" section.
|
||||
|
||||
import React from 'react';
|
||||
import FeaturesRevealCardsBento from '@/components/sections/features/FeaturesRevealCardsBento';
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
|
||||
export default function ProcessSection(): React.JSX.Element {
|
||||
return (
|
||||
<div id="process" data-section="process">
|
||||
<SectionErrorBoundary name="process">
|
||||
<FeaturesRevealCardsBento
|
||||
tag="How We Work"
|
||||
title="The G&M Experience"
|
||||
description="Seamless, transparent, and respectful service at every turn."
|
||||
items={[
|
||||
{
|
||||
title: "Digital Quote",
|
||||
description: "Request a quote online; transparent pricing from the start.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/white-kitchen-sink-faucet_58702-1832.jpg",
|
||||
},
|
||||
{
|
||||
title: "Prep Protocols",
|
||||
description: "We arrive on-time with floor protection and clean uniforms.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/sanitary-equipment_93675-132393.jpg",
|
||||
},
|
||||
{
|
||||
title: "Master Plumbing",
|
||||
description: "Top-tier craftsmanship using the highest quality materials.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/authentic-woman-using-handheld-mixer_158595-5630.jpg",
|
||||
},
|
||||
{
|
||||
title: "Clean Execution",
|
||||
description: "We leave your space cleaner than we found it, every time.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/high-angle-man-cleaning-sink_23-2149535089.jpg",
|
||||
},
|
||||
{
|
||||
title: "Quality Audit",
|
||||
description: "Final check against our internal standards of excellence.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/side-view-man-working-as-plumber_23-2150746307.jpg",
|
||||
},
|
||||
{
|
||||
title: "Lifetime Support",
|
||||
description: "We stand by our work; call anytime with follow-up questions.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/copy-space-mechanical-tools_23-2148557958.jpg",
|
||||
},
|
||||
{
|
||||
title: "Feedback Loop",
|
||||
description: "Help us improve by sharing your experience post-service.",
|
||||
href: "#contact",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/tools-hardware-set_23-2151979300.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
52
src/pages/HomePage/sections/Reviews.tsx
Normal file
52
src/pages/HomePage/sections/Reviews.tsx
Normal file
@@ -0,0 +1,52 @@
|
||||
// AUTO-GENERATED by per-section-migrate. Edit freely — Bob will treat this
|
||||
// file as the canonical source for the "reviews" section.
|
||||
|
||||
import React from 'react';
|
||||
import TestimonialQuoteCards from '@/components/sections/testimonial/TestimonialQuoteCards';
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
|
||||
export default function ReviewsSection(): React.JSX.Element {
|
||||
return (
|
||||
<div id="reviews" data-section="reviews">
|
||||
<SectionErrorBoundary name="reviews">
|
||||
<TestimonialQuoteCards
|
||||
tag="Client Stories"
|
||||
title="Earned Trust, Not Claimed"
|
||||
description="See why top homeowners choose our plumbing services."
|
||||
testimonials={[
|
||||
{
|
||||
name: "Jonathan Reed",
|
||||
role: "Homeowner",
|
||||
quote: "Finally, a plumbing service that understands the level of care required in a luxury home. Impeccable work.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/amazing-laughing-redhead-young-lady-standing-cafe_171337-15271.jpg",
|
||||
},
|
||||
{
|
||||
name: "Sarah Miller",
|
||||
role: "Interior Designer",
|
||||
quote: "I trust G&M with all my client installations. They are punctual, clean, and masterfully thorough.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/happy-business-woman-resting-couch_23-2148095785.jpg",
|
||||
},
|
||||
{
|
||||
name: "David Thorne",
|
||||
role: "Property Manager",
|
||||
quote: "Rare to find such professionalism in the trades. Honest, transparent, and technically elite.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/old-man-posing-living-room_23-2148441065.jpg",
|
||||
},
|
||||
{
|
||||
name: "Elena Vance",
|
||||
role: "Estate Owner",
|
||||
quote: "The only plumber I'll call now. They arrive on time, respect the property, and get it right the first time.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/collaboration-two-carpenters-building_329181-15617.jpg",
|
||||
},
|
||||
{
|
||||
name: "Marcus Chen",
|
||||
role: "Homeowner",
|
||||
quote: "Craftsmanship at its finest. They handled our bathroom renovation flawlessly.",
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/portrait-man-smiling-camera_23-2148238839.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
76
src/pages/HomePage/sections/Services.tsx
Normal file
76
src/pages/HomePage/sections/Services.tsx
Normal file
@@ -0,0 +1,76 @@
|
||||
// AUTO-GENERATED by per-section-migrate. Edit freely — Bob will treat this
|
||||
// file as the canonical source for the "services" section.
|
||||
|
||||
import React from 'react';
|
||||
import FeaturesDetailedCards from '@/components/sections/features/FeaturesDetailedCards';
|
||||
import SectionErrorBoundary from "@/components/ui/SectionErrorBoundary";
|
||||
|
||||
export default function ServicesSection(): React.JSX.Element {
|
||||
return (
|
||||
<div id="services" data-section="services">
|
||||
<SectionErrorBoundary name="services">
|
||||
<FeaturesDetailedCards
|
||||
tag="Our Expertise"
|
||||
title="Professional Plumbing Solutions"
|
||||
description="Comprehensive, craftsman-grade solutions tailored for luxury residential needs."
|
||||
items={[
|
||||
{
|
||||
title: "Precision Pipe Repair",
|
||||
description: "Expert solutions for aging or damaged lines, ensuring structural integrity.",
|
||||
tags: [
|
||||
"Reliable",
|
||||
"Craftsman",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/closeup-shot-metal-wrenches-wooden-surface_181624-19856.jpg?_wi=1",
|
||||
},
|
||||
{
|
||||
title: "Drain & Sewer Care",
|
||||
description: "High-tech diagnostics and non-invasive clearing for modern plumbing needs.",
|
||||
tags: [
|
||||
"Tech-enabled",
|
||||
"Clean",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/plumber-man_1368-949.jpg",
|
||||
},
|
||||
{
|
||||
title: "Boiler & Heating",
|
||||
description: "Efficient installation and maintenance for luxury residential boilers.",
|
||||
tags: [
|
||||
"Efficient",
|
||||
"Comfort",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/medium-shot-black-man-working_23-2149546192.jpg",
|
||||
},
|
||||
{
|
||||
title: "Luxury Fixture Install",
|
||||
description: "Professional mounting of designer hardware and high-end faucets.",
|
||||
tags: [
|
||||
"Designer",
|
||||
"Precise",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/steel-faucet-interior-modern-bathroom-with-window_169016-26975.jpg",
|
||||
},
|
||||
{
|
||||
title: "Kitchen Plumbing",
|
||||
description: "Refined installation for modern gourmet kitchens and sink systems.",
|
||||
tags: [
|
||||
"Gourmet",
|
||||
"Seamless",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/man-drying-glass-with-kitchen-towel-by-black-faucet-drying-dishes_169016-69554.jpg",
|
||||
},
|
||||
{
|
||||
title: "Leak Diagnostics",
|
||||
description: "Advanced non-destructive testing for hidden plumbing issues.",
|
||||
tags: [
|
||||
"Advanced",
|
||||
"Thorough",
|
||||
],
|
||||
imageSrc: "http://img.b2bpic.net/free-photo/female-mechanic-removing-tool-from-tool-box_1170-1228.jpg",
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</SectionErrorBoundary>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user