Place transit and shop markers from the vector tile, not Overpass #31
Labels
No labels
agent
agent:ci
agent:done
agent:failed
agent:needs-input
agent:refined
agent:refining
agent:running
agent:skip
autonomous
driven
local
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
jeroen/cartopolis#31
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Problem
The transit and shop marker layers were streamed entirely from the Overpass API.
LAYER_CELL_RADIUS = 3(crates/viberfox/src/systems/gui/data_layers.rs:103)means a 7×7 ring of z14 cells per layer per anchor — 98 live bbox queries to
establish a location, against a service that rate-limits, answers a timeout with
HTTP 200, and needs the 15 s → 30 s → 1 m → 2 m → 4 m backoff ladder in
CellStreamto survive (data_layers.rs:678). Until Overpass answered, nothingstood on the map.
Meanwhile
map_geometryhas already fetched, cached and decoded the vector tilethose markers stand on, and Shortbread puts the same features in it. Measured on
the Groningen z14 fixture (
crates/viberfox/tests/fixtures/groningen_z14.mvt,tile z14/8490/5319):
public_transportholds 25 stops andpoisholds 467features, 55 of them carrying a
shop.docs/notes/vector-tile-unused-layers.md:23records
public_transportas used for "nothing — transit stops come fromOverpass instead".
Approach
Two commits, already on this branch.
crates/geo/src/pois.rs—extract_pois(pois.rs:91) reads a tile pointlayer into classified
TilePois, following the two rulesfurniturealreadyuses for the same layer: classify on key and value (
poiscarries nokind),and own exactly
[0, extent)so a feature buffered into two neighbouring tileslands in one cell with no tolerance to tune.
single_pointandtag_strmovehere from
furnitureso the two readers of the layer share one implementation.Bevy-free, per the crate's rule.
crates/viberfox/src/systems/gui/data_layers.rs— a layer cell is a tile(
LAYER_ZOOM = 14is the tileset's deepest zoom,data_layers.rs:96), soplacement costs a
tile_sourcecache hit and a marker stands the frame its tilelands. It inherits that module's single-flight and byte cache rather than keeping
a parallel one.
Overpass is demoted, not deleted, because the tile carries no identity or
contact detail: no OSM id, no
website, noaddr:street, noref:IFOPT(thekey
transit_livefetches departure boards by). On the same fixture Overpassanswers 65 shops to the tile's 55, 32 of them with a website.
Feature::idlookslike an OSM id and is not one — zero of the 55 intersect the node ids Overpass
returns for the same bbox — so it is neither a join key nor a link. The detail
pass therefore runs on its own stream at
DETAIL_CELL_RADIUS = 1(
data_layers.rs:117) — 9 cells, not 49 — andmerge_details(
data_layers.rs:1799) patches answers onto markers that are already standing,matching on position (
DETAIL_MATCH_M = 10 m,data_layers.rs:127) andcategory. It spawns nothing, may arrive in either order, and may never arrive.
Radius 1 is sized to its two readers: a popup needs the POI inside
handle_poi_click's 500 m (data_layers.rs:1139) and a board needs its stopinside
transit_live::FETCH_RANGE's 800 m(
crates/viberfox/src/systems/nav/transit_live.rs:49), both within a 3×3 ring of~1.4 km cells.
A raster tile source has no point layers to read, so Overpass stays the whole
marker source there — the
from_tilegate is per source kind, not per layer(
data_layers.rs:758), and--shotruns with no manifesttile_urlland onthat path, which keeps the fallback live rather than dead.
Acceptance criteria
request needed to make them appear.
CellStream(data_layers.rs:488).merge_detailsmatches on position and category, spends each detailPOI once, and is order-independent — a marker never waits on it and never
disappears without it.
--shotrun with no manifesttile_url), Overpass still places the markers.described by Overpass cannot land in different categories — covered by
the_two_transit_classifiers_agree(data_layers.rs:2259) andthe_two_shop_classifiers_agree(data_layers.rs:2279).docs/notes/vector-tile-unused-layers.md:23no longer sayspublic_transportis used for nothing, and thepoisrow reflects thesecond reader. Not yet done — this is the one code-side item still open.
cargo check --target wasm32-unknown-unknownpasses. Not yet run — seeVerification.
same colours and pole heights. Not yet run.
Verification
Runnable in the container:
(Both test runs were still in flight when this issue was filed — whoever picks
it up should re-run them rather than take a green here on trust.)
Two checks that cannot run here and are the reason this ticket stays open:
cargo check -p viberfox --target wasm32-unknown-unknown— the container hasno wasm target installed (
rustup target list --installedshows onlyx86_64-unknown-linux-gnuandx86_64-pc-windows-gnu).cargo shots/--shotcannot run. Compare transit and shop markers againstmainover Groningen at a camera altitude belowSURFACE_LAYER_MAX_ALT = 20 km(data_layers.rs:101), on a vectorVIBE_TILE_URL, and again on a raster one to exercise the Overpass fallback.Out of scope
website,addr:streetandref:IFOPT, and the only marker source on a raster basemap.Feature::idis not an OSM id; position +category is the match, and widening
DETAIL_MATCH_Mis not a fix for a missedone.
docs/notes/vector-tile-unused-layers.md(
addresses,place_labels,street_labels_points) — this ticket coverspublic_transportand theshopshare ofpoisonly.transit_live). They still key onref:IFOPTfromthe Overpass detail pass; nothing about how they fetch or render changes here.
Branch:
feat/31-pois-from-vector-tile