- Draw mode shows the current segment length near the cursor (metres or feet+inches
per the HA unit system). New pure helpers segmentCm/formatLength (unit-tested).
- New per-space 'Scale (grid cell size)' field (space.cell_cm, default 5 cm) so each
plan has its own real-world dimensions. i18n en/ru, .measurelabel style. +3 tests (61).
- comfort bounds: parseFloat+isFinite guard (empty input collapsed a bound to 0
and the auto-swap made 'comfort from 25' behave as 0-25 → green at 24°)
- avg room temperature in the room tooltip (what the temp fill actually uses)
- hover darkens the current fill instead of recoloring blue; grey when unfilled
- fill mode as a radio group with short labels; compact inline bounds inputs
- space dialog widened to 500px; TESTING.md updated in the same commit
- fill_mode 'temp': below comfort → #4fc3f7, inside → #66d17a, above → #ffd45c;
bounds default 20-25°C, editable in the space dialog (visible only for this
mode), swapped bounds tolerated; rooms without a temperature reading unfilled
- areaTemp(): average of the area devices' temperatures
- tests: roomFillColor temp bands + bounds, spaceDisplayOf defaults, areaTemp,
backend schema (fill_mode temp + temp_min/temp_max); smoke_temp_fill.mjs
- TESTING.md updated in the same commit (policy)
- space dialog 'Display' section: room borders/names toggles, color+opacity,
fill by zigbee signal or lights (tri-state: on/off/no-lights)
- draggable room name labels persisted as layout rl_<roomId>
- 'no image, outline by hand' space source with canvas orientation; image
optional now; switching an existing space to draw detaches its plan
- demo/ synthetic-home harness lives in the repo (serve.mjs + smokes + icons gen)
- docs/TESTING.md checklist (same-commit update policy); self-run found and
fixed: plan_url not detached on image->draw, _stateClass crash on states
without entity_id; perf measured (162 devices ~14ms build)
- backend: SPACE_DISPLAY_SCHEMA validation (+test)
- 12-test buildDevices suite on a fake hass (curation, markers, groups, dedup,
icon rules, lock override, device_class fallback, primary/LQI/temp)
- t() substitutes all placeholder occurrences (pure subst() + regression test)
- _saveConfigNow resyncs config on rev conflict before rethrowing
- pointercancel clears the long-press timer (phantom info card on touch)
- repairs.py: plan-file check re-runs after every config save
- test build compiles devices.ts/types.ts; fix-test-build.mjs adds .js to ESM imports
- floors wizard: spaces from the HA floor registry, step-by-step with mandatory
plan upload per floor, skip support, auto-markup after the last one
- icon rules as data (settings.icon_rules) + in-card editor with live test,
invalid-regex guard, bilingual defaults, device_class fallback chain
- tap_action (card) + per-device override; security model: card-wide toggle only
for light/switch/fan/humidifier, explicit override for covers, never lock/alarm;
600ms long-press always opens the info card
- i18n dictionaries → src/i18n/*.json (+parity tests); light-theme badge fixes
- frontend tests 15→28