Real Estate Platform
A bold and sleek property platform with immersive listings, powerful search filters, agent profiles, and interactive property cards. Built for luxury real estate.
Overview
Luxury Property Platform
This real estate template provides a premium property browsing experience with immersive imagery, powerful filtering, and agent integration. Perfect for luxury real estate agencies and property marketplaces.
Property Listings
Beautiful property cards with images, pricing, and key details
Advanced Search
Filter by location, price range, property type, and more
Agent Profiles
Showcase top agents with ratings and deal counts
Statistics Display
Highlight company achievements and trust signals
Live Demo
Find YourDream Home
Discover exceptional properties in prime locations.
2,400+
Properties Sold
1,800+
Happy Clients
15+
Years Experience
48
Awards Won
Featured Properties
Handpicked luxury homes
$4,250,000
Modern Penthouse Suite
Manhattan, New York
$8,900,000
Oceanfront Villa
Malibu, California
$1,850,000
Contemporary Townhouse
Austin, Texas
Meet Our Top Agents
Expert professionals ready to help you
Sarah Mitchell
Senior Agent
142 deals closed
James Cooper
Luxury Specialist
98 deals closed
Emily Chen
Commercial Expert
76 deals closed
Ready to Find Your Dream Home?
Get personalized property recommendations and exclusive access to off-market listings.
Implementation Guide
Set Up Project Structure
Create the real estate platform layout with navigation and property pages.
123456789101112131415161718192021// Recommended folder structure src/ ├── app/ │ └── properties/ │ ├── layout.tsx # Main layout with nav │ ├── page.tsx # Property listings │ ├── [id]/page.tsx # Property details │ └── search/page.tsx # Search results ├── components/ │ ├── properties/ │ │ ├── PropertyCard.tsx │ │ ├── PropertyGrid.tsx │ │ ├── SearchBox.tsx │ │ └── FilterPanel.tsx │ ├── agents/ │ │ └── AgentCard.tsx │ └── layout/ │ ├── Header.tsx │ └── Footer.tsx └── lib/ └── property-data.ts
Create Property Card Component
Build reusable property cards with image, details, and hover effects.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263interface PropertyCardProps { id: number; title: string; location: string; price: string; beds: number; baths: number; sqft: string; type: string; featured: boolean; image: string; } function PropertyCard({ property }: { property: PropertyCardProps }) { return ( <div className="group bg-white rounded-2xl border overflow-hidden hover:shadow-2xl transition-all duration-300 hover:-translate-y-1"> {/* Image */} <div className="relative aspect-[4/3] overflow-hidden"> <img src={property.image} alt={property.title} className="absolute inset-0 w-full h-full object-cover transition-transform duration-500 group-hover:scale-110" /> <div className="absolute inset-0 bg-gradient-to-t from-slate-900/80 via-slate-900/20 to-transparent" /> {/* Badges */} <div className="absolute top-4 left-4 flex gap-2"> {property.featured && ( <span className="px-3 py-1 bg-red-500 text-white text-xs font-bold rounded-full"> Featured </span> )} <span className="px-3 py-1 bg-white/20 backdrop-blur-sm text-white text-xs rounded-full"> {property.type} </span> </div> {/* Price */} <div className="absolute bottom-4 left-4"> <p className="text-2xl font-bold text-white">{property.price}</p> </div> </div> {/* Content */} <div className="p-4"> <h3 className="text-lg font-bold group-hover:text-red-500 transition-colors"> {property.title} </h3> <p className="text-slate-500 flex items-center gap-1 mb-3 text-sm"> <LocationIcon className="w-4 h-4" /> {property.location} </p> <div className="flex items-center gap-3 pt-3 border-t text-xs text-slate-600"> <span>{property.beds} Beds</span> <span>•</span> <span>{property.baths} Baths</span> <span>•</span> <span>{property.sqft} sqft</span> </div> </div> </div> ); }
Build Hero Search Component
Create an immersive hero section with integrated search functionality.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475function HeroSearch() { const [activeFilter, setActiveFilter] = useState("all"); const [searchQuery, setSearchQuery] = useState(""); const [priceRange, setPriceRange] = useState("any"); const filters = ["all", "buy", "rent", "commercial"]; return ( <div className="relative bg-slate-950 overflow-hidden py-20"> {/* Background Effects */} <div className="absolute inset-0"> <div className="absolute inset-0 bg-gradient-to-br from-slate-900 via-slate-950 to-slate-900" /> <div className="absolute top-0 right-0 w-[800px] h-[800px] bg-red-500/10 rounded-full blur-3xl" /> <div className="absolute bottom-0 left-0 w-[600px] h-[600px] bg-orange-500/10 rounded-full blur-3xl" /> </div> <div className="relative max-w-7xl mx-auto px-6 text-center"> <h1 className="text-5xl md:text-7xl font-bold text-white mb-6"> Find Your <span className="block bg-gradient-to-r from-red-400 to-orange-400 bg-clip-text text-transparent"> Dream Home </span> </h1> {/* Search Box */} <div className="bg-white rounded-2xl p-2 shadow-2xl max-w-4xl mx-auto"> <div className="flex items-center gap-2"> {/* Filter Tabs */} <div className="flex bg-slate-100 rounded-xl p-1"> {filters.map((filter) => ( <button key={filter} onClick={() => setActiveFilter(filter)} className={`px-3 py-2 text-sm font-medium rounded-lg capitalize ${ activeFilter === filter ? "bg-white text-slate-900 shadow-sm" : "text-slate-500 hover:text-slate-700" }`} > {filter} </button> ))} </div> {/* Search Input */} <input type="text" value={searchQuery} onChange={(e) => setSearchQuery(e.target.value)} placeholder="City, neighborhood, or address..." className="flex-1 px-4 py-3 focus:outline-none" /> {/* Price Dropdown */} <select value={priceRange} onChange={(e) => setPriceRange(e.target.value)} className="px-4 py-3 bg-slate-100 rounded-xl" > <option value="any">Any Price</option> <option value="0-500k">$0 - $500K</option> <option value="500k-1m">$500K - $1M</option> <option value="1m+">$1M+</option> </select> {/* Search Button */} <button className="px-6 py-3 bg-gradient-to-r from-red-500 to-orange-500 text-white font-semibold rounded-xl"> Search </button> </div> </div> </div> </div> ); }
Full Source Code
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260"use client"; import { useState } from "react"; interface Property { id: number; title: string; location: string; price: string; beds: number; baths: number; sqft: string; type: string; featured: boolean; image: string; } interface Agent { id: number; name: string; role: string; deals: number; rating: number; } export default function RealEstatePlatform() { const [activeFilter, setActiveFilter] = useState("all"); const [searchQuery, setSearchQuery] = useState(""); const [priceRange, setPriceRange] = useState("any"); const [sidebarOpen, setSidebarOpen] = useState(true); const properties: Property[] = [ { id: 1, title: "Modern Penthouse Suite", location: "Manhattan, New York", price: "$4,250,000", beds: 4, baths: 3, sqft: "3,200", type: "Penthouse", featured: true, image: "https://images.unsplash.com/photo-1600596542815-ffad4c1539a9", }, // Add more properties... ]; const agents: Agent[] = [ { id: 1, name: "Sarah Mitchell", role: "Senior Agent", deals: 142, rating: 4.9 }, { id: 2, name: "James Cooper", role: "Luxury Specialist", deals: 98, rating: 4.8 }, ]; const filters = ["all", "buy", "rent", "commercial"]; return ( <div className="min-h-screen bg-slate-950 flex"> {/* Collapsible Sidebar */} <aside className={`${sidebarOpen ? "w-64" : "w-0"} bg-slate-900 border-r border-slate-800 transition-all`}> <div className="w-64 h-full flex flex-col"> {/* Logo */} <div className="flex items-center gap-3 px-6 h-16 border-b border-slate-800"> <div className="w-10 h-10 rounded-xl bg-gradient-to-br from-red-500 to-orange-500 flex items-center justify-center"> <HomeIcon className="w-6 h-6 text-white" /> </div> <div> <span className="text-xl font-bold text-white">Luxe</span> <span className="text-xl font-light text-red-400">Estate</span> </div> </div> {/* Navigation */} <nav className="p-4 space-y-1 flex-1"> {["Dashboard", "Properties", "Agents", "Clients", "Analytics", "Messages", "Settings"].map((item) => ( <button key={item} className="w-full flex items-center gap-3 px-4 py-2.5 rounded-xl text-sm font-medium text-slate-400 hover:bg-slate-800 hover:text-white" > {item} </button> ))} </nav> {/* User Profile */} <div className="p-4 border-t border-slate-800"> <div className="flex items-center gap-3"> <div className="w-10 h-10 rounded-full bg-gradient-to-br from-red-500 to-orange-500 flex items-center justify-center text-white font-semibold"> SM </div> <div> <p className="text-sm font-medium text-white">Sarah Mitchell</p> <p className="text-xs text-slate-500">Senior Agent</p> </div> </div> </div> </div> </aside> {/* Main Content */} <div className="flex-1 flex flex-col"> {/* Header */} <header className="sticky top-0 z-30 h-16 bg-slate-950/80 backdrop-blur-xl border-b border-slate-800"> <div className="flex items-center justify-between h-full px-6"> <button onClick={() => setSidebarOpen(!sidebarOpen)} className="p-2 hover:bg-slate-800 rounded-lg"> {/* Menu Icon */} </button> <div className="flex items-center gap-3"> {/* Search, Notifications, Add Property Button */} </div> </div> </header> {/* Hero with Search */} <div className="relative bg-slate-950 py-20"> <div className="max-w-7xl mx-auto px-6 text-center"> <h1 className="text-5xl font-bold text-white mb-6"> Find Your <span className="text-red-400">Dream Home</span> </h1> {/* Search Box */} <div className="bg-white rounded-2xl p-2 shadow-2xl max-w-3xl mx-auto"> <div className="flex items-center gap-2"> {/* Filter Tabs */} <div className="flex bg-slate-100 rounded-xl p-1"> {filters.map((filter) => ( <button key={filter} onClick={() => setActiveFilter(filter)} className={`px-3 py-2 text-sm font-medium rounded-lg capitalize ${ activeFilter === filter ? "bg-white text-slate-900 shadow-sm" : "text-slate-500" }`} > {filter} </button> ))} </div> {/* Search Input */} <input type="text" value={searchQuery} onChange={(e) => setSearchQuery(e.target.value)} placeholder="City, neighborhood..." className="flex-1 px-4 py-3 focus:outline-none" /> {/* Price Dropdown */} <select value={priceRange} onChange={(e) => setPriceRange(e.target.value)} className="px-4 py-3 bg-slate-100 rounded-xl" > <option value="any">Any Price</option> <option value="0-500k">$0 - $500K</option> <option value="500k-1m">$500K - $1M</option> </select> {/* Search Button */} <button className="px-6 py-3 bg-gradient-to-r from-red-500 to-orange-500 text-white font-semibold rounded-xl"> Search </button> </div> </div> </div> </div> {/* Properties Grid */} <div className="bg-slate-950 py-12"> <div className="max-w-7xl mx-auto px-6"> <h2 className="text-2xl font-bold text-white mb-8">Featured Properties</h2> <div className="grid md:grid-cols-3 gap-6"> {properties.map((property) => ( <PropertyCard key={property.id} property={property} /> ))} </div> </div> </div> {/* Agents Section */} <div className="bg-slate-900 py-12 border-t border-slate-800"> <div className="max-w-7xl mx-auto px-6"> <h2 className="text-2xl font-bold text-white mb-8 text-center">Top Agents</h2> <div className="grid md:grid-cols-3 gap-6"> {agents.map((agent) => ( <AgentCard key={agent.id} agent={agent} /> ))} </div> </div> </div> </div> </div> ); } function PropertyCard({ property }: { property: Property }) { return ( <div className="group bg-slate-900 rounded-2xl border border-slate-800 overflow-hidden hover:shadow-2xl hover:shadow-red-500/10 transition-all duration-300 hover:-translate-y-1"> {/* Image */} <div className="relative aspect-[4/3] overflow-hidden"> <img src={property.image} alt={property.title} className="absolute inset-0 w-full h-full object-cover transition-transform duration-500 group-hover:scale-110" /> <div className="absolute inset-0 bg-gradient-to-t from-slate-900/80 via-slate-900/20 to-transparent" /> {/* Badges */} <div className="absolute top-4 left-4 flex gap-2"> {property.featured && ( <span className="px-3 py-1 bg-red-500 text-white text-xs font-bold rounded-full"> Featured </span> )} </div> {/* Price */} <div className="absolute bottom-4 left-4"> <p className="text-2xl font-bold text-white">{property.price}</p> </div> </div> {/* Content */} <div className="p-4"> <h3 className="text-lg font-bold text-white group-hover:text-red-400 transition-colors"> {property.title} </h3> <p className="text-slate-500 text-sm mb-3">{property.location}</p> <div className="flex items-center gap-3 pt-3 border-t border-slate-800 text-xs text-slate-400"> <span>{property.beds} Beds</span> <span>|</span> <span>{property.baths} Baths</span> <span>|</span> <span>{property.sqft} sqft</span> </div> </div> </div> ); } function AgentCard({ agent }: { agent: Agent }) { return ( <div className="text-center"> <div className="relative w-24 h-24 mx-auto mb-4"> <div className="w-full h-full rounded-full bg-gradient-to-br from-red-500 to-orange-500 flex items-center justify-center text-white text-2xl font-bold"> {agent.name.charAt(0)} </div> <div className="absolute -bottom-1 left-1/2 -translate-x-1/2 px-2 py-0.5 bg-emerald-500 text-white text-xs font-bold rounded-full"> {agent.rating} </div> </div> <h3 className="text-lg font-bold text-white">{agent.name}</h3> <p className="text-red-400 text-sm">{agent.role}</p> <p className="text-slate-500 text-xs mt-1">{agent.deals} deals closed</p> <button className="mt-4 px-4 py-2 bg-slate-800 border border-slate-700 text-slate-300 rounded-xl hover:border-red-500 hover:text-red-400 transition-all text-sm"> Contact Agent </button> </div> ); }
Customization Guide
Brand Colors
Update the color scheme to match your real estate brand.
// Replace rose/orange with your brand colors
// In tailwind.config.ts:
colors: {
brand: {
50: '#fff1f2',
500: '#f43f5e',
600: '#e11d48',
700: '#be123c',
},
accent: {
400: '#fb923c',
500: '#f97316',
}
}
// Then update classes:
// from-red-500 to-orange-500 → from-brand-500 to-accent-500
// bg-red-500 → bg-brand-500Property Types
Customize property categories for your market.
const propertyTypes = [
{ value: "all", label: "All Properties" },
{ value: "house", label: "Houses" },
{ value: "apartment", label: "Apartments" },
{ value: "condo", label: "Condos" },
{ value: "villa", label: "Villas" },
{ value: "penthouse", label: "Penthouses" },
{ value: "commercial", label: "Commercial" },
];
// Use in filter component
<select>
{propertyTypes.map((type) => (
<option key={type.value} value={type.value}>
{type.label}
</option>
))}
</select>Search Filters
Add more search filters for detailed property queries.
interface SearchFilters {
location: string;
priceMin: number;
priceMax: number;
beds: number;
baths: number;
propertyType: string;
amenities: string[];
yearBuilt: number;
sqftMin: number;
sqftMax: number;
}
// Amenities options
const amenities = [
"Pool", "Garage", "Garden", "Gym",
"Security", "Elevator", "Parking",
"AC", "Heating", "Fireplace"
];Map Integration
Add interactive maps to display property locations.
import { GoogleMap, Marker } from '@react-google-maps/api';
function PropertyMap({ properties }) {
return (
<GoogleMap
mapContainerStyle={{ width: '100%', height: '400px' }}
center={{ lat: 34.0522, lng: -118.2437 }}
zoom={10}
>
{properties.map((property) => (
<Marker
key={property.id}
position={{ lat: property.lat, lng: property.lng }}
onClick={() => handleMarkerClick(property)}
/>
))}
</GoogleMap>
);
}
// Or use Mapbox for a more customizable solution
import Map, { Marker } from 'react-map-gl';Ready to Build Your Property Platform?
Copy this template, customize it to your brand, and start showcasing properties. All the components you need are included.