2026-05-19 14:44:20 +05:30
2026-04-27 12:48:37 +05:30
2026-05-19 14:44:20 +05:30
2026-05-13 17:17:34 +05:30
2026-05-02 16:44:03 +05:30
2026-04-27 12:48:37 +05:30
2026-04-27 13:08:27 +05:30
2026-04-27 12:48:37 +05:30
2026-04-27 12:48:37 +05:30
2026-05-02 16:44:03 +05:30
2026-05-02 11:03:27 +05:30
2026-04-27 12:48:37 +05:30
2026-04-27 12:48:37 +05:30
2026-04-27 12:48:37 +05:30
2026-04-27 12:48:37 +05:30

KML Map Tool — User Guide

Tauri 2 desktop app for reviewing, correcting and exporting fixed-asset / range-asset annotations produced by the dashcam labelling pipeline. Replaces the legacy FastAPI + Leaflet tools.


Quick start

  1. Login — pick or create a user when the app opens. The username is stamped on every audit-log entry.
  2. Import data — top-left Import… button:
    • Fixed assets (JSON) — point assets like streetlights, signs.
    • Range assets (JSON) — linear assets with start / mid / end (e.g., crash barriers).
    • KML scope polygon — defines which assets are "in scope". Points outside the polygon are hidden by default.
    • OSM roads (GeoJSON) — imported road network for snapping / direction lookups.
    • Per-video metadata (JSON) — vehicle GPS track per video; takes priority over OSM for direction inference. Persists in the SQLite database, so you only pick the file once — every subsequent app start hydrates it automatically. Cleared only by the Clear button on the Per-video metadata row, or by Reset DB.
  3. The map auto-centers on the first imported asset. Pan / zoom triggers viewport-bounded fetches (debounced) to keep the deck.gl rendering snappy.

Map basics

  • Basemaps — Basemap selector at the top. Default: Google Satellite (deep zoom) which uses Google Earth tiles and goes deeper than the regular Google Satellite layer (helpful at z≥22 to see streetlights / road surface).
  • Compare mode — secondary basemap layered side-by-side via the Compare toggle.
  • Layer toggles — Fixed / Range / OSM / Scope / Metadata visibility.
  • Filters panel (left side) — narrow the visible set by Asset type, Side, Video, Asset name. Counts update live with the current viewport.
  • Show out-of-scope / Show deleted — toggles to expose hidden assets for inspection or restore.

Selecting and editing one asset

  • Click an asset to select. The right-side Selected panel shows type, name, row_id, video, side. By default an image popup opens (toggle in Settings).
  • Drag the pin on the map to move the asset. Range assets show S / M / E (start / mid / end) draggable pins.
  • [ / ] keyboard shortcuts step through the visible filtered list.
  • Reset to original — restores the lat/lng captured at first import. Useful if a snap or drag went wrong.
  • Snap to nearest road — shifts the asset to the OSM road centerline or its lane-offset side. Direction priority: metadata polyline → OSM oneway → position-based fallback. Idempotent above 0.5 m drift.
  • Side: Left / Right — toggle without moving the geometry.
  • Rename class… — change asset_name (e.g. fix a mis-classified label). Pulls suggestions from classes.txt.
  • Delete — soft-delete (recoverable via Restore or Undo).
  • Mark as anchor — flag for the bulk Distribute correction flow (see below).

Lasso selection (for bulk operations)

  • Start lasso then pick a shape: circle, rect, or polygon.
  • Polygon mode: click to add vertices, click near the first vertex (gold ring) or double-click to close. Pan / zoom while drawing — vertices stay anchored to the map.
  • ESC cancels at any time and clears the lingering polygon panel.
  • Once selected, you get bulk actions: In-scope / Out-of-scope / Auto / Delete / Restore / Rename / Set Left / Set Right / Reset to original / Clear links.
  • Polygon-only extras: Auto-link L↔R, Auto-link by video, Auto-link nearest (see Pair linking).

Single-video focus mode

When you want to inspect / clean one video's worth of data in isolation:

  • Tap that video's metadata polyline on the map, or
  • Leave exactly one video checked in the Filters panel.

Either path triggers focus mode:

  • Other videos' metadata polylines are hidden — only the focused track renders.
  • OSM roads are spatially filtered to those within ~75 m of the focused track (cheap spatial-hash buffer; recomputed on each switch).
  • Clicking the metadata line again, or unchecking the lone video filter, restores the full view.

Focus mode also unlocks the bulk OSM road tools (multi-select / hide / merge — see OSM road editing). Selection and hidden state are session-scoped: they reset whenever you exit OSM edit mode or change the focused video.


Cross-side / cross-video pair linking

Common situation: one physical asset (e.g., a median streetlight) is captured in two videos (LHS and RHS) and shows up as two near-duplicate points. Pair linking marks them as the same physical thing without deleting either.

  • Auto-link — draw a polygon lasso over the area, then pick the matching strategy in the polygon panel:
    • L↔R: requires assets to have a side label; pairs Left with Right.
    • By video: pairs across the two largest video buckets (use when both videos see the same poles from opposite sides).
    • Nearest: pairs by proximity regardless of side or video. Use when video_name is Not available / NA.
  • Pair max slider (260 m, default 30 m) — the maximum allowed pair distance. Independent from the duplicate epsilon.
  • Manual links override auto-links:
    • Right-click an asset → right-click another — locks them as a pair (pink line). The "anchor" asset gets a status-bar prompt.
    • Right-click two already-linked assets — unlinks them.
  • Click a link line to select it; press Delete to clear that link.
  • Link colors: pink = locked manual link (survives Auto-link re-runs); blue = auto link (replaceable on the next re-run).
  • Unlink an asset directly via Unlink button on the selected panel.
  • After fixing a few wrong pairs manually, click Auto-link again — locked links stay; orphaned partners get re-matched among the remaining unlocked candidates.

Duplicates

  • Find duplicates — scans the currently visible viewport for clusters of points within the chosen ε (metres). Zoom out to widen the search; zoom out fully to scan everywhere.
  • Cross-video only — restrict matches to pairs from different videos.
  • For each cluster you can Delete losers (keep one, delete the rest) or Move losers out-of-scope.

Distribute correction (GPS bias fix)

When the GPS is uniformly off for a whole video / stretch, you don't want to drag every streetlight by hand.

  1. Filter the map to the affected slice (e.g., video=X, name=Streetlight).
  2. Click an asset → Mark as anchor (gold ring appears).
  3. Drag the gold-ringed asset to where it should be. Repeat for as many anchors as you like.
  4. Click Distribute correction in the yellow panel that appears at the top of the actions sidebar.
    • 1 anchor → all visible assets shift by the same Δlat/Δlng (uniform).
    • 2+ anchors → row_id-sorted piecewise linear interpolation between consecutive anchors. Assets outside the firstlast anchor span are not touched.
  5. Undo in Recent actions reverts the entire distribution in one step.

Range assets (start / mid / end) translate as a rigid body — all three vertices shift by the same Δ.


OSM road editing

Modes

  • OSM tools… modal — generate roads for the visible bbox or for a buffer around imported assets (Overpass), import existing GeoJSON, export current roads, prune small road classes.
  • Edit OSM roads button — toggles OSM edit mode. While on, every other layer is dimmed and only OSM roads are interactive.
  • Magnifier button — cursor-following circular lens that zooms +3 levels around the cursor; renders satellite + OSM cyan + dashed-green metadata + red asset dots. Toggle on, hover anywhere, then ESC or click again to exit.
  • Lane offset (m) — controls the parallel offset used by snap-to-road. Range 0.130 m.

Two click models

OSM edit mode behaves differently depending on whether a single video is focused (see Single-video focus mode):

  • Non-focus — click a road to enter the legacy single-road vertex editor (the only road remains visible; vertex pins appear). One road at a time.
  • Focus mode — click a road to toggle multi-select (yellow highlight). All roads stay visible. When the selection narrows to exactly one road, the vertex editor automatically engages on it (Flip / Simplify / Delete this road / Ignore for snap appear inline). Click the road again to drop back to multi-select.

Modifying a road's vertices (single road active)

  • Drag a yellow pin — moves that vertex. Saved immediately.
  • Click a yellow + ghost pin between two vertices — inserts a new vertex at that midpoint.
  • Flip direction — cycles oneway through forward (1) → reverse (-1) → undirected (0).
  • Vertex handles render at z ≥ 14; zoom in if you don't see them.

Deleting vertices

A. Surgical — Shift-click + Del

  1. Shift-click a vertex pin → turns red with . Repeat to mark more.
  2. Press Del → all marked vertices removed in one shot.
  3. Clear marks unselects without deleting. Shift-click a marked vertex to unmark.
  4. The road must keep ≥ 2 vertices.

B. Sweeping — Simplify by tolerance

  1. Simplify (m) slider (0.520 m, default 2 m). Higher = more aggressive.
  2. Click Simplify this road → Douglas-Peucker on the polyline.
  3. Status bar reports before → after vertex counts.

Bulk road tools (focus mode only)

A "Bulk road tools — focus:

  • Click roads to build a selection (yellow + thicker stroke).
  • Right-click any road → instantly hides it (no selection needed).
  • Del → moves all currently-selected roads into the hidden bucket and clears the selection.
  • Hide selected / Clear selection / Restore hidden buttons in the panel mirror those shortcuts.
  • Merge selected (≥ 2 picked) — concatenates connected ways into one. Endpoints within ~8 m of each other are clustered first, so OSM ways with near-but-not-touching endpoints still merge — both ends are snapped to the cluster centroid so the merged geometry has no visible gap. Disconnected clusters become independent merged roads (no false bridging).
  • Merge all visible — same logic over every non-hidden road in the focused area.
  • Branched clusters (any node with > 2 incident ways) are skipped rather than corrupted; the toast tells you how many.

Both hidden and selection sets are session-scoped — cleared on Exit OSM edit mode or focused-video change, never persisted.

Ignore-for-snap (persistent)

Per-road toggle that keeps a road on the map for visual reference but excludes it from snap candidates. Useful for service roads / driveways that the snap should never pick.

  • With one road selected in the vertex editor, the Ignore for snap button appears next to Flip direction.
  • Ignored roads render in grey (vs. the default cyan) and are skipped by both single-asset and bulk snap.
  • Stored as a snap_ignored column on the roads table — survives app restarts. Toggle again to re-enable.

Whole-road actions

  • Delete this road — removes the road (with confirmation).
  • Deselect road — exits the per-road editor (non-focus only; in focus mode, click the road again).

Per-session OSM edit undo

A 3-deep ring buffer scoped to the current OSM edit session captures the last edits so you can revert them without affecting the global asset audit log.

  • ↶ Undo last edit (N) button right under "Exit OSM edit mode" — visible in both focused and non-focused mode. Tooltip names the action it will undo.
  • Covers: flip direction, simplify road, delete vertices, drag vertex, ignore-for-snap toggle, hide road (right-click + Del), restore hidden.
  • Not undoable via this stack: merge selected / merge all visible (they consume source rows; this stack doesn't recreate them), creating new roads, deleting whole roads.
  • Cleared on Exit OSM edit mode.

Snap-to-road

  • Per-asset — Snap to nearest road on the selected panel.
  • Bulk visible — snap every visible fixed asset to the nearest road (50 m max).
  • Snap by video — snap every asset (fixed + range) for a given video.
  • Range assets snap all three vertices independently (not just mid).
  • Direction priority: metadata polyline > OSM oneway > position-based.

Quality dashboard

A <details> panel in the right sidebar that scans the live asset set for likely-bad rows. Click Run scan the first time, Refresh thereafter.

Three checks (cap 500 hits each; totals shown even when capped):

  • Moved far from import — modified rows whose current position is > 50 m from the original (import-time) lat/lng. Flags accidental drags.
  • Off track (far from metadata polyline) — perpendicular distance to the asset's video metadata polyline exceeds the configured threshold (default 30 m, tunable in Settings). Flags assets that were assigned to a video / side they don't actually belong to. Skipped silently for videos with no metadata loaded.
  • Missing sideside IS NULL. Flags assets the labeller didn't tag.

For any non-zero count, View in the row launches a step-through:

  • Zooms the map to z=18 on the first issue.
  • Prev / Next in the same panel walks through the rest, one at a time at z=18.

Post-snap quality check

Every snap entrypoint (single asset, bulk visible, snap by video, snap to road) runs a quality scan immediately after and surfaces a toast:

  • Green — "No quality issues."
  • Red — "N quality issues found (M moved · O off track · P no side)."

The scan reuses your configured off-track threshold. Toast auto-dismisses after 8 s; click × to dismiss sooner.


Centerline override

Some asset classes (expansion joint, vms gantry) belong on the road centerline, not the LHS/RHS offset. Settings → Snap to centerline (instead of offset lane) lets you tick those class names.


Settings ⚙ modal

  • Image popup
    • On / off (when off, marker pins still appear but no image opens on click).
    • Width: S / M / L / XL.
    • Aspect ratio: 16:9 / 4:3 / 3:2 / 1:1.
  • Quality thresholds
    • Off-track distance (m) — perpendicular distance from metadata polyline beyond which an asset is flagged "off track" by the Quality dashboard and post-snap scan. Default 30 m. Reset to 30 m button restores the default. Persisted in localStorage. Lowering below ~25 m starts producing noise on curved / sparse polylines (chord cuts a corner the asset is on).
  • Diagnostics
    • Performance mode — while panning / zooming, render only basemap + asset markers + range paths (hide roads / scope / metadata / links / labels). Diagnostic; leave off for normal use.
  • Snap to centerline names — list of asset_names that should snap to centerline.
  • Image folder (offline) — a local folder used to resolve image_path URLs to disk (HTTPS URLs always pass through unchanged).

Export

The Export data… button writes every non-deleted asset in one of four formats:

  • .json Source JSON — round-trippable. Same shape import_fixed_assets and import_range_assets accept (separate fixed and range arrays). Includes image_path*, side, deleted, etc.
  • .geojson — FeatureCollection. Points for fixed assets, LineStrings for ranges. Properties include image_path*, link_pair_id, link_locked, in_scope, modified.
  • .kml — Placemarks for GIS tools. Includes name, description, geometry.
  • .csv — full row dump for spreadsheets / external pipelines.

OSM roads can be exported separately via OSM tools… → Export current roads (writes GeoJSON with name, highway, oneway preserved).


Keyboard shortcuts

Key Context Action
[ / ] filtered list Step prev / next asset
ESC various Cancel: lasso / link-pick / draw-road / road-edit / image popup / metadata focus / magnifier
Delete / Backspace link selected Unlink the currently-selected link line
Shift + click OSM vertex Mark / unmark a road vertex (red ✕)
Delete / Backspace OSM edit, marked vertices Delete all marked vertices on the active road
Delete / Backspace OSM edit, focus + selection Hide all currently-selected roads (session-only)
Right-click OSM edit, focus Hide that road instantly

Undo / Redo

Two independent stacks:

Asset audit log — every state-changing asset action writes an audit row. The Recent actions panel shows the last N. Undo on any row reverts; Redo replays. Multi-asset operations (bulk delete, distribute, auto-link, snap) revert atomically as a single step.

OSM edit ring buffer — separate 3-deep, in-session undo for road edits, with its own ↶ Undo last edit button in the OSM edit panel. Covers flip / simplify / delete vertices / drag vertex / ignore-for-snap toggle / hide / restore-hidden. Cleared on Exit OSM edit mode. Merge and whole-road creation / deletion are not captured here — be deliberate with those.

Road edits do not appear in the asset audit log; the asset Undo and the OSM Undo never collide.


Performance notes

  • Viewport-bounded fetch: assets only contains rows inside the current map bbox, debounced ~400 ms after pan / zoom.
  • Bulk operations use 500-id chunks to stay safely under SQLite's 999-bind-param ceiling.
  • Auto-link / Distribute over very large viewports may take several seconds at 50k+ rows; prefer narrowing with filters or zoom first.
  • Image prefetching warms the previous / next two thumbnails so [ / ] navigation feels instant.

Troubleshooting

  • No assets visible after import — check Filters panel (especially Videos), Show out-of-scope toggle, and whether a stale KML scope from a previous import is filtering everything out.
  • Streetlights not visible on satellite — switch to Google Satellite (deep zoom) basemap and zoom to z≥22.
  • Snap moves assets to the wrong side — load the metadata polyline (gives true vehicle heading), or fix the OSM road's oneway direction.
  • Re-importing wipes my edits — re-import preserves rows where modified=1 (manual moves) and rows the user deleted; only modified=0 geometry is re-stamped from source. If you need a fresh start, use Reset DB in the Data section first.
  • Per-video metadata didn't auto-load on startup — confirm the Per-video metadata row in the Loaded data section shows a non-zero count. If it does and the polylines aren't drawing, toggle Metadata in the Layers picker. If the count is zero after a previous import, the DB was wiped (Reset DB or manual markers.db delete) — re-pick the JSON.
  • Quality "Off track" flags too many / too few rows — adjust Settings → Quality thresholds → Off-track distance. Default 30 m. Going below ~25 m starts producing noise on curved / sparse polylines (chord cuts a corner the asset is on).
  • Off-track flagged assets that look fine on the map — check that the asset's video_name has metadata loaded. If the metadata is for a different video the chord-distance calc compares against the wrong track.
  • Bulk road tools panel doesn't show — needs OSM edit mode AND a focused video. Tap a metadata polyline on the map (or check exactly one video in Filters) to focus, then press Edit OSM roads.
  • Magnifier shows a black circle — basemap tile fetch hadn't completed when the lens map mounted; move the cursor a couple of pixels to trigger a re-render, or close and re-open the magnifier.
Description
for kml verification and data modification
Readme 2.6 MiB
Languages
TypeScript 56.8%
Rust 41.6%
CSS 1.5%