diff options
author | Samuel Newman <mozzius@protonmail.com> | 2024-10-14 22:09:47 +0300 |
---|---|---|
committer | GitHub <noreply@github.com> | 2024-10-14 22:09:47 +0300 |
commit | 2d88463453abfad1e9e45bbd6cdbcd5824a7e770 (patch) | |
tree | 40c411208b5e0c68d02814d5f525243c27cce306 /src | |
parent | 0f40013963aaf4f3ac893ce58958ea30bc7a1efd (diff) | |
download | voidsky-2d88463453abfad1e9e45bbd6cdbcd5824a7e770.tar.zst |
Remove top padding from shell, move down into individual screens (#5548)
Diffstat (limited to 'src')
53 files changed, 1545 insertions, 1385 deletions
diff --git a/src/Navigation.tsx b/src/Navigation.tsx index 323f668b7..81d08c7da 100644 --- a/src/Navigation.tsx +++ b/src/Navigation.tsx @@ -17,7 +17,6 @@ import { import {timeout} from '#/lib/async/timeout' import {useColorSchemeStyle} from '#/lib/hooks/useColorSchemeStyle' -import {usePalette} from '#/lib/hooks/usePalette' import {useWebScrollRestoration} from '#/lib/hooks/useWebScrollRestoration' import {buildStateObject} from '#/lib/routes/helpers' import { @@ -93,6 +92,7 @@ import { StarterPackScreenShort, } from '#/screens/StarterPack/StarterPackScreen' import {Wizard} from '#/screens/StarterPack/Wizard' +import {useTheme} from '#/alf' import {router} from '#/routes' import {Referrer} from '../modules/expo-bluesky-swiss-army' @@ -412,7 +412,7 @@ function TabsNavigator() { } function HomeTabNavigator() { - const pal = usePalette('default') + const t = useTheme() return ( <HomeTab.Navigator @@ -422,7 +422,7 @@ function HomeTabNavigator() { gestureEnabled: true, fullScreenGestureEnabled: true, headerShown: false, - contentStyle: pal.view, + contentStyle: t.atoms.bg, }}> <HomeTab.Screen name="Home" getComponent={() => HomeScreen} /> <HomeTab.Screen name="Start" getComponent={() => HomeScreen} /> @@ -432,7 +432,7 @@ function HomeTabNavigator() { } function SearchTabNavigator() { - const pal = usePalette('default') + const t = useTheme() return ( <SearchTab.Navigator screenOptions={{ @@ -441,7 +441,7 @@ function SearchTabNavigator() { gestureEnabled: true, fullScreenGestureEnabled: true, headerShown: false, - contentStyle: pal.view, + contentStyle: t.atoms.bg, }}> <SearchTab.Screen name="Search" getComponent={() => SearchScreen} /> {commonScreens(SearchTab as typeof HomeTab)} @@ -450,7 +450,7 @@ function SearchTabNavigator() { } function NotificationsTabNavigator() { - const pal = usePalette('default') + const t = useTheme() return ( <NotificationsTab.Navigator screenOptions={{ @@ -459,7 +459,7 @@ function NotificationsTabNavigator() { gestureEnabled: true, fullScreenGestureEnabled: true, headerShown: false, - contentStyle: pal.view, + contentStyle: t.atoms.bg, }}> <NotificationsTab.Screen name="Notifications" @@ -472,7 +472,7 @@ function NotificationsTabNavigator() { } function MyProfileTabNavigator() { - const pal = usePalette('default') + const t = useTheme() return ( <MyProfileTab.Navigator screenOptions={{ @@ -481,7 +481,7 @@ function MyProfileTabNavigator() { gestureEnabled: true, fullScreenGestureEnabled: true, headerShown: false, - contentStyle: pal.view, + contentStyle: t.atoms.bg, }}> <MyProfileTab.Screen // @ts-ignore // TODO: fix this broken type in ProfileScreen @@ -498,7 +498,7 @@ function MyProfileTabNavigator() { } function MessagesTabNavigator() { - const pal = usePalette('default') + const t = useTheme() return ( <MessagesTab.Navigator screenOptions={{ @@ -507,7 +507,7 @@ function MessagesTabNavigator() { gestureEnabled: true, fullScreenGestureEnabled: true, headerShown: false, - contentStyle: pal.view, + contentStyle: t.atoms.bg, }}> <MessagesTab.Screen name="Messages" @@ -527,7 +527,7 @@ function MessagesTabNavigator() { * in a single ("flat") stack. */ const FlatNavigator = () => { - const pal = usePalette('default') + const t = useTheme() const numUnread = useUnreadNotifications() const screenListeners = useWebScrollRestoration() const title = (page: MessageDescriptor) => bskyTitle(i18n._(page), numUnread) @@ -541,7 +541,7 @@ const FlatNavigator = () => { gestureEnabled: true, fullScreenGestureEnabled: true, headerShown: false, - contentStyle: pal.view, + contentStyle: t.atoms.bg, }}> <Flat.Screen name="Home" diff --git a/src/components/Layout.tsx b/src/components/Layout.tsx new file mode 100644 index 000000000..57e373164 --- /dev/null +++ b/src/components/Layout.tsx @@ -0,0 +1,41 @@ +import React from 'react' +import {View, ViewStyle} from 'react-native' +import {StyleProp} from 'react-native' +import {useSafeAreaInsets} from 'react-native-safe-area-context' + +import {atoms as a} from '#/alf' + +// Every screen should have a Layout component wrapping it. +// This component provides a default padding for the top of the screen. +// This allows certain screens to avoid the top padding if they want to. +// +// In a future PR I will add a unified header component to this file and +// things like a preconfigured scrollview. + +/** + * Every screen should have a Layout.Screen component wrapping it. + * This component provides a default padding for the top of the screen + * and height/minHeight + */ +let Screen = ({ + disableTopPadding, + style, + ...props +}: React.ComponentProps<typeof View> & { + disableTopPadding?: boolean + style?: StyleProp<ViewStyle> +}): React.ReactNode => { + const {top} = useSafeAreaInsets() + return ( + <View + style={[ + {paddingTop: disableTopPadding ? 0 : top}, + a.util_screen_outer, + style, + ]} + {...props} + /> + ) +} +Screen = React.memo(Screen) +export {Screen} diff --git a/src/screens/E2E/SharedPreferencesTesterScreen.tsx b/src/screens/E2E/SharedPreferencesTesterScreen.tsx index 06bf538ea..5a9e6cd22 100644 --- a/src/screens/E2E/SharedPreferencesTesterScreen.tsx +++ b/src/screens/E2E/SharedPreferencesTesterScreen.tsx @@ -1,9 +1,10 @@ import React from 'react' import {View} from 'react-native' -import {ScrollView} from 'view/com/util/Views' +import {ScrollView} from '#/view/com/util/Views' import {atoms as a} from '#/alf' import {Button, ButtonText} from '#/components/Button' +import * as Layout from '#/components/Layout' import {Text} from '#/components/Typography' import {SharedPrefs} from '../../../modules/expo-bluesky-swiss-army' @@ -11,103 +12,105 @@ export function SharedPreferencesTesterScreen() { const [currentTestOutput, setCurrentTestOutput] = React.useState<string>('') return ( - <ScrollView contentContainerStyle={{backgroundColor: 'red'}}> - <View style={[a.flex_1]}> - <View> - <Text testID="testOutput">{currentTestOutput}</Text> + <Layout.Screen> + <ScrollView contentContainerStyle={{backgroundColor: 'red'}}> + <View style={[a.flex_1]}> + <View> + <Text testID="testOutput">{currentTestOutput}</Text> + </View> + <View style={[a.flex_wrap]}> + <Button + label="btn" + testID="setStringBtn" + style={[a.self_center]} + variant="solid" + color="primary" + size="small" + onPress={async () => { + SharedPrefs.removeValue('testerString') + SharedPrefs.setValue('testerString', 'Hello') + const str = SharedPrefs.getString('testerString') + console.log(JSON.stringify(str)) + setCurrentTestOutput(`${str}`) + }}> + <ButtonText>Set String</ButtonText> + </Button> + <Button + label="btn" + testID="removeStringBtn" + style={[a.self_center]} + variant="solid" + color="primary" + size="small" + onPress={async () => { + SharedPrefs.removeValue('testerString') + const str = SharedPrefs.getString('testerString') + setCurrentTestOutput(`${str}`) + }}> + <ButtonText>Remove String</ButtonText> + </Button> + <Button + label="btn" + testID="setBoolBtn" + style={[a.self_center]} + variant="solid" + color="primary" + size="small" + onPress={async () => { + SharedPrefs.removeValue('testerBool') + SharedPrefs.setValue('testerBool', true) + const bool = SharedPrefs.getBool('testerBool') + setCurrentTestOutput(`${bool}`) + }}> + <ButtonText>Set Bool</ButtonText> + </Button> + <Button + label="btn" + testID="setNumberBtn" + style={[a.self_center]} + variant="solid" + color="primary" + size="small" + onPress={async () => { + SharedPrefs.removeValue('testerNumber') + SharedPrefs.setValue('testerNumber', 123) + const num = SharedPrefs.getNumber('testerNumber') + setCurrentTestOutput(`${num}`) + }}> + <ButtonText>Set Number</ButtonText> + </Button> + <Button + label="btn" + testID="addToSetBtn" + style={[a.self_center]} + variant="solid" + color="primary" + size="small" + onPress={async () => { + SharedPrefs.removeFromSet('testerSet', 'Hello!') + SharedPrefs.addToSet('testerSet', 'Hello!') + const contains = SharedPrefs.setContains('testerSet', 'Hello!') + setCurrentTestOutput(`${contains}`) + }}> + <ButtonText>Add to Set</ButtonText> + </Button> + <Button + label="btn" + testID="removeFromSetBtn" + style={[a.self_center]} + variant="solid" + color="primary" + size="small" + onPress={async () => { + SharedPrefs.removeFromSet('testerSet', 'Hello!') + const contains = SharedPrefs.setContains('testerSet', 'Hello!') + setCurrentTestOutput(`${contains}`) + }}> + <ButtonText>Remove from Set</ButtonText> + </Button> + </View> </View> - <View style={[a.flex_wrap]}> - <Button - label="btn" - testID="setStringBtn" - style={[a.self_center]} - variant="solid" - color="primary" - size="small" - onPress={async () => { - SharedPrefs.removeValue('testerString') - SharedPrefs.setValue('testerString', 'Hello') - const str = SharedPrefs.getString('testerString') - console.log(JSON.stringify(str)) - setCurrentTestOutput(`${str}`) - }}> - <ButtonText>Set String</ButtonText> - </Button> - <Button - label="btn" - testID="removeStringBtn" - style={[a.self_center]} - variant="solid" - color="primary" - size="small" - onPress={async () => { - SharedPrefs.removeValue('testerString') - const str = SharedPrefs.getString('testerString') - setCurrentTestOutput(`${str}`) - }}> - <ButtonText>Remove String</ButtonText> - </Button> - <Button - label="btn" - testID="setBoolBtn" - style={[a.self_center]} - variant="solid" - color="primary" - size="small" - onPress={async () => { - SharedPrefs.removeValue('testerBool') - SharedPrefs.setValue('testerBool', true) - const bool = SharedPrefs.getBool('testerBool') - setCurrentTestOutput(`${bool}`) - }}> - <ButtonText>Set Bool</ButtonText> - </Button> - <Button - label="btn" - testID="setNumberBtn" - style={[a.self_center]} - variant="solid" - color="primary" - size="small" - onPress={async () => { - SharedPrefs.removeValue('testerNumber') - SharedPrefs.setValue('testerNumber', 123) - const num = SharedPrefs.getNumber('testerNumber') - setCurrentTestOutput(`${num}`) - }}> - <ButtonText>Set Number</ButtonText> - </Button> - <Button - label="btn" - testID="addToSetBtn" - style={[a.self_center]} - variant="solid" - color="primary" - size="small" - onPress={async () => { - SharedPrefs.removeFromSet('testerSet', 'Hello!') - SharedPrefs.addToSet('testerSet', 'Hello!') - const contains = SharedPrefs.setContains('testerSet', 'Hello!') - setCurrentTestOutput(`${contains}`) - }}> - <ButtonText>Add to Set</ButtonText> - </Button> - <Button - label="btn" - testID="removeFromSetBtn" - style={[a.self_center]} - variant="solid" - color="primary" - size="small" - onPress={async () => { - SharedPrefs.removeFromSet('testerSet', 'Hello!') - const contains = SharedPrefs.setContains('testerSet', 'Hello!') - setCurrentTestOutput(`${contains}`) - }}> - <ButtonText>Remove from Set</ButtonText> - </Button> - </View> - </View> - </ScrollView> + </ScrollView> + </Layout.Screen> ) } diff --git a/src/screens/Hashtag.tsx b/src/screens/Hashtag.tsx index 964cb0191..adf5f0080 100644 --- a/src/screens/Hashtag.tsx +++ b/src/screens/Hashtag.tsx @@ -6,23 +6,24 @@ import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' import {NativeStackScreenProps} from '@react-navigation/native-stack' -import {HITSLOP_10} from 'lib/constants' -import {useInitialNumToRender} from 'lib/hooks/useInitialNumToRender' -import {CommonNavigatorParams} from 'lib/routes/types' -import {shareUrl} from 'lib/sharing' -import {cleanError} from 'lib/strings/errors' -import {sanitizeHandle} from 'lib/strings/handles' -import {enforceLen} from 'lib/strings/helpers' -import {isNative, isWeb} from 'platform/detection' -import {useSearchPostsQuery} from 'state/queries/search-posts' -import {useSetDrawerSwipeDisabled, useSetMinimalShellMode} from 'state/shell' +import {HITSLOP_10} from '#/lib/constants' +import {useInitialNumToRender} from '#/lib/hooks/useInitialNumToRender' +import {CommonNavigatorParams} from '#/lib/routes/types' +import {shareUrl} from '#/lib/sharing' +import {cleanError} from '#/lib/strings/errors' +import {sanitizeHandle} from '#/lib/strings/handles' +import {enforceLen} from '#/lib/strings/helpers' +import {isNative, isWeb} from '#/platform/detection' +import {useSearchPostsQuery} from '#/state/queries/search-posts' +import {useSetDrawerSwipeDisabled, useSetMinimalShellMode} from '#/state/shell' import {Pager} from '#/view/com/pager/Pager' import {TabBar} from '#/view/com/pager/TabBar' +import {Post} from '#/view/com/post/Post' +import {List} from '#/view/com/util/List' +import {ViewHeader} from '#/view/com/util/ViewHeader' import {CenteredView} from '#/view/com/util/Views' -import {Post} from 'view/com/post/Post' -import {List} from 'view/com/util/List' -import {ViewHeader} from 'view/com/util/ViewHeader' import {ArrowOutOfBox_Stroke2_Corner0_Rounded} from '#/components/icons/ArrowOutOfBox' +import * as Layout from '#/components/Layout' import {ListFooter, ListMaybePlaceholder} from '#/components/Lists' const renderItem = ({item}: ListRenderItemInfo<PostView>) => { @@ -108,7 +109,7 @@ export default function HashtagScreen({ }, [_, fullTag, author, activeTab]) return ( - <> + <Layout.Screen> <CenteredView sideBorders={true}> <ViewHeader showOnDesktop @@ -155,7 +156,7 @@ export default function HashtagScreen({ <View key={i}>{section.component}</View> ))} </Pager> - </> + </Layout.Screen> ) } diff --git a/src/screens/Messages/ChatList.tsx b/src/screens/Messages/ChatList.tsx index 9912456e1..45b3bf14f 100644 --- a/src/screens/Messages/ChatList.tsx +++ b/src/screens/Messages/ChatList.tsx @@ -28,6 +28,7 @@ import {CircleInfo_Stroke2_Corner0_Rounded as CircleInfo} from '#/components/ico import {Message_Stroke2_Corner0_Rounded as Message} from '#/components/icons/Message' import {PlusLarge_Stroke2_Corner0_Rounded as Plus} from '#/components/icons/Plus' import {SettingsSliderVertical_Stroke2_Corner0_Rounded as SettingsSlider} from '#/components/icons/SettingsSlider' +import * as Layout from '#/components/Layout' import {Link} from '#/components/Link' import {ListFooter} from '#/components/Lists' import {Loader} from '#/components/Loader' @@ -149,7 +150,7 @@ export function MessagesScreen({navigation, route}: Props) { if (conversations.length < 1) { return ( - <View style={a.flex_1}> + <Layout.Screen> <CenteredView sideBorders={gtMobile} style={[a.h_full_vh]}> {gtMobile ? ( <DesktopHeader @@ -231,12 +232,12 @@ export function MessagesScreen({navigation, route}: Props) { {!isLoading && !isError && ( <NewChat onNewChat={onNewChat} control={newChatControl} /> )} - </View> + </Layout.Screen> ) } return ( - <View style={a.flex_1}> + <Layout.Screen testID="messagesScreen"> {!gtMobile && ( <ViewHeader title={_(msg`Messages`)} @@ -276,7 +277,7 @@ export function MessagesScreen({navigation, route}: Props) { // @ts-ignore our .web version only -sfn desktopFixedHeight /> - </View> + </Layout.Screen> ) } diff --git a/src/screens/Messages/Conversation.tsx b/src/screens/Messages/Conversation.tsx index 21fdfe0ea..651915738 100644 --- a/src/screens/Messages/Conversation.tsx +++ b/src/screens/Messages/Conversation.tsx @@ -18,10 +18,11 @@ import {useProfileQuery} from '#/state/queries/profile' import {useSetMinimalShellMode} from '#/state/shell' import {CenteredView} from '#/view/com/util/Views' import {MessagesList} from '#/screens/Messages/components/MessagesList' -import {atoms as a, useBreakpoints, useTheme} from '#/alf' +import {atoms as a, useBreakpoints, useTheme, web} from '#/alf' import {MessagesListBlockedFooter} from '#/components/dms/MessagesListBlockedFooter' import {MessagesListHeader} from '#/components/dms/MessagesListHeader' import {Error} from '#/components/Error' +import * as Layout from '#/components/Layout' import {Loader} from '#/components/Loader' type Props = NativeStackScreenProps< @@ -64,9 +65,11 @@ export function MessagesConversationScreen({route}: Props) { ) return ( - <ConvoProvider key={convoId} convoId={convoId}> - <Inner /> - </ConvoProvider> + <Layout.Screen testID="convoScreen" style={web([{minHeight: 0}, a.flex_1])}> + <ConvoProvider key={convoId} convoId={convoId}> + <Inner /> + </ConvoProvider> + </Layout.Screen> ) } @@ -100,7 +103,7 @@ function Inner() { if (convoState.status === ConvoStatus.Error) { return ( - <CenteredView style={a.flex_1} sideBorders> + <CenteredView style={[a.flex_1]} sideBorders> <MessagesListHeader /> <Error title={_(msg`Something went wrong`)} diff --git a/src/screens/Messages/Settings.tsx b/src/screens/Messages/Settings.tsx index a7b55229f..93e3bc400 100644 --- a/src/screens/Messages/Settings.tsx +++ b/src/screens/Messages/Settings.tsx @@ -16,6 +16,7 @@ import {atoms as a} from '#/alf' import {Admonition} from '#/components/Admonition' import {Divider} from '#/components/Divider' import * as Toggle from '#/components/forms/Toggle' +import * as Layout from '#/components/Layout' import {Text} from '#/components/Typography' import {useBackgroundNotificationPreferences} from '../../../modules/expo-background-notification-handler/src/BackgroundNotificationHandlerProvider' @@ -55,91 +56,93 @@ export function MessagesSettingsScreen({}: Props) { ) return ( - <ScrollView stickyHeaderIndices={[0]}> - <ViewHeader title={_(msg`Chat Settings`)} showOnDesktop showBorder /> - <View style={[a.p_lg, a.gap_md]}> - <Text style={[a.text_lg, a.font_bold]}> - <Trans>Allow new messages from</Trans> - </Text> - <Toggle.Group - label={_(msg`Allow new messages from`)} - type="radio" - values={[ - (profile?.associated?.chat?.allowIncoming as AllowIncoming) ?? - 'following', - ]} - onChange={onSelectMessagesFrom}> - <View> - <Toggle.Item - name="all" - label={_(msg`Everyone`)} - style={[a.justify_between, a.py_sm]}> - <Toggle.LabelText> - <Trans>Everyone</Trans> - </Toggle.LabelText> - <Toggle.Radio /> - </Toggle.Item> - <Toggle.Item - name="following" - label={_(msg`Users I follow`)} - style={[a.justify_between, a.py_sm]}> - <Toggle.LabelText> - <Trans>Users I follow</Trans> - </Toggle.LabelText> - <Toggle.Radio /> - </Toggle.Item> - <Toggle.Item - name="none" - label={_(msg`No one`)} - style={[a.justify_between, a.py_sm]}> - <Toggle.LabelText> - <Trans>No one</Trans> - </Toggle.LabelText> - <Toggle.Radio /> - </Toggle.Item> - </View> - </Toggle.Group> - <Admonition type="tip"> - <Trans> - You can continue ongoing conversations regardless of which setting - you choose. - </Trans> - </Admonition> - {isNative && ( - <> - <Divider style={a.my_md} /> - <Text style={[a.text_lg, a.font_bold]}> - <Trans>Notification Sounds</Trans> - </Text> - <Toggle.Group - label={_(msg`Notification sounds`)} - type="radio" - values={[preferences.playSoundChat ? 'enabled' : 'disabled']} - onChange={onSelectSoundSetting}> - <View> - <Toggle.Item - name="enabled" - label={_(msg`Enabled`)} - style={[a.justify_between, a.py_sm]}> - <Toggle.LabelText> - <Trans>Enabled</Trans> - </Toggle.LabelText> - <Toggle.Radio /> - </Toggle.Item> - <Toggle.Item - name="disabled" - label={_(msg`Disabled`)} - style={[a.justify_between, a.py_sm]}> - <Toggle.LabelText> - <Trans>Disabled</Trans> - </Toggle.LabelText> - <Toggle.Radio /> - </Toggle.Item> - </View> - </Toggle.Group> - </> - )} - </View> - </ScrollView> + <Layout.Screen testID="messagesSettingsScreen"> + <ScrollView stickyHeaderIndices={[0]}> + <ViewHeader title={_(msg`Chat Settings`)} showOnDesktop showBorder /> + <View style={[a.p_lg, a.gap_md]}> + <Text style={[a.text_lg, a.font_bold]}> + <Trans>Allow new messages from</Trans> + </Text> + <Toggle.Group + label={_(msg`Allow new messages from`)} + type="radio" + values={[ + (profile?.associated?.chat?.allowIncoming as AllowIncoming) ?? + 'following', + ]} + onChange={onSelectMessagesFrom}> + <View> + <Toggle.Item + name="all" + label={_(msg`Everyone`)} + style={[a.justify_between, a.py_sm]}> + <Toggle.LabelText> + <Trans>Everyone</Trans> + </Toggle.LabelText> + <Toggle.Radio /> + </Toggle.Item> + <Toggle.Item + name="following" + label={_(msg`Users I follow`)} + style={[a.justify_between, a.py_sm]}> + <Toggle.LabelText> + <Trans>Users I follow</Trans> + </Toggle.LabelText> + <Toggle.Radio /> + </Toggle.Item> + <Toggle.Item + name="none" + label={_(msg`No one`)} + style={[a.justify_between, a.py_sm]}> + <Toggle.LabelText> + <Trans>No one</Trans> + </Toggle.LabelText> + <Toggle.Radio /> + </Toggle.Item> + </View> + </Toggle.Group> + <Admonition type="tip"> + <Trans> + You can continue ongoing conversations regardless of which setting + you choose. + </Trans> + </Admonition> + {isNative && ( + <> + <Divider style={a.my_md} /> + <Text style={[a.text_lg, a.font_bold]}> + <Trans>Notification Sounds</Trans> + </Text> + <Toggle.Group + label={_(msg`Notification sounds`)} + type="radio" + values={[preferences.playSoundChat ? 'enabled' : 'disabled']} + onChange={onSelectSoundSetting}> + <View> + <Toggle.Item + name="enabled" + label={_(msg`Enabled`)} + style={[a.justify_between, a.py_sm]}> + <Toggle.LabelText> + <Trans>Enabled</Trans> + </Toggle.LabelText> + <Toggle.Radio /> + </Toggle.Item> + <Toggle.Item + name="disabled" + label={_(msg`Disabled`)} + style={[a.justify_between, a.py_sm]}> + <Toggle.LabelText> + <Trans>Disabled</Trans> + </Toggle.LabelText> + <Toggle.Radio /> + </Toggle.Item> + </View> + </Toggle.Group> + </> + )} + </View> + </ScrollView> + </Layout.Screen> ) } diff --git a/src/screens/Moderation/index.tsx b/src/screens/Moderation/index.tsx index 070b87950..222774e05 100644 --- a/src/screens/Moderation/index.tsx +++ b/src/screens/Moderation/index.tsx @@ -41,6 +41,7 @@ import {Filter_Stroke2_Corner0_Rounded as Filter} from '#/components/icons/Filte import {Group3_Stroke2_Corner0_Rounded as Group} from '#/components/icons/Group' import {Person_Stroke2_Corner0_Rounded as Person} from '#/components/icons/Person' import * as LabelingService from '#/components/LabelingServiceCard' +import * as Layout from '#/components/Layout' import {InlineLinkText, Link} from '#/components/Link' import {Loader} from '#/components/Loader' import {GlobalLabelPreference} from '#/components/moderation/LabelPreference' @@ -94,31 +95,33 @@ export function ModerationScreen( const error = preferencesError return ( - <CenteredView - testID="moderationScreen" - style={[ - t.atoms.border_contrast_low, - t.atoms.bg, - {minHeight: height}, - ...(gtMobile ? [a.border_l, a.border_r] : []), - ]}> - <ViewHeader title={_(msg`Moderation`)} showOnDesktop /> + <Layout.Screen testID="moderationScreen"> + <CenteredView + testID="moderationScreen" + style={[ + t.atoms.border_contrast_low, + t.atoms.bg, + {minHeight: height}, + ...(gtMobile ? [a.border_l, a.border_r] : []), + ]}> + <ViewHeader title={_(msg`Moderation`)} showOnDesktop /> - {isLoading ? ( - <View style={[a.w_full, a.align_center, a.pt_2xl]}> - <Loader size="xl" fill={t.atoms.text.color} /> - </View> - ) : error || !preferences ? ( - <ErrorState - error={ - preferencesError?.toString() || - _(msg`Something went wrong, please try again.`) - } - /> - ) : ( - <ModerationScreenInner preferences={preferences} /> - )} - </CenteredView> + {isLoading ? ( + <View style={[a.w_full, a.align_center, a.pt_2xl]}> + <Loader size="xl" fill={t.atoms.text.color} /> + </View> + ) : error || !preferences ? ( + <ErrorState + error={ + preferencesError?.toString() || + _(msg`Something went wrong, please try again.`) + } + /> + ) : ( + <ModerationScreenInner preferences={preferences} /> + )} + </CenteredView> + </Layout.Screen> ) } diff --git a/src/screens/Post/PostLikedBy.tsx b/src/screens/Post/PostLikedBy.tsx index ea522488c..6fc485f34 100644 --- a/src/screens/Post/PostLikedBy.tsx +++ b/src/screens/Post/PostLikedBy.tsx @@ -5,12 +5,12 @@ import {useFocusEffect} from '@react-navigation/native' import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' import {makeRecordUri} from '#/lib/strings/url-helpers' +import {isWeb} from '#/platform/detection' import {useSetMinimalShellMode} from '#/state/shell' -import {isWeb} from 'platform/detection' import {PostLikedBy as PostLikedByComponent} from '#/view/com/post-thread/PostLikedBy' import {ViewHeader} from '#/view/com/util/ViewHeader' -import {CenteredView} from 'view/com/util/Views' -import {atoms as a} from '#/alf' +import {CenteredView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' import {ListHeaderDesktop} from '#/components/Lists' type Props = NativeStackScreenProps<CommonNavigatorParams, 'PostLikedBy'> @@ -27,10 +27,12 @@ export const PostLikedByScreen = ({route}: Props) => { ) return ( - <CenteredView style={a.util_screen_outer} sideBorders={true}> - <ListHeaderDesktop title={_(msg`Liked By`)} /> - <ViewHeader title={_(msg`Liked By`)} showBorder={!isWeb} /> - <PostLikedByComponent uri={uri} /> - </CenteredView> + <Layout.Screen> + <CenteredView sideBorders={true}> + <ListHeaderDesktop title={_(msg`Liked By`)} /> + <ViewHeader title={_(msg`Liked By`)} showBorder={!isWeb} /> + <PostLikedByComponent uri={uri} /> + </CenteredView> + </Layout.Screen> ) } diff --git a/src/screens/Post/PostQuotes.tsx b/src/screens/Post/PostQuotes.tsx index 0d59418f1..71dd8ad8d 100644 --- a/src/screens/Post/PostQuotes.tsx +++ b/src/screens/Post/PostQuotes.tsx @@ -5,12 +5,12 @@ import {useFocusEffect} from '@react-navigation/native' import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' import {makeRecordUri} from '#/lib/strings/url-helpers' +import {isWeb} from '#/platform/detection' import {useSetMinimalShellMode} from '#/state/shell' -import {isWeb} from 'platform/detection' import {PostQuotes as PostQuotesComponent} from '#/view/com/post-thread/PostQuotes' import {ViewHeader} from '#/view/com/util/ViewHeader' -import {CenteredView} from 'view/com/util/Views' -import {atoms as a} from '#/alf' +import {CenteredView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' import {ListHeaderDesktop} from '#/components/Lists' type Props = NativeStackScreenProps<CommonNavigatorParams, 'PostQuotes'> @@ -27,10 +27,12 @@ export const PostQuotesScreen = ({route}: Props) => { ) return ( - <CenteredView style={a.util_screen_outer} sideBorders={true}> - <ListHeaderDesktop title={_(msg`Quotes`)} /> - <ViewHeader title={_(msg`Quotes`)} showBorder={!isWeb} /> - <PostQuotesComponent uri={uri} /> - </CenteredView> + <Layout.Screen> + <CenteredView sideBorders={true}> + <ListHeaderDesktop title={_(msg`Quotes`)} /> + <ViewHeader title={_(msg`Quotes`)} showBorder={!isWeb} /> + <PostQuotesComponent uri={uri} /> + </CenteredView> + </Layout.Screen> ) } diff --git a/src/screens/Post/PostRepostedBy.tsx b/src/screens/Post/PostRepostedBy.tsx index f8c058ff7..c1e8b2987 100644 --- a/src/screens/Post/PostRepostedBy.tsx +++ b/src/screens/Post/PostRepostedBy.tsx @@ -5,12 +5,12 @@ import {useFocusEffect} from '@react-navigation/native' import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' import {makeRecordUri} from '#/lib/strings/url-helpers' +import {isWeb} from '#/platform/detection' import {useSetMinimalShellMode} from '#/state/shell' -import {isWeb} from 'platform/detection' import {PostRepostedBy as PostRepostedByComponent} from '#/view/com/post-thread/PostRepostedBy' import {ViewHeader} from '#/view/com/util/ViewHeader' -import {CenteredView} from 'view/com/util/Views' -import {atoms as a} from '#/alf' +import {CenteredView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' import {ListHeaderDesktop} from '#/components/Lists' type Props = NativeStackScreenProps<CommonNavigatorParams, 'PostRepostedBy'> @@ -27,10 +27,12 @@ export const PostRepostedByScreen = ({route}: Props) => { ) return ( - <CenteredView style={a.util_screen_outer} sideBorders={true}> - <ListHeaderDesktop title={_(msg`Reposted By`)} /> - <ViewHeader title={_(msg`Reposted By`)} showBorder={!isWeb} /> - <PostRepostedByComponent uri={uri} /> - </CenteredView> + <Layout.Screen> + <CenteredView sideBorders={true}> + <ListHeaderDesktop title={_(msg`Reposted By`)} /> + <ViewHeader title={_(msg`Reposted By`)} showBorder={!isWeb} /> + <PostRepostedByComponent uri={uri} /> + </CenteredView> + </Layout.Screen> ) } diff --git a/src/screens/Profile/KnownFollowers.tsx b/src/screens/Profile/KnownFollowers.tsx index 5cb45a11e..7e396c350 100644 --- a/src/screens/Profile/KnownFollowers.tsx +++ b/src/screens/Profile/KnownFollowers.tsx @@ -1,20 +1,20 @@ import React from 'react' -import {View} from 'react-native' import {AppBskyActorDefs} from '@atproto/api' import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' +import {useInitialNumToRender} from '#/lib/hooks/useInitialNumToRender' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' import {cleanError} from '#/lib/strings/errors' import {logger} from '#/logger' import {useProfileKnownFollowersQuery} from '#/state/queries/known-followers' import {useResolveDidQuery} from '#/state/queries/resolve-uri' import {useSetMinimalShellMode} from '#/state/shell' -import {useInitialNumToRender} from 'lib/hooks/useInitialNumToRender' -import {CommonNavigatorParams, NativeStackScreenProps} from 'lib/routes/types' import {ProfileCardWithFollowBtn} from '#/view/com/profile/ProfileCard' import {List} from '#/view/com/util/List' import {ViewHeader} from '#/view/com/util/ViewHeader' +import * as Layout from '#/components/Layout' import { ListFooter, ListHeaderDesktop, @@ -92,19 +92,21 @@ export const ProfileKnownFollowersScreen = ({route}: Props) => { if (followers.length < 1) { return ( - <ListMaybePlaceholder - isLoading={isDidLoading || isFollowersLoading} - isError={isError} - emptyType="results" - emptyMessage={_(msg`You don't follow any users who follow @${name}.`)} - errorMessage={cleanError(resolveError || error)} - onRetry={isError ? refetch : undefined} - /> + <Layout.Screen> + <ListMaybePlaceholder + isLoading={isDidLoading || isFollowersLoading} + isError={isError} + emptyType="results" + emptyMessage={_(msg`You don't follow any users who follow @${name}.`)} + errorMessage={cleanError(resolveError || error)} + onRetry={isError ? refetch : undefined} + /> + </Layout.Screen> ) } return ( - <View style={{flex: 1}}> + <Layout.Screen> <ViewHeader title={_(msg`Followers you know`)} /> <List data={followers} @@ -129,6 +131,6 @@ export const ProfileKnownFollowersScreen = ({route}: Props) => { initialNumToRender={initialNumToRender} windowSize={11} /> - </View> + </Layout.Screen> ) } diff --git a/src/screens/Profile/ProfileLabelerLikedBy.tsx b/src/screens/Profile/ProfileLabelerLikedBy.tsx index 8650ac2e6..ccc270084 100644 --- a/src/screens/Profile/ProfileLabelerLikedBy.tsx +++ b/src/screens/Profile/ProfileLabelerLikedBy.tsx @@ -1,5 +1,4 @@ import React from 'react' -import {View} from 'react-native' import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' @@ -8,6 +7,7 @@ import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' import {makeRecordUri} from '#/lib/strings/url-helpers' import {useSetMinimalShellMode} from '#/state/shell' import {ViewHeader} from '#/view/com/util/ViewHeader' +import * as Layout from '#/components/Layout' import {LikedByList} from '#/components/LikedByList' export function ProfileLabelerLikedByScreen({ @@ -25,9 +25,9 @@ export function ProfileLabelerLikedByScreen({ ) return ( - <View style={{flex: 1}}> + <Layout.Screen> <ViewHeader title={_(msg`Liked By`)} /> <LikedByList uri={uri} /> - </View> + </Layout.Screen> ) } diff --git a/src/screens/Settings/AppearanceSettings.tsx b/src/screens/Settings/AppearanceSettings.tsx index 69e04f4af..c317c930f 100644 --- a/src/screens/Settings/AppearanceSettings.tsx +++ b/src/screens/Settings/AppearanceSettings.tsx @@ -10,7 +10,6 @@ import {useLingui} from '@lingui/react' import {useWebMediaQueries} from '#/lib/hooks/useWebMediaQueries' import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' -import {s} from '#/lib/styles' import {useSetThemePrefs, useThemePrefs} from '#/state/shell' import {SimpleViewHeader} from '#/view/com/util/SimpleViewHeader' import {ScrollView} from '#/view/com/util/Views' @@ -21,6 +20,7 @@ import {Moon_Stroke2_Corner0_Rounded as MoonIcon} from '#/components/icons/Moon' import {Phone_Stroke2_Corner0_Rounded as PhoneIcon} from '#/components/icons/Phone' import {TextSize_Stroke2_Corner0_Rounded as TextSize} from '#/components/icons/TextSize' import {TitleCase_Stroke2_Corner0_Rounded as Aa} from '#/components/icons/TitleCase' +import * as Layout from '#/components/Layout' import {Text} from '#/components/Typography' type Props = NativeStackScreenProps<CommonNavigatorParams, 'AppearanceSettings'> @@ -76,7 +76,7 @@ export function AppearanceSettingsScreen({}: Props) { return ( <LayoutAnimationConfig skipExiting skipEntering> - <View testID="preferencesThreadsScreen" style={s.hContentRegion}> + <Layout.Screen testID="preferencesThreadsScreen"> <ScrollView // @ts-ignore web only -prf dataSet={{'stable-gutters': 1}} @@ -180,7 +180,7 @@ export function AppearanceSettingsScreen({}: Props) { </View> </View> </ScrollView> - </View> + </Layout.Screen> </LayoutAnimationConfig> ) } diff --git a/src/screens/StarterPack/StarterPackScreen.tsx b/src/screens/StarterPack/StarterPackScreen.tsx index 68803ac00..4baec9ec1 100644 --- a/src/screens/StarterPack/StarterPackScreen.tsx +++ b/src/screens/StarterPack/StarterPackScreen.tsx @@ -53,6 +53,7 @@ import {CircleInfo_Stroke2_Corner0_Rounded as CircleInfo} from '#/components/ico import {DotGrid_Stroke2_Corner0_Rounded as Ellipsis} from '#/components/icons/DotGrid' import {Pencil_Stroke2_Corner0_Rounded as Pencil} from '#/components/icons/Pencil' import {Trash_Stroke2_Corner0_Rounded as Trash} from '#/components/icons/Trash' +import * as Layout from '#/components/Layout' import {ListMaybePlaceholder} from '#/components/Lists' import {Loader} from '#/components/Loader' import * as Menu from '#/components/Menu' @@ -76,7 +77,11 @@ type StarterPackScreenShortProps = NativeStackScreenProps< > export function StarterPackScreen({route}: StarterPackScreeProps) { - return <StarterPackScreenInner routeParams={route.params} /> + return ( + <Layout.Screen> + <StarterPackScreenInner routeParams={route.params} /> + </Layout.Screen> + ) } export function StarterPackScreenShort({route}: StarterPackScreenShortProps) { @@ -91,15 +96,21 @@ export function StarterPackScreenShort({route}: StarterPackScreenShortProps) { if (isLoading || isError || !resolvedStarterPack) { return ( - <ListMaybePlaceholder - isLoading={isLoading} - isError={isError} - errorMessage={_(msg`That starter pack could not be found.`)} - emptyMessage={_(msg`That starter pack could not be found.`)} - /> + <Layout.Screen> + <ListMaybePlaceholder + isLoading={isLoading} + isError={isError} + errorMessage={_(msg`That starter pack could not be found.`)} + emptyMessage={_(msg`That starter pack could not be found.`)} + /> + </Layout.Screen> ) } - return <StarterPackScreenInner routeParams={resolvedStarterPack} /> + return ( + <Layout.Screen> + <StarterPackScreenInner routeParams={resolvedStarterPack} /> + </Layout.Screen> + ) } export function StarterPackScreenInner({ diff --git a/src/screens/StarterPack/Wizard/index.tsx b/src/screens/StarterPack/Wizard/index.tsx index 29ef44ee0..f8d503274 100644 --- a/src/screens/StarterPack/Wizard/index.tsx +++ b/src/screens/StarterPack/Wizard/index.tsx @@ -19,32 +19,32 @@ import {useLingui} from '@lingui/react' import {useFocusEffect, useNavigation} from '@react-navigation/native' import {NativeStackScreenProps} from '@react-navigation/native-stack' -import {logger} from '#/logger' -import {HITSLOP_10, STARTER_PACK_MAX_SIZE} from 'lib/constants' -import {createSanitizedDisplayName} from 'lib/moderation/create-sanitized-display-name' -import {CommonNavigatorParams, NavigationProp} from 'lib/routes/types' -import {logEvent} from 'lib/statsig/statsig' -import {sanitizeDisplayName} from 'lib/strings/display-names' -import {sanitizeHandle} from 'lib/strings/handles' -import {enforceLen} from 'lib/strings/helpers' +import {HITSLOP_10, STARTER_PACK_MAX_SIZE} from '#/lib/constants' +import {createSanitizedDisplayName} from '#/lib/moderation/create-sanitized-display-name' +import {CommonNavigatorParams, NavigationProp} from '#/lib/routes/types' +import {logEvent} from '#/lib/statsig/statsig' +import {sanitizeDisplayName} from '#/lib/strings/display-names' +import {sanitizeHandle} from '#/lib/strings/handles' +import {enforceLen} from '#/lib/strings/helpers' import { getStarterPackOgCard, parseStarterPackUri, -} from 'lib/strings/starter-pack' -import {isAndroid, isNative, isWeb} from 'platform/detection' -import {useModerationOpts} from 'state/preferences/moderation-opts' -import {useAllListMembersQuery} from 'state/queries/list-members' -import {useProfileQuery} from 'state/queries/profile' +} from '#/lib/strings/starter-pack' +import {logger} from '#/logger' +import {isAndroid, isNative, isWeb} from '#/platform/detection' +import {useModerationOpts} from '#/state/preferences/moderation-opts' +import {useAllListMembersQuery} from '#/state/queries/list-members' +import {useProfileQuery} from '#/state/queries/profile' import { useCreateStarterPackMutation, useEditStarterPackMutation, useStarterPackQuery, -} from 'state/queries/starter-packs' -import {useSession} from 'state/session' -import {useSetMinimalShellMode} from 'state/shell' +} from '#/state/queries/starter-packs' +import {useSession} from '#/state/session' +import {useSetMinimalShellMode} from '#/state/shell' import * as Toast from '#/view/com/util/Toast' -import {UserAvatar} from 'view/com/util/UserAvatar' -import {CenteredView} from 'view/com/util/Views' +import {UserAvatar} from '#/view/com/util/UserAvatar' +import {CenteredView} from '#/view/com/util/Views' import {useWizardState, WizardStep} from '#/screens/StarterPack/Wizard/State' import {StepDetails} from '#/screens/StarterPack/Wizard/StepDetails' import {StepFeeds} from '#/screens/StarterPack/Wizard/StepFeeds' @@ -52,6 +52,7 @@ import {StepProfiles} from '#/screens/StarterPack/Wizard/StepProfiles' import {atoms as a, useTheme} from '#/alf' import {Button, ButtonText} from '#/components/Button' import {useDialogControl} from '#/components/Dialog' +import * as Layout from '#/components/Layout' import {ListMaybePlaceholder} from '#/components/Lists' import {Loader} from '#/components/Loader' import {WizardEditListDialog} from '#/components/StarterPack/Wizard/WizardEditListDialog' @@ -97,33 +98,39 @@ export function Wizard({ if (!isReady) { return ( - <ListMaybePlaceholder - isLoading={ - isLoadingStarterPack || isLoadingProfiles || isLoadingProfile - } - isError={isErrorStarterPack || isErrorProfiles || isErrorProfile} - errorMessage={_(msg`That starter pack could not be found.`)} - /> + <Layout.Screen> + <ListMaybePlaceholder + isLoading={ + isLoadingStarterPack || isLoadingProfiles || isLoadingProfile + } + isError={isErrorStarterPack || isErrorProfiles || isErrorProfile} + errorMessage={_(msg`That starter pack could not be found.`)} + /> + </Layout.Screen> ) } else if (isEdit && starterPack?.creator.did !== currentAccount?.did) { return ( - <ListMaybePlaceholder - isLoading={false} - isError={true} - errorMessage={_(msg`That starter pack could not be found.`)} - /> + <Layout.Screen> + <ListMaybePlaceholder + isLoading={false} + isError={true} + errorMessage={_(msg`That starter pack could not be found.`)} + /> + </Layout.Screen> ) } return ( - <Provider starterPack={starterPack} listItems={listItems}> - <WizardInner - currentStarterPack={starterPack} - currentListItems={listItems} - profile={profile} - moderationOpts={moderationOpts} - /> - </Provider> + <Layout.Screen> + <Provider starterPack={starterPack} listItems={listItems}> + <WizardInner + currentStarterPack={starterPack} + currentListItems={listItems} + profile={profile} + moderationOpts={moderationOpts} + /> + </Provider> + </Layout.Screen> ) } diff --git a/src/view/screens/AccessibilitySettings.tsx b/src/view/screens/AccessibilitySettings.tsx index 5d314e8e6..bf9f5fcb5 100644 --- a/src/view/screens/AccessibilitySettings.tsx +++ b/src/view/screens/AccessibilitySettings.tsx @@ -27,6 +27,7 @@ import {SimpleViewHeader} from '#/view/com/util/SimpleViewHeader' import {Text} from '#/view/com/util/text/Text' import {ScrollView} from '#/view/com/util/Views' import {atoms as a} from '#/alf' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -54,7 +55,7 @@ export function AccessibilitySettingsScreen({}: Props) { ) return ( - <View style={s.hContentRegion} testID="accessibilitySettingsScreen"> + <Layout.Screen testID="accessibilitySettingsScreen"> <SimpleViewHeader showBackButton={isTabletOrMobile} style={[ @@ -128,7 +129,7 @@ export function AccessibilitySettingsScreen({}: Props) { </> )} </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/AppPasswords.tsx b/src/view/screens/AppPasswords.tsx index 21a9cb0eb..48abd964f 100644 --- a/src/view/screens/AppPasswords.tsx +++ b/src/view/screens/AppPasswords.tsx @@ -30,10 +30,19 @@ import {ViewHeader} from '#/view/com/util/ViewHeader' import {CenteredView} from '#/view/com/util/Views' import {atoms as a} from '#/alf' import {useDialogControl} from '#/components/Dialog' +import * as Layout from '#/components/Layout' import * as Prompt from '#/components/Prompt' type Props = NativeStackScreenProps<CommonNavigatorParams, 'AppPasswords'> export function AppPasswords({}: Props) { + return ( + <Layout.Screen testID="AppPasswordsScreen"> + <AppPasswordsInner /> + </Layout.Screen> + ) +} + +function AppPasswordsInner() { const pal = usePalette('default') const {_} = useLingui() const setMinimalShellMode = useSetMinimalShellMode() diff --git a/src/view/screens/CommunityGuidelines.tsx b/src/view/screens/CommunityGuidelines.tsx index f6c29a3b8..76993d5b7 100644 --- a/src/view/screens/CommunityGuidelines.tsx +++ b/src/view/screens/CommunityGuidelines.tsx @@ -1,16 +1,18 @@ import React from 'react' import {View} from 'react-native' +import {msg, Trans} from '@lingui/macro' +import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' -import {Text} from 'view/com/util/text/Text' -import {TextLink} from 'view/com/util/Link' -import {NativeStackScreenProps, CommonNavigatorParams} from 'lib/routes/types' -import {ViewHeader} from '../com/util/ViewHeader' -import {ScrollView} from 'view/com/util/Views' -import {usePalette} from 'lib/hooks/usePalette' -import {s} from 'lib/styles' + +import {usePalette} from '#/lib/hooks/usePalette' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {s} from '#/lib/styles' import {useSetMinimalShellMode} from '#/state/shell' -import {Trans, msg} from '@lingui/macro' -import {useLingui} from '@lingui/react' +import {TextLink} from '#/view/com/util/Link' +import {Text} from '#/view/com/util/text/Text' +import {ScrollView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' +import {ViewHeader} from '../com/util/ViewHeader' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -28,7 +30,7 @@ export const CommunityGuidelinesScreen = (_props: Props) => { ) return ( - <View> + <Layout.Screen> <ViewHeader title={_(msg`Community Guidelines`)} /> <ScrollView style={[s.hContentRegion, pal.view]}> <View style={[s.p20]}> @@ -45,6 +47,6 @@ export const CommunityGuidelinesScreen = (_props: Props) => { </View> <View style={s.footerSpacer} /> </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/CopyrightPolicy.tsx b/src/view/screens/CopyrightPolicy.tsx index 522a9e4db..fe2731c53 100644 --- a/src/view/screens/CopyrightPolicy.tsx +++ b/src/view/screens/CopyrightPolicy.tsx @@ -1,16 +1,18 @@ import React from 'react' import {View} from 'react-native' +import {msg, Trans} from '@lingui/macro' +import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' -import {Text} from 'view/com/util/text/Text' -import {TextLink} from 'view/com/util/Link' -import {NativeStackScreenProps, CommonNavigatorParams} from 'lib/routes/types' -import {ViewHeader} from '../com/util/ViewHeader' -import {ScrollView} from 'view/com/util/Views' -import {usePalette} from 'lib/hooks/usePalette' -import {s} from 'lib/styles' + +import {usePalette} from '#/lib/hooks/usePalette' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {s} from '#/lib/styles' import {useSetMinimalShellMode} from '#/state/shell' -import {Trans, msg} from '@lingui/macro' -import {useLingui} from '@lingui/react' +import {TextLink} from '#/view/com/util/Link' +import {Text} from '#/view/com/util/text/Text' +import {ScrollView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' +import {ViewHeader} from '../com/util/ViewHeader' type Props = NativeStackScreenProps<CommonNavigatorParams, 'CopyrightPolicy'> export const CopyrightPolicyScreen = (_props: Props) => { @@ -25,7 +27,7 @@ export const CopyrightPolicyScreen = (_props: Props) => { ) return ( - <View> + <Layout.Screen> <ViewHeader title={_(msg`Copyright Policy`)} /> <ScrollView style={[s.hContentRegion, pal.view]}> <View style={[s.p20]}> @@ -42,6 +44,6 @@ export const CopyrightPolicyScreen = (_props: Props) => { </View> <View style={s.footerSpacer} /> </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/Debug.tsx b/src/view/screens/Debug.tsx index f26b1505a..60dc089dd 100644 --- a/src/view/screens/Debug.tsx +++ b/src/view/screens/Debug.tsx @@ -1,24 +1,29 @@ import React from 'react' import {ScrollView, View} from 'react-native' -import {NativeStackScreenProps, CommonNavigatorParams} from 'lib/routes/types' -import {ViewHeader} from '../com/util/ViewHeader' -import {ThemeProvider, PaletteColorName} from 'lib/ThemeContext' -import {usePalette} from 'lib/hooks/usePalette' -import {s} from 'lib/styles' -import * as Toast from 'view/com/util/Toast' -import {Text} from '../com/util/text/Text' -import {ViewSelector} from '../com/util/ViewSelector' -import {EmptyState} from '../com/util/EmptyState' -import * as LoadingPlaceholder from '../com/util/LoadingPlaceholder' -import {Button, ButtonType} from '../com/util/forms/Button' -import {DropdownButton, DropdownItem} from '../com/util/forms/DropdownButton' -import {ToggleButton} from '../com/util/forms/ToggleButton' -import {RadioGroup} from '../com/util/forms/RadioGroup' -import {ErrorScreen} from '../com/util/error/ErrorScreen' -import {ErrorMessage} from '../com/util/error/ErrorMessage' import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' +import {usePalette} from '#/lib/hooks/usePalette' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {s} from '#/lib/styles' +import {PaletteColorName, ThemeProvider} from '#/lib/ThemeContext' +import {EmptyState} from '#/view/com/util/EmptyState' +import {ErrorMessage} from '#/view/com/util/error/ErrorMessage' +import {ErrorScreen} from '#/view/com/util/error/ErrorScreen' +import {Button, ButtonType} from '#/view/com/util/forms/Button' +import { + DropdownButton, + DropdownItem, +} from '#/view/com/util/forms/DropdownButton' +import {RadioGroup} from '#/view/com/util/forms/RadioGroup' +import {ToggleButton} from '#/view/com/util/forms/ToggleButton' +import * as LoadingPlaceholder from '#/view/com/util/LoadingPlaceholder' +import {Text} from '#/view/com/util/text/Text' +import * as Toast from '#/view/com/util/Toast' +import {ViewHeader} from '#/view/com/util/ViewHeader' +import {ViewSelector} from '#/view/com/util/ViewSelector' +import * as Layout from '#/components/Layout' + const MAIN_VIEWS = ['Base', 'Controls', 'Error', 'Notifs'] export const DebugScreen = ({}: NativeStackScreenProps< @@ -33,10 +38,12 @@ export const DebugScreen = ({}: NativeStackScreenProps< } return ( <ThemeProvider theme={colorScheme}> - <DebugInner - colorScheme={colorScheme} - onToggleColorScheme={onToggleColorScheme} - /> + <Layout.Screen> + <DebugInner + colorScheme={colorScheme} + onToggleColorScheme={onToggleColorScheme} + /> + </Layout.Screen> </ThemeProvider> ) } diff --git a/src/view/screens/DebugMod.tsx b/src/view/screens/DebugMod.tsx index d83623adc..b87fc8683 100644 --- a/src/view/screens/DebugMod.tsx +++ b/src/view/screens/DebugMod.tsx @@ -21,6 +21,7 @@ import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' import {useGlobalLabelStrings} from '#/lib/moderation/useGlobalLabelStrings' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' import {moderationOptsOverrideContext} from '#/state/preferences/moderation-opts' import {FeedNotification} from '#/state/queries/notifications/types' import { @@ -28,7 +29,6 @@ import { shouldFilterNotif, } from '#/state/queries/notifications/util' import {useSession} from '#/state/session' -import {CommonNavigatorParams, NativeStackScreenProps} from 'lib/routes/types' import {CenteredView, ScrollView} from '#/view/com/util/Views' import {ProfileHeaderStandard} from '#/screens/Profile/Header/ProfileHeaderStandard' import {atoms as a, useTheme} from '#/alf' @@ -41,6 +41,7 @@ import { ChevronBottom_Stroke2_Corner0_Rounded as ChevronBottom, ChevronTop_Stroke2_Corner0_Rounded as ChevronTop, } from '#/components/icons/Chevron' +import * as Layout from '#/components/Layout' import {H1, H3, P, Text} from '#/components/Typography' import {ScreenHider} from '../../components/moderation/ScreenHider' import {FeedItem as NotifFeedItem} from '../com/notifications/FeedItem' @@ -264,309 +265,325 @@ export const DebugModScreen = ({}: NativeStackScreenProps< }, [post, modOpts]) return ( - <moderationOptsOverrideContext.Provider value={modOpts}> - <ScrollView> - <CenteredView style={[t.atoms.bg, a.px_lg, a.py_lg]}> - <H1 style={[a.text_5xl, a.font_bold, a.pb_lg]}>Moderation states</H1> - - <Heading title="" subtitle="Scenario" /> - <ToggleButton.Group - label="Scenario" - values={scenario} - onChange={setScenario}> - <ToggleButton.Button name="label" label="Label"> - <ToggleButton.ButtonText>Label</ToggleButton.ButtonText> - </ToggleButton.Button> - <ToggleButton.Button name="block" label="Block"> - <ToggleButton.ButtonText>Block</ToggleButton.ButtonText> - </ToggleButton.Button> - <ToggleButton.Button name="mute" label="Mute"> - <ToggleButton.ButtonText>Mute</ToggleButton.ButtonText> - </ToggleButton.Button> - </ToggleButton.Group> - - {scenario[0] === 'label' && ( - <> - <View - style={[ - a.border, - a.rounded_sm, - a.mt_lg, - a.mb_lg, - a.p_lg, - t.atoms.border_contrast_medium, - ]}> - <Toggle.Group - label="Toggle" - type="radio" - values={label} - onChange={setLabel}> - <View style={[a.flex_row, a.gap_md, a.flex_wrap]}> - {LABEL_VALUES.map(labelValue => { - let targetFixed = target[0] - if ( - targetFixed !== 'account' && - targetFixed !== 'profile' - ) { - targetFixed = 'content' - } - const disabled = - isSelfLabel && - LABELS[labelValue].flags.includes('no-self') - return ( - <Toggle.Item - key={labelValue} - name={labelValue} - label={labelStrings[labelValue].name} - disabled={disabled} - style={disabled ? {opacity: 0.5} : undefined}> - <Toggle.Radio /> - <Toggle.LabelText>{labelValue}</Toggle.LabelText> - </Toggle.Item> - ) - })} - <Toggle.Item - name="custom" - label="Custom label" - disabled={isSelfLabel} - style={isSelfLabel ? {opacity: 0.5} : undefined}> - <Toggle.Radio /> - <Toggle.LabelText>Custom label</Toggle.LabelText> - </Toggle.Item> - </View> - </Toggle.Group> - - {label[0] === 'custom' ? ( - <CustomLabelForm - def={customLabelDef} - setDef={setCustomLabelDef} - /> - ) : ( - <> - <View style={{height: 10}} /> - <Divider /> - </> - )} - - <View style={{height: 10}} /> - - <SmallToggler label="Advanced"> + <Layout.Screen> + <moderationOptsOverrideContext.Provider value={modOpts}> + <ScrollView> + <CenteredView style={[t.atoms.bg, a.px_lg, a.py_lg]}> + <H1 style={[a.text_5xl, a.font_bold, a.pb_lg]}> + Moderation states + </H1> + + <Heading title="" subtitle="Scenario" /> + <ToggleButton.Group + label="Scenario" + values={scenario} + onChange={setScenario}> + <ToggleButton.Button name="label" label="Label"> + <ToggleButton.ButtonText>Label</ToggleButton.ButtonText> + </ToggleButton.Button> + <ToggleButton.Button name="block" label="Block"> + <ToggleButton.ButtonText>Block</ToggleButton.ButtonText> + </ToggleButton.Button> + <ToggleButton.Button name="mute" label="Mute"> + <ToggleButton.ButtonText>Mute</ToggleButton.ButtonText> + </ToggleButton.Button> + </ToggleButton.Group> + + {scenario[0] === 'label' && ( + <> + <View + style={[ + a.border, + a.rounded_sm, + a.mt_lg, + a.mb_lg, + a.p_lg, + t.atoms.border_contrast_medium, + ]}> <Toggle.Group label="Toggle" - type="checkbox" - values={scenarioSwitches} - onChange={setScenarioSwitches}> - <View style={[a.gap_md, a.flex_row, a.flex_wrap, a.pt_md]}> - <Toggle.Item name="targetMe" label="Target is me"> - <Toggle.Checkbox /> - <Toggle.LabelText>Target is me</Toggle.LabelText> - </Toggle.Item> - <Toggle.Item name="following" label="Following target"> - <Toggle.Checkbox /> - <Toggle.LabelText>Following target</Toggle.LabelText> - </Toggle.Item> - <Toggle.Item name="selfLabel" label="Self label"> - <Toggle.Checkbox /> - <Toggle.LabelText>Self label</Toggle.LabelText> - </Toggle.Item> - <Toggle.Item name="noAdult" label="Adult disabled"> - <Toggle.Checkbox /> - <Toggle.LabelText>Adult disabled</Toggle.LabelText> - </Toggle.Item> - <Toggle.Item name="loggedOut" label="Logged out"> - <Toggle.Checkbox /> - <Toggle.LabelText>Logged out</Toggle.LabelText> + type="radio" + values={label} + onChange={setLabel}> + <View style={[a.flex_row, a.gap_md, a.flex_wrap]}> + {LABEL_VALUES.map(labelValue => { + let targetFixed = target[0] + if ( + targetFixed !== 'account' && + targetFixed !== 'profile' + ) { + targetFixed = 'content' + } + const disabled = + isSelfLabel && + LABELS[labelValue].flags.includes('no-self') + return ( + <Toggle.Item + key={labelValue} + name={labelValue} + label={labelStrings[labelValue].name} + disabled={disabled} + style={disabled ? {opacity: 0.5} : undefined}> + <Toggle.Radio /> + <Toggle.LabelText>{labelValue}</Toggle.LabelText> + </Toggle.Item> + ) + })} + <Toggle.Item + name="custom" + label="Custom label" + disabled={isSelfLabel} + style={isSelfLabel ? {opacity: 0.5} : undefined}> + <Toggle.Radio /> + <Toggle.LabelText>Custom label</Toggle.LabelText> </Toggle.Item> </View> </Toggle.Group> - {LABELS[label[0] as keyof typeof LABELS]?.configurable !== - false && ( - <View style={[a.mt_md]}> - <Text - style={[a.font_bold, a.text_xs, t.atoms.text, a.pb_sm]}> - Preference - </Text> - <Toggle.Group - label="Preference" - type="radio" - values={visibility} - onChange={setVisiblity}> - <View + {label[0] === 'custom' ? ( + <CustomLabelForm + def={customLabelDef} + setDef={setCustomLabelDef} + /> + ) : ( + <> + <View style={{height: 10}} /> + <Divider /> + </> + )} + + <View style={{height: 10}} /> + + <SmallToggler label="Advanced"> + <Toggle.Group + label="Toggle" + type="checkbox" + values={scenarioSwitches} + onChange={setScenarioSwitches}> + <View + style={[a.gap_md, a.flex_row, a.flex_wrap, a.pt_md]}> + <Toggle.Item name="targetMe" label="Target is me"> + <Toggle.Checkbox /> + <Toggle.LabelText>Target is me</Toggle.LabelText> + </Toggle.Item> + <Toggle.Item name="following" label="Following target"> + <Toggle.Checkbox /> + <Toggle.LabelText>Following target</Toggle.LabelText> + </Toggle.Item> + <Toggle.Item name="selfLabel" label="Self label"> + <Toggle.Checkbox /> + <Toggle.LabelText>Self label</Toggle.LabelText> + </Toggle.Item> + <Toggle.Item name="noAdult" label="Adult disabled"> + <Toggle.Checkbox /> + <Toggle.LabelText>Adult disabled</Toggle.LabelText> + </Toggle.Item> + <Toggle.Item name="loggedOut" label="Logged out"> + <Toggle.Checkbox /> + <Toggle.LabelText>Logged out</Toggle.LabelText> + </Toggle.Item> + </View> + </Toggle.Group> + + {LABELS[label[0] as keyof typeof LABELS]?.configurable !== + false && ( + <View style={[a.mt_md]}> + <Text style={[ - a.flex_row, - a.gap_md, - a.flex_wrap, - a.align_center, + a.font_bold, + a.text_xs, + t.atoms.text, + a.pb_sm, ]}> - <Toggle.Item name="hide" label="Hide"> + Preference + </Text> + <Toggle.Group + label="Preference" + type="radio" + values={visibility} + onChange={setVisiblity}> + <View + style={[ + a.flex_row, + a.gap_md, + a.flex_wrap, + a.align_center, + ]}> + <Toggle.Item name="hide" label="Hide"> + <Toggle.Radio /> + <Toggle.LabelText>Hide</Toggle.LabelText> + </Toggle.Item> + <Toggle.Item name="warn" label="Warn"> + <Toggle.Radio /> + <Toggle.LabelText>Warn</Toggle.LabelText> + </Toggle.Item> + <Toggle.Item name="ignore" label="Ignore"> + <Toggle.Radio /> + <Toggle.LabelText>Ignore</Toggle.LabelText> + </Toggle.Item> + </View> + </Toggle.Group> + </View> + )} + </SmallToggler> + </View> + + <View style={[a.flex_row, a.flex_wrap, a.gap_md]}> + <View> + <Text + style={[ + a.font_bold, + a.text_xs, + t.atoms.text, + a.pl_md, + a.pb_xs, + ]}> + Target + </Text> + <View + style={[ + a.border, + a.rounded_full, + a.px_md, + a.py_sm, + t.atoms.border_contrast_medium, + t.atoms.bg, + ]}> + <Toggle.Group + label="Target" + type="radio" + values={target} + onChange={setTarget}> + <View style={[a.flex_row, a.gap_md, a.flex_wrap]}> + <Toggle.Item name="account" label="Account"> + <Toggle.Radio /> + <Toggle.LabelText>Account</Toggle.LabelText> + </Toggle.Item> + <Toggle.Item name="profile" label="Profile"> <Toggle.Radio /> - <Toggle.LabelText>Hide</Toggle.LabelText> + <Toggle.LabelText>Profile</Toggle.LabelText> </Toggle.Item> - <Toggle.Item name="warn" label="Warn"> + <Toggle.Item name="post" label="Post"> <Toggle.Radio /> - <Toggle.LabelText>Warn</Toggle.LabelText> + <Toggle.LabelText>Post</Toggle.LabelText> </Toggle.Item> - <Toggle.Item name="ignore" label="Ignore"> + <Toggle.Item name="embed" label="Embed"> <Toggle.Radio /> - <Toggle.LabelText>Ignore</Toggle.LabelText> + <Toggle.LabelText>Embed</Toggle.LabelText> </Toggle.Item> </View> </Toggle.Group> </View> - )} - </SmallToggler> - </View> - - <View style={[a.flex_row, a.flex_wrap, a.gap_md]}> - <View> - <Text - style={[ - a.font_bold, - a.text_xs, - t.atoms.text, - a.pl_md, - a.pb_xs, - ]}> - Target - </Text> - <View - style={[ - a.border, - a.rounded_full, - a.px_md, - a.py_sm, - t.atoms.border_contrast_medium, - t.atoms.bg, - ]}> - <Toggle.Group - label="Target" - type="radio" - values={target} - onChange={setTarget}> - <View style={[a.flex_row, a.gap_md, a.flex_wrap]}> - <Toggle.Item name="account" label="Account"> - <Toggle.Radio /> - <Toggle.LabelText>Account</Toggle.LabelText> - </Toggle.Item> - <Toggle.Item name="profile" label="Profile"> - <Toggle.Radio /> - <Toggle.LabelText>Profile</Toggle.LabelText> - </Toggle.Item> - <Toggle.Item name="post" label="Post"> - <Toggle.Radio /> - <Toggle.LabelText>Post</Toggle.LabelText> - </Toggle.Item> - <Toggle.Item name="embed" label="Embed"> - <Toggle.Radio /> - <Toggle.LabelText>Embed</Toggle.LabelText> - </Toggle.Item> - </View> - </Toggle.Group> </View> </View> - </View> - </> - )} - - <Spacer /> - - <Heading title="" subtitle="Results" /> - - <ToggleButton.Group label="Results" values={view} onChange={setView}> - <ToggleButton.Button name="post" label="Post"> - <ToggleButton.ButtonText>Post</ToggleButton.ButtonText> - </ToggleButton.Button> - <ToggleButton.Button name="notifications" label="Notifications"> - <ToggleButton.ButtonText>Notifications</ToggleButton.ButtonText> - </ToggleButton.Button> - <ToggleButton.Button name="account" label="Account"> - <ToggleButton.ButtonText>Account</ToggleButton.ButtonText> - </ToggleButton.Button> - <ToggleButton.Button name="data" label="Data"> - <ToggleButton.ButtonText>Data</ToggleButton.ButtonText> - </ToggleButton.Button> - </ToggleButton.Group> - - <View - style={[ - a.border, - a.rounded_sm, - a.mt_lg, - a.p_md, - t.atoms.border_contrast_medium, - ]}> - {view[0] === 'post' && ( - <> - <Heading title="Post" subtitle="in feed" /> - <MockPostFeedItem post={post} moderation={postModeration} /> - - <Heading title="Post" subtitle="viewed directly" /> - <MockPostThreadItem post={post} moderation={postModeration} /> - - <Heading title="Post" subtitle="reply in thread" /> - <MockPostThreadItem - post={post} - moderation={postModeration} - reply - /> - </> - )} - - {view[0] === 'notifications' && ( - <> - <Heading title="Notification" subtitle="quote or reply" /> - <MockNotifItem notif={replyNotif} moderationOpts={modOpts} /> - <View style={{height: 20}} /> - <Heading title="Notification" subtitle="follow or like" /> - <MockNotifItem notif={followNotif} moderationOpts={modOpts} /> </> )} - {view[0] === 'account' && ( - <> - <Heading title="Account" subtitle="in listing" /> - <MockAccountCard - profile={profile} - moderation={profileModeration} - /> - - <Heading title="Account" subtitle="viewing directly" /> - <MockAccountScreen - profile={profile} - moderation={profileModeration} - moderationOpts={modOpts} - /> - </> - )} + <Spacer /> + + <Heading title="" subtitle="Results" /> + + <ToggleButton.Group + label="Results" + values={view} + onChange={setView}> + <ToggleButton.Button name="post" label="Post"> + <ToggleButton.ButtonText>Post</ToggleButton.ButtonText> + </ToggleButton.Button> + <ToggleButton.Button name="notifications" label="Notifications"> + <ToggleButton.ButtonText>Notifications</ToggleButton.ButtonText> + </ToggleButton.Button> + <ToggleButton.Button name="account" label="Account"> + <ToggleButton.ButtonText>Account</ToggleButton.ButtonText> + </ToggleButton.Button> + <ToggleButton.Button name="data" label="Data"> + <ToggleButton.ButtonText>Data</ToggleButton.ButtonText> + </ToggleButton.Button> + </ToggleButton.Group> + + <View + style={[ + a.border, + a.rounded_sm, + a.mt_lg, + a.p_md, + t.atoms.border_contrast_medium, + ]}> + {view[0] === 'post' && ( + <> + <Heading title="Post" subtitle="in feed" /> + <MockPostFeedItem post={post} moderation={postModeration} /> + + <Heading title="Post" subtitle="viewed directly" /> + <MockPostThreadItem post={post} moderation={postModeration} /> + + <Heading title="Post" subtitle="reply in thread" /> + <MockPostThreadItem + post={post} + moderation={postModeration} + reply + /> + </> + )} + + {view[0] === 'notifications' && ( + <> + <Heading title="Notification" subtitle="quote or reply" /> + <MockNotifItem notif={replyNotif} moderationOpts={modOpts} /> + <View style={{height: 20}} /> + <Heading title="Notification" subtitle="follow or like" /> + <MockNotifItem notif={followNotif} moderationOpts={modOpts} /> + </> + )} + + {view[0] === 'account' && ( + <> + <Heading title="Account" subtitle="in listing" /> + <MockAccountCard + profile={profile} + moderation={profileModeration} + /> - {view[0] === 'data' && ( - <> - <ModerationUIView - label="Profile Moderation UI" - mod={profileModeration} - /> - <ModerationUIView - label="Post Moderation UI" - mod={postModeration} - /> - <DataView - label={label[0]} - data={LABELS[label[0] as keyof typeof LABELS]} - /> - <DataView - label="Profile Moderation Data" - data={profileModeration} - /> - <DataView label="Post Moderation Data" data={postModeration} /> - </> - )} - </View> + <Heading title="Account" subtitle="viewing directly" /> + <MockAccountScreen + profile={profile} + moderation={profileModeration} + moderationOpts={modOpts} + /> + </> + )} + + {view[0] === 'data' && ( + <> + <ModerationUIView + label="Profile Moderation UI" + mod={profileModeration} + /> + <ModerationUIView + label="Post Moderation UI" + mod={postModeration} + /> + <DataView + label={label[0]} + data={LABELS[label[0] as keyof typeof LABELS]} + /> + <DataView + label="Profile Moderation Data" + data={profileModeration} + /> + <DataView + label="Post Moderation Data" + data={postModeration} + /> + </> + )} + </View> - <View style={{height: 400}} /> - </CenteredView> - </ScrollView> - </moderationOptsOverrideContext.Provider> + <View style={{height: 400}} /> + </CenteredView> + </ScrollView> + </moderationOptsOverrideContext.Provider> + </Layout.Screen> ) } diff --git a/src/view/screens/Feeds.tsx b/src/view/screens/Feeds.tsx index 87af59f7f..404145714 100644 --- a/src/view/screens/Feeds.tsx +++ b/src/view/screens/Feeds.tsx @@ -40,6 +40,7 @@ import {ChevronRight_Stroke2_Corner0_Rounded as ChevronRight} from '#/components import {FilterTimeline_Stroke2_Corner0_Rounded as FilterTimeline} from '#/components/icons/FilterTimeline' import {ListMagnifyingGlass_Stroke2_Corner0_Rounded} from '#/components/icons/ListMagnifyingGlass' import {ListSparkle_Stroke2_Corner0_Rounded} from '#/components/icons/ListSparkle' +import * as Layout from '#/components/Layout' import * as ListCard from '#/components/ListCard' type Props = NativeStackScreenProps<CommonNavigatorParams, 'Feeds'> @@ -545,7 +546,7 @@ export function FeedsScreen(_props: Props) { ) return ( - <View style={[pal.view, styles.container]}> + <Layout.Screen testID="FeedsScreen"> {isMobile && ( <ViewHeader title={_(msg`Feeds`)} @@ -582,7 +583,7 @@ export function FeedsScreen(_props: Props) { accessibilityHint="" /> )} - </View> + </Layout.Screen> ) } @@ -768,9 +769,6 @@ function FeedsAboutHeader() { } const styles = StyleSheet.create({ - container: { - flex: 1, - }, list: { height: '100%', }, diff --git a/src/view/screens/Home.tsx b/src/view/screens/Home.tsx index 4172d6408..237449383 100644 --- a/src/view/screens/Home.tsx +++ b/src/view/screens/Home.tsx @@ -1,5 +1,5 @@ import React from 'react' -import {ActivityIndicator, StyleSheet, View} from 'react-native' +import {ActivityIndicator, StyleSheet} from 'react-native' import {useFocusEffect} from '@react-navigation/native' import {PROD_DEFAULT_FEED} from '#/lib/constants' @@ -23,12 +23,13 @@ import {useSetDrawerSwipeDisabled, useSetMinimalShellMode} from '#/state/shell' import {useLoggedOutViewControls} from '#/state/shell/logged-out' import {useSelectedFeed, useSetSelectedFeed} from '#/state/shell/selected-feed' import {FeedPage} from '#/view/com/feeds/FeedPage' +import {HomeHeader} from '#/view/com/home/HomeHeader' import {Pager, PagerRef, RenderTabBarFnProps} from '#/view/com/pager/Pager' import {CustomFeedEmptyState} from '#/view/com/posts/CustomFeedEmptyState' import {FollowingEmptyState} from '#/view/com/posts/FollowingEmptyState' import {FollowingEndOfFeed} from '#/view/com/posts/FollowingEndOfFeed' import {NoFeedsPinned} from '#/screens/Home/NoFeedsPinned' -import {HomeHeader} from '../com/home/HomeHeader' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<HomeTabNavigatorParams, 'Home' | 'Start'> export function HomeScreen(props: Props) { @@ -70,17 +71,19 @@ export function HomeScreen(props: Props) { if (preferences && pinnedFeedInfos && !isPinnedFeedsLoading) { return ( - <HomeScreenReady - {...props} - preferences={preferences} - pinnedFeedInfos={pinnedFeedInfos} - /> + <Layout.Screen testID="HomeScreen"> + <HomeScreenReady + {...props} + preferences={preferences} + pinnedFeedInfos={pinnedFeedInfos} + /> + </Layout.Screen> ) } else { return ( - <View style={styles.loading}> + <Layout.Screen style={styles.loading}> <ActivityIndicator size="large" /> - </View> + </Layout.Screen> ) } } diff --git a/src/view/screens/LanguageSettings.tsx b/src/view/screens/LanguageSettings.tsx index c1daa54e6..6af18103c 100644 --- a/src/view/screens/LanguageSettings.tsx +++ b/src/view/screens/LanguageSettings.tsx @@ -19,9 +19,10 @@ import {useModalControls} from '#/state/modals' import {useLanguagePrefs, useLanguagePrefsApi} from '#/state/preferences' import {useSetMinimalShellMode} from '#/state/shell' import {Button} from '#/view/com/util/forms/Button' +import {Text} from '#/view/com/util/text/Text' import {ViewHeader} from '#/view/com/util/ViewHeader' import {CenteredView} from '#/view/com/util/Views' -import {Text} from '../com/util/text/Text' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<CommonNavigatorParams, 'LanguageSettings'> @@ -76,232 +77,234 @@ export function LanguageSettingsScreen(_props: Props) { }, [langPrefs.contentLanguages]) return ( - <CenteredView - style={[ - pal.view, - pal.border, - styles.container, - isTabletOrDesktop && styles.desktopContainer, - ]}> - <ViewHeader title={_(msg`Language Settings`)} showOnDesktop /> + <Layout.Screen testID="PreferencesLanguagesScreen"> + <CenteredView + style={[ + pal.view, + pal.border, + styles.container, + isTabletOrDesktop && styles.desktopContainer, + ]}> + <ViewHeader title={_(msg`Language Settings`)} showOnDesktop /> - <View style={{paddingTop: 20, paddingHorizontal: 20}}> - {/* APP LANGUAGE */} - <View style={{paddingBottom: 20}}> - <Text type="title-sm" style={[pal.text, s.pb5]}> - <Trans>App Language</Trans> - </Text> - <Text style={[pal.text, s.pb10]}> - <Trans> - Select your app language for the default text to display in the - app. - </Trans> - </Text> + <View style={{paddingTop: 20, paddingHorizontal: 20}}> + {/* APP LANGUAGE */} + <View style={{paddingBottom: 20}}> + <Text type="title-sm" style={[pal.text, s.pb5]}> + <Trans>App Language</Trans> + </Text> + <Text style={[pal.text, s.pb10]}> + <Trans> + Select your app language for the default text to display in the + app. + </Trans> + </Text> - <View style={{position: 'relative'}}> - <RNPickerSelect - placeholder={{}} - value={sanitizeAppLanguageSetting(langPrefs.appLanguage)} - onValueChange={onChangeAppLanguage} - items={APP_LANGUAGES.filter(l => Boolean(l.code2)).map(l => ({ - label: l.name, - value: l.code2, - key: l.code2, - }))} - style={{ - inputAndroid: { - backgroundColor: pal.viewLight.backgroundColor, - color: pal.text.color, - fontSize: 14, - letterSpacing: 0.5, - fontWeight: '600', - paddingHorizontal: 14, - paddingVertical: 8, - borderRadius: 24, - }, - inputIOS: { - backgroundColor: pal.viewLight.backgroundColor, - color: pal.text.color, - fontSize: 14, - letterSpacing: 0.5, - fontWeight: '600', - paddingHorizontal: 14, - paddingVertical: 8, - borderRadius: 24, - }, + <View style={{position: 'relative'}}> + <RNPickerSelect + placeholder={{}} + value={sanitizeAppLanguageSetting(langPrefs.appLanguage)} + onValueChange={onChangeAppLanguage} + items={APP_LANGUAGES.filter(l => Boolean(l.code2)).map(l => ({ + label: l.name, + value: l.code2, + key: l.code2, + }))} + style={{ + inputAndroid: { + backgroundColor: pal.viewLight.backgroundColor, + color: pal.text.color, + fontSize: 14, + letterSpacing: 0.5, + fontWeight: '600', + paddingHorizontal: 14, + paddingVertical: 8, + borderRadius: 24, + }, + inputIOS: { + backgroundColor: pal.viewLight.backgroundColor, + color: pal.text.color, + fontSize: 14, + letterSpacing: 0.5, + fontWeight: '600', + paddingHorizontal: 14, + paddingVertical: 8, + borderRadius: 24, + }, + + inputWeb: { + cursor: 'pointer', + // @ts-ignore web only + '-moz-appearance': 'none', + '-webkit-appearance': 'none', + appearance: 'none', + outline: 0, + borderWidth: 0, + backgroundColor: pal.viewLight.backgroundColor, + color: pal.text.color, + fontSize: 14, + fontFamily: 'inherit', + letterSpacing: 0.5, + fontWeight: '600', + paddingHorizontal: 14, + paddingVertical: 8, + borderRadius: 24, + }, + }} + /> - inputWeb: { - cursor: 'pointer', - // @ts-ignore web only - '-moz-appearance': 'none', - '-webkit-appearance': 'none', - appearance: 'none', - outline: 0, - borderWidth: 0, + <View + style={{ + position: 'absolute', + top: 1, + right: 1, + bottom: 1, + width: 40, backgroundColor: pal.viewLight.backgroundColor, - color: pal.text.color, - fontSize: 14, - fontFamily: 'inherit', - letterSpacing: 0.5, - fontWeight: '600', - paddingHorizontal: 14, - paddingVertical: 8, borderRadius: 24, - }, - }} - /> - - <View - style={{ - position: 'absolute', - top: 1, - right: 1, - bottom: 1, - width: 40, - backgroundColor: pal.viewLight.backgroundColor, - borderRadius: 24, - pointerEvents: 'none', - alignItems: 'center', - justifyContent: 'center', - }}> - <FontAwesomeIcon - icon="chevron-down" - style={pal.text as FontAwesomeIconStyle} - /> + pointerEvents: 'none', + alignItems: 'center', + justifyContent: 'center', + }}> + <FontAwesomeIcon + icon="chevron-down" + style={pal.text as FontAwesomeIconStyle} + /> + </View> </View> </View> - </View> - <View - style={{ - height: 1, - backgroundColor: pal.border.borderColor, - marginBottom: 20, - }} - /> + <View + style={{ + height: 1, + backgroundColor: pal.border.borderColor, + marginBottom: 20, + }} + /> - {/* PRIMARY LANGUAGE */} - <View style={{paddingBottom: 20}}> - <Text type="title-sm" style={[pal.text, s.pb5]}> - <Trans>Primary Language</Trans> - </Text> - <Text style={[pal.text, s.pb10]}> - <Trans> - Select your preferred language for translations in your feed. - </Trans> - </Text> + {/* PRIMARY LANGUAGE */} + <View style={{paddingBottom: 20}}> + <Text type="title-sm" style={[pal.text, s.pb5]}> + <Trans>Primary Language</Trans> + </Text> + <Text style={[pal.text, s.pb10]}> + <Trans> + Select your preferred language for translations in your feed. + </Trans> + </Text> - <View style={{position: 'relative'}}> - <RNPickerSelect - placeholder={{}} - value={langPrefs.primaryLanguage} - onValueChange={onChangePrimaryLanguage} - items={LANGUAGES.filter(l => Boolean(l.code2)).map(l => ({ - label: l.name, - value: l.code2, - key: l.code2 + l.code3, - }))} - style={{ - inputAndroid: { - backgroundColor: pal.viewLight.backgroundColor, - color: pal.text.color, - fontSize: 14, - letterSpacing: 0.5, - fontWeight: '600', - paddingHorizontal: 14, - paddingVertical: 8, - borderRadius: 24, - }, - inputIOS: { - backgroundColor: pal.viewLight.backgroundColor, - color: pal.text.color, - fontSize: 14, - letterSpacing: 0.5, - fontWeight: '600', - paddingHorizontal: 14, - paddingVertical: 8, - borderRadius: 24, - }, - inputWeb: { - cursor: 'pointer', - // @ts-ignore web only - '-moz-appearance': 'none', - '-webkit-appearance': 'none', - appearance: 'none', - outline: 0, - borderWidth: 0, + <View style={{position: 'relative'}}> + <RNPickerSelect + placeholder={{}} + value={langPrefs.primaryLanguage} + onValueChange={onChangePrimaryLanguage} + items={LANGUAGES.filter(l => Boolean(l.code2)).map(l => ({ + label: l.name, + value: l.code2, + key: l.code2 + l.code3, + }))} + style={{ + inputAndroid: { + backgroundColor: pal.viewLight.backgroundColor, + color: pal.text.color, + fontSize: 14, + letterSpacing: 0.5, + fontWeight: '600', + paddingHorizontal: 14, + paddingVertical: 8, + borderRadius: 24, + }, + inputIOS: { + backgroundColor: pal.viewLight.backgroundColor, + color: pal.text.color, + fontSize: 14, + letterSpacing: 0.5, + fontWeight: '600', + paddingHorizontal: 14, + paddingVertical: 8, + borderRadius: 24, + }, + inputWeb: { + cursor: 'pointer', + // @ts-ignore web only + '-moz-appearance': 'none', + '-webkit-appearance': 'none', + appearance: 'none', + outline: 0, + borderWidth: 0, + backgroundColor: pal.viewLight.backgroundColor, + color: pal.text.color, + fontSize: 14, + fontFamily: 'inherit', + letterSpacing: 0.5, + fontWeight: '600', + paddingHorizontal: 14, + paddingVertical: 8, + borderRadius: 24, + }, + }} + /> + + <View + style={{ + position: 'absolute', + top: 1, + right: 1, + bottom: 1, + width: 40, backgroundColor: pal.viewLight.backgroundColor, - color: pal.text.color, - fontSize: 14, - fontFamily: 'inherit', - letterSpacing: 0.5, - fontWeight: '600', - paddingHorizontal: 14, - paddingVertical: 8, borderRadius: 24, - }, - }} - /> - - <View - style={{ - position: 'absolute', - top: 1, - right: 1, - bottom: 1, - width: 40, - backgroundColor: pal.viewLight.backgroundColor, - borderRadius: 24, - pointerEvents: 'none', - alignItems: 'center', - justifyContent: 'center', - }}> - <FontAwesomeIcon - icon="chevron-down" - style={pal.text as FontAwesomeIconStyle} - /> + pointerEvents: 'none', + alignItems: 'center', + justifyContent: 'center', + }}> + <FontAwesomeIcon + icon="chevron-down" + style={pal.text as FontAwesomeIconStyle} + /> + </View> </View> </View> - </View> - - <View - style={{ - height: 1, - backgroundColor: pal.border.borderColor, - marginBottom: 20, - }} - /> - {/* CONTENT LANGUAGES */} - <View style={{paddingBottom: 20}}> - <Text type="title-sm" style={[pal.text, s.pb5]}> - <Trans>Content Languages</Trans> - </Text> - <Text style={[pal.text, s.pb10]}> - <Trans> - Select which languages you want your subscribed feeds to include. - If none are selected, all languages will be shown. - </Trans> - </Text> + <View + style={{ + height: 1, + backgroundColor: pal.border.borderColor, + marginBottom: 20, + }} + /> - <Button - type="default" - onPress={onPressContentLanguages} - style={styles.button}> - <FontAwesomeIcon - icon={myLanguages.length ? 'check' : 'plus'} - style={pal.text as FontAwesomeIconStyle} - /> - <Text - type="button" - style={[pal.text, {flexShrink: 1, overflow: 'hidden'}]} - numberOfLines={1}> - {myLanguages.length ? myLanguages : _(msg`Select languages`)} + {/* CONTENT LANGUAGES */} + <View style={{paddingBottom: 20}}> + <Text type="title-sm" style={[pal.text, s.pb5]}> + <Trans>Content Languages</Trans> </Text> - </Button> + <Text style={[pal.text, s.pb10]}> + <Trans> + Select which languages you want your subscribed feeds to + include. If none are selected, all languages will be shown. + </Trans> + </Text> + + <Button + type="default" + onPress={onPressContentLanguages} + style={styles.button}> + <FontAwesomeIcon + icon={myLanguages.length ? 'check' : 'plus'} + style={pal.text as FontAwesomeIconStyle} + /> + <Text + type="button" + style={[pal.text, {flexShrink: 1, overflow: 'hidden'}]} + numberOfLines={1}> + {myLanguages.length ? myLanguages : _(msg`Select languages`)} + </Text> + </Button> + </View> </View> - </View> - </CenteredView> + </CenteredView> + </Layout.Screen> ) } diff --git a/src/view/screens/Lists.tsx b/src/view/screens/Lists.tsx index d6a86e514..b79da6d54 100644 --- a/src/view/screens/Lists.tsx +++ b/src/view/screens/Lists.tsx @@ -16,6 +16,7 @@ import {MyLists} from '#/view/com/lists/MyLists' import {Button} from '#/view/com/util/forms/Button' import {SimpleViewHeader} from '#/view/com/util/SimpleViewHeader' import {Text} from '#/view/com/util/text/Text' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<CommonNavigatorParams, 'Lists'> export function ListsScreen({}: Props) { @@ -48,7 +49,7 @@ export function ListsScreen({}: Props) { }, [openModal, navigation]) return ( - <View style={s.hContentRegion} testID="listsScreen"> + <Layout.Screen testID="listsScreen"> <SimpleViewHeader showBackButton={isMobile} style={[ @@ -86,6 +87,6 @@ export function ListsScreen({}: Props) { </View> </SimpleViewHeader> <MyLists filter="curate" style={s.flexGrow1} /> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/Log.tsx b/src/view/screens/Log.tsx index e6040b77e..026319baf 100644 --- a/src/view/screens/Log.tsx +++ b/src/view/screens/Log.tsx @@ -5,16 +5,17 @@ import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' +import {usePalette} from '#/lib/hooks/usePalette' import {useGetTimeAgo} from '#/lib/hooks/useTimeAgo' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {s} from '#/lib/styles' import {getEntries} from '#/logger/logDump' import {useTickEveryMinute} from '#/state/shell' import {useSetMinimalShellMode} from '#/state/shell' -import {usePalette} from 'lib/hooks/usePalette' -import {CommonNavigatorParams, NativeStackScreenProps} from 'lib/routes/types' -import {s} from 'lib/styles' -import {Text} from '../com/util/text/Text' -import {ViewHeader} from '../com/util/ViewHeader' -import {ScrollView} from '../com/util/Views' +import {Text} from '#/view/com/util/text/Text' +import {ViewHeader} from '#/view/com/util/ViewHeader' +import {ScrollView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' export function LogScreen({}: NativeStackScreenProps< CommonNavigatorParams, @@ -42,7 +43,7 @@ export function LogScreen({}: NativeStackScreenProps< } return ( - <View style={[s.flex1]}> + <Layout.Screen> <ViewHeader title="Log" /> <ScrollView style={s.flex1}> {getEntries() @@ -91,7 +92,7 @@ export function LogScreen({}: NativeStackScreenProps< })} <View style={s.footerSpacer} /> </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/ModerationBlockedAccounts.tsx b/src/view/screens/ModerationBlockedAccounts.tsx index 88a5df7ec..53e31d1d2 100644 --- a/src/view/screens/ModerationBlockedAccounts.tsx +++ b/src/view/screens/ModerationBlockedAccounts.tsx @@ -20,10 +20,11 @@ import {logger} from '#/logger' import {useMyBlockedAccountsQuery} from '#/state/queries/my-blocked-accounts' import {useSetMinimalShellMode} from '#/state/shell' import {ProfileCard} from '#/view/com/profile/ProfileCard' +import {ErrorScreen} from '#/view/com/util/error/ErrorScreen' +import {Text} from '#/view/com/util/text/Text' +import {ViewHeader} from '#/view/com/util/ViewHeader' import {CenteredView} from '#/view/com/util/Views' -import {ErrorScreen} from '../com/util/error/ErrorScreen' -import {Text} from '../com/util/text/Text' -import {ViewHeader} from '../com/util/ViewHeader' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -95,76 +96,78 @@ export function ModerationBlockedAccounts({}: Props) { /> ) return ( - <CenteredView - style={[ - styles.container, - isTabletOrDesktop && styles.containerDesktop, - pal.view, - pal.border, - ]} - testID="blockedAccountsScreen"> - <ViewHeader title={_(msg`Blocked Accounts`)} showOnDesktop /> - <Text - type="sm" + <Layout.Screen testID="blockedAccountsScreen"> + <CenteredView style={[ - styles.description, - pal.text, - isTabletOrDesktop && styles.descriptionDesktop, - ]}> - <Trans> - Blocked accounts cannot reply in your threads, mention you, or - otherwise interact with you. You will not see their content and they - will be prevented from seeing yours. - </Trans> - </Text> - {isEmpty ? ( - <View style={[pal.border, !isTabletOrDesktop && styles.flex1]}> - {isError ? ( - <ErrorScreen - title="Oops!" - message={cleanError(error)} - onPressTryAgain={refetch} - /> - ) : ( - <View style={[styles.empty, pal.viewLight]}> - <Text type="lg" style={[pal.text, styles.emptyText]}> - <Trans> - You have not blocked any accounts yet. To block an account, go - to their profile and select "Block account" from the menu on - their account. - </Trans> - </Text> - </View> - )} - </View> - ) : ( - <FlatList - style={[!isTabletOrDesktop && styles.flex1]} - data={profiles} - keyExtractor={(item: ActorDefs.ProfileView) => item.did} - refreshControl={ - <RefreshControl - refreshing={isPTRing} - onRefresh={onRefresh} - tintColor={pal.colors.text} - titleColor={pal.colors.text} - /> - } - onEndReached={onEndReached} - renderItem={renderItem} - initialNumToRender={15} - // FIXME(dan) + styles.container, + isTabletOrDesktop && styles.containerDesktop, + pal.view, + pal.border, + ]} + testID="blockedAccountsScreen"> + <ViewHeader title={_(msg`Blocked Accounts`)} showOnDesktop /> + <Text + type="sm" + style={[ + styles.description, + pal.text, + isTabletOrDesktop && styles.descriptionDesktop, + ]}> + <Trans> + Blocked accounts cannot reply in your threads, mention you, or + otherwise interact with you. You will not see their content and they + will be prevented from seeing yours. + </Trans> + </Text> + {isEmpty ? ( + <View style={[pal.border, !isTabletOrDesktop && styles.flex1]}> + {isError ? ( + <ErrorScreen + title="Oops!" + message={cleanError(error)} + onPressTryAgain={refetch} + /> + ) : ( + <View style={[styles.empty, pal.viewLight]}> + <Text type="lg" style={[pal.text, styles.emptyText]}> + <Trans> + You have not blocked any accounts yet. To block an account, + go to their profile and select "Block account" from the menu + on their account. + </Trans> + </Text> + </View> + )} + </View> + ) : ( + <FlatList + style={[!isTabletOrDesktop && styles.flex1]} + data={profiles} + keyExtractor={(item: ActorDefs.ProfileView) => item.did} + refreshControl={ + <RefreshControl + refreshing={isPTRing} + onRefresh={onRefresh} + tintColor={pal.colors.text} + titleColor={pal.colors.text} + /> + } + onEndReached={onEndReached} + renderItem={renderItem} + initialNumToRender={15} + // FIXME(dan) - ListFooterComponent={() => ( - <View style={styles.footer}> - {(isFetching || isFetchingNextPage) && <ActivityIndicator />} - </View> - )} - // @ts-ignore our .web version only -prf - desktopFixedHeight - /> - )} - </CenteredView> + ListFooterComponent={() => ( + <View style={styles.footer}> + {(isFetching || isFetchingNextPage) && <ActivityIndicator />} + </View> + )} + // @ts-ignore our .web version only -prf + desktopFixedHeight + /> + )} + </CenteredView> + </Layout.Screen> ) } diff --git a/src/view/screens/ModerationModlists.tsx b/src/view/screens/ModerationModlists.tsx index 39ba540b4..b147ba502 100644 --- a/src/view/screens/ModerationModlists.tsx +++ b/src/view/screens/ModerationModlists.tsx @@ -16,6 +16,7 @@ import {MyLists} from '#/view/com/lists/MyLists' import {Button} from '#/view/com/util/forms/Button' import {SimpleViewHeader} from '#/view/com/util/SimpleViewHeader' import {Text} from '#/view/com/util/text/Text' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<CommonNavigatorParams, 'ModerationModlists'> export function ModerationModlistsScreen({}: Props) { @@ -48,7 +49,7 @@ export function ModerationModlistsScreen({}: Props) { }, [openModal, navigation]) return ( - <View style={s.hContentRegion} testID="moderationModlistsScreen"> + <Layout.Screen testID="moderationModlistsScreen"> <SimpleViewHeader showBackButton={isMobile} style={ @@ -82,6 +83,6 @@ export function ModerationModlistsScreen({}: Props) { </View> </SimpleViewHeader> <MyLists filter="mod" style={s.flexGrow1} /> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/ModerationMutedAccounts.tsx b/src/view/screens/ModerationMutedAccounts.tsx index bd29cb2d9..6d34c8a5f 100644 --- a/src/view/screens/ModerationMutedAccounts.tsx +++ b/src/view/screens/ModerationMutedAccounts.tsx @@ -20,10 +20,11 @@ import {logger} from '#/logger' import {useMyMutedAccountsQuery} from '#/state/queries/my-muted-accounts' import {useSetMinimalShellMode} from '#/state/shell' import {ProfileCard} from '#/view/com/profile/ProfileCard' +import {ErrorScreen} from '#/view/com/util/error/ErrorScreen' +import {Text} from '#/view/com/util/text/Text' +import {ViewHeader} from '#/view/com/util/ViewHeader' import {CenteredView} from '#/view/com/util/Views' -import {ErrorScreen} from '../com/util/error/ErrorScreen' -import {Text} from '../com/util/text/Text' -import {ViewHeader} from '../com/util/ViewHeader' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -95,75 +96,77 @@ export function ModerationMutedAccounts({}: Props) { /> ) return ( - <CenteredView - style={[ - styles.container, - isTabletOrDesktop && styles.containerDesktop, - pal.view, - pal.border, - ]} - testID="mutedAccountsScreen"> - <ViewHeader title={_(msg`Muted Accounts`)} showOnDesktop /> - <Text - type="sm" + <Layout.Screen testID="mutedAccountsScreen"> + <CenteredView style={[ - styles.description, - pal.text, - isTabletOrDesktop && styles.descriptionDesktop, - ]}> - <Trans> - Muted accounts have their posts removed from your feed and from your - notifications. Mutes are completely private. - </Trans> - </Text> - {isEmpty ? ( - <View style={[pal.border, !isTabletOrDesktop && styles.flex1]}> - {isError ? ( - <ErrorScreen - title="Oops!" - message={cleanError(error)} - onPressTryAgain={refetch} - /> - ) : ( - <View style={[styles.empty, pal.viewLight]}> - <Text type="lg" style={[pal.text, styles.emptyText]}> - <Trans> - You have not muted any accounts yet. To mute an account, go to - their profile and select "Mute account" from the menu on their - account. - </Trans> - </Text> - </View> - )} - </View> - ) : ( - <FlatList - style={[!isTabletOrDesktop && styles.flex1]} - data={profiles} - keyExtractor={item => item.did} - refreshControl={ - <RefreshControl - refreshing={isPTRing} - onRefresh={onRefresh} - tintColor={pal.colors.text} - titleColor={pal.colors.text} - /> - } - onEndReached={onEndReached} - renderItem={renderItem} - initialNumToRender={15} - // FIXME(dan) + styles.container, + isTabletOrDesktop && styles.containerDesktop, + pal.view, + pal.border, + ]} + testID="mutedAccountsScreen"> + <ViewHeader title={_(msg`Muted Accounts`)} showOnDesktop /> + <Text + type="sm" + style={[ + styles.description, + pal.text, + isTabletOrDesktop && styles.descriptionDesktop, + ]}> + <Trans> + Muted accounts have their posts removed from your feed and from your + notifications. Mutes are completely private. + </Trans> + </Text> + {isEmpty ? ( + <View style={[pal.border, !isTabletOrDesktop && styles.flex1]}> + {isError ? ( + <ErrorScreen + title="Oops!" + message={cleanError(error)} + onPressTryAgain={refetch} + /> + ) : ( + <View style={[styles.empty, pal.viewLight]}> + <Text type="lg" style={[pal.text, styles.emptyText]}> + <Trans> + You have not muted any accounts yet. To mute an account, go + to their profile and select "Mute account" from the menu on + their account. + </Trans> + </Text> + </View> + )} + </View> + ) : ( + <FlatList + style={[!isTabletOrDesktop && styles.flex1]} + data={profiles} + keyExtractor={item => item.did} + refreshControl={ + <RefreshControl + refreshing={isPTRing} + onRefresh={onRefresh} + tintColor={pal.colors.text} + titleColor={pal.colors.text} + /> + } + onEndReached={onEndReached} + renderItem={renderItem} + initialNumToRender={15} + // FIXME(dan) - ListFooterComponent={() => ( - <View style={styles.footer}> - {(isFetching || isFetchingNextPage) && <ActivityIndicator />} - </View> - )} - // @ts-ignore our .web version only -prf - desktopFixedHeight - /> - )} - </CenteredView> + ListFooterComponent={() => ( + <View style={styles.footer}> + {(isFetching || isFetchingNextPage) && <ActivityIndicator />} + </View> + )} + // @ts-ignore our .web version only -prf + desktopFixedHeight + /> + )} + </CenteredView> + </Layout.Screen> ) } diff --git a/src/view/screens/NotFound.tsx b/src/view/screens/NotFound.tsx index 7d51619b3..90d5e17dd 100644 --- a/src/view/screens/NotFound.tsx +++ b/src/view/screens/NotFound.tsx @@ -1,19 +1,21 @@ import React from 'react' import {StyleSheet, View} from 'react-native' +import {msg, Trans} from '@lingui/macro' +import {useLingui} from '@lingui/react' import { - useNavigation, StackActions, useFocusEffect, + useNavigation, } from '@react-navigation/native' -import {ViewHeader} from '../com/util/ViewHeader' -import {Text} from '../com/util/text/Text' -import {Button} from 'view/com/util/forms/Button' -import {NavigationProp} from 'lib/routes/types' -import {usePalette} from 'lib/hooks/usePalette' -import {s} from 'lib/styles' + +import {usePalette} from '#/lib/hooks/usePalette' +import {NavigationProp} from '#/lib/routes/types' +import {s} from '#/lib/styles' import {useSetMinimalShellMode} from '#/state/shell' -import {Trans, msg} from '@lingui/macro' -import {useLingui} from '@lingui/react' +import {Button} from '#/view/com/util/forms/Button' +import {Text} from '#/view/com/util/text/Text' +import {ViewHeader} from '#/view/com/util/ViewHeader' +import * as Layout from '#/components/Layout' export const NotFoundScreen = () => { const pal = usePalette('default') @@ -38,7 +40,7 @@ export const NotFoundScreen = () => { }, [navigation, canGoBack]) return ( - <View testID="notFoundView" style={pal.view}> + <Layout.Screen testID="notFoundView"> <ViewHeader title={_(msg`Page Not Found`)} /> <View style={styles.container}> <Text type="title-2xl" style={[pal.text, s.mb10]}> @@ -61,7 +63,7 @@ export const NotFoundScreen = () => { onPress={onPressHome} /> </View> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/Notifications.tsx b/src/view/screens/Notifications.tsx index 818d3d0ed..531d10a7f 100644 --- a/src/view/screens/Notifications.tsx +++ b/src/view/screens/Notifications.tsx @@ -34,6 +34,7 @@ import {CenteredView} from '#/view/com/util/Views' import {atoms as a, useTheme} from '#/alf' import {Button} from '#/components/Button' import {SettingsGear2_Stroke2_Corner0_Rounded as SettingsIcon} from '#/components/icons/SettingsGear2' +import * as Layout from '#/components/Layout' import {Link} from '#/components/Link' import {Loader} from '#/components/Loader' import {Text} from '#/components/Typography' @@ -192,39 +193,38 @@ export function NotificationsScreen({route: {params}}: Props) { }, [renderButton, isLoadingLatest]) return ( - <CenteredView - testID="notificationsScreen" - style={[s.hContentRegion, {paddingTop: 2}]} - sideBorders={true}> - <ViewHeader - title={_(msg`Notifications`)} - canGoBack={false} - showBorder={true} - renderButton={renderHeaderSpinner} - /> - <MainScrollProvider> - <Feed - onScrolledDownChange={setIsScrolledDown} - scrollElRef={scrollElRef} - ListHeaderComponent={ListHeaderComponent} - overridePriorityNotifications={params?.show === 'all'} + <Layout.Screen testID="notificationsScreen"> + <CenteredView style={[a.flex_1, {paddingTop: 2}]} sideBorders={true}> + <ViewHeader + title={_(msg`Notifications`)} + canGoBack={false} + showBorder={true} + renderButton={renderHeaderSpinner} /> - </MainScrollProvider> - {(isScrolledDown || hasNew) && ( - <LoadLatestBtn - onPress={onPressLoadLatest} - label={_(msg`Load new notifications`)} - showIndicator={hasNew} + <MainScrollProvider> + <Feed + onScrolledDownChange={setIsScrolledDown} + scrollElRef={scrollElRef} + ListHeaderComponent={ListHeaderComponent} + overridePriorityNotifications={params?.show === 'all'} + /> + </MainScrollProvider> + {(isScrolledDown || hasNew) && ( + <LoadLatestBtn + onPress={onPressLoadLatest} + label={_(msg`Load new notifications`)} + showIndicator={hasNew} + /> + )} + <FAB + testID="composeFAB" + onPress={() => openComposer({})} + icon={<ComposeIcon2 strokeWidth={1.5} size={29} style={s.white} />} + accessibilityRole="button" + accessibilityLabel={_(msg`New post`)} + accessibilityHint="" /> - )} - <FAB - testID="composeFAB" - onPress={() => openComposer({})} - icon={<ComposeIcon2 strokeWidth={1.5} size={29} style={s.white} />} - accessibilityRole="button" - accessibilityLabel={_(msg`New post`)} - accessibilityHint="" - /> - </CenteredView> + </CenteredView> + </Layout.Screen> ) } diff --git a/src/view/screens/NotificationsSettings.tsx b/src/view/screens/NotificationsSettings.tsx index f395941df..f8d848a62 100644 --- a/src/view/screens/NotificationsSettings.tsx +++ b/src/view/screens/NotificationsSettings.tsx @@ -13,6 +13,7 @@ import {atoms as a, useTheme} from '#/alf' import {Admonition} from '#/components/Admonition' import {Error} from '#/components/Error' import * as Toggle from '#/components/forms/Toggle' +import * as Layout from '#/components/Layout' import {Loader} from '#/components/Loader' import {Text} from '#/components/Typography' @@ -35,52 +36,54 @@ export function NotificationsSettingsScreen({}: Props) { : serverPriority return ( - <ScrollView stickyHeaderIndices={[0]}> - <ViewHeader - title={_(msg`Notification Settings`)} - showOnDesktop - showBorder - /> - {isQueryError ? ( - <Error - title={_(msg`Oops!`)} - message={_(msg`Something went wrong!`)} - onRetry={refetch} - sideBorders={false} + <Layout.Screen> + <ScrollView stickyHeaderIndices={[0]}> + <ViewHeader + title={_(msg`Notification Settings`)} + showOnDesktop + showBorder /> - ) : ( - <View style={[a.p_lg, a.gap_md]}> - <Text style={[a.text_lg, a.font_bold]}> - <FontAwesomeIcon icon="flask" style={t.atoms.text} />{' '} - <Trans>Notification filters</Trans> - </Text> - <Toggle.Group - label={_(msg`Priority notifications`)} - type="checkbox" - values={priority ? ['enabled'] : []} - onChange={onChangePriority} - disabled={typeof priority !== 'boolean' || isMutationPending}> - <View> - <Toggle.Item - name="enabled" - label={_(msg`Enable priority notifications`)} - style={[a.justify_between, a.py_sm]}> - <Toggle.LabelText> - <Trans>Enable priority notifications</Trans> - </Toggle.LabelText> - {!data ? <Loader size="md" /> : <Toggle.Platform />} - </Toggle.Item> - </View> - </Toggle.Group> - <Admonition type="warning" style={[a.mt_sm]}> - <Trans> - Experimental: When this preference is enabled, you'll only receive - reply and quote notifications from users you follow. We'll - continue to add more controls here over time. - </Trans> - </Admonition> - </View> - )} - </ScrollView> + {isQueryError ? ( + <Error + title={_(msg`Oops!`)} + message={_(msg`Something went wrong!`)} + onRetry={refetch} + sideBorders={false} + /> + ) : ( + <View style={[a.p_lg, a.gap_md]}> + <Text style={[a.text_lg, a.font_bold]}> + <FontAwesomeIcon icon="flask" style={t.atoms.text} />{' '} + <Trans>Notification filters</Trans> + </Text> + <Toggle.Group + label={_(msg`Priority notifications`)} + type="checkbox" + values={priority ? ['enabled'] : []} + onChange={onChangePriority} + disabled={typeof priority !== 'boolean' || isMutationPending}> + <View> + <Toggle.Item + name="enabled" + label={_(msg`Enable priority notifications`)} + style={[a.justify_between, a.py_sm]}> + <Toggle.LabelText> + <Trans>Enable priority notifications</Trans> + </Toggle.LabelText> + {!data ? <Loader size="md" /> : <Toggle.Platform />} + </Toggle.Item> + </View> + </Toggle.Group> + <Admonition type="warning" style={[a.mt_sm]}> + <Trans> + Experimental: When this preference is enabled, you'll only + receive reply and quote notifications from users you follow. + We'll continue to add more controls here over time. + </Trans> + </Admonition> + </View> + )} + </ScrollView> + </Layout.Screen> ) } diff --git a/src/view/screens/PostThread.tsx b/src/view/screens/PostThread.tsx index 88d0726c1..c183569b7 100644 --- a/src/view/screens/PostThread.tsx +++ b/src/view/screens/PostThread.tsx @@ -2,11 +2,12 @@ import React from 'react' import {View} from 'react-native' import {useFocusEffect} from '@react-navigation/native' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {makeRecordUri} from '#/lib/strings/url-helpers' import {useSetMinimalShellMode} from '#/state/shell' -import {CommonNavigatorParams, NativeStackScreenProps} from 'lib/routes/types' -import {makeRecordUri} from 'lib/strings/url-helpers' -import {s} from 'lib/styles' -import {PostThread as PostThreadComponent} from '../com/post-thread/PostThread' +import {PostThread as PostThreadComponent} from '#/view/com/post-thread/PostThread' +import {atoms as a} from '#/alf' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<CommonNavigatorParams, 'PostThread'> export function PostThreadScreen({route}: Props) { @@ -22,10 +23,10 @@ export function PostThreadScreen({route}: Props) { ) return ( - <View style={s.hContentRegion}> - <View style={s.flex1}> + <Layout.Screen testID="postThreadScreen"> + <View style={a.flex_1}> <PostThreadComponent uri={uri} /> </View> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/PreferencesExternalEmbeds.tsx b/src/view/screens/PreferencesExternalEmbeds.tsx index ae23b6e95..5a657ce84 100644 --- a/src/view/screens/PreferencesExternalEmbeds.tsx +++ b/src/view/screens/PreferencesExternalEmbeds.tsx @@ -10,17 +10,17 @@ import { EmbedPlayerSource, externalEmbedLabels, } from '#/lib/strings/embed-player' -import {s} from '#/lib/styles' import { useExternalEmbedsPrefs, useSetExternalEmbedPref, } from '#/state/preferences' import {useSetMinimalShellMode} from '#/state/shell' import {ToggleButton} from '#/view/com/util/forms/ToggleButton' +import {SimpleViewHeader} from '#/view/com/util/SimpleViewHeader' +import {Text} from '#/view/com/util/text/Text' +import {ScrollView} from '#/view/com/util/Views' import {atoms as a} from '#/alf' -import {SimpleViewHeader} from '../com/util/SimpleViewHeader' -import {Text} from '../com/util/text/Text' -import {ScrollView} from '../com/util/Views' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -38,7 +38,7 @@ export function PreferencesExternalEmbeds({}: Props) { ) return ( - <View style={s.hContentRegion} testID="preferencesExternalEmbedsScreen"> + <Layout.Screen testID="preferencesExternalEmbedsScreen"> <ScrollView // @ts-ignore web only -prf dataSet={{'stable-gutters': 1}} @@ -81,7 +81,7 @@ export function PreferencesExternalEmbeds({}: Props) { /> ))} </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/PreferencesFollowingFeed.tsx b/src/view/screens/PreferencesFollowingFeed.tsx index 085250e3b..3d9928901 100644 --- a/src/view/screens/PreferencesFollowingFeed.tsx +++ b/src/view/screens/PreferencesFollowingFeed.tsx @@ -17,6 +17,7 @@ import {SimpleViewHeader} from '#/view/com/util/SimpleViewHeader' import {Text} from '#/view/com/util/text/Text' import {ScrollView} from '#/view/com/util/Views' import {atoms as a} from '#/alf' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -35,7 +36,7 @@ export function PreferencesFollowingFeed({}: Props) { ) return ( - <View testID="preferencesHomeFeedScreen" style={s.hContentRegion}> + <Layout.Screen testID="preferencesHomeFeedScreen"> <ScrollView // @ts-ignore web only -sfn dataSet={{'stable-gutters': 1}} @@ -185,7 +186,7 @@ export function PreferencesFollowingFeed({}: Props) { </View> </View> </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/PreferencesThreads.tsx b/src/view/screens/PreferencesThreads.tsx index 7a5a88869..c3992276a 100644 --- a/src/view/screens/PreferencesThreads.tsx +++ b/src/view/screens/PreferencesThreads.tsx @@ -18,6 +18,7 @@ import {SimpleViewHeader} from '#/view/com/util/SimpleViewHeader' import {Text} from '#/view/com/util/text/Text' import {ScrollView} from '#/view/com/util/Views' import {atoms as a} from '#/alf' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<CommonNavigatorParams, 'PreferencesThreads'> export function PreferencesThreads({}: Props) { @@ -38,7 +39,7 @@ export function PreferencesThreads({}: Props) { ) return ( - <View testID="preferencesThreadsScreen" style={s.hContentRegion}> + <Layout.Screen testID="preferencesThreadsScreen"> <ScrollView // @ts-ignore web only -prf dataSet={{'stable-gutters': 1}} @@ -134,7 +135,7 @@ export function PreferencesThreads({}: Props) { <ActivityIndicator style={a.flex_1} /> )} </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/PrivacyPolicy.tsx b/src/view/screens/PrivacyPolicy.tsx index 776d83918..57e4652b5 100644 --- a/src/view/screens/PrivacyPolicy.tsx +++ b/src/view/screens/PrivacyPolicy.tsx @@ -1,16 +1,18 @@ import React from 'react' import {View} from 'react-native' +import {msg, Trans} from '@lingui/macro' +import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' -import {Text} from 'view/com/util/text/Text' -import {TextLink} from 'view/com/util/Link' -import {NativeStackScreenProps, CommonNavigatorParams} from 'lib/routes/types' -import {ViewHeader} from '../com/util/ViewHeader' -import {ScrollView} from 'view/com/util/Views' -import {usePalette} from 'lib/hooks/usePalette' -import {s} from 'lib/styles' + +import {usePalette} from '#/lib/hooks/usePalette' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {s} from '#/lib/styles' import {useSetMinimalShellMode} from '#/state/shell' -import {Trans, msg} from '@lingui/macro' -import {useLingui} from '@lingui/react' +import {TextLink} from '#/view/com/util/Link' +import {Text} from '#/view/com/util/text/Text' +import {ScrollView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' +import {ViewHeader} from '../com/util/ViewHeader' type Props = NativeStackScreenProps<CommonNavigatorParams, 'PrivacyPolicy'> export const PrivacyPolicyScreen = (_props: Props) => { @@ -25,7 +27,7 @@ export const PrivacyPolicyScreen = (_props: Props) => { ) return ( - <View> + <Layout.Screen> <ViewHeader title={_(msg`Privacy Policy`)} /> <ScrollView style={[s.hContentRegion, pal.view]}> <View style={[s.p20]}> @@ -42,6 +44,6 @@ export const PrivacyPolicyScreen = (_props: Props) => { </View> <View style={s.footerSpacer} /> </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/Profile.tsx b/src/view/screens/Profile.tsx index 772625695..677fe09f4 100644 --- a/src/view/screens/Profile.tsx +++ b/src/view/screens/Profile.tsx @@ -45,6 +45,7 @@ import {ProfileHeader, ProfileHeaderLoading} from '#/screens/Profile/Header' import {ProfileFeedSection} from '#/screens/Profile/Sections/Feed' import {ProfileLabelsSection} from '#/screens/Profile/Sections/Labels' import {web} from '#/alf' +import * as Layout from '#/components/Layout' import {ScreenHider} from '#/components/moderation/ScreenHider' import {ProfileStarterPacks} from '#/components/StarterPack/ProfileStarterPacks' import {navigate} from '#/Navigation' @@ -55,7 +56,15 @@ interface SectionRef { } type Props = NativeStackScreenProps<CommonNavigatorParams, 'Profile'> -export function ProfileScreen({route}: Props) { +export function ProfileScreen(props: Props) { + return ( + <Layout.Screen testID="profileScreen"> + <ProfileScreenInner {...props} /> + </Layout.Screen> + ) +} + +function ProfileScreenInner({route}: Props) { const {_} = useLingui() const {currentAccount} = useSession() const queryClient = useQueryClient() diff --git a/src/view/screens/ProfileFeed.tsx b/src/view/screens/ProfileFeed.tsx index a094cc3dd..6b9288f3b 100644 --- a/src/view/screens/ProfileFeed.tsx +++ b/src/view/screens/ProfileFeed.tsx @@ -61,6 +61,7 @@ import { } from '#/components/icons/Heart2' import {PlusLarge_Stroke2_Corner0_Rounded as Plus} from '#/components/icons/Plus' import {Trash_Stroke2_Corner0_Rounded as Trash} from '#/components/icons/Trash' +import * as Layout from '#/components/Layout' import {InlineLinkText} from '#/components/Link' import * as Menu from '#/components/Menu' import {ReportDialog, useReportDialogControl} from '#/components/ReportDialog' @@ -96,36 +97,42 @@ export function ProfileFeedScreen(props: Props) { if (error) { return ( - <CenteredView> - <View style={[pal.view, pal.border, styles.notFoundContainer]}> - <Text type="title-lg" style={[pal.text, s.mb10]}> - <Trans>Could not load feed</Trans> - </Text> - <Text type="md" style={[pal.text, s.mb20]}> - {error.toString()} - </Text> - - <View style={{flexDirection: 'row'}}> - <Button - type="default" - accessibilityLabel={_(msg`Go back`)} - accessibilityHint={_(msg`Returns to previous page`)} - onPress={onPressBack} - style={{flexShrink: 1}}> - <Text type="button" style={pal.text}> - <Trans>Go Back</Trans> - </Text> - </Button> + <Layout.Screen testID="profileFeedScreenError"> + <CenteredView> + <View style={[pal.view, pal.border, styles.notFoundContainer]}> + <Text type="title-lg" style={[pal.text, s.mb10]}> + <Trans>Could not load feed</Trans> + </Text> + <Text type="md" style={[pal.text, s.mb20]}> + {error.toString()} + </Text> + + <View style={{flexDirection: 'row'}}> + <Button + type="default" + accessibilityLabel={_(msg`Go back`)} + accessibilityHint={_(msg`Returns to previous page`)} + onPress={onPressBack} + style={{flexShrink: 1}}> + <Text type="button" style={pal.text}> + <Trans>Go Back</Trans> + </Text> + </Button> + </View> </View> - </View> - </CenteredView> + </CenteredView> + </Layout.Screen> ) } return resolvedUri ? ( - <ProfileFeedScreenIntermediate feedUri={resolvedUri.uri} /> + <Layout.Screen> + <ProfileFeedScreenIntermediate feedUri={resolvedUri.uri} /> + </Layout.Screen> ) : ( - <LoadingScreen /> + <Layout.Screen> + <LoadingScreen /> + </Layout.Screen> ) } diff --git a/src/view/screens/ProfileFeedLikedBy.tsx b/src/view/screens/ProfileFeedLikedBy.tsx index bb9ec2bae..b796480f3 100644 --- a/src/view/screens/ProfileFeedLikedBy.tsx +++ b/src/view/screens/ProfileFeedLikedBy.tsx @@ -1,14 +1,14 @@ import React from 'react' -import {View} from 'react-native' import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {makeRecordUri} from '#/lib/strings/url-helpers' import {useSetMinimalShellMode} from '#/state/shell' -import {CommonNavigatorParams, NativeStackScreenProps} from 'lib/routes/types' -import {makeRecordUri} from 'lib/strings/url-helpers' -import {PostLikedBy as PostLikedByComponent} from '../com/post-thread/PostLikedBy' -import {ViewHeader} from '../com/util/ViewHeader' +import {PostLikedBy as PostLikedByComponent} from '#/view/com/post-thread/PostLikedBy' +import {ViewHeader} from '#/view/com/util/ViewHeader' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<CommonNavigatorParams, 'ProfileFeedLikedBy'> export const ProfileFeedLikedByScreen = ({route}: Props) => { @@ -24,9 +24,9 @@ export const ProfileFeedLikedByScreen = ({route}: Props) => { ) return ( - <View style={{flex: 1}}> + <Layout.Screen testID="postLikedByScreen"> <ViewHeader title={_(msg`Liked By`)} /> <PostLikedByComponent uri={uri} /> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/ProfileFollowers.tsx b/src/view/screens/ProfileFollowers.tsx index 3a01edff5..9fa98cb1a 100644 --- a/src/view/screens/ProfileFollowers.tsx +++ b/src/view/screens/ProfileFollowers.tsx @@ -3,14 +3,14 @@ import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {isWeb} from '#/platform/detection' import {useSetMinimalShellMode} from '#/state/shell' -import {CommonNavigatorParams, NativeStackScreenProps} from 'lib/routes/types' -import {isWeb} from 'platform/detection' -import {CenteredView} from 'view/com/util/Views' -import {atoms as a} from '#/alf' +import {ProfileFollowers as ProfileFollowersComponent} from '#/view/com/profile/ProfileFollowers' +import {ViewHeader} from '#/view/com/util/ViewHeader' +import {CenteredView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' import {ListHeaderDesktop} from '#/components/Lists' -import {ProfileFollowers as ProfileFollowersComponent} from '../com/profile/ProfileFollowers' -import {ViewHeader} from '../com/util/ViewHeader' type Props = NativeStackScreenProps<CommonNavigatorParams, 'ProfileFollowers'> export const ProfileFollowersScreen = ({route}: Props) => { @@ -25,10 +25,12 @@ export const ProfileFollowersScreen = ({route}: Props) => { ) return ( - <CenteredView style={a.util_screen_outer} sideBorders={true}> - <ListHeaderDesktop title={_(msg`Followers`)} /> - <ViewHeader title={_(msg`Followers`)} showBorder={!isWeb} /> - <ProfileFollowersComponent name={name} /> - </CenteredView> + <Layout.Screen testID="profileFollowersScreen"> + <CenteredView sideBorders={true}> + <ListHeaderDesktop title={_(msg`Followers`)} /> + <ViewHeader title={_(msg`Followers`)} showBorder={!isWeb} /> + <ProfileFollowersComponent name={name} /> + </CenteredView> + </Layout.Screen> ) } diff --git a/src/view/screens/ProfileFollows.tsx b/src/view/screens/ProfileFollows.tsx index 762a84a37..483ee93ec 100644 --- a/src/view/screens/ProfileFollows.tsx +++ b/src/view/screens/ProfileFollows.tsx @@ -3,14 +3,14 @@ import {msg} from '@lingui/macro' import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {isWeb} from '#/platform/detection' import {useSetMinimalShellMode} from '#/state/shell' -import {CommonNavigatorParams, NativeStackScreenProps} from 'lib/routes/types' -import {isWeb} from 'platform/detection' -import {CenteredView} from 'view/com/util/Views' -import {atoms as a} from '#/alf' +import {ProfileFollows as ProfileFollowsComponent} from '#/view/com/profile/ProfileFollows' +import {ViewHeader} from '#/view/com/util/ViewHeader' +import {CenteredView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' import {ListHeaderDesktop} from '#/components/Lists' -import {ProfileFollows as ProfileFollowsComponent} from '../com/profile/ProfileFollows' -import {ViewHeader} from '../com/util/ViewHeader' type Props = NativeStackScreenProps<CommonNavigatorParams, 'ProfileFollows'> export const ProfileFollowsScreen = ({route}: Props) => { @@ -25,10 +25,12 @@ export const ProfileFollowsScreen = ({route}: Props) => { ) return ( - <CenteredView style={a.util_screen_outer} sideBorders={true}> - <ListHeaderDesktop title={_(msg`Following`)} /> - <ViewHeader title={_(msg`Following`)} showBorder={!isWeb} /> - <ProfileFollowsComponent name={name} /> - </CenteredView> + <Layout.Screen testID="profileFollowsScreen"> + <CenteredView sideBorders={true}> + <ListHeaderDesktop title={_(msg`Following`)} /> + <ViewHeader title={_(msg`Following`)} showBorder={!isWeb} /> + <ProfileFollowsComponent name={name} /> + </CenteredView> + </Layout.Screen> ) } diff --git a/src/view/screens/ProfileList.tsx b/src/view/screens/ProfileList.tsx index e0fd18ae9..cb333befa 100644 --- a/src/view/screens/ProfileList.tsx +++ b/src/view/screens/ProfileList.tsx @@ -73,6 +73,7 @@ import {CenteredView} from '#/view/com/util/Views' import {ListHiddenScreen} from '#/screens/List/ListHiddenScreen' import {atoms as a, useTheme} from '#/alf' import {useDialogControl} from '#/components/Dialog' +import * as Layout from '#/components/Layout' import * as Hider from '#/components/moderation/Hider' import * as Prompt from '#/components/Prompt' import {ReportDialog, useReportDialogControl} from '#/components/ReportDialog' @@ -87,6 +88,14 @@ interface SectionRef { type Props = NativeStackScreenProps<CommonNavigatorParams, 'ProfileList'> export function ProfileListScreen(props: Props) { + return ( + <Layout.Screen testID="profileListScreen"> + <ProfileListScreenInner {...props} /> + </Layout.Screen> + ) +} + +function ProfileListScreenInner(props: Props) { const {_} = useLingui() const {name: handleOrDid, rkey} = props.route.params const {data: resolvedUri, error: resolveError} = useResolveUriQuery( diff --git a/src/view/screens/SavedFeeds.tsx b/src/view/screens/SavedFeeds.tsx index 2334abb5d..e88866f5b 100644 --- a/src/view/screens/SavedFeeds.tsx +++ b/src/view/screens/SavedFeeds.tsx @@ -32,6 +32,7 @@ import {NoSavedFeedsOfAnyType} from '#/screens/Feeds/NoSavedFeedsOfAnyType' import {atoms as a, useTheme} from '#/alf' import {Button, ButtonIcon, ButtonText} from '#/components/Button' import {FilterTimeline_Stroke2_Corner0_Rounded as FilterTimeline} from '#/components/icons/FilterTimeline' +import * as Layout from '#/components/Layout' import {Loader} from '#/components/Loader' type Props = NativeStackScreenProps<CommonNavigatorParams, 'SavedFeeds'> @@ -106,120 +107,117 @@ function SavedFeedsInner({ }, [_, isDesktop, onSaveChanges, hasUnsavedChanges, isOverwritePending]) return ( - <CenteredView - style={[ - s.hContentRegion, - pal.border, - isTabletOrDesktop && styles.desktopContainer, - ]}> - <ViewHeader - title={_(msg`Edit My Feeds`)} - showOnDesktop - showBorder - renderButton={renderHeaderBtn} - /> - <ScrollView style={s.flex1} contentContainerStyle={[styles.noBorder]}> - {noSavedFeedsOfAnyType && ( - <View - style={[pal.border, {borderBottomWidth: StyleSheet.hairlineWidth}]}> - <NoSavedFeedsOfAnyType /> + <Layout.Screen> + <CenteredView + style={[a.util_screen_outer]} + sideBorders={isTabletOrDesktop}> + <ViewHeader + title={_(msg`Edit My Feeds`)} + showOnDesktop + showBorder + renderButton={renderHeaderBtn} + /> + <ScrollView style={[a.flex_1]} contentContainerStyle={[a.border_0]}> + {noSavedFeedsOfAnyType && ( + <View style={[pal.border, a.border_b]}> + <NoSavedFeedsOfAnyType /> + </View> + )} + + <View style={[pal.text, pal.border, styles.title]}> + <Text type="title" style={pal.text}> + <Trans>Pinned Feeds</Trans> + </Text> </View> - )} - <View style={[pal.text, pal.border, styles.title]}> - <Text type="title" style={pal.text}> - <Trans>Pinned Feeds</Trans> - </Text> - </View> + {preferences ? ( + !pinnedFeeds.length ? ( + <View + style={[ + pal.border, + isMobile && s.flex1, + pal.viewLight, + styles.empty, + ]}> + <Text type="lg" style={[pal.text]}> + <Trans>You don't have any pinned feeds.</Trans> + </Text> + </View> + ) : ( + pinnedFeeds.map(f => ( + <ListItem + key={f.id} + feed={f} + isPinned + currentFeeds={currentFeeds} + setCurrentFeeds={setCurrentFeeds} + preferences={preferences} + /> + )) + ) + ) : ( + <ActivityIndicator style={{marginTop: 20}} /> + )} - {preferences ? ( - !pinnedFeeds.length ? ( - <View - style={[ - pal.border, - isMobile && s.flex1, - pal.viewLight, - styles.empty, - ]}> - <Text type="lg" style={[pal.text]}> - <Trans>You don't have any pinned feeds.</Trans> - </Text> + {noFollowingFeed && ( + <View style={[pal.border, a.border_b]}> + <NoFollowingFeed /> </View> - ) : ( - pinnedFeeds.map(f => ( - <ListItem - key={f.id} - feed={f} - isPinned - currentFeeds={currentFeeds} - setCurrentFeeds={setCurrentFeeds} - preferences={preferences} - /> - )) - ) - ) : ( - <ActivityIndicator style={{marginTop: 20}} /> - )} + )} - {noFollowingFeed && ( - <View - style={[pal.border, {borderBottomWidth: StyleSheet.hairlineWidth}]}> - <NoFollowingFeed /> + <View style={[pal.text, pal.border, styles.title]}> + <Text type="title" style={pal.text}> + <Trans>Saved Feeds</Trans> + </Text> </View> - )} - - <View style={[pal.text, pal.border, styles.title]}> - <Text type="title" style={pal.text}> - <Trans>Saved Feeds</Trans> - </Text> - </View> - {preferences ? ( - !unpinnedFeeds.length ? ( - <View - style={[ - pal.border, - isMobile && s.flex1, - pal.viewLight, - styles.empty, - ]}> - <Text type="lg" style={[pal.text]}> - <Trans>You don't have any saved feeds.</Trans> - </Text> - </View> + {preferences ? ( + !unpinnedFeeds.length ? ( + <View + style={[ + pal.border, + isMobile && s.flex1, + pal.viewLight, + styles.empty, + ]}> + <Text type="lg" style={[pal.text]}> + <Trans>You don't have any saved feeds.</Trans> + </Text> + </View> + ) : ( + unpinnedFeeds.map(f => ( + <ListItem + key={f.id} + feed={f} + isPinned={false} + currentFeeds={currentFeeds} + setCurrentFeeds={setCurrentFeeds} + preferences={preferences} + /> + )) + ) ) : ( - unpinnedFeeds.map(f => ( - <ListItem - key={f.id} - feed={f} - isPinned={false} - currentFeeds={currentFeeds} - setCurrentFeeds={setCurrentFeeds} - preferences={preferences} - /> - )) - ) - ) : ( - <ActivityIndicator style={{marginTop: 20}} /> - )} + <ActivityIndicator style={{marginTop: 20}} /> + )} - <View style={styles.footerText}> - <Text type="sm" style={pal.textLight}> - <Trans> - Feeds are custom algorithms that users build with a little coding - expertise.{' '} - <TextLink - type="sm" - style={pal.link} - href="https://github.com/bluesky-social/feed-generator" - text={_(msg`See this guide`)} - />{' '} - for more information. - </Trans> - </Text> - </View> - <View style={{height: 100}} /> - </ScrollView> - </CenteredView> + <View style={styles.footerText}> + <Text type="sm" style={pal.textLight}> + <Trans> + Feeds are custom algorithms that users build with a little + coding expertise.{' '} + <TextLink + type="sm" + style={pal.link} + href="https://github.com/bluesky-social/feed-generator" + text={_(msg`See this guide`)} + />{' '} + for more information. + </Trans> + </Text> + </View> + <View style={{height: 100}} /> + </ScrollView> + </CenteredView> + </Layout.Screen> ) } @@ -434,12 +432,6 @@ function FollowingFeedCard() { } const styles = StyleSheet.create({ - desktopContainer: { - borderLeftWidth: 1, - borderRightWidth: 1, - // @ts-ignore only rendered on web - minHeight: '100vh', - }, empty: { paddingHorizontal: 20, paddingVertical: 20, @@ -463,10 +455,4 @@ const styles = StyleSheet.create({ paddingTop: 22, paddingBottom: 100, }, - noBorder: { - borderBottomWidth: 0, - borderRightWidth: 0, - borderLeftWidth: 0, - borderTopWidth: 0, - }, }) diff --git a/src/view/screens/Search/Explore.tsx b/src/view/screens/Search/Explore.tsx index 650fd4354..6aff9b88a 100644 --- a/src/view/screens/Search/Explore.tsx +++ b/src/view/screens/Search/Explore.tsx @@ -10,20 +10,20 @@ import { import {msg, Trans} from '@lingui/macro' import {useLingui} from '@lingui/react' +import {cleanError} from '#/lib/strings/errors' import {logger} from '#/logger' import {isWeb} from '#/platform/detection' import {useModerationOpts} from '#/state/preferences/moderation-opts' import {useGetPopularFeedsQuery} from '#/state/queries/feed' import {usePreferencesQuery} from '#/state/queries/preferences' import {useSuggestedFollowsQuery} from '#/state/queries/suggested-follows' -import {cleanError} from 'lib/strings/errors' import {ProfileCardWithFollowBtn} from '#/view/com/profile/ProfileCard' import {List} from '#/view/com/util/List' -import {UserAvatar} from '#/view/com/util/UserAvatar' import { FeedFeedLoadingPlaceholder, ProfileCardFeedLoadingPlaceholder, -} from 'view/com/util/LoadingPlaceholder' +} from '#/view/com/util/LoadingPlaceholder' +import {UserAvatar} from '#/view/com/util/UserAvatar' import {atoms as a, useTheme, ViewStyleProp} from '#/alf' import {Button} from '#/components/Button' import * as FeedCard from '#/components/FeedCard' @@ -564,6 +564,8 @@ export function Explore() { [t, moderationOpts], ) + // note: actually not a screen, instead it's nested within + // the search screen. so we don't need Layout.Screen return ( <List data={items} diff --git a/src/view/screens/Search/Search.tsx b/src/view/screens/Search/Search.tsx index f4bbde567..5b4faacec 100644 --- a/src/view/screens/Search/Search.tsx +++ b/src/view/screens/Search/Search.tsx @@ -65,6 +65,7 @@ import * as FeedCard from '#/components/FeedCard' import {SearchInput} from '#/components/forms/SearchInput' import {ChevronBottom_Stroke2_Corner0_Rounded as ChevronDown} from '#/components/icons/Chevron' import {Menu_Stroke2_Corner0_Rounded as Menu} from '#/components/icons/Menu' +import * as Layout from '#/components/Layout' function Loader() { const pal = usePalette('default') @@ -852,7 +853,7 @@ export function SearchScreen( }, [setShowAutocomplete]) return ( - <View style={isWeb ? null : {flex: 1}}> + <Layout.Screen testID="searchScreen"> <CenteredView style={[ a.p_md, @@ -957,7 +958,7 @@ export function SearchScreen( headerHeight={headerHeight} /> </View> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/Settings/index.tsx b/src/view/screens/Settings/index.tsx index a40cc4f26..ce21a043b 100644 --- a/src/view/screens/Settings/index.tsx +++ b/src/view/screens/Settings/index.tsx @@ -57,6 +57,7 @@ import {atoms as a, useTheme} from '#/alf' import {useDialogControl} from '#/components/Dialog' import {BirthDateSettingsDialog} from '#/components/dialogs/BirthDateSettings' import {VerifyEmailDialog} from '#/components/dialogs/VerifyEmailDialog' +import * as Layout from '#/components/Layout' import {Email2FAToggle} from './Email2FAToggle' import {ExportCarDialog} from './ExportCarDialog' @@ -286,7 +287,7 @@ export function SettingsScreen({}: Props) { const {mutate: onPressDeleteChatDeclaration} = useDeleteActorDeclaration() return ( - <View style={s.hContentRegion} testID="settingsScreen"> + <Layout.Screen testID="settingsScreen"> <ExportCarDialog control={exportCarControl} /> <BirthDateSettingsDialog control={birthdayControl} /> @@ -919,7 +920,7 @@ export function SettingsScreen({}: Props) { </View> <View style={s.footerSpacer} /> </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/Storybook/index.tsx b/src/view/screens/Storybook/index.tsx index c737dad5b..f1152fb7e 100644 --- a/src/view/screens/Storybook/index.tsx +++ b/src/view/screens/Storybook/index.tsx @@ -7,6 +7,7 @@ import {CenteredView} from '#/view/com/util/Views' import {ListContained} from '#/view/screens/Storybook/ListContained' import {atoms as a, ThemeProvider, useTheme} from '#/alf' import {Button, ButtonText} from '#/components/Button' +import * as Layout from '#/components/Layout' import {Admonitions} from './Admonitions' import {Breakpoints} from './Breakpoints' import {Buttons} from './Buttons' @@ -21,12 +22,16 @@ import {Theming} from './Theming' import {Typography} from './Typography' export function Storybook() { - if (isWeb) return <StorybookInner /> - return ( - <ScrollView> - <StorybookInner /> - </ScrollView> + <Layout.Screen> + {isWeb ? ( + <StorybookInner /> + ) : ( + <ScrollView> + <StorybookInner /> + </ScrollView> + )} + </Layout.Screen> ) } diff --git a/src/view/screens/Support.tsx b/src/view/screens/Support.tsx index 9e7d36ec7..8782e911b 100644 --- a/src/view/screens/Support.tsx +++ b/src/view/screens/Support.tsx @@ -1,17 +1,18 @@ import React from 'react' -import {View} from 'react-native' +import {msg, Trans} from '@lingui/macro' +import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' -import {NativeStackScreenProps, CommonNavigatorParams} from 'lib/routes/types' -import {ViewHeader} from '../com/util/ViewHeader' -import {Text} from 'view/com/util/text/Text' -import {TextLink} from 'view/com/util/Link' -import {CenteredView} from 'view/com/util/Views' -import {usePalette} from 'lib/hooks/usePalette' -import {s} from 'lib/styles' -import {HELP_DESK_URL} from 'lib/constants' + +import {HELP_DESK_URL} from '#/lib/constants' +import {usePalette} from '#/lib/hooks/usePalette' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {s} from '#/lib/styles' import {useSetMinimalShellMode} from '#/state/shell' -import {Trans, msg} from '@lingui/macro' -import {useLingui} from '@lingui/react' +import {TextLink} from '#/view/com/util/Link' +import {Text} from '#/view/com/util/text/Text' +import {ViewHeader} from '#/view/com/util/ViewHeader' +import {CenteredView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' type Props = NativeStackScreenProps<CommonNavigatorParams, 'Support'> export const SupportScreen = (_props: Props) => { @@ -26,7 +27,7 @@ export const SupportScreen = (_props: Props) => { ) return ( - <View> + <Layout.Screen> <ViewHeader title={_(msg`Support`)} /> <CenteredView> <Text type="title-xl" style={[pal.text, s.p20, s.pb5]}> @@ -44,6 +45,6 @@ export const SupportScreen = (_props: Props) => { </Trans> </Text> </CenteredView> - </View> + </Layout.Screen> ) } diff --git a/src/view/screens/TermsOfService.tsx b/src/view/screens/TermsOfService.tsx index 47aa9f268..fa40fbca3 100644 --- a/src/view/screens/TermsOfService.tsx +++ b/src/view/screens/TermsOfService.tsx @@ -1,16 +1,18 @@ import React from 'react' import {View} from 'react-native' +import {msg, Trans} from '@lingui/macro' +import {useLingui} from '@lingui/react' import {useFocusEffect} from '@react-navigation/native' -import {Text} from 'view/com/util/text/Text' -import {TextLink} from 'view/com/util/Link' -import {NativeStackScreenProps, CommonNavigatorParams} from 'lib/routes/types' -import {ViewHeader} from '../com/util/ViewHeader' -import {ScrollView} from 'view/com/util/Views' -import {usePalette} from 'lib/hooks/usePalette' -import {s} from 'lib/styles' + +import {usePalette} from '#/lib/hooks/usePalette' +import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types' +import {s} from '#/lib/styles' import {useSetMinimalShellMode} from '#/state/shell' -import {Trans, msg} from '@lingui/macro' -import {useLingui} from '@lingui/react' +import {TextLink} from '#/view/com/util/Link' +import {Text} from '#/view/com/util/text/Text' +import {ScrollView} from '#/view/com/util/Views' +import * as Layout from '#/components/Layout' +import {ViewHeader} from '../com/util/ViewHeader' type Props = NativeStackScreenProps<CommonNavigatorParams, 'TermsOfService'> export const TermsOfServiceScreen = (_props: Props) => { @@ -25,7 +27,7 @@ export const TermsOfServiceScreen = (_props: Props) => { ) return ( - <View> + <Layout.Screen> <ViewHeader title={_(msg`Terms of Service`)} /> <ScrollView style={[s.hContentRegion, pal.view]}> <View style={[s.p20]}> @@ -40,6 +42,6 @@ export const TermsOfServiceScreen = (_props: Props) => { </View> <View style={s.footerSpacer} /> </ScrollView> - </View> + </Layout.Screen> ) } diff --git a/src/view/shell/index.tsx b/src/view/shell/index.tsx index 79fc1a069..43f8ee656 100644 --- a/src/view/shell/index.tsx +++ b/src/view/shell/index.tsx @@ -1,14 +1,7 @@ import React from 'react' -import { - BackHandler, - DimensionValue, - StyleSheet, - useWindowDimensions, - View, -} from 'react-native' +import {BackHandler, StyleSheet, useWindowDimensions, View} from 'react-native' import {Drawer} from 'react-native-drawer-layout' import Animated from 'react-native-reanimated' -import {useSafeAreaInsets} from 'react-native-safe-area-context' import * as NavigationBar from 'expo-navigation-bar' import {StatusBar} from 'expo-status-bar' import {useNavigation, useNavigationState} from '@react-navigation/native' @@ -32,6 +25,7 @@ import {useCloseAnyActiveElement} from '#/state/util' import {Lightbox} from '#/view/com/lightbox/Lightbox' import {ModalsContainer} from '#/view/com/modals/Modal' import {ErrorBoundary} from '#/view/com/util/ErrorBoundary' +import {atoms as a} from '#/alf' import {MutedWordsDialog} from '#/components/dialogs/MutedWords' import {SigninDialog} from '#/components/dialogs/Signin' import {Outlet as PortalOutlet} from '#/components/Portal' @@ -46,11 +40,7 @@ function ShellInner() { const isDrawerSwipeDisabled = useIsDrawerSwipeDisabled() const setIsDrawerOpen = useSetDrawerOpen() const winDim = useWindowDimensions() - const safeAreaInsets = useSafeAreaInsets() - const containerPadding = React.useMemo( - () => ({height: '100%' as DimensionValue, paddingTop: safeAreaInsets.top}), - [safeAreaInsets], - ) + const renderDrawerContent = React.useCallback(() => <DrawerContent />, []) const onOpenDrawer = React.useCallback( () => setIsDrawerOpen(true), @@ -68,14 +58,14 @@ function ShellInner() { useNotificationsHandler() React.useEffect(() => { - let listener = {remove() {}} if (isAndroid) { - listener = BackHandler.addEventListener('hardwareBackPress', () => { + const listener = BackHandler.addEventListener('hardwareBackPress', () => { return closeAnyActiveElement() }) - } - return () => { - listener.remove() + + return () => { + listener.remove() + } } }, [closeAnyActiveElement]) @@ -102,7 +92,7 @@ function ShellInner() { return ( <> - <Animated.View style={containerPadding}> + <Animated.View style={[a.h_full]}> <ErrorBoundary> <Drawer renderDrawerContent={renderDrawerContent} diff --git a/src/view/shell/index.web.tsx b/src/view/shell/index.web.tsx index 2c7cd7b08..eeb1f13dd 100644 --- a/src/view/shell/index.web.tsx +++ b/src/view/shell/index.web.tsx @@ -7,19 +7,20 @@ import {useNavigation} from '@react-navigation/native' import {useColorSchemeStyle} from '#/lib/hooks/useColorSchemeStyle' import {useIntentHandler} from '#/lib/hooks/useIntentHandler' import {useWebBodyScrollLock} from '#/lib/hooks/useWebBodyScrollLock' +import {useWebMediaQueries} from '#/lib/hooks/useWebMediaQueries' import {NavigationProp} from '#/lib/routes/types' -import {colors, s} from '#/lib/styles' +import {colors} from '#/lib/styles' import {useIsDrawerOpen, useSetDrawerOpen} from '#/state/shell' import {useComposerKeyboardShortcut} from '#/state/shell/composer/useComposerKeyboardShortcut' import {useCloseAllActiveElements} from '#/state/util' +import {Lightbox} from '#/view/com/lightbox/Lightbox' +import {ModalsContainer} from '#/view/com/modals/Modal' +import {ErrorBoundary} from '#/view/com/util/ErrorBoundary' +import {atoms as a} from '#/alf' import {MutedWordsDialog} from '#/components/dialogs/MutedWords' import {SigninDialog} from '#/components/dialogs/Signin' import {Outlet as PortalOutlet} from '#/components/Portal' -import {useWebMediaQueries} from '../../lib/hooks/useWebMediaQueries' -import {FlatNavigator, RoutesContainer} from '../../Navigation' -import {Lightbox} from '../com/lightbox/Lightbox' -import {ModalsContainer} from '../com/modals/Modal' -import {ErrorBoundary} from '../com/util/ErrorBoundary' +import {FlatNavigator, RoutesContainer} from '#/Navigation' import {Composer} from './Composer.web' import {DrawerContent} from './Drawer' @@ -78,7 +79,7 @@ function ShellInner() { export const Shell: React.FC = function ShellImpl() { const pageBg = useColorSchemeStyle(styles.bgLight, styles.bgDark) return ( - <View style={[s.hContentRegion, pageBg]}> + <View style={[a.util_screen_outer, pageBg]}> <RoutesContainer> <ShellInner /> </RoutesContainer> |