Settings revamp (#5745)
* start building storybook * add title * add some styles * try out new icons * more settings list component parts * make text do the spacing * clean up storybook * gated new settings screen * switch account * add current profile * use Layout.Screen * Layout.Header and Layout.Content * translate helpdesk text thanks @surfdude29! Co-authored-by: surfdude29 <149612116+surfdude29@users.noreply.github.com> * add account settings * undo changes to export car dialog * privacy and security screen * Translate protect account stuff Thanks @surfdude29! Co-authored-by: surfdude29 <149612116+surfdude29@users.noreply.github.com> * content and media settings * about settings * 2fa copy Co-authored-by: surfdude29 <149612116+surfdude29@users.noreply.github.com> * a11y and appearance * use new components for appearance settings * redesign accessibility settings * Update ContentAndMediaSettings.tsx Co-authored-by: surfdude29 <149612116+surfdude29@users.noreply.github.com> * add divider * remove a11y and appearance middleman screen * fix web settingslist styles * new SettingsList.Group component * explain how portal magic works * hide pwioptout in old location * Update Settings.tsx Co-authored-by: surfdude29 <149612116+surfdude29@users.noreply.github.com> * replace gate with `IS_INTERNAL` * add IS_INTERNAL to app-info.web * fix profile area growing * add close button to switch account --------- Co-authored-by: surfdude29 <149612116+surfdude29@users.noreply.github.com>
This commit is contained in:
@@ -10,15 +10,15 @@ import {LinearGradient} from 'expo-linear-gradient'
|
||||
import {msg, Trans} from '@lingui/macro'
|
||||
import {useLingui} from '@lingui/react'
|
||||
|
||||
import {usePalette} from '#/lib/hooks/usePalette'
|
||||
import {useWebMediaQueries} from '#/lib/hooks/useWebMediaQueries'
|
||||
import {cleanError} from '#/lib/strings/errors'
|
||||
import {colors, gradients, s} from '#/lib/styles'
|
||||
import {useTheme} from '#/lib/ThemeContext'
|
||||
import {isAndroid, isWeb} from '#/platform/detection'
|
||||
import {useModalControls} from '#/state/modals'
|
||||
import {DM_SERVICE_HEADERS} from '#/state/queries/messages/const'
|
||||
import {useAgent, useSession, useSessionApi} from '#/state/session'
|
||||
import {usePalette} from 'lib/hooks/usePalette'
|
||||
import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries'
|
||||
import {cleanError} from 'lib/strings/errors'
|
||||
import {colors, gradients, s} from 'lib/styles'
|
||||
import {useTheme} from 'lib/ThemeContext'
|
||||
import {isAndroid, isWeb} from 'platform/detection'
|
||||
import {DeactivateAccountDialog} from '#/screens/Settings/components/DeactivateAccountDialog'
|
||||
import {atoms as a, useTheme as useNewTheme} from '#/alf'
|
||||
import {useDialogControl} from '#/components/Dialog'
|
||||
@@ -210,6 +210,7 @@ export function Component({}: {}) {
|
||||
to="#"
|
||||
onPress={e => {
|
||||
e.preventDefault()
|
||||
closeModal()
|
||||
deactivateAccountControl.open()
|
||||
return false
|
||||
}}>
|
||||
|
||||
@@ -4,6 +4,7 @@ import {msg, Trans} from '@lingui/macro'
|
||||
import {useLingui} from '@lingui/react'
|
||||
import {useFocusEffect} from '@react-navigation/native'
|
||||
|
||||
import {IS_INTERNAL} from '#/lib/app-info'
|
||||
import {usePalette} from '#/lib/hooks/usePalette'
|
||||
import {useWebMediaQueries} from '#/lib/hooks/useWebMediaQueries'
|
||||
import {CommonNavigatorParams, NativeStackScreenProps} from '#/lib/routes/types'
|
||||
@@ -26,6 +27,7 @@ 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 {AccessibilitySettingsScreen as NewAccessibilitySettingsScreen} from '#/screens/Settings/AccessibilitySettings'
|
||||
import {atoms as a} from '#/alf'
|
||||
import * as Layout from '#/components/Layout'
|
||||
|
||||
@@ -33,7 +35,15 @@ type Props = NativeStackScreenProps<
|
||||
CommonNavigatorParams,
|
||||
'AccessibilitySettings'
|
||||
>
|
||||
export function AccessibilitySettingsScreen({}: Props) {
|
||||
export function AccessibilitySettingsScreen(props: Props) {
|
||||
return IS_INTERNAL ? (
|
||||
<NewAccessibilitySettingsScreen {...props} />
|
||||
) : (
|
||||
<LegacyAccessibilitySettingsScreen {...props} />
|
||||
)
|
||||
}
|
||||
|
||||
function LegacyAccessibilitySettingsScreen({}: Props) {
|
||||
const pal = usePalette('default')
|
||||
const setMinimalShellMode = useSetMinimalShellMode()
|
||||
const {isMobile, isTabletOrMobile} = useWebMediaQueries()
|
||||
|
||||
@@ -108,7 +108,11 @@ export function DisableEmail2FADialog({
|
||||
{error ? <ErrorMessage message={error} /> : undefined}
|
||||
|
||||
{stage === Stages.Email ? (
|
||||
<View style={gtMobile && [a.flex_row, a.justify_end, a.gap_md]}>
|
||||
<View
|
||||
style={[
|
||||
a.gap_sm,
|
||||
gtMobile && [a.flex_row, a.justify_end, a.gap_md],
|
||||
]}>
|
||||
<Button
|
||||
testID="sendEmailButton"
|
||||
variant="solid"
|
||||
@@ -157,7 +161,11 @@ export function DisableEmail2FADialog({
|
||||
/>
|
||||
</TextField.Root>
|
||||
</View>
|
||||
<View style={gtMobile && [a.flex_row, a.justify_end]}>
|
||||
<View
|
||||
style={[
|
||||
a.gap_sm,
|
||||
gtMobile && [a.flex_row, a.justify_end, a.gap_md],
|
||||
]}>
|
||||
<Button
|
||||
testID="resendCodeBtn"
|
||||
variant="ghost"
|
||||
|
||||
@@ -10,6 +10,7 @@ import * as Toast from '#/view/com/util/Toast'
|
||||
import {atoms as a, useTheme} from '#/alf'
|
||||
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
||||
import * as Dialog from '#/components/Dialog'
|
||||
import {Download_Stroke2_Corner0_Rounded as DownloadIcon} from '#/components/icons/Download'
|
||||
import {InlineLinkText} from '#/components/Link'
|
||||
import {Loader} from '#/components/Loader'
|
||||
import {Text} from '#/components/Typography'
|
||||
@@ -76,6 +77,7 @@ export function ExportCarDialog({
|
||||
label={_(msg`Download CAR file`)}
|
||||
disabled={loading}
|
||||
onPress={download}>
|
||||
<ButtonIcon icon={DownloadIcon} />
|
||||
<ButtonText>
|
||||
<Trans>Download CAR file</Trans>
|
||||
</ButtonText>
|
||||
|
||||
@@ -18,7 +18,7 @@ import {useLingui} from '@lingui/react'
|
||||
import {useFocusEffect, useNavigation} from '@react-navigation/native'
|
||||
import {useQueryClient} from '@tanstack/react-query'
|
||||
|
||||
import {appVersion, BUNDLE_DATE, bundleInfo} from '#/lib/app-info'
|
||||
import {appVersion, BUNDLE_DATE, bundleInfo, IS_INTERNAL} from '#/lib/app-info'
|
||||
import {STATUS_PAGE_URL} from '#/lib/constants'
|
||||
import {useAccountSwitcher} from '#/lib/hooks/useAccountSwitcher'
|
||||
import {useCustomPalette} from '#/lib/hooks/useCustomPalette'
|
||||
@@ -53,6 +53,7 @@ import * as Toast from '#/view/com/util/Toast'
|
||||
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
||||
import {ScrollView} from '#/view/com/util/Views'
|
||||
import {DeactivateAccountDialog} from '#/screens/Settings/components/DeactivateAccountDialog'
|
||||
import {SettingsScreen as NewSettingsScreen} from '#/screens/Settings/Settings'
|
||||
import {atoms as a, useTheme} from '#/alf'
|
||||
import {useDialogControl} from '#/components/Dialog'
|
||||
import {BirthDateSettingsDialog} from '#/components/dialogs/BirthDateSettings'
|
||||
@@ -137,7 +138,15 @@ function SettingsAccountCard({
|
||||
}
|
||||
|
||||
type Props = NativeStackScreenProps<CommonNavigatorParams, 'Settings'>
|
||||
export function SettingsScreen({}: Props) {
|
||||
export function SettingsScreen(props: Props) {
|
||||
return IS_INTERNAL ? (
|
||||
<NewSettingsScreen {...props} />
|
||||
) : (
|
||||
<LegacySettingsScreen {...props} />
|
||||
)
|
||||
}
|
||||
|
||||
function LegacySettingsScreen({}: Props) {
|
||||
const queryClient = useQueryClient()
|
||||
const pal = usePalette('default')
|
||||
const {_} = useLingui()
|
||||
|
||||
@@ -0,0 +1,134 @@
|
||||
import React from 'react'
|
||||
import {View} from 'react-native'
|
||||
|
||||
import * as Toast from '#/view/com/util/Toast'
|
||||
import * as SettingsList from '#/screens/Settings/components/SettingsList'
|
||||
import {atoms as a, useTheme} from '#/alf'
|
||||
import {Alien_Stroke2_Corner0_Rounded as AlienIcon} from '#/components/icons/Alien'
|
||||
import {BirthdayCake_Stroke2_Corner2_Rounded as BirthdayCakeIcon} from '#/components/icons/BirthdayCake'
|
||||
import {BubbleInfo_Stroke2_Corner2_Rounded as BubbleInfoIcon} from '#/components/icons/BubbleInfo'
|
||||
import {CircleQuestion_Stroke2_Corner2_Rounded as CircleQuestionIcon} from '#/components/icons/CircleQuestion'
|
||||
import {Envelope_Stroke2_Corner2_Rounded as EnvelopeIcon} from '#/components/icons/Envelope'
|
||||
import {Explosion_Stroke2_Corner0_Rounded as ExplosionIcon} from '#/components/icons/Explosion'
|
||||
import {Earth_Stroke2_Corner2_Rounded as EarthIcon} from '#/components/icons/Globe'
|
||||
import {PaintRoller_Stroke2_Corner2_Rounded as PaintRollerIcon} from '#/components/icons/PaintRoller'
|
||||
import {Person_Stroke2_Corner2_Rounded as PersonIcon} from '#/components/icons/Person'
|
||||
import {Pizza_Stroke2_Corner0_Rounded as PizzaIcon} from '#/components/icons/Pizza'
|
||||
import {RaisingHand4Finger_Stroke2_Corner2_Rounded as HandIcon} from '#/components/icons/RaisingHand'
|
||||
import {Verified_Stroke2_Corner2_Rounded as VerifiedIcon} from '#/components/icons/Verified'
|
||||
import {Window_Stroke2_Corner2_Rounded as WindowIcon} from '#/components/icons/Window'
|
||||
import {Text} from '#/components/Typography'
|
||||
|
||||
export function Settings() {
|
||||
const t = useTheme()
|
||||
return (
|
||||
<View style={{marginLeft: -20, marginRight: -20}}>
|
||||
<Text style={{marginLeft: 20, paddingBottom: 12}}>Settings</Text>
|
||||
<SettingsList.LinkItem to="/settings" label="Account">
|
||||
<SettingsList.ItemIcon icon={PersonIcon} />
|
||||
<SettingsList.ItemText>Account</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.LinkItem to="/settings" label="Privacy and security">
|
||||
<SettingsList.ItemIcon icon={PaintRollerIcon} />
|
||||
<SettingsList.ItemText>Privacy and security</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.LinkItem to="/settings" label="Moderation">
|
||||
<SettingsList.ItemIcon icon={HandIcon} />
|
||||
<SettingsList.ItemText>Moderation</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.LinkItem to="/settings" label="Content and media">
|
||||
<SettingsList.ItemIcon icon={WindowIcon} />
|
||||
<SettingsList.ItemText>Content and media</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.LinkItem
|
||||
to="/settings"
|
||||
label="Accessibility and appearance">
|
||||
<SettingsList.ItemIcon icon={PaintRollerIcon} />
|
||||
<SettingsList.ItemText>
|
||||
Accessibilty and appearance
|
||||
</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.LinkItem to="/settings" label="Languages">
|
||||
<SettingsList.ItemIcon icon={EarthIcon} />
|
||||
<SettingsList.ItemText>Languages</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.LinkItem to="/settings" label="Help">
|
||||
<SettingsList.ItemIcon icon={CircleQuestionIcon} />
|
||||
<SettingsList.ItemText>Help</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.LinkItem to="/settings" label="About">
|
||||
<SettingsList.ItemIcon icon={BubbleInfoIcon} />
|
||||
<SettingsList.ItemText>About</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.Divider />
|
||||
<SettingsList.PressableItem
|
||||
destructive
|
||||
onPress={() => Toast.show('Sign out pressed')}
|
||||
label="Sign out">
|
||||
<SettingsList.ItemText>Sign out</SettingsList.ItemText>
|
||||
</SettingsList.PressableItem>
|
||||
<SettingsList.Item style={[a.mt_xl]}>
|
||||
<SettingsList.ItemIcon icon={PizzaIcon} />
|
||||
<SettingsList.ItemText>Not pressable</SettingsList.ItemText>
|
||||
</SettingsList.Item>
|
||||
<SettingsList.PressableItem
|
||||
onPress={() => Toast.show('Pressable pressed')}
|
||||
label="Pressable">
|
||||
<SettingsList.ItemIcon icon={AlienIcon} />
|
||||
<SettingsList.ItemText>Pressable</SettingsList.ItemText>
|
||||
</SettingsList.PressableItem>
|
||||
<SettingsList.LinkItem
|
||||
to="/settings"
|
||||
label="Destructive link"
|
||||
destructive>
|
||||
<SettingsList.ItemIcon icon={ExplosionIcon} />
|
||||
<SettingsList.ItemText>Destructive link</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
<SettingsList.PressableItem
|
||||
label="Email"
|
||||
onPress={() => Toast.show('Email change dialog goes here')}>
|
||||
<SettingsList.ItemIcon icon={EnvelopeIcon} />
|
||||
<SettingsList.ItemText>Email</SettingsList.ItemText>
|
||||
<SettingsList.BadgeText>hello@example.com</SettingsList.BadgeText>
|
||||
</SettingsList.PressableItem>
|
||||
<SettingsList.PressableItem
|
||||
onPress={() => Toast.show('Pressable pressed')}
|
||||
label="Protect your account"
|
||||
style={[
|
||||
a.my_sm,
|
||||
a.mx_lg,
|
||||
a.rounded_md,
|
||||
{backgroundColor: t.palette.primary_50},
|
||||
]}
|
||||
hoverStyle={[{backgroundColor: t.palette.primary_100}]}
|
||||
contentContainerStyle={[a.rounded_md, a.px_lg]}>
|
||||
<SettingsList.ItemIcon
|
||||
icon={VerifiedIcon}
|
||||
color={t.palette.primary_500}
|
||||
/>
|
||||
<SettingsList.ItemText
|
||||
style={[{color: t.palette.primary_500}, a.font_bold]}>
|
||||
Protect your account
|
||||
</SettingsList.ItemText>
|
||||
<SettingsList.Chevron color={t.palette.primary_500} />
|
||||
</SettingsList.PressableItem>
|
||||
<SettingsList.Divider />
|
||||
<SettingsList.Item>
|
||||
<SettingsList.ItemIcon icon={BirthdayCakeIcon} />
|
||||
<SettingsList.ItemText>Birthday</SettingsList.ItemText>
|
||||
<SettingsList.BadgeButton
|
||||
label="Edit"
|
||||
onPress={() => Toast.show('Show edit birthday dialog')}
|
||||
/>
|
||||
</SettingsList.Item>
|
||||
<SettingsList.LinkItem to="/settings" label="Long test">
|
||||
<SettingsList.ItemIcon icon={ExplosionIcon} />
|
||||
<SettingsList.ItemText>
|
||||
long long long long long long long long long long long long long long
|
||||
long long long long long long long long long long long long long long
|
||||
long long long long long long long long long
|
||||
</SettingsList.ItemText>
|
||||
</SettingsList.LinkItem>
|
||||
</View>
|
||||
)
|
||||
}
|
||||
@@ -18,6 +18,7 @@ import {Forms} from './Forms'
|
||||
import {Icons} from './Icons'
|
||||
import {Links} from './Links'
|
||||
import {Menus} from './Menus'
|
||||
import {Settings} from './Settings'
|
||||
import {Shadows} from './Shadows'
|
||||
import {Spacing} from './Spacing'
|
||||
import {Theming} from './Theming'
|
||||
@@ -101,6 +102,8 @@ function StorybookInner() {
|
||||
|
||||
<Admonitions />
|
||||
|
||||
<Settings />
|
||||
|
||||
<ThemeProvider theme="light">
|
||||
<Theming />
|
||||
</ThemeProvider>
|
||||
|
||||
Reference in New Issue
Block a user