Add a framework-free HTML/CSS/JS labeling UI: set/session/status
filters, a frame browser, drag-to-draw/move/resize bounding boxes with
a per-set class picker, per-frame status control, and Left/Right frame
navigation. No login - a locally cached username is sent for
attribution only, matching the backend's get-or-create user model.
Backend additions the frontend needed: serve frame images from a
configurable FRAMES_ROOT via a /images static mount, permissive CORS
(internal tool, not publicly exposed), and a GET /sets/{id}/frames
endpoint returning frames joined with their per-set label status
(defaulting missing rows to unlabeled) for the frame browser.
Verified the full call chain end-to-end against a running backend +
static frontend server (set/class creation, frame ingest, image
serving, label CRUD, status updates, CORS preflight) - every field
name the JS reads matches the API responses. 18/18 backend tests
pass. Not yet verified: actual interactive browser use (no browser
tooling available here) - try drag-to-draw/resize locally.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
59 lines
2.7 KiB
Markdown
59 lines
2.7 KiB
Markdown
# Labeling Tool — Frontend
|
|
|
|
UI for the bounding-box labeling tool: pick a label set, browse its frames, draw/
|
|
edit/delete boxes, assign classes, and mark per-frame status.
|
|
|
|
See CLAUDE.md §3.2 for full requirements.
|
|
|
|
**Status:** core labeling UI implemented — plain HTML/CSS/JS, **no framework, no
|
|
build step** (matches "simple frontend — functionality over polish"). Not yet
|
|
implemented: dataset-version browsing/promotion (backend doesn't have it yet
|
|
either — see `labeling/backend/README.md`), multi-box copy/paste, and any kind of
|
|
zoom/pan (assumes the fixed 1280x720 capture resolution fits on screen).
|
|
|
|
## How it works
|
|
|
|
- `index.html` / `style.css` — layout: top bar (set/session/status filters), a
|
|
frame view with an absolutely-positioned box overlay, and a class-picker sidebar.
|
|
- `app.js` — everything else: talks to the backend via `fetch`, renders boxes as
|
|
DOM `div`s scaled to the displayed image size, and handles drawing (drag on
|
|
empty space), moving (drag a box), resizing (drag its corner handle), selecting
|
|
and deleting (click, then Delete/Backspace), and frame navigation (buttons or
|
|
Left/Right arrow keys).
|
|
- No login: a username is captured once via a prompt on first use, cached in
|
|
`localStorage`, and sent as `created_by`/`updated_by` on writes purely for
|
|
attribution (see the backend's multi-user notes).
|
|
- Each sub-class gets a stable color derived from its id (`colorForId` in
|
|
`app.js`), reused consistently across the class picker and the boxes.
|
|
|
|
## Running it
|
|
|
|
This is static files — any static file server works, e.g. Python's stdlib one:
|
|
|
|
```
|
|
cd labeling/frontend
|
|
python3 -m http.server 5500
|
|
```
|
|
|
|
Then open `http://127.0.0.1:5500`. The backend must be running separately (see
|
|
`labeling/backend/README.md`); the frontend defaults to
|
|
`http://127.0.0.1:8000` and the backend allows all CORS origins (it's an
|
|
internal tool, not exposed publicly), so no extra configuration is needed for the
|
|
default setup. To point at a different backend, set
|
|
`window.SPELUNKAI_API_BASE = "http://host:port"` in a `<script>` tag before
|
|
`app.js` loads in `index.html`.
|
|
|
|
You'll also need at least one label set with classes and some ingested frames to
|
|
see anything — create those via the backend's API (`/docs` has interactive
|
|
Swagger UI once it's running) until there's a bulk-ingest script.
|
|
|
|
## Testing
|
|
|
|
No JS test framework/build step is set up (matches the "no build step" choice
|
|
above). Verified so far: the full backend API contract this UI relies on is
|
|
covered by the backend's pytest suite, and the static files + wiring (image
|
|
serving, CORS, correct field names) were checked end-to-end via curl against a
|
|
running backend. **Not yet verified: actual interactive use in a browser**
|
|
(drag-to-draw, drag-to-resize) — try it locally and report anything that feels
|
|
off.
|