diff --git a/packages/lexical-selection/src/__tests__/unit/LexicalSelectionHelpers.test.ts b/packages/lexical-selection/src/__tests__/unit/LexicalSelectionHelpers.test.ts index 48fefebc3db..3d151f31b7d 100644 --- a/packages/lexical-selection/src/__tests__/unit/LexicalSelectionHelpers.test.ts +++ b/packages/lexical-selection/src/__tests__/unit/LexicalSelectionHelpers.test.ts @@ -27,6 +27,7 @@ import { $setSelection, ElementNode, LexicalEditor, + LexicalNode, ParagraphNode, RangeSelection, TextNode, @@ -3075,4 +3076,51 @@ describe('$patchStyleText', () => { expect(color).toEqual(''); }); }); + + test('preserve backward selection when changing style of 2 different text nodes', async () => { + const editor = createTestEditor(); + + const element = document.createElement('div'); + + editor.setRootElement(element); + + editor.update(() => { + const root = $getRoot(); + + const paragraph = $createParagraphNode(); + root.append(paragraph); + + const firstText = $createTextNode('first ').setFormat('bold'); + paragraph.append(firstText); + + const secondText = $createTextNode('second').setFormat('italic'); + paragraph.append(secondText); + + $setAnchorPoint({ + key: secondText.getKey(), + offset: 'sec'.length, + type: 'text', + }); + + $setFocusPoint({ + key: firstText.getKey(), + offset: 'fir'.length, + type: 'text', + }); + + const selection = $getSelection(); + + $patchStyleText(selection!, {'font-size': '11px'}); + + const [newAnchor, newFocus] = selection!.getStartEndPoints()!; + + const newAnchorNode: LexicalNode = newAnchor.getNode(); + expect(newAnchorNode.getTextContent()).toBe('sec'); + expect(newAnchor.offset).toBe('sec'.length); + + const newFocusNode: LexicalNode = newFocus.getNode(); + expect(newFocusNode.getTextContent()).toBe('st '); + expect(newFocus.offset).toBe(0); + }); + }); }); diff --git a/packages/lexical-selection/src/lexical-node.ts b/packages/lexical-selection/src/lexical-node.ts index 8d38092cf8d..492f12e8159 100644 --- a/packages/lexical-selection/src/lexical-node.ts +++ b/packages/lexical-selection/src/lexical-node.ts @@ -427,7 +427,11 @@ export function $patchStyleText( // the entire first node isn't selected, so split it firstNode = firstNode.splitText(startOffset)[1]; startOffset = 0; - anchor.set(firstNode.getKey(), startOffset, 'text'); + if (isBefore) { + anchor.set(firstNode.getKey(), startOffset, 'text'); + } else { + focus.set(firstNode.getKey(), startOffset, 'text'); + } } $patchStyle(firstNode as TextNode, patch);