import LAENDER from '../../data/laender.json'; import { BY_CODE, CONTINENTS, continentOf, countryName, distanceKm, num } from './laender.js'; const pct = (part, total) => (total ? (part / total) * 100 : 0); const fmtPct = (p) => `${p.toLocaleString('de-DE', { maximumFractionDigits: p < 10 ? 1 : 0 })} %`; const TOTAL_AREA = LAENDER.reduce((s, c) => s + (c.area || 0), 0); /** * Statistik: Länder (Welt und je Kontinent), Fläche, äußerste Punkte, Kilometer entlang der Zeitleiste. * Grundlage für "Welt": alle Länder und Gebiete der Länderdaten (world-countries). */ export default function TravelStats({ visited, cities, visits, wishes, onSelectCity }) { const codes = [...visited].filter((c) => BY_CODE.has(c)); const area = codes.reduce((s, c) => s + (BY_CODE.get(c).area || 0), 0); const continents = CONTINENTS.map((name) => { const total = LAENDER.filter((c) => c.continent === name).length; const seen = codes.filter((c) => continentOf(c) === name).length; return { name, total, seen }; }).filter((c) => c.total); // Äußerste Punkte (nur besuchte Städte) const extreme = (pick) => (cities.length ? cities.reduce((a, b) => (pick(b) > pick(a) ? b : a)) : null); const points = [ ['Nördlichster Ort', extreme((c) => c.lat), (c) => `${c.lat.toFixed(1).replace('.', ',')}° N`], ['Südlichster Ort', extreme((c) => -c.lat), (c) => `${Math.abs(c.lat).toFixed(1).replace('.', ',')}° ${c.lat < 0 ? 'S' : 'N'}`], ['Östlichster Ort', extreme((c) => c.lon), (c) => `${Math.abs(c.lon).toFixed(1).replace('.', ',')}° ${c.lon < 0 ? 'W' : 'O'}`], ['Westlichster Ort', extreme((c) => -c.lon), (c) => `${Math.abs(c.lon).toFixed(1).replace('.', ',')}° ${c.lon < 0 ? 'W' : 'O'}`], ]; // Kilometer: Besuche in zeitlicher Reihenfolge, Luftlinie von Ort zu Ort const byId = new Map(cities.map((c) => [c.id, c])); const route = [...visits].sort((a, b) => a.dateFrom.localeCompare(b.dateFrom)).map((v) => byId.get(v.cityId)).filter(Boolean); let km = 0; for (let i = 1; i < route.length; i += 1) if (route[i].id !== route[i - 1].id) km += distanceKm(route[i - 1], route[i]); const days = visits.reduce((s, v) => s + 1 + (v.dateTo ? Math.round((new Date(v.dateTo) - new Date(v.dateFrom)) / 864e5) : 0), 0); return (