mirror of
https://github.com/tooot-app/app
synced 2025-06-05 22:19:13 +02:00
Use simpler Account page
This commit is contained in:
@@ -9,7 +9,12 @@ import { useScrollToTop } from '@react-navigation/native'
|
|||||||
import { localUpdateNotification } from '@utils/slices/instancesSlice'
|
import { localUpdateNotification } from '@utils/slices/instancesSlice'
|
||||||
import { StyleConstants } from '@utils/styles/constants'
|
import { StyleConstants } from '@utils/styles/constants'
|
||||||
import React, { useCallback, useEffect, useMemo, useRef } from 'react'
|
import React, { useCallback, useEffect, useMemo, useRef } from 'react'
|
||||||
import { Platform, RefreshControl, StyleSheet } from 'react-native'
|
import {
|
||||||
|
FlatListProps,
|
||||||
|
Platform,
|
||||||
|
RefreshControl,
|
||||||
|
StyleSheet
|
||||||
|
} from 'react-native'
|
||||||
import { FlatList } from 'react-native-gesture-handler'
|
import { FlatList } from 'react-native-gesture-handler'
|
||||||
import { useDispatch } from 'react-redux'
|
import { useDispatch } from 'react-redux'
|
||||||
import { QueryKeyTimeline, useTimelineQuery } from '@utils/queryHooks/timeline'
|
import { QueryKeyTimeline, useTimelineQuery } from '@utils/queryHooks/timeline'
|
||||||
@@ -24,6 +29,7 @@ export interface Props {
|
|||||||
account?: Mastodon.Account['id']
|
account?: Mastodon.Account['id']
|
||||||
disableRefresh?: boolean
|
disableRefresh?: boolean
|
||||||
disableInfinity?: boolean
|
disableInfinity?: boolean
|
||||||
|
customProps?: Partial<FlatListProps<any>>
|
||||||
}
|
}
|
||||||
|
|
||||||
const Timeline: React.FC<Props> = ({
|
const Timeline: React.FC<Props> = ({
|
||||||
@@ -33,7 +39,8 @@ const Timeline: React.FC<Props> = ({
|
|||||||
toot,
|
toot,
|
||||||
account,
|
account,
|
||||||
disableRefresh = false,
|
disableRefresh = false,
|
||||||
disableInfinity = false
|
disableInfinity = false,
|
||||||
|
customProps
|
||||||
}) => {
|
}) => {
|
||||||
const queryKeyParams = {
|
const queryKeyParams = {
|
||||||
page,
|
page,
|
||||||
@@ -208,7 +215,6 @@ const Timeline: React.FC<Props> = ({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<FlatList
|
<FlatList
|
||||||
bounces={!disableRefresh}
|
|
||||||
ref={flRef}
|
ref={flRef}
|
||||||
windowSize={11}
|
windowSize={11}
|
||||||
data={flattenData}
|
data={flattenData}
|
||||||
@@ -230,6 +236,7 @@ const Timeline: React.FC<Props> = ({
|
|||||||
// minIndexForVisible: 0,
|
// minIndexForVisible: 0,
|
||||||
// autoscrollToTopThreshold: 2
|
// autoscrollToTopThreshold: 2
|
||||||
// }}
|
// }}
|
||||||
|
{...customProps}
|
||||||
/>
|
/>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@@ -1,19 +1,15 @@
|
|||||||
import BottomSheet from '@components/BottomSheet'
|
import BottomSheet from '@components/BottomSheet'
|
||||||
import { HeaderRight } from '@components/Header'
|
import { HeaderRight } from '@components/Header'
|
||||||
|
import Timeline from '@components/Timelines/Timeline'
|
||||||
import HeaderActionsAccount from '@components/Timelines/Timeline/Shared/HeaderActions/ActionsAccount'
|
import HeaderActionsAccount from '@components/Timelines/Timeline/Shared/HeaderActions/ActionsAccount'
|
||||||
import { useAccountQuery } from '@utils/queryHooks/account'
|
import { useAccountQuery } from '@utils/queryHooks/account'
|
||||||
import { getLocalAccount } from '@utils/slices/instancesSlice'
|
import { getLocalAccount } from '@utils/slices/instancesSlice'
|
||||||
import React, { useEffect, useReducer, useState } from 'react'
|
import React, { useCallback, useEffect, useReducer, useState } from 'react'
|
||||||
import Animated, {
|
import { useSharedValue } from 'react-native-reanimated'
|
||||||
useAnimatedScrollHandler,
|
|
||||||
useSharedValue
|
|
||||||
} from 'react-native-reanimated'
|
|
||||||
import { useSelector } from 'react-redux'
|
import { useSelector } from 'react-redux'
|
||||||
import AccountHeader from './Account/Header'
|
import AccountHeader from './Account/Header'
|
||||||
import AccountInformation from './Account/Information'
|
import AccountInformation from './Account/Information'
|
||||||
import AccountNav from './Account/Nav'
|
import AccountNav from './Account/Nav'
|
||||||
import AccountSegmentedControl from './Account/SegmentedControl'
|
|
||||||
import AccountToots from './Account/Toots'
|
|
||||||
import AccountContext from './Account/utils/createContext'
|
import AccountContext from './Account/utils/createContext'
|
||||||
import accountInitialState from './Account/utils/initialState'
|
import accountInitialState from './Account/utils/initialState'
|
||||||
import accountReducer from './Account/utils/reducer'
|
import accountReducer from './Account/utils/reducer'
|
||||||
@@ -50,26 +46,29 @@ const ScreenSharedAccount: React.FC<SharedAccountProp> = ({
|
|||||||
return updateHeaderRight()
|
return updateHeaderRight()
|
||||||
}, [])
|
}, [])
|
||||||
|
|
||||||
const onScroll = useAnimatedScrollHandler(event => {
|
const onScroll = useCallback(({ nativeEvent }) => {
|
||||||
scrollY.value = event.contentOffset.y
|
scrollY.value = nativeEvent.contentOffset.y
|
||||||
})
|
}, [])
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<AccountContext.Provider value={{ accountState, accountDispatch }}>
|
<AccountContext.Provider value={{ accountState, accountDispatch }}>
|
||||||
<AccountNav scrollY={scrollY} account={data} />
|
<AccountNav scrollY={scrollY} account={data} />
|
||||||
{accountState.informationLayout?.height &&
|
|
||||||
accountState.informationLayout.y ? (
|
<Timeline
|
||||||
<AccountSegmentedControl scrollY={scrollY} />
|
page='Account_Default'
|
||||||
) : null}
|
account={account.id}
|
||||||
<Animated.ScrollView
|
disableRefresh
|
||||||
scrollEventThrottle={16}
|
customProps={{
|
||||||
showsVerticalScrollIndicator={false}
|
onScroll,
|
||||||
onScroll={onScroll}
|
scrollEventThrottle: 16,
|
||||||
>
|
ListHeaderComponent: (
|
||||||
<AccountHeader account={data} />
|
<>
|
||||||
<AccountInformation account={data} />
|
<AccountHeader account={data} />
|
||||||
<AccountToots id={account.id} />
|
<AccountInformation account={data} />
|
||||||
</Animated.ScrollView>
|
</>
|
||||||
|
)
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
|
||||||
<BottomSheet
|
<BottomSheet
|
||||||
visible={modalVisible}
|
visible={modalVisible}
|
||||||
|
@@ -43,8 +43,8 @@ const AccountHeader: React.FC<Props> = ({ account, limitHeight = false }) => {
|
|||||||
}, [account])
|
}, [account])
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Animated.View
|
<Animated.Image
|
||||||
// source={{ uri: account?.header }}
|
source={{ uri: account?.header }}
|
||||||
style={[styleHeight, { backgroundColor: theme.disabled }]}
|
style={[styleHeight, { backgroundColor: theme.disabled }]}
|
||||||
/>
|
/>
|
||||||
)
|
)
|
||||||
|
@@ -1,4 +1,5 @@
|
|||||||
import { StyleConstants } from '@utils/styles/constants'
|
import { StyleConstants } from '@utils/styles/constants'
|
||||||
|
import { useTheme } from '@utils/styles/ThemeManager'
|
||||||
import React, { createRef, useCallback, useContext, useEffect } from 'react'
|
import React, { createRef, useCallback, useContext, useEffect } from 'react'
|
||||||
import { Animated, StyleSheet, View } from 'react-native'
|
import { Animated, StyleSheet, View } from 'react-native'
|
||||||
import AccountInformationAccount from './Information/Account'
|
import AccountInformationAccount from './Information/Account'
|
||||||
@@ -21,7 +22,9 @@ const AccountInformation: React.FC<Props> = ({
|
|||||||
account,
|
account,
|
||||||
ownAccount = false
|
ownAccount = false
|
||||||
}) => {
|
}) => {
|
||||||
|
const { theme } = useTheme()
|
||||||
const { accountDispatch } = useContext(AccountContext)
|
const { accountDispatch } = useContext(AccountContext)
|
||||||
|
|
||||||
const shimmerAvatarRef = createRef<any>()
|
const shimmerAvatarRef = createRef<any>()
|
||||||
const shimmerNameRef = createRef<any>()
|
const shimmerNameRef = createRef<any>()
|
||||||
const shimmerAccountRef = createRef<any>()
|
const shimmerAccountRef = createRef<any>()
|
||||||
@@ -56,7 +59,10 @@ const AccountInformation: React.FC<Props> = ({
|
|||||||
)
|
)
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View style={styles.base} onLayout={onLayout}>
|
<View
|
||||||
|
style={[styles.base, { borderBottomColor: theme.border }]}
|
||||||
|
onLayout={onLayout}
|
||||||
|
>
|
||||||
{/* <Text>Moved or not: {account.moved}</Text> */}
|
{/* <Text>Moved or not: {account.moved}</Text> */}
|
||||||
<View style={styles.avatarAndActions}>
|
<View style={styles.avatarAndActions}>
|
||||||
<AccountInformationAvatar ref={shimmerAvatarRef} account={account} />
|
<AccountInformationAvatar ref={shimmerAvatarRef} account={account} />
|
||||||
@@ -99,7 +105,8 @@ const AccountInformation: React.FC<Props> = ({
|
|||||||
const styles = StyleSheet.create({
|
const styles = StyleSheet.create({
|
||||||
base: {
|
base: {
|
||||||
marginTop: -StyleConstants.Spacing.Global.PagePadding * 3,
|
marginTop: -StyleConstants.Spacing.Global.PagePadding * 3,
|
||||||
padding: StyleConstants.Spacing.Global.PagePadding
|
padding: StyleConstants.Spacing.Global.PagePadding,
|
||||||
|
borderBottomWidth: StyleSheet.hairlineWidth
|
||||||
},
|
},
|
||||||
avatarAndActions: {
|
avatarAndActions: {
|
||||||
flexDirection: 'row',
|
flexDirection: 'row',
|
||||||
|
@@ -23,7 +23,7 @@ const AccountInformationAccount = forwardRef<ShimmerPlaceholder, Props>(
|
|||||||
ref={ref}
|
ref={ref}
|
||||||
visible={account?.acct !== undefined}
|
visible={account?.acct !== undefined}
|
||||||
width={StyleConstants.Font.Size.M * 8}
|
width={StyleConstants.Font.Size.M * 8}
|
||||||
height={StyleConstants.Font.Size.M}
|
height={StyleConstants.Font.LineHeight.M}
|
||||||
style={{ marginBottom: StyleConstants.Spacing.L }}
|
style={{ marginBottom: StyleConstants.Spacing.L }}
|
||||||
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
||||||
>
|
>
|
||||||
|
@@ -24,7 +24,7 @@ const AccountInformationCreated = forwardRef<ShimmerPlaceholder, Props>(
|
|||||||
ref={ref}
|
ref={ref}
|
||||||
visible={account?.created_at !== undefined}
|
visible={account?.created_at !== undefined}
|
||||||
width={StyleConstants.Font.Size.S * 8}
|
width={StyleConstants.Font.Size.S * 8}
|
||||||
height={StyleConstants.Font.Size.S}
|
height={StyleConstants.Font.LineHeight.S}
|
||||||
style={{ marginBottom: StyleConstants.Spacing.M }}
|
style={{ marginBottom: StyleConstants.Spacing.M }}
|
||||||
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
||||||
>
|
>
|
||||||
|
@@ -9,47 +9,52 @@ export interface Props {
|
|||||||
account: Mastodon.Account
|
account: Mastodon.Account
|
||||||
}
|
}
|
||||||
|
|
||||||
const AccountInformationFields: React.FC<Props> = ({ account }) => {
|
const AccountInformationFields = React.memo(
|
||||||
const { theme } = useTheme()
|
({ account }: Props) => {
|
||||||
|
const { theme } = useTheme()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View style={[styles.fields, { borderTopColor: theme.border }]}>
|
<View style={[styles.fields, { borderTopColor: theme.border }]}>
|
||||||
{account.fields.map((field, index) => (
|
{account.fields.map((field, index) => (
|
||||||
<View
|
<View
|
||||||
key={index}
|
key={index}
|
||||||
style={[styles.field, { borderBottomColor: theme.border }]}
|
style={[styles.field, { borderBottomColor: theme.border }]}
|
||||||
>
|
>
|
||||||
<View style={[styles.fieldLeft, { borderRightColor: theme.border }]}>
|
<View
|
||||||
<ParseHTML
|
style={[styles.fieldLeft, { borderRightColor: theme.border }]}
|
||||||
content={field.name}
|
>
|
||||||
size={'M'}
|
<ParseHTML
|
||||||
emojis={account.emojis}
|
content={field.name}
|
||||||
showFullLink
|
size={'M'}
|
||||||
numberOfLines={3}
|
emojis={account.emojis}
|
||||||
/>
|
showFullLink
|
||||||
{field.verified_at ? (
|
numberOfLines={3}
|
||||||
<Icon
|
|
||||||
name='CheckCircle'
|
|
||||||
size={StyleConstants.Font.Size.M}
|
|
||||||
color={theme.primary}
|
|
||||||
style={styles.fieldCheck}
|
|
||||||
/>
|
/>
|
||||||
) : null}
|
{field.verified_at ? (
|
||||||
|
<Icon
|
||||||
|
name='CheckCircle'
|
||||||
|
size={StyleConstants.Font.Size.M}
|
||||||
|
color={theme.primary}
|
||||||
|
style={styles.fieldCheck}
|
||||||
|
/>
|
||||||
|
) : null}
|
||||||
|
</View>
|
||||||
|
<View style={styles.fieldRight}>
|
||||||
|
<ParseHTML
|
||||||
|
content={field.value}
|
||||||
|
size={'M'}
|
||||||
|
emojis={account.emojis}
|
||||||
|
showFullLink
|
||||||
|
numberOfLines={3}
|
||||||
|
/>
|
||||||
|
</View>
|
||||||
</View>
|
</View>
|
||||||
<View style={styles.fieldRight}>
|
))}
|
||||||
<ParseHTML
|
</View>
|
||||||
content={field.value}
|
)
|
||||||
size={'M'}
|
},
|
||||||
emojis={account.emojis}
|
() => true
|
||||||
showFullLink
|
)
|
||||||
numberOfLines={3}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
</View>
|
|
||||||
))}
|
|
||||||
</View>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
const styles = StyleSheet.create({
|
const styles = StyleSheet.create({
|
||||||
fields: {
|
fields: {
|
||||||
|
@@ -24,7 +24,7 @@ const AccountInformationName = forwardRef<ShimmerPlaceholder, Props>(
|
|||||||
account?.display_name !== undefined || account?.username !== undefined
|
account?.display_name !== undefined || account?.username !== undefined
|
||||||
}
|
}
|
||||||
width={StyleConstants.Font.Size.L * 8}
|
width={StyleConstants.Font.Size.L * 8}
|
||||||
height={StyleConstants.Font.Size.L}
|
height={StyleConstants.Font.LineHeight.L}
|
||||||
style={styles.name}
|
style={styles.name}
|
||||||
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
||||||
>
|
>
|
||||||
|
@@ -7,13 +7,16 @@ export interface Props {
|
|||||||
account: Mastodon.Account
|
account: Mastodon.Account
|
||||||
}
|
}
|
||||||
|
|
||||||
const AccountInformationNotes: React.FC<Props> = ({ account }) => {
|
const AccountInformationNotes = React.memo(
|
||||||
return (
|
({ account }: Props) => {
|
||||||
<View style={styles.note}>
|
return (
|
||||||
<ParseHTML content={account.note!} size={'M'} emojis={account.emojis} />
|
<View style={styles.note}>
|
||||||
</View>
|
<ParseHTML content={account.note!} size={'M'} emojis={account.emojis} />
|
||||||
)
|
</View>
|
||||||
}
|
)
|
||||||
|
},
|
||||||
|
() => true
|
||||||
|
)
|
||||||
|
|
||||||
const styles = StyleSheet.create({
|
const styles = StyleSheet.create({
|
||||||
note: {
|
note: {
|
||||||
|
@@ -40,7 +40,7 @@ const AccountInformationStats = forwardRef<any, Props>(({ account }, ref) => {
|
|||||||
ref={ref1}
|
ref={ref1}
|
||||||
visible={account !== undefined}
|
visible={account !== undefined}
|
||||||
width={StyleConstants.Font.Size.S * 5}
|
width={StyleConstants.Font.Size.S * 5}
|
||||||
height={StyleConstants.Font.Size.S}
|
height={StyleConstants.Font.LineHeight.S}
|
||||||
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
||||||
>
|
>
|
||||||
<Text style={[styles.stat, { color: theme.primary }]}>
|
<Text style={[styles.stat, { color: theme.primary }]}>
|
||||||
@@ -53,7 +53,7 @@ const AccountInformationStats = forwardRef<any, Props>(({ account }, ref) => {
|
|||||||
ref={ref2}
|
ref={ref2}
|
||||||
visible={account !== undefined}
|
visible={account !== undefined}
|
||||||
width={StyleConstants.Font.Size.S * 5}
|
width={StyleConstants.Font.Size.S * 5}
|
||||||
height={StyleConstants.Font.Size.S}
|
height={StyleConstants.Font.LineHeight.S}
|
||||||
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
||||||
>
|
>
|
||||||
<Text
|
<Text
|
||||||
@@ -75,7 +75,7 @@ const AccountInformationStats = forwardRef<any, Props>(({ account }, ref) => {
|
|||||||
ref={ref3}
|
ref={ref3}
|
||||||
visible={account !== undefined}
|
visible={account !== undefined}
|
||||||
width={StyleConstants.Font.Size.S * 5}
|
width={StyleConstants.Font.Size.S * 5}
|
||||||
height={StyleConstants.Font.Size.S}
|
height={StyleConstants.Font.LineHeight.S}
|
||||||
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
shimmerColors={[theme.shimmerDefault, theme.shimmerHighlight, theme.shimmerDefault]}
|
||||||
>
|
>
|
||||||
<Text
|
<Text
|
||||||
|
@@ -1,93 +0,0 @@
|
|||||||
import SegmentedControl from '@react-native-community/segmented-control'
|
|
||||||
import { StyleConstants } from '@root/utils/styles/constants'
|
|
||||||
import { useTheme } from '@root/utils/styles/ThemeManager'
|
|
||||||
import React, { useContext } from 'react'
|
|
||||||
import { useTranslation } from 'react-i18next'
|
|
||||||
import { StyleSheet } from 'react-native'
|
|
||||||
import Animated, {
|
|
||||||
Extrapolate,
|
|
||||||
interpolate,
|
|
||||||
useAnimatedStyle
|
|
||||||
} from 'react-native-reanimated'
|
|
||||||
import { useSafeAreaInsets } from 'react-native-safe-area-context'
|
|
||||||
import AccountContext from './utils/createContext'
|
|
||||||
|
|
||||||
export interface Props {
|
|
||||||
scrollY: Animated.SharedValue<number>
|
|
||||||
}
|
|
||||||
|
|
||||||
const AccountSegmentedControl: React.FC<Props> = ({ scrollY }) => {
|
|
||||||
const { accountState, accountDispatch } = useContext(AccountContext)
|
|
||||||
const { t } = useTranslation('sharedAccount')
|
|
||||||
const { mode, theme } = useTheme()
|
|
||||||
|
|
||||||
const headerHeight = useSafeAreaInsets().top + 44
|
|
||||||
const styleTransform = useAnimatedStyle(() => {
|
|
||||||
return {
|
|
||||||
transform: [
|
|
||||||
{
|
|
||||||
translateY: interpolate(
|
|
||||||
scrollY.value,
|
|
||||||
[
|
|
||||||
0,
|
|
||||||
(accountState.informationLayout?.y || 0) +
|
|
||||||
(accountState.informationLayout?.height || 0) -
|
|
||||||
headerHeight
|
|
||||||
],
|
|
||||||
[
|
|
||||||
0,
|
|
||||||
-(accountState.informationLayout?.y || 0) -
|
|
||||||
(accountState.informationLayout?.height || 0) +
|
|
||||||
headerHeight
|
|
||||||
],
|
|
||||||
Extrapolate.CLAMP
|
|
||||||
)
|
|
||||||
}
|
|
||||||
]
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Animated.View
|
|
||||||
style={[
|
|
||||||
styles.base,
|
|
||||||
styleTransform,
|
|
||||||
{
|
|
||||||
top:
|
|
||||||
(accountState.informationLayout?.y || 0) +
|
|
||||||
(accountState.informationLayout?.height || 0),
|
|
||||||
borderTopColor: theme.border,
|
|
||||||
backgroundColor: theme.background
|
|
||||||
}
|
|
||||||
]}
|
|
||||||
>
|
|
||||||
<SegmentedControl
|
|
||||||
values={[
|
|
||||||
t('content.segments.left'),
|
|
||||||
t('content.segments.middle'),
|
|
||||||
t('content.segments.right')
|
|
||||||
]}
|
|
||||||
selectedIndex={accountState.segmentedIndex}
|
|
||||||
onChange={({ nativeEvent }) =>
|
|
||||||
accountDispatch({
|
|
||||||
type: 'segmentedIndex',
|
|
||||||
payload: nativeEvent.selectedSegmentIndex
|
|
||||||
})
|
|
||||||
}
|
|
||||||
appearance={mode}
|
|
||||||
/>
|
|
||||||
</Animated.View>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
const styles = StyleSheet.create({
|
|
||||||
base: {
|
|
||||||
...StyleSheet.absoluteFillObject,
|
|
||||||
zIndex: 99,
|
|
||||||
borderTopWidth: StyleSheet.hairlineWidth,
|
|
||||||
padding: StyleConstants.Spacing.Global.PagePadding,
|
|
||||||
height: 33 + StyleConstants.Spacing.Global.PagePadding * 2
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
export default React.memo(AccountSegmentedControl, () => true)
|
|
@@ -1,70 +0,0 @@
|
|||||||
import Timeline from '@components/Timelines/Timeline'
|
|
||||||
import { useBottomTabBarHeight } from '@react-navigation/bottom-tabs'
|
|
||||||
import { StyleConstants } from '@utils/styles/constants'
|
|
||||||
import React, { useCallback, useContext } from 'react'
|
|
||||||
import { Dimensions, StyleSheet } from 'react-native'
|
|
||||||
import { useSafeAreaInsets } from 'react-native-safe-area-context'
|
|
||||||
import { TabView } from 'react-native-tab-view'
|
|
||||||
import ViewPagerAdapter from 'react-native-tab-view-viewpager-adapter'
|
|
||||||
import AccountContext from './utils/createContext'
|
|
||||||
|
|
||||||
export interface Props {
|
|
||||||
id: Mastodon.Account['id']
|
|
||||||
}
|
|
||||||
|
|
||||||
const AccountToots: React.FC<Props> = ({ id }) => {
|
|
||||||
const { accountState, accountDispatch } = useContext(AccountContext)
|
|
||||||
const headerHeight = useSafeAreaInsets().top + 44
|
|
||||||
const footerHeight = useSafeAreaInsets().bottom + useBottomTabBarHeight()
|
|
||||||
|
|
||||||
const routes: { key: App.Pages }[] = [
|
|
||||||
{ key: 'Account_Default' },
|
|
||||||
{ key: 'Account_All' },
|
|
||||||
{ key: 'Account_Media' }
|
|
||||||
]
|
|
||||||
|
|
||||||
const renderScene = ({
|
|
||||||
route
|
|
||||||
}: {
|
|
||||||
route: {
|
|
||||||
key: App.Pages
|
|
||||||
}
|
|
||||||
}) => {
|
|
||||||
return <Timeline page={route.key} account={id} disableRefresh />
|
|
||||||
}
|
|
||||||
|
|
||||||
const renderPager = useCallback(props => <ViewPagerAdapter {...props} />, [])
|
|
||||||
|
|
||||||
return (
|
|
||||||
<TabView
|
|
||||||
lazy
|
|
||||||
swipeEnabled
|
|
||||||
renderPager={renderPager}
|
|
||||||
renderScene={renderScene}
|
|
||||||
renderTabBar={() => null}
|
|
||||||
initialLayout={{ width: Dimensions.get('window').width }}
|
|
||||||
navigationState={{ index: accountState.segmentedIndex, routes }}
|
|
||||||
onIndexChange={index =>
|
|
||||||
accountDispatch({ type: 'segmentedIndex', payload: index })
|
|
||||||
}
|
|
||||||
style={[
|
|
||||||
styles.base,
|
|
||||||
{
|
|
||||||
height:
|
|
||||||
Dimensions.get('window').height -
|
|
||||||
headerHeight -
|
|
||||||
footerHeight -
|
|
||||||
(33 + StyleConstants.Spacing.Global.PagePadding * 2)
|
|
||||||
}
|
|
||||||
]}
|
|
||||||
/>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
const styles = StyleSheet.create({
|
|
||||||
base: {
|
|
||||||
marginTop: StyleConstants.Spacing.Global.PagePadding + 33
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
export default React.memo(AccountToots, () => true)
|
|
@@ -1,9 +1,9 @@
|
|||||||
import { AccountState } from "./types"
|
import { AccountState } from './types'
|
||||||
|
|
||||||
const accountInitialState: AccountState = {
|
const accountInitialState: AccountState = {
|
||||||
headerRatio: 0.4,
|
headerRatio: 1 / 3,
|
||||||
informationLayout: { height: 0, y: 100 },
|
informationLayout: { height: 0, y: 100 },
|
||||||
segmentedIndex: 0
|
segmentedIndex: 0
|
||||||
}
|
}
|
||||||
|
|
||||||
export default accountInitialState
|
export default accountInitialState
|
||||||
|
Reference in New Issue
Block a user