Skip to content

v2.10.0

@0Smallcat0 0Smallcat0 tagged this 06 Aug 00:20
A component keeps its text in a shadow root and querySelectorAll does not go
in, so a page built out of them was reported translated while most of it was
untouched. Measured before: two paragraphs inside an open shadow root, and the
badge read "Done — 1 translated" — the one paragraph in the light DOM.

Each root is now collected on its own terms: its own main, its own navigation
and citation skips, its own leaf-most-wins. That is not a shortcut, it is the
right answer — closest() does not cross a shadow boundary either, and a
component's <nav> is its navigation rather than the page's.

The toggle had to learn the same trick, or a translation inserted inside a
component would be one it could never find to remove.

Verified on a page with a light-DOM paragraph, a component containing a <nav>
and two paragraphs, and a second component nested inside the first:
translating gives light 1, shadow 2, nested 1, nav 0, "Done — 4 translated";
toggling off clears all of them. Closed shadow roots stay out of reach, which
is what closed means.

The "does this block already carry its translation" check becomes a
direct-child scan rather than a `:scope >` selector. Same rule, but `:scope`
inside a shadow root is not something to depend on — jsdom answers it wrong,
and a selector that quietly means something else in one tree is a bad
foundation for a skip rule.

Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
Assets 2
Loading