Bring the Photos/People/Places UI that main added (in the legacy vanilla frontend) into the SvelteKit rewrite, wired to the now-merged backend (/api/photos/geo, /api/people/*). Photos page (routes/photos/+page.svelte): - Moments | Places | People sub-tabs (the People tab appears only when the faces feature is enabled, via a /api/people capability probe), mirroring the vanilla photos sub-nav. - Square ↔ justified layout toggle. Justified uses a Flickr-style row-packer over the width/height the photos list endpoint returns (PhotoItem), falling back to 1:1 when dimensions are missing. New components: - PhotoLightbox.svelte — the lightbox extracted from the photos page into a reusable component (items + bindable index, onDelete callback) so the grid, People and Places all share one implementation (no duplication). - PlacesMap.svelte — MapLibre GL map with server-clustered markers; the vector basemap is optional (probed at /basemaps/basemap.pmtiles, themed fallback otherwise). Cluster click zooms in or opens the lightbox. - PeopleView.svelte — identity-cluster grid → per-person photo grid, with rename via the in-app prompt dialog. Supporting: - api/endpoints/people.ts (+ peopleEnabled probe); photos.ts gains fetchPhotosGeo + GeoCluster + PhotoItem; fileThumbnailUrl takes a size. - lib/vendor/maplibre.ts — minimal typings + lazy loader for the vendored MapLibre GL + pmtiles globals (kept any-free for ESLint). - utils/media.ts — shared isVideo / photoTimestamp / minimalPhotoItem. - Vendored maplibre-gl 5.24.0 + pmtiles 4.4.1 under static/vendors and an optional static/basemaps dir, matching the PR's vendored-asset pattern. - New photos.tab_*/layout_*/map_* + people.* keys in en.json. Verified: npm run check (svelte-check + eslint + stylelint + prettier), npm run test:unit (36 pass), and npm run build all green.
1.6 KiB
Places basemap (optional)
The Places photo map renders your geotagged photos as clusters. It works out of the box without a basemap (clusters on a plain background). To get a real street/terrain backdrop, drop a self-hosted vector basemap here — no third-party tile API, fully offline.
How it works (Approach "A")
OxiCloud already serves static/ through tower-http's ServeDir, which
honours HTTP Range requests. A PMTiles
basemap is a single file read directly by the browser via Range — so the
basemap is just a static file the app already knows how to serve. No extra
backend, no tile server, no API keys.
Enabling it
- Get a Protomaps
.pmtilesbasemap (vector, ODbL OpenStreetMap data):- Whole planet z0–15 (~120 GB) or a smaller global
z0-6(~60 MB), or - A regional extract (recommended — only the area you need, a few MB):
See https://docs.protomaps.com/basemaps/downloads
# one-time, downloads only your bounding box from the remote planet pmtiles extract https://build.protomaps.com/<DATE>.pmtiles basemap.pmtiles \ --bbox=<west>,<south>,<east>,<north>
- Whole planet z0–15 (~120 GB) or a smaller global
- Place it here as
static/basemaps/basemap.pmtiles(this path is git-ignored on purpose — see.gitignore). - Reload the Places view. The map will pick it up automatically.
The bundled style is label-light (water / land / roads / buildings, no text) so it needs no glyph/sprite assets. Attribution “© OpenStreetMap” (ODbL) is shown automatically when a basemap is present.