mirror of
https://github.com/outline/outline.git
synced 2026-06-13 11:25:03 +03:00
fix: Theme override does not persist between navigations (#11176)
This commit is contained in:
@@ -10,7 +10,12 @@ import { Theme } from "~/stores/UiStore";
|
||||
export const AppearanceAction = observer(() => {
|
||||
const { t } = useTranslation();
|
||||
const { ui } = useStores();
|
||||
const { resolvedTheme } = ui;
|
||||
const { resolvedTheme, themeOverride } = ui;
|
||||
|
||||
// Hide when theme is locked via query parameter
|
||||
if (themeOverride) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return (
|
||||
<Action>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { useMemo } from "react";
|
||||
import { useEffect, useMemo } from "react";
|
||||
import { breakpoints } from "@shared/styles";
|
||||
import {
|
||||
buildDarkTheme,
|
||||
@@ -6,7 +6,7 @@ import {
|
||||
buildPitchBlackTheme,
|
||||
} from "@shared/styles/theme";
|
||||
import type { CustomTheme } from "@shared/types";
|
||||
import type { Theme } from "~/stores/UiStore";
|
||||
import { Theme } from "~/stores/UiStore";
|
||||
import useMediaQuery from "~/hooks/useMediaQuery";
|
||||
import useStores from "./useStores";
|
||||
import useQuery from "./useQuery";
|
||||
@@ -28,7 +28,18 @@ export default function useBuildTheme(
|
||||
const isMobile = useMediaQuery(`(max-width: ${breakpoints.tablet}px)`);
|
||||
const isPrinting = useMediaQuery("print");
|
||||
const queryTheme = (params.get("theme") as Theme) || undefined;
|
||||
const resolvedTheme = overrideTheme ?? queryTheme ?? ui.resolvedTheme;
|
||||
|
||||
// Store the theme override in UiStore so it persists during navigation
|
||||
useEffect(() => {
|
||||
if (
|
||||
queryTheme &&
|
||||
(queryTheme === Theme.Light || queryTheme === Theme.Dark)
|
||||
) {
|
||||
ui.setThemeOverride(queryTheme);
|
||||
}
|
||||
}, [queryTheme, ui]);
|
||||
|
||||
const resolvedTheme = overrideTheme ?? ui.resolvedTheme;
|
||||
|
||||
const theme = useMemo(
|
||||
() =>
|
||||
|
||||
@@ -43,6 +43,10 @@ class UiStore {
|
||||
@observable
|
||||
theme: Theme;
|
||||
|
||||
// themeOverride is set when a theme query parameter is detected, persists for the session
|
||||
@observable
|
||||
themeOverride: Theme | undefined;
|
||||
|
||||
// systemTheme represents the system UI theme (Settings -> General in macOS)
|
||||
@observable
|
||||
systemTheme: SystemTheme;
|
||||
@@ -156,6 +160,17 @@ class UiStore {
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* Set a theme override from a query parameter. This persists for the session
|
||||
* but is not saved to localStorage.
|
||||
*
|
||||
* @param theme The theme to override with, or undefined to clear.
|
||||
*/
|
||||
@action
|
||||
setThemeOverride = (theme: Theme | undefined) => {
|
||||
this.themeOverride = theme;
|
||||
};
|
||||
|
||||
@action
|
||||
setActiveDocument = (document: Document | string): void => {
|
||||
if (typeof document === "string") {
|
||||
@@ -300,6 +315,10 @@ class UiStore {
|
||||
|
||||
@computed
|
||||
get resolvedTheme(): Theme | SystemTheme {
|
||||
if (this.themeOverride) {
|
||||
return this.themeOverride;
|
||||
}
|
||||
|
||||
if (this.theme === "system") {
|
||||
return this.systemTheme;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user