mirror of
https://github.com/bilawalsidhu/gods-eye-view.git
synced 2026-11-12 14:22:21 +00:00
feat(street-level): KartaView as a third, keyless imagery provider
Coverage lines from KartaView's z13-14 JSON tiles (OSM ways with photos, chained end to start), the photo nearest a clicked line, cones along its sequence, and a viewer for flat photos and 360° panoramas (a small WebGL equirectangular renderer, no new dependency) with ‹ › along the sequence. Mapillary's camera-driven line coverage and sequence cones move to the provider-neutral core (lineCoverage.js, sequenceCones.js) with the tile fetch, zoom ladder, colours and pick prefixes injected; Mapillary keeps thin wrappers and its tests pass unchanged. KartaView quirks handled: api.kartaview.org (the documented api.openstreetcam.org serves empty tiles), photo URLs that name storage1 for photos stored elsewhere, and a photo API that answers 429 to more than about three requests at once (two in flight, retried with backoff). Co-Authored-By: Claude Opus 5.5 <[email protected]>
This commit is contained in:
1 parent
9beadbda63
commit
cb01014e36
33 files changed
+4046
-1196
No files matched your search
@@ -22,6 +22,7 @@ export function filtersOf(provider) {
|
||||
* @property {boolean} [defaultOn] Default true.
|
||||
* @property {{kind: 'view-cone', color: string}} [marker] Default: GEV's pin.
|
||||
* @property {Array<'pano'|'since'>} [filters] Filters it honours (default both).
|
||||
* @property {{noun: string, action: string}} [coverageLabel] How the panel counts its lines and says what a click does (default: sequences, "click a line for its photos").
|
||||
* @property {(context: ProviderContext) => ProviderInstance} create
|
||||
*
|
||||
* @typedef {object} ProviderContext Handed to `create()` once by the core.
|
||||
@@ -32,7 +33,7 @@ export function filtersOf(provider) {
|
||||
* @property {GroundCaster|null} groundCaster Bare-earth heights for terrain mode (groundCast.js); null without a terrain service.
|
||||
* @property {{meshAt: (lon: number, lat: number) => number|undefined, request: (points: Array<[number, number]>) => void, onSampled: (listener: (cells: Array<[number, number]>) => void) => () => void}|null} meshSampler Sampled Google 3D surface heights (meshSampler.js); pass `meshAt` to `castLine`.
|
||||
* @property {() => void} notify Ask the core to publish a new UI snapshot.
|
||||
* @property {{openImage: (imageId: string) => Promise<void>, reportError: (message: string|null) => void}} actions
|
||||
* @property {{openImage: (imageId: string) => Promise<void>, openNearest: (point: {lon: number, lat: number}) => Promise<boolean>, reportError: (message: string|null) => void}} actions
|
||||
*
|
||||
* @typedef {object} ProviderInstance
|
||||
* @property {() => Promise<{configured: boolean}>} status
|
||||
@@ -44,7 +45,7 @@ export function filtersOf(provider) {
|
||||
* @property {(filter: {pano: string, sinceMs: number|null}) => void} setFilter The filter changed: redraw (reading `getFilter()`).
|
||||
* @property {(mode: 'draped'|'terrain') => void} [setSurface] Redraw coverage and cones for the new surface mode.
|
||||
* @property {() => {count: number, zoom: number|null, kind: string|null, loading: boolean, hint: string, error: string|null, keyRequired: boolean}} coverageStats
|
||||
* @property {(pickId: string) => boolean} handlePick The id carries the provider's own prefix.
|
||||
* @property {(pickId: string, click?: {groundPoint: () => {lon: number, lat: number}|null}) => boolean} handlePick The id carries the provider's own prefix; `groundPoint` is where the click met the ground.
|
||||
* @property {(sequenceId: string) => Promise<void>} [selectSequence]
|
||||
* @property {() => void} [clearSequence]
|
||||
* @property {() => {selectedId: string|null, images: number, loading: boolean}} [sequenceStats]
|
||||
|
||||
Reference in new issue
Block a user