From 79c6b627f417f31aff974837120cec39b5c87292 Mon Sep 17 00:00:00 2001 From: nelsonkct Date: Tue, 3 Dec 2024 19:40:53 +0800 Subject: [PATCH] feat : add search bar at event index page --- src/routes/events/index.tsx | 87 ++++++++++++++++++++++++++----------- 1 file changed, 61 insertions(+), 26 deletions(-) diff --git a/src/routes/events/index.tsx b/src/routes/events/index.tsx index b834045..2bc316f 100644 --- a/src/routes/events/index.tsx +++ b/src/routes/events/index.tsx @@ -1,51 +1,82 @@ import { createFileRoute } from '@tanstack/react-router'; -import { Clock } from "flowbite-react-icons/solid"; +import { Clock, Search } from "flowbite-react-icons/outline"; +import { useState } from 'react'; import { BellIcon, Header, PinIcon, PlusIcon } from '../../components'; import { AuthGuard } from '../../utils/auth'; import { supabase } from '../../utils/supabase'; + interface Event { - created_at: string; - description: string | null; - end_time: string | null; - fee: number | null; - id: number; - name: string | null; - start_time: string | null; - type: number | null; - user_id: string; - location: string | null; + created_at: string; + description: string | null; + end_time: string | null; + fee: number | null; + id: number; + name: string | null; + start_time: string | null; + type: number | null; + user_id: string; + location: string | null; } export const Route = createFileRoute('/events/')({ beforeLoad: AuthGuard, loader: async () => { - const { data, error } = await supabase - .from('events') - .select('*') + const { data, error } = await supabase.from('events').select('*'); if (error !== null) { - throw error + throw error; } - return { events: data } + return { events: data }; }, - component: EventIndex -}) + component: EventIndex, +}); function EventIndex() { - const { events } = Route.useLoaderData() + const { events } = Route.useLoaderData(); const navigate = Route.useNavigate(); - // console.log(events[0].start_time) + const [searchTerm, setSearchTerm] = useState(''); + const [isFocused, setIsFocused] = useState(false); + + const filteredEvents = events.filter( + (event) => + event.name && + event.name.toLowerCase().includes(searchTerm.toLowerCase()) + ); return ( <>
+
+ setSearchTerm(e.target.value)} + onFocus={() => setIsFocused(true)} + onBlur={() => setIsFocused(false)} + className="input input-bordered w-full pl-12 pr-12" + /> + {!searchTerm && !isFocused && ( +
+ + 搜尋 +
+ )} + {searchTerm && ( + + )} +
+

最新揪人

- {events.map((event) => ( + {filteredEvents.map((event) => ( ))}
@@ -54,7 +85,7 @@ function EventIndex() {

最新活動

- {events.map((event) => ( + {filteredEvents.map((event) => ( ))}
@@ -65,7 +96,9 @@ function EventIndex() { className="btn btn-circle fixed right-4 bottom-4" onClick={() => { if (document) { - (document.getElementById('my_modal_4') as HTMLFormElement).showModal(); + ( + document.getElementById('my_modal_4') as HTMLFormElement + ).showModal(); } }} > @@ -94,11 +127,13 @@ function EventIndex() {
- ) + ); } function EventCard({ event }: { event: Event }) { - const startTime = event.start_time ? new Date(event.start_time) : new Date(); + const startTime = event.start_time + ? new Date(event.start_time) + : new Date(); return (
@@ -120,4 +155,4 @@ function EventCard({ event }: { event: Event }) {
); -} +} \ No newline at end of file