trackers: group cars, trains, planes and wildlife under one spotting tracker with /trackers/spotting landing page and category switcher
All checks were successful
Deploy production / deploy (push) Successful in 1m9s
All checks were successful
Deploy production / deploy (push) Successful in 1m9s
This commit is contained in:
74
src/lib/components/SpottingSwitcher.svelte
Normal file
74
src/lib/components/SpottingSwitcher.svelte
Normal file
@@ -0,0 +1,74 @@
|
||||
<script lang="ts">
|
||||
// Small switcher shown above the cars/trains/planes/wildlife pages (via their +layout),
|
||||
// to hop between the spotting pokedexes or back to /trackers/spotting.
|
||||
import { resolve } from '$app/paths';
|
||||
import { page } from '$app/state';
|
||||
import Binoculars from 'lucide-svelte/icons/binoculars';
|
||||
import TrackerIcon from '#lib/components/TrackerIcon.svelte';
|
||||
import { spottingTrackers } from '#lib/projects.js';
|
||||
|
||||
const active = $derived(
|
||||
spottingTrackers.find(
|
||||
(t) => page.url.pathname === t.href || page.url.pathname.startsWith(`${t.href}/`)
|
||||
)?.name
|
||||
);
|
||||
</script>
|
||||
|
||||
<nav
|
||||
aria-label="Spotting trackers"
|
||||
class="relative mx-auto -mb-6 max-w-6xl px-4 pt-6 sm:-mb-8 sm:px-6 sm:pt-8"
|
||||
>
|
||||
<div class="flex flex-wrap items-center gap-1.5">
|
||||
<a
|
||||
href={resolve('/trackers/spotting')}
|
||||
class="pill flex items-center gap-1.5 px-2.5 py-1.5 text-sm"
|
||||
><Binoculars size={14} aria-hidden="true" class="text-[var(--site-muted)]" />spotting</a
|
||||
>
|
||||
<span class="mx-1 h-4 w-px bg-border" aria-hidden="true"></span>
|
||||
{#each spottingTrackers as t (t.name)}
|
||||
<a
|
||||
href={resolve(t.href as '/')}
|
||||
aria-current={active === t.name ? 'page' : undefined}
|
||||
class="pill flex items-center gap-1.5 py-1 pr-2.5 pl-1 text-sm"
|
||||
><TrackerIcon name={t.name} class="pill-icon size-6" />{t.name}</a
|
||||
>
|
||||
{/each}
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<style>
|
||||
.pill {
|
||||
border: 1px solid color-mix(in oklab, var(--foreground) 9%, transparent);
|
||||
border-radius: 999px;
|
||||
background: color-mix(in oklab, var(--foreground) 2%, transparent);
|
||||
color: var(--foreground);
|
||||
outline: none;
|
||||
transition:
|
||||
transform 160ms cubic-bezier(0.2, 0.8, 0.2, 1),
|
||||
background-color 160ms ease,
|
||||
border-color 160ms ease;
|
||||
}
|
||||
.pill:hover {
|
||||
background: color-mix(in oklab, var(--foreground) 6%, transparent);
|
||||
border-color: color-mix(in oklab, var(--foreground) 22%, transparent);
|
||||
transform: translateY(-1px);
|
||||
}
|
||||
.pill:focus-visible {
|
||||
outline: 2px solid var(--foreground);
|
||||
outline-offset: 2px;
|
||||
}
|
||||
.pill[aria-current='page'] {
|
||||
background: color-mix(in oklab, var(--foreground) 10%, transparent);
|
||||
border-color: color-mix(in oklab, var(--foreground) 35%, transparent);
|
||||
font-weight: 500;
|
||||
}
|
||||
.pill :global(.pill-icon) {
|
||||
border-radius: 999px;
|
||||
}
|
||||
@media (prefers-reduced-motion: reduce) {
|
||||
.pill,
|
||||
.pill:hover {
|
||||
transform: none;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
Reference in New Issue
Block a user