From 480954ee87ed53d48ef3399c0625d146c270e42a Mon Sep 17 00:00:00 2001 From: Elian Doran Date: Mon, 29 Dec 2025 12:51:43 +0200 Subject: [PATCH] feat(pdfjs): react to dark mode --- .../src/widgets/type_widgets/file/Pdf.tsx | 49 ++++++++++++++----- packages/pdfjs-viewer/src/custom.css | 12 +++-- 2 files changed, 44 insertions(+), 17 deletions(-) diff --git a/apps/client/src/widgets/type_widgets/file/Pdf.tsx b/apps/client/src/widgets/type_widgets/file/Pdf.tsx index bca0b06db..1146ad60f 100644 --- a/apps/client/src/widgets/type_widgets/file/Pdf.tsx +++ b/apps/client/src/widgets/type_widgets/file/Pdf.tsx @@ -1,4 +1,5 @@ -import { useEffect, useRef } from "preact/hooks"; +import { RefObject } from "preact"; +import { useCallback, useEffect, useRef } from "preact/hooks"; import FNote from "../../../entities/fnote"; import server from "../../../services/server"; @@ -11,7 +12,8 @@ const VARIABLE_WHITELIST = new Set([ ]); export default function PdfPreview({ note }: { note: FNote }) { - const iframeRef = useRef(null); + const iframeRef = useRef(null); + const { onLoad } = useStyleInjection(iframeRef); useEffect(() => { function handleMessage(event: MessageEvent) { @@ -32,20 +34,43 @@ export default function PdfPreview({ note }: { note: FNote }) { ref={iframeRef} class="pdf-preview" src={`pdfjs/web/viewer.html?file=../../api/notes/${note.noteId}/open`} - onLoad={() => { - const doc = iframeRef.current?.contentDocument; - if (!doc) return; - - const style = doc.createElement('style'); - style.id = 'client-root-vars'; - style.textContent = cssVarsToString(getRootCssVariables()); - - doc.head.appendChild(style); - }} + onLoad={onLoad} /> ); } +function useStyleInjection(iframeRef: RefObject) { + const styleRef = useRef(null); + + // First load. + const onLoad = useCallback(() => { + const doc = iframeRef.current?.contentDocument; + if (!doc) return; + + const style = doc.createElement('style'); + style.id = 'client-root-vars'; + style.textContent = cssVarsToString(getRootCssVariables()); + styleRef.current = style; + + doc.head.appendChild(style); + }, [ iframeRef ]); + + // React to changes. + useEffect(() => { + const listener = () => { + styleRef.current!.textContent = cssVarsToString(getRootCssVariables()); + }; + + const media = window.matchMedia("(prefers-color-scheme: dark)"); + media.addEventListener("change", listener); + return () => media.removeEventListener("change", listener); + }, [ iframeRef ]); + + return { + onLoad + }; +} + function getRootCssVariables() { const styles = getComputedStyle(document.documentElement); const vars = {}; diff --git a/packages/pdfjs-viewer/src/custom.css b/packages/pdfjs-viewer/src/custom.css index f681e7301..ac5b49035 100644 --- a/packages/pdfjs-viewer/src/custom.css +++ b/packages/pdfjs-viewer/src/custom.css @@ -1,12 +1,14 @@ :root { --main-color: var(--tn-main-text-color); - --body-bg-color: var(--tn-main-background); - --toolbar-bg-color: var(--tn-main-background); + --body-bg-color: var(--tn-main-background-color); + --toolbar-bg-color: var(--tn-main-background-color); --toolbar-border-color: var(--tn-main-border-color); --toolbar-icon-opacity: 1; } -.page .canvasWrapper { - border: 1px solid var(--tn-main-border-color); - box-shadow: 0 0 3px rgba(0, 0, 0, 0.2); +.pdfViewer { + .page .canvasWrapper { + border: 1px solid var(--tn-main-border-color); + box-shadow: 0 0 3px rgba(0, 0, 0, 0.2); + } }