From f1610dae3ddc7068298e7de5cf5763c5976c3f44 Mon Sep 17 00:00:00 2001 From: Florian Duros Date: Wed, 26 Oct 2022 14:53:44 +0200 Subject: [PATCH] Fix selection --- .../components/PlainTextComposer.tsx | 2 ++ .../components/WysiwygComposer.tsx | 5 +++-- .../hooks/useSetCursorPosition.ts | 6 +++--- .../rooms/wysiwyg_composer/hooks/utils.ts | 6 +++--- .../EditWysiwygComposer-test.tsx | 2 ++ .../SendWysiwygComposer-test.tsx | 3 +++ .../components/WysiwygComposer-test.tsx | 18 +++++++++++++++--- 7 files changed, 31 insertions(+), 11 deletions(-) diff --git a/src/components/views/rooms/wysiwyg_composer/components/PlainTextComposer.tsx b/src/components/views/rooms/wysiwyg_composer/components/PlainTextComposer.tsx index f23c1725c2..64c940c2fd 100644 --- a/src/components/views/rooms/wysiwyg_composer/components/PlainTextComposer.tsx +++ b/src/components/views/rooms/wysiwyg_composer/components/PlainTextComposer.tsx @@ -19,6 +19,7 @@ import React, { MutableRefObject, ReactNode } from 'react'; import { useComposerFunctions } from '../hooks/useComposerFunctions'; import { usePlainTextInitialization } from '../hooks/usePlainTextInitialization'; import { usePlainTextListeners } from '../hooks/usePlainTextListeners'; +import { useSetCursorPosition } from '../hooks/useSetCursorPosition'; import { ComposerFunctions } from '../types'; import { Editor } from "./Editor"; @@ -40,6 +41,7 @@ export function PlainTextComposer({ const { ref, onInput, onPaste, onKeyDown } = usePlainTextListeners(onChange, onSend); const composerFunctions = useComposerFunctions(ref); usePlainTextInitialization(initialContent, ref); + useSetCursorPosition(disabled, ref); return
diff --git a/src/components/views/rooms/wysiwyg_composer/components/WysiwygComposer.tsx b/src/components/views/rooms/wysiwyg_composer/components/WysiwygComposer.tsx index dce20f6815..73125a910a 100644 --- a/src/components/views/rooms/wysiwyg_composer/components/WysiwygComposer.tsx +++ b/src/components/views/rooms/wysiwyg_composer/components/WysiwygComposer.tsx @@ -48,12 +48,13 @@ export const WysiwygComposer = memo(function WysiwygComposer( } }, [onChange, content, disabled]); - useSetCursorPosition(isWysiwygReady, ref); + const isReady = isWysiwygReady && !disabled; + useSetCursorPosition(!isReady, ref); return (
- + { children?.(ref, wysiwyg) }
); diff --git a/src/components/views/rooms/wysiwyg_composer/hooks/useSetCursorPosition.ts b/src/components/views/rooms/wysiwyg_composer/hooks/useSetCursorPosition.ts index 92555f563f..ef14d44255 100644 --- a/src/components/views/rooms/wysiwyg_composer/hooks/useSetCursorPosition.ts +++ b/src/components/views/rooms/wysiwyg_composer/hooks/useSetCursorPosition.ts @@ -18,10 +18,10 @@ import { RefObject, useEffect } from "react"; import { setCursorPositionAtTheEnd } from "./utils"; -export function useSetCursorPosition(isComposerReady: boolean, ref: RefObject) { +export function useSetCursorPosition(disabled: boolean, ref: RefObject) { useEffect(() => { - if (ref.current && isComposerReady) { + if (ref.current && !disabled) { setCursorPositionAtTheEnd(ref.current); } - }, [ref, isComposerReady]); + }, [ref, disabled]); } diff --git a/src/components/views/rooms/wysiwyg_composer/hooks/utils.ts b/src/components/views/rooms/wysiwyg_composer/hooks/utils.ts index 0ae3d7a880..bfaf526f72 100644 --- a/src/components/views/rooms/wysiwyg_composer/hooks/utils.ts +++ b/src/components/views/rooms/wysiwyg_composer/hooks/utils.ts @@ -46,9 +46,9 @@ export function setCursorPositionAtTheEnd(element: HTMLElement) { const range = document.createRange(); range.selectNodeContents(element); range.collapse(false); - const sel = document.getSelection(); - sel.removeAllRanges(); - sel.addRange(range); + const selection = document.getSelection(); + selection.removeAllRanges(); + selection.addRange(range); element.focus(); } diff --git a/test/components/views/rooms/wysiwyg_composer/EditWysiwygComposer-test.tsx b/test/components/views/rooms/wysiwyg_composer/EditWysiwygComposer-test.tsx index 051d25b435..00d6a43f97 100644 --- a/test/components/views/rooms/wysiwyg_composer/EditWysiwygComposer-test.tsx +++ b/test/components/views/rooms/wysiwyg_composer/EditWysiwygComposer-test.tsx @@ -186,6 +186,7 @@ describe('EditWysiwygComposer', () => { it('Should focus when receiving an Action.FocusEditMessageComposer action', async () => { // Given we don't have focus customRender(); + screen.getByLabelText('Bold').focus(); expect(screen.getByRole('textbox')).not.toHaveFocus(); // When we send the right action @@ -201,6 +202,7 @@ describe('EditWysiwygComposer', () => { it('Should not focus when disabled', async () => { // Given we don't have focus and we are disabled customRender(true); + screen.getByLabelText('Bold').focus(); expect(screen.getByRole('textbox')).not.toHaveFocus(); // When we send an action that would cause us to get focus diff --git a/test/components/views/rooms/wysiwyg_composer/SendWysiwygComposer-test.tsx b/test/components/views/rooms/wysiwyg_composer/SendWysiwygComposer-test.tsx index c97e5e9086..573ae451be 100644 --- a/test/components/views/rooms/wysiwyg_composer/SendWysiwygComposer-test.tsx +++ b/test/components/views/rooms/wysiwyg_composer/SendWysiwygComposer-test.tsx @@ -81,6 +81,7 @@ describe('SendWysiwygComposer', () => { it('Should focus when receiving an Action.FocusSendMessageComposer action', async () => { // Given we don't have focus customRender(jest.fn(), jest.fn()); + screen.getByLabelText('Bold').focus(); expect(screen.getByRole('textbox')).not.toHaveFocus(); // When we send the right action @@ -96,6 +97,7 @@ describe('SendWysiwygComposer', () => { it('Should focus and clear when receiving an Action.ClearAndFocusSendMessageComposer', async () => { // Given we don't have focus customRender(jest.fn(), jest.fn()); + screen.getByLabelText('Bold').focus(); expect(screen.getByRole('textbox')).not.toHaveFocus(); // When we send the right action @@ -112,6 +114,7 @@ describe('SendWysiwygComposer', () => { it('Should focus when receiving a reply_to_event action', async () => { // Given we don't have focus customRender(jest.fn(), jest.fn()); + screen.getByLabelText('Bold').focus(); expect(screen.getByRole('textbox')).not.toHaveFocus(); // When we send the right action diff --git a/test/components/views/rooms/wysiwyg_composer/components/WysiwygComposer-test.tsx b/test/components/views/rooms/wysiwyg_composer/components/WysiwygComposer-test.tsx index e7e21ca839..cb9c37071c 100644 --- a/test/components/views/rooms/wysiwyg_composer/components/WysiwygComposer-test.tsx +++ b/test/components/views/rooms/wysiwyg_composer/components/WysiwygComposer-test.tsx @@ -73,11 +73,15 @@ describe('WysiwygComposer', () => { const defaultRoomContext: IRoomState = getRoomContext(mockRoom, {}); - const customRender = (onChange = (_content: string) => void 0, onSend = () => void 0, disabled = false) => { + const customRender = ( + onChange = (_content: string) => void 0, + onSend = () => void 0, + disabled = false, + initialContent?: string) => { return render( - + , ); @@ -91,6 +95,14 @@ describe('WysiwygComposer', () => { expect(screen.getByRole('textbox')).toHaveAttribute('contentEditable', "false"); }); + it('Should have focus', () => { + // When + customRender(jest.fn(), jest.fn(), false); + + // Then + expect(screen.getByRole('textbox')).toHaveFocus(); + }); + it('Should call onChange handler', (done) => { const html = 'html'; customRender((content) => { @@ -104,7 +116,7 @@ describe('WysiwygComposer', () => { const onSend = jest.fn(); customRender(jest.fn(), onSend); - // When we tell its inputEventProcesser that the user pressed Enter + // When we tell its inputEventProcessor that the user pressed Enter const event = new InputEvent("insertParagraph", { inputType: "insertParagraph" }); const wysiwyg = { actions: { clear: () => {} } } as Wysiwyg; inputEventProcessor(event, wysiwyg);