Rotator classification: reject element-bearing containers, non-destructive runtime
A progressively-growing feed panel (rows injected after cap tagging) passed the rotator leaf guard - which only rejected containers with CAPPED children - and the rotator runtime's textContent writes then flattened 51 statically-emitted descendants to one text node. Three layers: emission drops rotators whose IR target has element children; the capture leaf guard rejects any element child (capped or not); the DittoMotion runtime saves/restores cloned child nodes via replaceChildren so even a misclassified rotator can't destroy structure. 425 tests pass (6 new), typecheck clean. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Fable 5
parent
ec4e4397cc
commit
f16c3aa4e8
@@ -482,8 +482,11 @@ export async function captureMotion(page: Page, opts?: { observeMs?: number; log
|
||||
const cap = el && (el as Element).getAttribute?.("data-cid-cap");
|
||||
if (!cap) continue;
|
||||
const elem = el as Element;
|
||||
// only track small text-bearing elements (a rotating word/phrase, not a big block)
|
||||
if (elem.querySelector("[data-cid-cap]")) continue; // has element children → not a leaf word
|
||||
// only track small text-bearing elements (a rotating word/phrase, not a big block).
|
||||
// Reject ANY element child, capped or not: rows injected at runtime (after cid-cap
|
||||
// tagging, so uncapped) would otherwise defeat a capped-only check and let a
|
||||
// multi-element panel pass as a "leaf word".
|
||||
if (elem.firstElementChild) continue; // has element children → not a leaf word
|
||||
const txt = norm(elem.textContent || "");
|
||||
if (!txt || txt.length > 80) continue;
|
||||
const e = changes.get(cap) ?? { texts: [], times: [] };
|
||||
|
||||
Reference in New Issue
Block a user