diff --git a/native/profile/appearance-preferences.react.js b/native/profile/appearance-preferences.react.js index d5a7b76d4..9e0a82d8d 100644 --- a/native/profile/appearance-preferences.react.js +++ b/native/profile/appearance-preferences.react.js @@ -1,172 +1,172 @@ // @flow import * as React from 'react'; import { View, Text, Platform } from 'react-native'; import { ScrollView } from 'react-native-gesture-handler'; import { useDispatch } from 'react-redux'; import type { Dispatch } from 'lib/types/redux-types.js'; import type { GlobalThemeInfo, GlobalThemePreference, } from 'lib/types/theme-types.js'; import Button from '../components/button.react.js'; import SWMansionIcon from '../components/swmansion-icon.react.js'; import { updateThemeInfoActionType } from '../redux/action-types.js'; import { useSelector } from '../redux/redux-utils.js'; import { type Colors, useColors, useStyles } from '../themes/colors.js'; -import { osCanTheme } from '../types/themes.js'; +import { osCanTheme } from '../themes/theme-utils.js'; const CheckIcon = () => ( ); type OptionText = { themePreference: GlobalThemePreference, text: string, }; const optionTexts: OptionText[] = [ { themePreference: 'light', text: 'Light' }, { themePreference: 'dark', text: 'Dark' }, ]; if (osCanTheme) { optionTexts.push({ themePreference: 'system', text: 'Follow system preferences', }); } type Props = { +globalThemeInfo: GlobalThemeInfo, +styles: typeof unboundStyles, +colors: Colors, +dispatch: Dispatch, ... }; class AppearancePreferences extends React.PureComponent { render() { const { panelIosHighlightUnderlay: underlay } = this.props.colors; const options = []; for (let i = 0; i < optionTexts.length; i++) { const { themePreference, text } = optionTexts[i]; const icon = themePreference === this.props.globalThemeInfo.preference ? ( ) : null; options.push( , ); if (i + 1 < optionTexts.length) { options.push( , ); } } return ( APP THEME {options} ); } onSelectThemePreference = (themePreference: GlobalThemePreference) => { if (themePreference === this.props.globalThemeInfo.preference) { return; } const theme = themePreference === 'system' ? this.props.globalThemeInfo.systemTheme : themePreference; this.props.dispatch({ type: updateThemeInfoActionType, payload: { preference: themePreference, activeTheme: theme, }, }); }; } const unboundStyles = { header: { color: 'panelBackgroundLabel', fontSize: 12, fontWeight: '400', paddingBottom: 3, paddingHorizontal: 24, }, hr: { backgroundColor: 'panelForegroundBorder', height: 1, marginHorizontal: 15, }, icon: { lineHeight: Platform.OS === 'ios' ? 18 : 20, }, option: { color: 'panelForegroundLabel', fontSize: 16, }, row: { flexDirection: 'row', justifyContent: 'space-between', paddingHorizontal: 24, paddingVertical: 10, }, scrollView: { backgroundColor: 'panelBackground', }, scrollViewContentContainer: { paddingTop: 24, }, section: { backgroundColor: 'panelForeground', borderBottomWidth: 1, borderColor: 'panelForegroundBorder', borderTopWidth: 1, marginBottom: 24, paddingVertical: 2, }, }; const ConnectedAppearancePreferences: React.ComponentType<{ ... }> = React.memo<{ ... }>(function ConnectedAppearancePreferences(props: { ... }) { const globalThemeInfo = useSelector(state => state.globalThemeInfo); const styles = useStyles(unboundStyles); const colors = useColors(); const dispatch = useDispatch(); return ( ); }); export default ConnectedAppearancePreferences; diff --git a/native/themes/theme-handler.react.js b/native/themes/theme-handler.react.js index 0792e4777..2317e0ef5 100644 --- a/native/themes/theme-handler.react.js +++ b/native/themes/theme-handler.react.js @@ -1,65 +1,65 @@ // @flow import invariant from 'invariant'; import * as React from 'react'; import { Appearance } from 'react-native'; import { useDispatch } from 'react-redux'; import type { Shape } from 'lib/types/core.js'; import type { GlobalTheme, GlobalThemeInfo } from 'lib/types/theme-types.js'; import { updateThemeInfoActionType } from '../redux/action-types.js'; import { useSelector } from '../redux/redux-utils.js'; -import { osCanTheme } from '../types/themes.js'; +import { osCanTheme } from '../themes/theme-utils.js'; function ThemeHandler(): null { const globalThemeInfo = useSelector(state => state.globalThemeInfo); const dispatch = useDispatch(); const updateSystemTheme = React.useCallback( (colorScheme: ?GlobalTheme) => { if (globalThemeInfo.systemTheme === colorScheme) { return; } let updateObject: Shape = { systemTheme: colorScheme, }; if (globalThemeInfo.preference === 'system') { updateObject = { ...updateObject, activeTheme: colorScheme }; } dispatch({ type: updateThemeInfoActionType, payload: updateObject, }); }, [globalThemeInfo, dispatch], ); React.useEffect(() => { if (!osCanTheme) { return undefined; } const subscription = Appearance.addChangeListener(({ colorScheme }) => { invariant( colorScheme === undefined || colorScheme === null || colorScheme === 'light' || colorScheme === 'dark', 'Flow types for Appearance module are non-specific', ); updateSystemTheme(colorScheme); }); return () => subscription.remove(); }, [updateSystemTheme]); React.useEffect( () => updateSystemTheme(Appearance.getColorScheme()), // eslint-disable-next-line react-hooks/exhaustive-deps [], ); return null; } export default ThemeHandler; diff --git a/native/types/themes.js b/native/themes/theme-utils.js similarity index 100% rename from native/types/themes.js rename to native/themes/theme-utils.js