Commit Graph
62 Commits
Author SHA1 Message Date
Sergey MatyuninandClaude Opus 5.5 c8c470ed57 feat(view): the moon in its phase over the "Follow the Sun" background (#661)
At dawn, dusk and night the environment shows the moon in the top-left
corner of the scene, behind the plan: computed in the card from the home
coordinates and the browser clock (short Meeus series + topocentric
parallax, within 1.4° / 1.8 pp of JPL Horizons), one designer image under
a continuous phase mask with the lit side always on the left (owner
2026-09-29), a feathered terminator, 3°/3 % thresholds and the 2 s fade of
the window rays. Everything but a small gate lives in the lazy
moon-runtime chunk, with its own 30 s ticker. General settings: "Sun"
becomes "Sun and Moon" with one switch, on for new installations
(DEFAULT_CONFIG), off for existing ones.

The initial View graph sat 728 B under its budget: the gate is paid for by
moving fifteen dialog-only strings of General settings into the lazy
settings dictionary (#459) and by one build fingerprint literal instead of
three, so the graph ends 4 B above dev. Golden: two new moon scenes, and
the two General settings help frames show «Sun and Moon»; the WSL artifact
test fixture now models scenes whose first capture awaits acceptance.

Issue: #661
User-Visible: yes
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018qZfe7YS4rqEMKoVeS3GKd
2026-09-30 12:25:46 +03:00
Sergey Matyunin d03a68b88a feat: добавить лестницы между этажами (#663)
Прямые и винтовые лестницы получили отдельную модель, инструменты редактора, безопасную межэтажную навигацию, вычитание из чистой площади и плоское отображение в 2.5D.

Issue: #663
User-Visible: yes
2026-09-26 21:00:43 +03:00
Claude e5ab4659f6 feat: 2.5D stage 6 — public setting, raised tiles, soft sun, theme-free walls (#649)
- settings.volumetric_view (General settings › Display, third switch) replaces
  the alpha entry, the header projection toggle and the phone-menu item; one
  rule for card, sidebar page and kiosk; editors stay Flat; backend accepts
  only a boolean, support package copies it.
- Raised tiles in 2.5D View: no ring, rounded body min(0.275 D, 0.3 h), edge
  0.1 D with the lab filters, ×1.12 size also in layout/collision, lift
  0.075 D, one floor-shadow layer under all markers (theme × floor table),
  frames hugging tile and edge (Alert > Focus > Selected > Hover), forced
  colours without edge and shadow (src/iso-tiles.ts, styles/iso-tiles).
- Soft sun wash instead of projected Flat wedges (src/iso-sun.ts): same gates
  and windows as sun_rays, length from elevation, parallelogram along the sun,
  tone and streaks by floor lightness, sill line.
- Walls take the user's wall colour (top opaque, sides × .77/.68/.60); theme
  rules for walls/openings/labels removed; furniture uses the Flat stroke rule.
- Smokes smoke_iso_tiles/iso_sun/iso_theme_walls/volumetric_setting, 16 new
  mutants, acceptance scenes STAGE6_ACCEPTANCE_SCENARIOS (golden with their
  Linux CI baselines), ACCEPTANCE.md side by side.

Issue: #649
User-Visible: yes
2026-09-25 18:55:14 +03:00
Claude 99e1765d22 feat: режим «Значение + статичный значок» (#588)
Пятый вариант «Отображение»: маркер показывает выбранное значение и при этом
никогда не меняет цвет — ни по состоянию, ни по тревоге, ни по недоступности,
ни под цвет RGB-света, ни по активности.

Четыре прежних режима задавали одним выбором две независимые вещи: что
нарисовано внутри маркера и красится ли он состоянием. Поэтому вместо
сравнения с одним токеном появились два производных предиката рядом с
`normalizeDeviceDisplay` — `displayWantsValue` и `displayIsNeutral`, — и их
спрашивают политика, слой пульсации, внешний бейдж, редактор и три ветки
живого слоя пылесоса.

Две ловушки, из-за которых режим не сводится к одной строке в словаре:

- быстрый путь «статичному маркеру источники не нужны» (`sourceDetails: false`)
  — это основной путь рендера плана, карточки пространства и PDF. Он оставлен
  только режиму без значения: иначе число пропало бы именно на плане и
  осталось в предпросмотре редактора;
- три ветки живого пылесоса сравнивают режим строкой и не читают политику,
  поэтому зелёная политика их не гарантирует. Свидетель держит две
  конфигурации карты: сопоставленная доказывает puck и след, несопоставленная
  — бейдж маршрута (при совпадающей калибровке маршрут `ready`, и бейджа не
  было бы ни в одном режиме). Бейдж проверяется при наполненном буфере
  позиций, иначе его отсутствие объяснялось бы первой веткой.

Потолок initial View перецентрирован 291_700 → 292_400 без изменения общего
бюджета: измеренный факт 291 346 Б оставлял под прежним центром 354 Б —
внутри шумовой полосы метрики.

Эталон: в `device-icon-state-table-{light,dark}` включённая RGB-лампа
переведена в новый режим. Кадры обязаны разойтись; приёмка — отдельным
коммитом класса D с полного линуксового артефакта Validate.

Issue: #588
User-Visible: yes
2026-09-18 13:40:57 +03:00
Sergey Matyunin db4b397e2e feat: выбор граней окон для солнечных лучей (#577)
Issue: #577
User-Visible: yes
2026-09-15 00:16:35 +03:00
Matysh d12488f40d fix: harden presence radar stage one
User-Visible: yes
Issue: #485
2026-09-09 03:52:23 +03:00
Matysh 58f5f18540 feat: add presence radar stage 1
User-Visible: yes
Issue: #485
2026-09-09 03:51:25 +03:00
Sergey Matyunin 96e07b9a02 feat: add configurable summary panel (#437)
Issue: #437
User-Visible: yes
2026-09-08 18:49:36 +03:00
Matysh e2751062dc feat: add per-room temperature thresholds
Issue: #487
User-Visible: yes
2026-09-08 10:44:13 +03:00
Matysh 5ab41a7299 refactor: remove persisted room drafts
Issue: #478
User-Visible: yes
2026-09-06 17:38:47 +03:00
Sergey Matyunin 85702afc0c feat: add contextual Zigbee topology hover
Issue: #54
User-Visible: yes
2026-09-04 14:40:09 +03:00
Codex c38501ef50 feat: route live vacuum overlays to the active map space
User-Visible: yes
Issue: #162
2026-09-03 19:18:13 +03:00
Codex d4dd027b0a build: prepare v1.71.0-beta.2 candidate
Issue: #426
Issue: #427
Issue: #428
Issue: #431
Issue: #432
Issue: #434
User-Visible: no
2026-09-03 15:23:40 +03:00
Matysh 633cb20e59 fix: follow Home Assistant Area marker moves
Issue: #126
User-Visible: yes
2026-08-31 09:45:53 +03:00
Codex 24681ee26f feat: schema manifest, parity allow-list and lifecycle fixtures (#33)
The Voluptuous schema is now dumped into a deterministic committed
manifest (265 leaf paths); a pytest fails on drift. A parity test
compares manifest enums with the exported frontend const lists through
a machine-readable allow-list that also refuses to rot. The field
registry gains passports (allow-extra / lovelace-card), enforcedBy
citations for mechanisms that already shipped, and passports for the
v1.68-v1.69 fields; a completeness test bans dead decisions. Lifecycle
fixtures (oldest / current / future) prove lossless loading, and the
config auditor gains the 0/3/2 exit-code contract.

User-Visible: yes
Issue: #33
2026-08-30 12:42:31 +03:00
Sergey Matyunin 591f8f6ac9 Add selectable value face sources
Issue: #378
User-Visible: yes
2026-08-29 22:20:18 +03:00
Matysh 6c9752f5e6 fix: follow marker placement for room climate
Issue: #317
User-Visible: yes
2026-08-28 16:48:10 +03:00
Matysh 6540474ff5 refactor: centralize i18n language registry
Issue: #62
User-Visible: no
2026-08-28 02:44:26 +03:00
Matysh a66fb7ef53 feat: unify zero-thickness walls
Issue: #306
User-Visible: yes
2026-08-26 13:39:52 +03:00
Matysh b336eee996 feat: stabilize persisted wall segment identity
Issue: #282
User-Visible: yes
2026-08-26 02:20:57 +03:00
Sergey Matyunin 0d91c1e18e fix: make plan visuals grid-scale invariant
Issue: #239
User-Visible: yes
2026-08-22 13:45:26 +03:00
Sergey Matyunin 6063eead10 fix: pin card instances to configured spaces
Issue: #210
User-Visible: yes
2026-08-20 01:38:01 +03:00
Sergey Matyunin 48bcdafab9 feat: redesign device marker faces
Issue: #179
User-Visible: yes
2026-08-19 22:37:25 +03:00
Sergey Matyunin 9f77e3e932 feat: support openings in independent walls
Issue: #132
User-Visible: yes
2026-08-19 01:11:55 +03:00
Sergey Matyunin 8086399aa6 feat: select exact toggle entity
Issue: #178
User-Visible: yes
2026-08-18 21:31:04 +03:00
Sergey Matyunin c9a00b2a37 feat: add open passage openings
Validate / docs (push) Failing after 20s
Validate / provenance (push) Successful in 54s
Validate / hacs (push) Failing after 15s
Validate / process-gate (push) Failing after 50s
Validate / changes (push) Successful in 46s
Validate / hassfest (push) Failing after 14s
Validate / frontend (push) Successful in 5m54s
Validate / backend (push) Failing after 8m1s
Validate / smoke (push) Failing after 4m25s
Validate / golden (push) Failing after 4m26s
Validate / performance_smoke (push) Failing after 8m39s
Issue: #157
User-Visible: yes
2026-08-17 16:45:41 +03:00
Matysh 9e74051652 Release v1.62.0-beta.8 candidate
Issue: #75
Issue: #76
Issue: #95
User-Visible: yes
2026-08-12 19:18:54 +03:00
Matysh c41231a7ba Release v1.62.0-beta.3 candidate 2026-08-12 02:33:54 +03:00
Matysh 554d2e6544 Release v1.62.0-beta.2 candidate 2026-08-11 22:12:08 +03:00
Matysh 446f33ed31 Release v1.62.0-beta.1 candidate 2026-08-11 19:15:21 +03:00
Matysh f8f1718ad2 Release v1.61.0-beta.5 candidate 2026-08-10 18:01:16 +03:00
Matysh cd55a8e897 Release v1.61.0-beta.3 candidate 2026-08-10 09:44:31 +03:00
Matysh fb382bfa11 Release v1.61.0-beta.2 candidate 2026-08-10 00:24:42 +03:00
Matysh 2219700d63 Release v1.60.2
Validate / hacs (push) Failing after 12s
Validate / hassfest (push) Failing after 12s
Validate / frontend (push) Successful in 3m58s
Validate / backend (push) Failing after 8m11s
Validate / smoke (push) Failing after 22m39s
2026-08-08 17:39:25 +03:00
Matysh 2a8302f4d6 v1.60.2-beta.3: unify boundaries and device presentation 2026-08-08 15:46:07 +03:00
Matysh d48d220a8c v1.60.2-beta.1: add persistent physical geometry 2026-08-07 22:02:41 +03:00
Matysh 3028122016 v1.60.0: harden background editing and device state 2026-08-07 13:02:46 +03:00
Matysh 29fb9deb43 v1.60.0-beta.1: unify background editing and device deletion 2026-08-07 11:14:20 +03:00
Matysh e0f6746d7f v1.59.0-rc.1: optimize plans and polish editor feedback
Validate / hacs (push) Failing after 7s
Validate / hassfest (push) Failing after 6s
Validate / frontend (push) Successful in 3m12s
Validate / backend (push) Failing after 8m53s
Validate / smoke (push) Failing after 13m51s
2026-08-06 10:14:52 +03:00
Matysh d2bec266ed v1.59.0-beta.10: unify device visuals and wall refinements
Validate / hacs (push) Failing after 6s
Validate / hassfest (push) Failing after 6s
Validate / frontend (push) Successful in 3m19s
Validate / smoke (push) Failing after 1m12s
Validate / backend (push) Failing after 7m45s
2026-08-05 23:38:01 +03:00
MatyshandCursor a7d956a072 v1.59.0-beta.4: wall thickness + white editor sheet with backdrop
Validate / backend (push) Failing after 9m24s
Validate / smoke (push) Failing after 22m47s
Validate / hassfest (push) Failing after 8s
Validate / hacs (push) Failing after 9s
Validate / frontend (push) Successful in 2m58s
Plan-editor wall thickness (docs/WALL-THICKNESS.md) and keep the white drawing sheet under the grid in editors even when a backdrop image is loaded.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-08-05 12:27:09 +03:00
Cursor AgentandMatysh e6579f1e55 fix(dev): audit P0/P3 — write policy, README diff, validation
- Default admin_only on; config/get returns can_write; card editors follow it
  and fail closed without hass.user (P0-4).
- README EN/RU differentiation vs GUI draw cards / easy-floorplan (P0-3).
- Tighten marker binding, ripple_color, decor extents, space id (P3-4).
- quality_scale test path + deprecated card tap_action note (P3-5).
- Demo hass.user + can_write; unique marker id in upload overwrite test.

Co-authored-by: Matysh <Matysh@users.noreply.github.com>
2026-08-05 08:10:51 +00:00
Matysh 33a960031e CLIMATE TEMP: opt-in room temperature from climate devices (owner 2026-08-03)
Marker dialog grows a checkbox (climate devices only, default OFF):
'Use the device's temperature sensor'. When ticked, the AC/thermostat's
attributes.current_temperature shows as the standard .tval badge next to
the icon (scales with --dev-size, honours show_temperature) and joins the
room average like a thermometer. Unavailable / missing attribute = no
badge, no vote; several climate entities - the first valid one wins;
hidden devices keep voting (room climate stays registry-wide, exactly
like hidden thermometers). Stored as marker.use_climate_temp (bool|None,
validated in MARKER_SCHEMA). Units in test/devices.test.mjs, smoke
demo/smoke_climate_temp.mjs (real checkbox click, 20 + 23.5 -> 21.8 on
the room card), backend test, docs/TESTING.md.
2026-08-03 10:24:51 +03:00
Matysh 75524d9d85 Trail modes + the tip grows glued to the icon
«Показывать путь робота» is a three-way choice now: never / while
cleaning (the default — the line hides the moment the run ends) /
always (the only mode that also shows the faded previous run).
trail_mode rides next to the legacy bool, which still maps in.

The last segment no longer pops in when the next telemetry point
arrives: a rAF sampler drags a tip line's endpoint to the puck's
animated centre every frame, so the path visually pours out strictly
from under the icon. The sampler runs only while pucks exist and stops
itself.
2026-07-31 11:30:17 +03:00
Matysh 40abbccbf0 Live robot vacuums, P1 (docs/VACUUM.md)
The base marker never moves — it is the dock. While the robot cleans, a
round pulsing puck (no badge plate) drives the plan over an affine
transform solved from vacuum-map coordinates: auto-calibration matches
the robot's room list against plan rooms by name, and a three-point
wizard covers integrations without room data. The trail rides the
integration's own path when offered (it predates the card being opened)
and a self-recorded thinned buffer otherwise, lingering ten minutes
after docking. Adapters read the Map Extractor / Tasshack / Valetudo
attribute dialects through one tolerant parser. Display only — no
commands, per the owner's decision.

vacuum.ts is pure logic under 8 new unit tests; the marker schema grew
an optional vacuum block (56 backend tests); smoke_vacuum drives 19
browser asserts including the wizard end to end.
2026-07-31 09:19:56 +03:00
Matysh 3e976562ff tap action: run an automation, a script or a scene — with a confirm guard
Owner's spec (2026-07-29), agreed points: one 'Run' action covering the
three runnable domains of HA (a script is the idiomatic 'action' — with
automations alone people would build trigger-less dummies); the confirm
checkbox guards BOTH toggle and run; covers and valves join the card-wide
toggle so curtains work natively.

- marker.tap_action gains 'run'; marker.tap_target (schema-bounded to
  automation./script./scene. ids); marker.tap_confirm.
- the dialog: a searchable picker over the three domains (friendly name +
  kind), save refuses a run action without a target, a vanished target gets
  a warning hint; the checkbox shows for any actionable tap (explicit or
  effective-default toggle).
- the tap: automation.trigger / script.turn_on / scene.turn_on, started/
  error toasts; with confirm on — our own dialog (not window.confirm, it
  must work on a wall tablet), Esc/backdrop/Cancel = no call. The guard
  covers the controls-toggle path too.
- 'run' is explicit-only by construction: it needs a per-marker target, so
  it can never arrive as a card-wide default.
- covers: the old test pinned 'garage stays shut' — that intent survives as
  COVER_GUARDED_CLASSES (garage/door/gate stay out of the CARD-WIDE toggle;
  an explicit per-device toggle remains the owner's conscious choice).
  Locks/alarms stay forbidden everywhere, run included is not affected —
  we do not inspect automation contents, same trust as HA's own Run button.

Tests: unit resolveTapAction/runServiceFor + cover guard, backend schema
parity picks 'run' automatically + tap_target bounds, smoke_tap_run with 11
assertions (picker, search, save guard, confirm cancel/ok, per-domain
services, missing target). smoke_tap_ctx: 4 options now.
Inventory: 148 / 52 / 43 / 72.
2026-07-30 01:26:30 +03:00
Matysh 694e1e9a3b filtering: hiding is an explicit per-device flag (docs/FILTERING.md)
Agreed with the owner: whether a device is on the plan is a CHECKBOX
('Hide device from plan', every kind incl. virtual), not a runtime
algorithm. The old filter survives only as the SEEDER of those flags.

- marker.hidden is the flag; hidden devices are BUILT (room LQI counts
  them — owner's decision) but rendered only in the device editor with
  'Show hidden' on, ghosted. They cast no glow and no light fill: an
  invisible device casts no visible light (owner's decision).
- seedHiddenBindings(): non-physical devices (excluded domains, Group,
  scene, bridge, myheat children, grouped lamps) in bound areas WITHOUT a
  marker. The editing client materialises them into hidden:true stub
  markers, sets settings.filter_seeded, retires settings.show_all, and
  strips fresh-hidden ids from the red-dot list. Unticking the checkbox
  keeps a hidden:false marker — the seeder never revisits a marked device,
  so the user's decision is final. New non-physical devices hide silently;
  physical ones keep the red-dot flow.
- legacy configs (no filter_seeded) keep the OLD behaviour verbatim —
  runtime filter, shared show_all, hidden-means-gone — until an editing
  client materialises them, so a read-only tablet never sees a half-state.
- 'Show all' is renamed 'Show hidden' and is LOCAL to the tab; the shared
  settings.show_all retires with the runtime filter.
- 'Remove from plan' disappears for auto/entity devices (the checkbox is
  the way); a virtual device's Delete remains a real deletion.
- docs/FILTERING.md is the source of truth for the mechanism.

Tests: seeder/seeded/legacy/lights units (146), smoke_hidden_flag with 12
assertions (68 smokes). Inventory: 146 / 51 / 43 / 68.
2026-07-29 11:35:35 +03:00
Matysh e04ef2f2e6 feat v1.44.0: control-first device card + light-source flag (user feedback)
- device card opens with controllable entities: toggles inline (finger
  targets), cover/lock/climate hand off to HA more-info; metadata and
  manuals moved below; config/diagnostic entities filtered; locks still
  never toggle from a card
- marker.is_light: a smart switch driving dumb fixtures glows in the
  light-sources fill (its own entity or the bound controls) — no
  light-group helper needed
- backend schema; smoke_card_controls.mjs, smoke_glow extended; docs
  same-commit
2026-07-27 12:41:26 +03:00
Matysh 10d4084d17 feat v1.42.1: room-card font sizes — 3 sliders with a live preview
- space.settings.card_font_scale (tier 2 base) + room.settings
  name_scale/label_scale (tier 3), 50-300%, multiplied together and
  stacking with resize-k and kiosk per-screen multipliers
- live sample card in both the space and room dialogs
- backend schema; smoke_font_scales.mjs (9 checks); docs same-commit
2026-07-27 10:12:22 +03:00
Matysh 19e19b5c5f feat v1.42.0: room settings — the third settings tier
- four-tier principle fixed in ARCHITECTURE: global > space > room >
  device, specific overrides general, unset inherits
- room.settings { fill_mode, temp_source, hum_source } with backend
  schema; pure roomFillModeOf + sourceValue (+2 test suites, 114)
- gear on room cards in the Plan editor opens Room settings: rename,
  re-area (current area included in the list), fill override (may opt
  out of glow darkness), explicit temp/hum source with a searchable
  device+entity dropdown; the same section in the creation dialog
- source feeds the room card, tooltip and temp fill; works for rooms
  without an HA area (user-feedback case #1)
- smoke_room_settings.mjs (10 checks); TESTING/CHANGELOG/ARCHITECTURE
  same-commit
2026-07-27 09:58:21 +03:00