From ba097d0ff5d0d5fa569e89e9410d45a7292262e2 Mon Sep 17 00:00:00 2001 From: jyswee Date: Thu, 23 Jul 2026 22:10:04 +0000 Subject: [PATCH] Seed: blog template (17 files) --- src/pages/Search.tsx | 179 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 179 insertions(+) create mode 100644 src/pages/Search.tsx diff --git a/src/pages/Search.tsx b/src/pages/Search.tsx new file mode 100644 index 0000000..af769d1 --- /dev/null +++ b/src/pages/Search.tsx @@ -0,0 +1,179 @@ +import { useState } from "react"; +import { Link } from "react-router-dom"; +import { Button } from "@/components/ui/button"; +import { Badge } from "@/components/ui/badge"; +import { Input } from "@/components/ui/input"; +import { Avatar, AvatarFallback } from "@/components/ui/avatar"; +import { Search as SearchIcon, X, FileText } from "lucide-react"; +import Header from "@/components/Header"; +import Footer from "@/components/Footer"; + +const categoryColors: Record = { + Technology: "bg-emerald-100 text-emerald-700", + Design: "bg-amber-100 text-amber-700", + Business: "bg-stone-200 text-stone-700", + Lifestyle: "bg-teal-100 text-teal-700", +}; + +const allArticles = [ + { id: 1, title: "Understanding React Server Components in Production", excerpt: "A practical guide to adopting RSC in existing React applications without a full rewrite.", category: "Technology", author: "Sarah Chen", initials: "SC", date: "Mar 12, 2025", gradient: "from-amber-200 to-orange-300", slug: "react-server-components" }, + { id: 2, title: "Building Design Systems That Scale", excerpt: "Lessons learned from building a design system used across 12 product teams.", category: "Design", author: "Marcus Rivera", initials: "MR", date: "Mar 10, 2025", gradient: "from-emerald-200 to-teal-300", slug: "design-systems-at-scale" }, + { id: 3, title: "Growth Strategies for Early-Stage Startups", excerpt: "How three founders went from zero to product-market fit in under 18 months.", category: "Business", author: "Aisha Patel", initials: "AP", date: "Mar 8, 2025", gradient: "from-stone-200 to-stone-400", slug: "startup-growth-strategies" }, + { id: 4, title: "TypeScript Best Practices for Large Codebases", excerpt: "Type-safe patterns and architectural decisions that pay off at scale.", category: "Technology", author: "James Liu", initials: "JL", date: "Mar 6, 2025", gradient: "from-amber-100 to-amber-300", slug: "typescript-best-practices" }, + { id: 5, title: "The Remote Worker's Guide to Deep Focus", excerpt: "Strategies for maintaining productivity and avoiding burnout while working from home.", category: "Lifestyle", author: "Elena Torres", initials: "ET", date: "Mar 4, 2025", gradient: "from-emerald-100 to-emerald-300", slug: "remote-work-productivity" }, + { id: 6, title: "Accessible UI Patterns Every Developer Should Know", excerpt: "Common accessibility mistakes and how to build inclusive interfaces by default.", category: "Design", author: "David Kim", initials: "DK", date: "Mar 2, 2025", gradient: "from-stone-100 to-amber-200", slug: "accessible-ui-patterns" }, + { id: 7, title: "React Hooks: Advanced Patterns and Pitfalls", excerpt: "Going beyond useState and useEffect to build truly reusable custom hooks.", category: "Technology", author: "Sarah Chen", initials: "SC", date: "Feb 28, 2025", gradient: "from-emerald-200 to-emerald-400", slug: "react-hooks-advanced" }, + { id: 8, title: "The Business Case for Design Tokens", excerpt: "How design tokens save engineering time and create consistency at scale.", category: "Business", author: "David Kim", initials: "DK", date: "Feb 25, 2025", gradient: "from-amber-100 to-stone-200", slug: "design-tokens-business" }, +]; + +const filterChips = ["All", "Technology", "Design", "Business", "Lifestyle"]; + +const suggestions = ["React hooks", "design systems", "TypeScript", "remote work", "accessibility"]; + +export default function SearchPage() { + const [query, setQuery] = useState("react hooks"); + const [activeFilter, setActiveFilter] = useState("All"); + + const highlightMatch = (text: string, term: string) => { + if (!term || term.length < 2) return text; + const idx = text.toLowerCase().indexOf(term.toLowerCase()); + if (idx === -1) return text; + const before = text.slice(0, idx); + const match = text.slice(idx, idx + term.length); + const after = text.slice(idx + term.length); + return <>{before}{match}{after}; + }; + + const filtered = allArticles.filter((a) => { + const matchesQuery = query.length === 0 || a.title.toLowerCase().includes(query.toLowerCase()) || a.excerpt.toLowerCase().includes(query.toLowerCase()); + const matchesFilter = activeFilter === "All" || a.category === activeFilter; + return matchesQuery && matchesFilter; + }); + + return ( +
+
+ +
+ {/* Search Input */} +
+
+ + setQuery(e.target.value)} + className="pl-14 pr-12 h-16 text-lg rounded-2xl border-stone-200 bg-white shadow-sm focus-visible:ring-emerald-500" + /> + {query && ( + + )} +
+ {!query && ( +
+ Popular: + {["React", "TypeScript", "AI", "Design Systems"].map((s) => ( + + ))} +
+ )} +
+ + {/* Results heading */} + {query && filtered.length > 0 && ( +

+ {filtered.length} results for{" "} + '{query}' +

+ )} + + {/* Filter Chips */} +
+ {filterChips.map((chip) => ( + + ))} +
+ + {/* Results List */} + {filtered.length > 0 ? ( +
+ {filtered.map((article) => ( + +
+
+
+
+
+
+ + {article.category} + +
+

+ {highlightMatch(article.title, query)} +

+

{highlightMatch(article.excerpt, query)}

+
+
+ + {article.initials} + + {article.author} +
+ · + {article.date} +
+
+
+ + ))} +
+ ) : ( + /* Empty State */ +
+
+ +
+

No articles found

+

+ We couldn't find any articles matching your search. Try different keywords or browse by category. +

+
+ Try searching for: + {suggestions.map((s) => ( + + ))} +
+
+ )} +
+ +
+ ); +}