The minimum primitives the closed architecture needs. No MorfoRuntime yet,
no provider migration — just the two operations that everything else will
compose on top of.
adom (only writer of mutable attrs):
- types StructuralChange + DomAttrValue
- applyChange(change) writes attrs (string/number → setAttribute, true →
presence flag, false/null/undefined → removeAttribute)
- removeAttrs(target, names) targeted cleanup
- ActiveDom exposes apply() + remove() — same surface every consumer uses
sema (perceptual signal channel):
- new SemanticSignal type (runtime payload distinct from declaration-time
SemaEvent): { target, name, intent?, family?, hold? }
- SemanticEngine accepts dom by construction (DI; not imported hard from
$uix/adom inside sema)
- new emit(signal) async method with the agreed lifecycle:
1. write data-event* via dom.apply
2. await one rAF (CSS gets a frame to observe)
3. resolve Promise (caller can dom.apply structural change)
4. hold N frames (default 1, configurable per signal)
5. clear data-event* via dom.remove
- legacy publish() flow untouched for backward compatibility
Tests: 12/12 green; full adom+sema+lib/dom suite 50/50 green;
svelte-check delta: -12 errors (no regressions in touched files).