From a6dc9d020a6505dd44340cc31514eb35ff700058 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Ska=C5=82ka?= Date: Mon, 15 Apr 2024 16:59:43 +0200 Subject: [PATCH 1/5] Fix selection prop useEffect --- src/MarkdownTextInput.web.tsx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/MarkdownTextInput.web.tsx b/src/MarkdownTextInput.web.tsx index 891b6b9c..48179099 100644 --- a/src/MarkdownTextInput.web.tsx +++ b/src/MarkdownTextInput.web.tsx @@ -575,7 +575,9 @@ const MarkdownTextInput = React.forwardRef( } CursorUtils.setCursorPosition(divRef.current, selection.start, selection.end); updateSelection(null, {start: selection.start, end: selection.end || selection.start}); - }, [selection, updateSelection]); + // we need to update the selection only when the selection prop changes, so it won't interfere with updating cursor position when typing + // eslint-disable-next-line react-hooks/exhaustive-deps + }, [selection]); useEffect(() => { if (history.current?.history.length !== 0) { From 0d08dc1bdbc18376dc342d8408432f628d1b316b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Ska=C5=82ka?= Date: Wed, 17 Apr 2024 11:57:30 +0200 Subject: [PATCH 2/5] Fix cursor position event order on pasting --- src/MarkdownTextInput.web.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/MarkdownTextInput.web.tsx b/src/MarkdownTextInput.web.tsx index 48179099..9965143e 100644 --- a/src/MarkdownTextInput.web.tsx +++ b/src/MarkdownTextInput.web.tsx @@ -573,8 +573,8 @@ const MarkdownTextInput = React.forwardRef( if (!divRef.current || !selection || (contentSelection.current && selection.start === contentSelection.current.start && selection.end === contentSelection.current.end)) { return; } - CursorUtils.setCursorPosition(divRef.current, selection.start, selection.end); updateSelection(null, {start: selection.start, end: selection.end || selection.start}); + CursorUtils.setCursorPosition(divRef.current, selection.start, selection.end); // we need to update the selection only when the selection prop changes, so it won't interfere with updating cursor position when typing // eslint-disable-next-line react-hooks/exhaustive-deps }, [selection]); From e6c6fb0fd3c8aab00bb2a0747f005f62f1303957 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Ska=C5=82ka?= Date: Fri, 19 Apr 2024 12:23:25 +0200 Subject: [PATCH 3/5] Fix cursor position setting on newlines --- src/web/cursorUtils.ts | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/src/web/cursorUtils.ts b/src/web/cursorUtils.ts index af0b97ae..73f979c2 100644 --- a/src/web/cursorUtils.ts +++ b/src/web/cursorUtils.ts @@ -60,21 +60,18 @@ function setCursorPosition(target: HTMLElement, start: number, end: number | nul if (!startNode && start >= charCount && (start <= nextCharCount || (start === nextCharCount && i < n - 1))) { startNode = textNode; - // There are 4(/5) cases to consider here: + // There are 4 cases to consider here: // 1. Caret in front of a character, when pressing enter // 2. Caret at the end of a line (not last one) - // 3a. Caret at the end of whole input, when pressing enter - On firefox - // 3b. Caret at the end of whole input, when pressing enter - On other browsers + // 3. Caret at the end of whole input, when pressing enter - On // 4. All other placements if (prevChar === '\n' && prevTextLength !== undefined && prevTextLength < textCharacters.length) { if (nextChar !== '\n') { range.setStart(textNodes[i + 1] as Node, 0); } else if (i !== textNodes.length - 1) { range.setStart(textNodes[i] as Node, 1); - } else if (BrowserUtils.isFirefox) { - range.setStart(textNode, start - charCount); } else { - range.setStart(textNodes[i] as Node, 2); + range.setStart(textNode, start - charCount); } } else { range.setStart(textNode, start - charCount); From 451302ddbeb0993b16e8889bc6e3cf6c82eab211 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Ska=C5=82ka?= Date: Fri, 19 Apr 2024 12:43:22 +0200 Subject: [PATCH 4/5] Remove ignore eslint comment --- src/MarkdownTextInput.web.tsx | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/src/MarkdownTextInput.web.tsx b/src/MarkdownTextInput.web.tsx index bcde9e1c..4ded68c5 100644 --- a/src/MarkdownTextInput.web.tsx +++ b/src/MarkdownTextInput.web.tsx @@ -580,11 +580,12 @@ const MarkdownTextInput = React.forwardRef( if (!divRef.current || !selection || (contentSelection.current && selection.start === contentSelection.current.start && selection.end === contentSelection.current.end)) { return; } - updateSelection(null, {start: selection.start, end: selection.end || selection.start}); - CursorUtils.setCursorPosition(divRef.current, selection.start, selection.end); - // we need to update the selection only when the selection prop changes, so it won't interfere with updating cursor position when typing - // eslint-disable-next-line react-hooks/exhaustive-deps - }, [selection]); + + const newSelection: Selection = {start: selection.start, end: selection.end ?? selection.start}; + contentSelection.current = newSelection; + updateRefSelectionVariables(newSelection); + CursorUtils.setCursorPosition(divRef.current, newSelection.start, newSelection.end); + }, [selection, updateRefSelectionVariables]); useEffect(() => { if (history.current?.history.length !== 0) { From d8231f7ad03ea25841ea2bb2dfb098b69f5de696 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Ska=C5=82ka?= Date: Tue, 23 Apr 2024 14:01:19 +0200 Subject: [PATCH 5/5] Fix typo --- src/web/cursorUtils.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/web/cursorUtils.ts b/src/web/cursorUtils.ts index 73f979c2..98c50ca0 100644 --- a/src/web/cursorUtils.ts +++ b/src/web/cursorUtils.ts @@ -63,7 +63,7 @@ function setCursorPosition(target: HTMLElement, start: number, end: number | nul // There are 4 cases to consider here: // 1. Caret in front of a character, when pressing enter // 2. Caret at the end of a line (not last one) - // 3. Caret at the end of whole input, when pressing enter - On + // 3. Caret at the end of whole input, when pressing enter // 4. All other placements if (prevChar === '\n' && prevTextLength !== undefined && prevTextLength < textCharacters.length) { if (nextChar !== '\n') {