@@ -40,4 +40,32 @@ describe('annotator/anchoring/html boundary handling', () => {
4040
4141 assert . equal ( anchoredRange . toString ( ) , 'bar' ) ;
4242 } ) ;
43+
44+ it ( 'describes selection spanning <br> with a space in exact' , ( ) => {
45+ // This is the bug the PR fixes: a selection that crosses a `<br>` used
46+ // to produce `exact: "foobar"` because `textContent` doesn't include a
47+ // character for the `<br>`. With the substitution, the stored quote
48+ // reflects what the user actually sees in the rendered page.
49+ const range = document . createRange ( ) ;
50+ range . selectNodeContents ( container . querySelector ( 'p' ) ) ;
51+
52+ const selectors = html . describe ( container , range ) ;
53+ const quoteSel = selectors . find ( s => s . type === 'TextQuoteSelector' ) ;
54+
55+ assert . equal ( quoteSel . exact , 'foo bar' ) ;
56+ } ) ;
57+
58+ it ( 'anchors a selector with the substituted space back to the original range' , async ( ) => {
59+ const range = document . createRange ( ) ;
60+ range . selectNodeContents ( container . querySelector ( 'p' ) ) ;
61+
62+ const selectors = html . describe ( container , range ) ;
63+ const anchoredRange = await html . anchor ( container , selectors ) ;
64+
65+ // The anchored range covers the same DOM content as the original.
66+ // `toString()` on either Range returns "foobar" because `<br>` has no
67+ // character contribution to `textContent` — the substituted space lives
68+ // only in the stored `exact`.
69+ assert . equal ( anchoredRange . toString ( ) , 'foobar' ) ;
70+ } ) ;
4371} ) ;
0 commit comments