feat(editor): auto-detect text direction for RTL support (#2389)

This commit is contained in:
Philip Okugbe
2026-08-12 23:48:03 +01:00
committed by GitHub
parent db3ff54da1
commit ea59912c7e
11 changed files with 19 additions and 2 deletions
@@ -255,6 +255,7 @@ export default function ChatInput({
}, },
content: "", content: "",
editable: true, editable: true,
textDirection: "auto",
immediatelyRender: true, immediatelyRender: true,
shouldRerenderOnTransaction: false, shouldRerenderOnTransaction: false,
autofocus: autofocus ? "end" : false, autofocus: autofocus ? "end" : false,
@@ -41,6 +41,7 @@ export default function ReadonlyTemplateEditor({
<EditorProvider <EditorProvider
editable={false} editable={false}
immediatelyRender={true} immediatelyRender={true}
textDirection="auto"
extensions={extensions} extensions={extensions}
content={template.content} content={template.content}
/> />
@@ -87,6 +87,7 @@ export default function TemplateEditor() {
const editor = useEditor({ const editor = useEditor({
extensions: templateExtensions, extensions: templateExtensions,
content: "", content: "",
textDirection: "auto",
editorProps: { editorProps: {
scrollThreshold: 80, scrollThreshold: 80,
scrollMargin: 80, scrollMargin: 80,
@@ -103,6 +103,7 @@ const CommentEditor = forwardRef(
}, },
content: defaultContent, content: defaultContent,
editable, editable,
textDirection: "auto",
immediatelyRender: true, immediatelyRender: true,
shouldRerenderOnTransaction: false, shouldRerenderOnTransaction: false,
autofocus: (autofocus && "end") || false, autofocus: (autofocus && "end") || false,
@@ -40,6 +40,7 @@ export default function TransclusionContent({ content }: Props) {
<EditorProvider <EditorProvider
editable={false} editable={false}
immediatelyRender={true} immediatelyRender={true}
textDirection="auto"
extensions={extensions} extensions={extensions}
content={content as any} content={content as any}
/> />
@@ -249,6 +249,7 @@ function CollabPageEditor({
{ {
extensions, extensions,
editable, editable,
textDirection: "auto",
immediatelyRender: true, immediatelyRender: true,
shouldRerenderOnTransaction: false, shouldRerenderOnTransaction: false,
editorProps: { editorProps: {
@@ -484,6 +485,7 @@ function StaticPageEditor({
<EditorProvider <EditorProvider
editable={false} editable={false}
immediatelyRender={true} immediatelyRender={true}
textDirection="auto"
extensions={mainExtensions} extensions={mainExtensions}
content={content} content={content}
editorProps={{ editorProps={{
@@ -85,6 +85,7 @@ export default function ReadonlyPageEditor({
<EditorProvider <EditorProvider
editable={false} editable={false}
immediatelyRender={true} immediatelyRender={true}
textDirection="auto"
extensions={titleExtensions} extensions={titleExtensions}
content={title} content={title}
></EditorProvider> ></EditorProvider>
@@ -93,6 +94,7 @@ export default function ReadonlyPageEditor({
<EditorProvider <EditorProvider
editable={false} editable={false}
immediatelyRender={true} immediatelyRender={true}
textDirection="auto"
extensions={extensions} extensions={extensions}
content={content} content={content}
onCreate={({ editor }) => { onCreate={({ editor }) => {
@@ -54,7 +54,7 @@
var(--mantine-color-dark-5) var(--mantine-color-dark-5)
); );
font-weight: bold; font-weight: bold;
text-align: left; text-align: start;
} }
.column-resize-handle { .column-resize-handle {
@@ -86,6 +86,7 @@ export function TitleEditor({
}, },
editable: editable, editable: editable,
content: title, content: title,
textDirection: "auto",
immediatelyRender: true, immediatelyRender: true,
shouldRerenderOnTransaction: false, shouldRerenderOnTransaction: false,
editorProps: { editorProps: {
@@ -31,6 +31,7 @@ export function HistoryEditor({
const editor = useEditor({ const editor = useEditor({
extensions: mainExtensions, extensions: mainExtensions,
editable: false, editable: false,
textDirection: "auto",
}); });
useEffect(() => { useEffect(() => {
@@ -50,7 +50,12 @@ import {
Footnote, Footnote,
FootnoteReference, FootnoteReference,
} from '@docmost/editor-ext'; } from '@docmost/editor-ext';
import { generateText, getSchema, JSONContent } from '@tiptap/core'; import {
extensions as coreExtensions,
generateText,
getSchema,
JSONContent,
} from '@tiptap/core';
import { generateHTML, generateJSON } from '../common/helpers/prosemirror/html'; import { generateHTML, generateJSON } from '../common/helpers/prosemirror/html';
// @tiptap/html library works best for generating prosemirror json state but not HTML // @tiptap/html library works best for generating prosemirror json state but not HTML
// see: https://github.com/ueberdosis/tiptap/issues/5352 // see: https://github.com/ueberdosis/tiptap/issues/5352
@@ -61,6 +66,7 @@ import * as Y from 'yjs';
import { Logger } from '@nestjs/common'; import { Logger } from '@nestjs/common';
export const tiptapExtensions = [ export const tiptapExtensions = [
coreExtensions.TextDirection.configure({ direction: 'auto' }),
StarterKit.configure({ StarterKit.configure({
document: false, document: false,
codeBlock: false, codeBlock: false,