Base dark theme implementation

This commit is contained in:
Patrick Fic
2025-10-23 13:44:33 -07:00
parent b6271b8ef2
commit f170192008
22 changed files with 308 additions and 176 deletions

1
hooks/index.ts Normal file
View File

@@ -0,0 +1 @@
export { useTheme } from "./useTheme";

View File

@@ -1 +0,0 @@
export { useColorScheme } from 'react-native';

View File

@@ -1,21 +0,0 @@
import { useEffect, useState } from 'react';
import { useColorScheme as useRNColorScheme } from 'react-native';
/**
* To support static rendering, this value needs to be re-calculated on the client side for web
*/
export function useColorScheme() {
const [hasHydrated, setHasHydrated] = useState(false);
useEffect(() => {
setHasHydrated(true);
}, []);
const colorScheme = useRNColorScheme();
if (hasHydrated) {
return colorScheme;
}
return 'light';
}

View File

@@ -1,21 +0,0 @@
/**
* Learn more about light and dark modes:
* https://docs.expo.dev/guides/color-schemes/
*/
import { Colors } from '@/constants/theme';
import { useColorScheme } from '@/hooks/use-color-scheme';
export function useThemeColor(
props: { light?: string; dark?: string },
colorName: keyof typeof Colors.light & keyof typeof Colors.dark
) {
const theme = useColorScheme() ?? 'light';
const colorFromProps = props[theme];
if (colorFromProps) {
return colorFromProps;
} else {
return Colors[theme][colorName];
}
}

57
hooks/useTheme.ts Normal file
View File

@@ -0,0 +1,57 @@
import { selectTheme } from "@/redux/user/user.selectors";
import { darkTheme, lightTheme } from "@/util/theme";
import { useColorScheme } from "react-native";
import { useSelector } from "react-redux";
type ThemePreference = "light" | "dark" | "system";
/**
* Custom hook that returns the appropriate theme based on user preference
*
* This hook automatically selects the correct theme (light or dark) based on:
* - User's explicit preference (light/dark)
* - System appearance when "system" is selected
* - Defaults to system theme if no preference is set
*
* @returns The theme object compatible with React Native Paper
*
* @example
* ```typescript
* import { useTheme } from "@/hooks/useTheme";
*
* const MyComponent = () => {
* const theme = useTheme();
*
* return (
* <View style={{ backgroundColor: theme.colors.background }}>
* <Text style={{ color: theme.colors.onBackground }}>
* Themed content
* </Text>
* </View>
* );
* };
* ```
*/
export const useTheme = () => {
const userThemePreference: ThemePreference = useSelector(selectTheme);
const systemColorScheme = useColorScheme();
// Determine which theme to use based on user preference
let selectedTheme;
switch (userThemePreference) {
case "light":
selectedTheme = lightTheme;
break;
case "dark":
selectedTheme = darkTheme;
break;
case "system":
default:
// Use system preference when user selects "system" or as fallback
selectedTheme = systemColorScheme === "dark" ? darkTheme : lightTheme;
break;
}
return selectedTheme;
};