aboutsummaryrefslogtreecommitdiffstats
path: root/apps/mobile/lib/readerSettings.tsx
diff options
context:
space:
mode:
authorEvan Simkowitz <esimkowitz@users.noreply.github.com>2025-12-14 16:39:25 -0800
committerGitHub <noreply@github.com>2025-12-15 00:39:25 +0000
commit7f4202afd73105b850498b55ad66922b3505f0e3 (patch)
treea45f9f1b2599f4c9925e36dc51563b06ba6854ac /apps/mobile/lib/readerSettings.tsx
parent6db14ac492cd5d9e26d0d986513771f14faa7fd0 (diff)
downloadkarakeep-7f4202afd73105b850498b55ad66922b3505f0e3.tar.zst
feat: Add unified reader settings with local overrides (#2230)
* Add initial impl * fix some format inconsistencies, add indicator in user settings when local is out of sync * Fix sliders in user settings, unify constants and formatting * address CodeRabbit suggestions * add mobile implementation * address coderabbit nitpicks * fix responsiveness of the reader settings popover * Move more of the web UI strings to i18n * update translations for more coverage * remove duplicate logic/definitions * fix android font family * add shared reading setting hook between web and mobile * unify reader settings context for both web and mobile * remove unused export * address coderabbit suggestions * fix tests
Diffstat (limited to 'apps/mobile/lib/readerSettings.tsx')
-rw-r--r--apps/mobile/lib/readerSettings.tsx93
1 files changed, 93 insertions, 0 deletions
diff --git a/apps/mobile/lib/readerSettings.tsx b/apps/mobile/lib/readerSettings.tsx
new file mode 100644
index 00000000..9a3fc835
--- /dev/null
+++ b/apps/mobile/lib/readerSettings.tsx
@@ -0,0 +1,93 @@
+import { ReactNode, useCallback } from "react";
+import { Platform } from "react-native";
+
+import {
+ ReaderSettingsProvider as BaseReaderSettingsProvider,
+ useReaderSettingsContext,
+} from "@karakeep/shared-react/hooks/reader-settings";
+import { ReaderSettingsPartial } from "@karakeep/shared/types/readers";
+import { ZReaderFontFamily } from "@karakeep/shared/types/users";
+
+import { useSettings } from "./settings";
+
+// Mobile-specific font families for native Text components
+// On Android, use generic font family names: "serif", "sans-serif", "monospace"
+// On iOS, use specific font names like "Georgia" and "Courier"
+// Note: undefined means use the system default font
+export const MOBILE_FONT_FAMILIES: Record<
+ ZReaderFontFamily,
+ string | undefined
+> = Platform.select({
+ android: {
+ serif: "serif",
+ sans: undefined,
+ mono: "monospace",
+ },
+ default: {
+ serif: "Georgia",
+ sans: undefined,
+ mono: "Courier",
+ },
+})!;
+
+// Font families for WebView HTML content (CSS font stacks)
+export const WEBVIEW_FONT_FAMILIES: Record<ZReaderFontFamily, string> = {
+ serif: "Georgia, 'Times New Roman', serif",
+ sans: "-apple-system, BlinkMacSystemFont, 'Segoe UI', system-ui, sans-serif",
+ mono: "ui-monospace, Menlo, Monaco, 'Courier New', monospace",
+} as const;
+
+/**
+ * Mobile-specific provider for reader settings.
+ * Wraps the shared provider with mobile storage callbacks.
+ */
+export function ReaderSettingsProvider({ children }: { children: ReactNode }) {
+ // Read from zustand store directly to keep callback stable (empty deps).
+ const getLocalOverrides = useCallback((): ReaderSettingsPartial => {
+ const currentSettings = useSettings.getState().settings.settings;
+ return {
+ fontSize: currentSettings.readerFontSize,
+ lineHeight: currentSettings.readerLineHeight,
+ fontFamily: currentSettings.readerFontFamily,
+ };
+ }, []);
+
+ const saveLocalOverrides = useCallback((overrides: ReaderSettingsPartial) => {
+ const currentSettings = useSettings.getState().settings.settings;
+ // Remove reader settings keys first, then add back only defined ones
+ const {
+ readerFontSize: _fs,
+ readerLineHeight: _lh,
+ readerFontFamily: _ff,
+ ...rest
+ } = currentSettings;
+
+ const newSettings = { ...rest };
+ if (overrides.fontSize !== undefined) {
+ (newSettings as typeof currentSettings).readerFontSize =
+ overrides.fontSize;
+ }
+ if (overrides.lineHeight !== undefined) {
+ (newSettings as typeof currentSettings).readerLineHeight =
+ overrides.lineHeight;
+ }
+ if (overrides.fontFamily !== undefined) {
+ (newSettings as typeof currentSettings).readerFontFamily =
+ overrides.fontFamily;
+ }
+
+ useSettings.getState().setSettings(newSettings);
+ }, []);
+
+ return (
+ <BaseReaderSettingsProvider
+ getLocalOverrides={getLocalOverrides}
+ saveLocalOverrides={saveLocalOverrides}
+ >
+ {children}
+ </BaseReaderSettingsProvider>
+ );
+}
+
+// Re-export the context hook as useReaderSettings for mobile consumers
+export { useReaderSettingsContext as useReaderSettings };