"use client"; import { STATUS_MAP } from "@/config/constants"; import { useState, useEffect, useMemo } from 'react'; import Link from 'next/link'; function getDistance(lat1: number, lon1: number, lat2: number, lon2: number) { try { const R = 6371; const dLat = (lat2 - lat1) * Math.PI / 180; const dLon = (lon2 - lon1) * Math.PI / 180; const a = Math.sin(dLat/2) * Math.sin(dLat/2) + Math.cos(lat1 * Math.PI / 180) * Math.cos(lat2 * Math.PI / 180) * Math.sin(dLon/2) * Math.sin(dLon/2); return R * 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a)); } catch (e) { return Infinity; } } export default function FacilitySearch({ initialFacilities }: { initialFacilities: any[] }) { const [searchQuery, setSearchQuery] = useState(""); const [userLocation, setUserLocation] = useState<{ lat: number, lng: number } | null>(null); const [mounted, setMounted] = useState(false); useEffect(() => { setMounted(true); if ("geolocation" in navigator) { navigator.geolocation.getCurrentPosition(p => setUserLocation({ lat: p.coords.latitude, lng: p.coords.longitude })); } }, []); const processed = useMemo(() => { if (!mounted || !Array.isArray(initialFacilities)) return []; const words = searchQuery.toLowerCase().trim().split(/\s+/).filter(w => w.length > 0); return initialFacilities.map(f => { // Skuddsikker status-vask const raw = Array.isArray(f.course_statuses) ? f.course_statuses : []; const statuses = raw.filter((s: any) => s && s.status && s.status !== 'finnes_ingen_bane_to' && s.name !== 'Bane 2'); const dist = userLocation && f.lat && f.lng ? getDistance(userLocation.lat, userLocation.lng, f.lat, f.lng) : Infinity; const searchBlob = `${f.name} ${f.city} ${f.county} ${statuses.map((s:any) => s.name + s.status).join(" ")}`.toLowerCase(); const matches = words.every(w => searchBlob.includes(w)); return { ...f, dist, statuses, matches }; }) .filter(f => f.matches) .sort((a, b) => (userLocation && a.dist !== b.dist ? a.dist - b.dist : (a.name || "").localeCompare(b.name || "", 'nb'))); }, [searchQuery, initialFacilities, userLocation, mounted]); if (!mounted) return null; return (
{userLocation ? "GPS AKTIV" : "SORTERER ALFABETISK"} • {processed.length} BANER
setSearchQuery(e.target.value)} />
{processed.map((f: any) => (
{f.name} {f.dist !== Infinity &&
{Math.round(f.dist)} km unna
}
{f.statuses.map((s: any, idx: number) => { const raw = (s.status || "ukjent").toLowerCase(); let color = "bg-gray-500 text-white"; if (raw.includes('aapen') && !raw.includes('vinter')) color = "bg-green-600 text-white"; else if (raw.includes('vinter')) color = "bg-emerald-400 text-gray-900"; else if (raw.includes('snart')) color = "bg-yellow-500 text-gray-900"; else if (raw.includes('stengt')) color = "bg-red-600 text-white"; return
{f.statuses.length > 1 ? `${s.name}: ${STATUS_MAP[raw] || raw}` : (STATUS_MAP[raw] || raw)}
; })}

{f.name}

{f.city}{f.county ? ` • ${f.county}` : ''}

{f.amenities?.antall_hull || f.holes || '--'} Hull {f.golfamore &&
G
} {f.nsg_data?.url &&
S
}
Se bane →
))}
); }