diff --git a/apps/client/src/widgets/NoteDetail.tsx b/apps/client/src/widgets/NoteDetail.tsx
index 8a11c404d..8c6df291b 100644
--- a/apps/client/src/widgets/NoteDetail.tsx
+++ b/apps/client/src/widgets/NoteDetail.tsx
@@ -19,6 +19,7 @@ import { ReadOnlyCode, EditableCode } from "./type_widgets/code/Code";
import Mermaid from "./type_widgets/Mermaid";
import MindMap from "./type_widgets/MindMap";
import { AttachmentDetail, AttachmentList } from "./type_widgets/Attachment";
+import ReadOnlyText from "./type_widgets/text/ReadOnlyText";
/**
* A `NoteType` altered by the note detail widget, taking into consideration whether the note is editable or not and adding special note types such as an empty one,
@@ -101,6 +102,7 @@ function getCorrespondingWidget(noteType: ExtendedNoteType | undefined, props: T
case "mindMap": return
case "attachmentList": return
case "attachmentDetail": return
+ case "readOnlyText": return
default: break;
}
}
diff --git a/apps/client/src/widgets/type_widgets/text/ReadOnlyText.css b/apps/client/src/widgets/type_widgets/text/ReadOnlyText.css
new file mode 100644
index 000000000..4ab25d973
--- /dev/null
+++ b/apps/client/src/widgets/type_widgets/text/ReadOnlyText.css
@@ -0,0 +1,58 @@
+/* h1 should not be used at all since semantically that's a note title */
+.note-detail-readonly-text h1 { font-size: 1.8em; }
+.note-detail-readonly-text h2 { font-size: 1.6em; }
+.note-detail-readonly-text h3 { font-size: 1.4em; }
+.note-detail-readonly-text h4 { font-size: 1.2em; }
+.note-detail-readonly-text h5 { font-size: 1.1em; }
+.note-detail-readonly-text h6 { font-size: 1.0em; }
+
+body.heading-style-markdown .note-detail-readonly-text h1::before { content: "#\\2004"; color: var(--muted-text-color); }
+body.heading-style-markdown .note-detail-readonly-text h2::before { content: "##\\2004"; color: var(--muted-text-color); }
+body.heading-style-markdown .note-detail-readonly-text h3::before { content: "###\\2004"; color: var(--muted-text-color); }
+body.heading-style-markdown .note-detail-readonly-text h4:not(.include-note-title)::before { content: "####\\2004"; color: var(--muted-text-color); }
+body.heading-style-markdown .note-detail-readonly-text h5::before { content: "#####\\2004"; color: var(--muted-text-color); }
+body.heading-style-markdown .note-detail-readonly-text h6::before { content: "######\\2004"; color: var(--muted-text-color); }
+
+body.heading-style-underline .note-detail-readonly-text h1 { border-bottom: 1px solid var(--main-border-color); }
+body.heading-style-underline .note-detail-readonly-text h2 { border-bottom: 1px solid var(--main-border-color); }
+body.heading-style-underline .note-detail-readonly-text h3 { border-bottom: 1px solid var(--main-border-color); }
+body.heading-style-underline .note-detail-readonly-text h4:not(.include-note-title) { border-bottom: 1px solid var(--main-border-color); }
+body.heading-style-underline .note-detail-readonly-text h5 { border-bottom: 1px solid var(--main-border-color); }
+body.heading-style-underline .note-detail-readonly-text h6 { border-bottom: 1px solid var(--main-border-color); }
+
+.note-detail-readonly-text {
+ padding-inline-start: 24px;
+ padding-top: 10px;
+ font-family: var(--detail-font-family);
+ min-height: 50px;
+ position: relative;
+}
+
+body.mobile .note-detail-readonly-text {
+ padding-left: 10px;
+}
+
+.note-detail-readonly-text p:first-child, .note-detail-readonly-text::before {
+ margin-top: 0;
+}
+
+.note-detail-readonly-text img {
+ max-width: 100%;
+ cursor: pointer;
+}
+
+.edit-text-note-button {
+ position: absolute;
+ top: 5px;
+ right: 10px;
+ font-size: 150%;
+ padding: 5px;
+ cursor: pointer;
+ border: 1px solid transparent;
+ border-radius: var(--button-border-radius);
+ color: var(--button-text-color);
+}
+
+.edit-text-note-button:hover {
+ border-color: var(--button-border-color);
+}
\ No newline at end of file
diff --git a/apps/client/src/widgets/type_widgets/text/ReadOnlyText.tsx b/apps/client/src/widgets/type_widgets/text/ReadOnlyText.tsx
new file mode 100644
index 000000000..fab9680f3
--- /dev/null
+++ b/apps/client/src/widgets/type_widgets/text/ReadOnlyText.tsx
@@ -0,0 +1,41 @@
+import { useEffect, useMemo, useRef } from "preact/hooks";
+import { TypeWidgetProps } from "../type_widget";
+import "./ReadOnlyText.css";
+import { useNoteBlob, useNoteLabel } from "../../react/hooks";
+import RawHtml from "../../react/RawHtml";
+
+// we load CKEditor also for read only notes because they contain content styles required for correct rendering of even read only notes
+// we could load just ckeditor-content.css but that causes CSS conflicts when both build CSS and this content CSS is loaded at the same time
+// (see https://github.com/zadam/trilium/issues/1590 for example of such conflict)
+import "@triliumnext/ckeditor5";
+import FNote from "../../../entities/fnote";
+import { getLocaleById } from "../../../services/i18n";
+
+export default function ReadOnlyText({ note }: TypeWidgetProps) {
+ const blob = useNoteBlob(note);
+ const contentRef = useRef(null);
+ const { isRtl } = useNoteLanguage(note);
+
+ return (
+
+
+
+ )
+}
+
+function useNoteLanguage(note: FNote) {
+ const [ language ] = useNoteLabel(note, "language");
+ const isRtl = useMemo(() => {
+ const correspondingLocale = getLocaleById(language);
+ return correspondingLocale?.rtl;
+ }, [ language ]);
+ return { isRtl };
+}
diff --git a/apps/client/src/widgets/type_widgets_old/read_only_text.ts b/apps/client/src/widgets/type_widgets_old/read_only_text.ts
index 59f99af33..223fa97f3 100644
--- a/apps/client/src/widgets/type_widgets_old/read_only_text.ts
+++ b/apps/client/src/widgets/type_widgets_old/read_only_text.ts
@@ -2,78 +2,10 @@ import AbstractTextTypeWidget from "./abstract_text_type_widget.js";
import { formatCodeBlocks } from "../../services/syntax_highlight.js";
import type FNote from "../../entities/fnote.js";
import type { CommandListenerData, EventData } from "../../components/app_context.js";
-import { getLocaleById } from "../../services/i18n.js";
import appContext from "../../components/app_context.js";
import { getMermaidConfig } from "../../services/mermaid.js";
import { renderMathInElement } from "../../services/math.js";
-const TPL = /*html*/`
-
-`;
-
export default class ReadOnlyTextTypeWidget extends AbstractTextTypeWidget {
private $content!: JQuery;
@@ -83,8 +15,6 @@ export default class ReadOnlyTextTypeWidget extends AbstractTextTypeWidget {
}
doRender() {
- this.$widget = $(TPL);
-
this.$content = this.$widget.find(".note-detail-readonly-text-content");
this.setupImageOpening(true);
@@ -97,11 +27,6 @@ export default class ReadOnlyTextTypeWidget extends AbstractTextTypeWidget {
}
async doRefresh(note: FNote) {
- // we load CKEditor also for read only notes because they contain content styles required for correct rendering of even read only notes
- // we could load just ckeditor-content.css but that causes CSS conflicts when both build CSS and this content CSS is loaded at the same time
- // (see https://github.com/zadam/trilium/issues/1590 for example of such conflict)
- await import("@triliumnext/ckeditor5");
-
this.onLanguageChanged();
const blob = await note.getBlob();
@@ -161,13 +86,6 @@ export default class ReadOnlyTextTypeWidget extends AbstractTextTypeWidget {
resolve(this.$content);
}
- async onLanguageChanged(): Promise {
- const languageCode = this.note?.getLabelValue("language");
- const correspondingLocale = getLocaleById(languageCode);
- const isRtl = correspondingLocale?.rtl;
- this.$widget.attr("dir", isRtl ? "rtl" : "ltr");
- }
-
buildTouchBarCommand({ TouchBar, buildIcon }: CommandListenerData<"buildTouchBar">) {
return [
new TouchBar.TouchBarSpacer({ size: "flexible" }),