mirror of
https://github.com/TriliumNext/Notes.git
synced 2025-08-12 20:02:28 +08:00
refactor(client): extract doc rendering to dedicated service
This commit is contained in:
parent
4124c96e02
commit
32f84e8378
59
src/public/app/services/doc_renderer.ts
Normal file
59
src/public/app/services/doc_renderer.ts
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
import type FNote from "../entities/fnote.js";
|
||||||
|
import { getCurrentLanguage } from "./i18n.js";
|
||||||
|
import { applySyntaxHighlight } from "./syntax_highlight.js";
|
||||||
|
|
||||||
|
export default function renderDoc(note: FNote) {
|
||||||
|
return new Promise<JQuery<HTMLElement>>((resolve) => {
|
||||||
|
let docName = note.getLabelValue("docName");
|
||||||
|
const $content = $("<div>");
|
||||||
|
|
||||||
|
if (docName) {
|
||||||
|
// find doc based on language
|
||||||
|
const url = getUrl(docName, getCurrentLanguage());
|
||||||
|
$content.load(url, (response, status) => {
|
||||||
|
// fallback to english doc if no translation available
|
||||||
|
if (status === "error") {
|
||||||
|
const fallbackUrl = getUrl(docName, "en");
|
||||||
|
$content.load(fallbackUrl, () => processContent(fallbackUrl, $content));
|
||||||
|
resolve($content);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
processContent(url, $content);
|
||||||
|
resolve($content);
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
resolve($content);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $content;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function processContent(url: string, $content: JQuery<HTMLElement>) {
|
||||||
|
const dir = url.substring(0, url.lastIndexOf("/"));
|
||||||
|
|
||||||
|
// Remove top-level heading since it's already handled by the note title
|
||||||
|
$content.find("h1").remove();
|
||||||
|
|
||||||
|
// Images are relative to the docnote but that will not work when rendered in the application since the path breaks.
|
||||||
|
$content.find("img").each((i, el) => {
|
||||||
|
const $img = $(el);
|
||||||
|
$img.attr("src", dir + "/" + $img.attr("src"));
|
||||||
|
});
|
||||||
|
|
||||||
|
applySyntaxHighlight($content);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getUrl(docNameValue: string, language: string) {
|
||||||
|
// For help notes, we only get the content to avoid loading of styles and meta.
|
||||||
|
let suffix = "";
|
||||||
|
if (docNameValue?.startsWith("User Guide")) {
|
||||||
|
suffix = " .content";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Cannot have spaces in the URL due to how JQuery.load works.
|
||||||
|
docNameValue = docNameValue.replaceAll(" ", "%20");
|
||||||
|
|
||||||
|
return `${window.glob.appPath}/doc_notes/${language}/${docNameValue}.html${suffix}`;
|
||||||
|
}
|
@ -1,8 +1,7 @@
|
|||||||
import type { EventData } from "../../components/app_context.js";
|
import type { EventData } from "../../components/app_context.js";
|
||||||
import type FNote from "../../entities/fnote.js";
|
import type FNote from "../../entities/fnote.js";
|
||||||
import { applySyntaxHighlight } from "../../services/syntax_highlight.js";
|
import renderDoc from "../../services/doc_renderer.js";
|
||||||
import TypeWidget from "./type_widget.js";
|
import TypeWidget from "./type_widget.js";
|
||||||
import { getCurrentLanguage } from "../../services/i18n.js";
|
|
||||||
|
|
||||||
const TPL = `<div class="note-detail-doc note-detail-printable">
|
const TPL = `<div class="note-detail-doc note-detail-printable">
|
||||||
<style>
|
<style>
|
||||||
@ -68,64 +67,12 @@ export default class DocTypeWidget extends TypeWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async doRefresh(note: FNote) {
|
async doRefresh(note: FNote) {
|
||||||
this.initialized = this.#loadContent(note);
|
this.initialized = renderDoc(note).then(($content) => {
|
||||||
|
this.$content.html($content.html());
|
||||||
|
});
|
||||||
this.$widget.toggleClass("contextual-help", this.noteContext?.viewScope?.viewMode === "contextual-help");
|
this.$widget.toggleClass("contextual-help", this.noteContext?.viewScope?.viewMode === "contextual-help");
|
||||||
}
|
}
|
||||||
|
|
||||||
#loadContent(note: FNote) {
|
|
||||||
return new Promise<void>((resolve) => {
|
|
||||||
let docName = note.getLabelValue("docName");
|
|
||||||
|
|
||||||
if (docName) {
|
|
||||||
// find doc based on language
|
|
||||||
const url = this.#getUrl(docName, getCurrentLanguage());
|
|
||||||
this.$content.load(url, (response, status) => {
|
|
||||||
// fallback to english doc if no translation available
|
|
||||||
if (status === "error") {
|
|
||||||
const fallbackUrl = this.#getUrl(docName, "en");
|
|
||||||
this.$content.load(fallbackUrl, () => this.#processContent(fallbackUrl));
|
|
||||||
resolve();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
this.#processContent(url);
|
|
||||||
resolve();
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
this.$content.empty();
|
|
||||||
resolve();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
#getUrl(docNameValue: string, language: string) {
|
|
||||||
// For help notes, we only get the content to avoid loading of styles and meta.
|
|
||||||
let suffix = "";
|
|
||||||
if (docNameValue?.startsWith("User Guide")) {
|
|
||||||
suffix = " .content";
|
|
||||||
}
|
|
||||||
|
|
||||||
// Cannot have spaces in the URL due to how JQuery.load works.
|
|
||||||
docNameValue = docNameValue.replaceAll(" ", "%20");
|
|
||||||
|
|
||||||
return `${window.glob.appPath}/doc_notes/${language}/${docNameValue}.html${suffix}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
#processContent(url: string) {
|
|
||||||
const dir = url.substring(0, url.lastIndexOf("/"));
|
|
||||||
|
|
||||||
// Remove top-level heading since it's already handled by the note title
|
|
||||||
this.$content.find("h1").remove();
|
|
||||||
|
|
||||||
// Images are relative to the docnote but that will not work when rendered in the application since the path breaks.
|
|
||||||
this.$content.find("img").each((i, el) => {
|
|
||||||
const $img = $(el);
|
|
||||||
$img.attr("src", dir + "/" + $img.attr("src"));
|
|
||||||
});
|
|
||||||
|
|
||||||
applySyntaxHighlight(this.$content);
|
|
||||||
}
|
|
||||||
|
|
||||||
async executeWithContentElementEvent({ resolve, ntxId }: EventData<"executeWithContentElement">) {
|
async executeWithContentElementEvent({ resolve, ntxId }: EventData<"executeWithContentElement">) {
|
||||||
if (!this.isNoteContext(ntxId)) {
|
if (!this.isNoteContext(ntxId)) {
|
||||||
return;
|
return;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user