Create ProfileBadges component
This commit is contained in:
@@ -12,14 +12,12 @@ import {useProfilesQuery} from '#/state/queries/profile'
|
|||||||
import {type SessionAccount, useSession} from '#/state/session'
|
import {type SessionAccount, useSession} from '#/state/session'
|
||||||
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {atoms as a, useTheme} from '#/alf'
|
import {atoms as a, useTheme} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {Button} from '#/components/Button'
|
import {Button} from '#/components/Button'
|
||||||
import {CheckThick_Stroke2_Corner0_Rounded as CheckIcon} from '#/components/icons/Check'
|
import {CheckThick_Stroke2_Corner0_Rounded as CheckIcon} from '#/components/icons/Check'
|
||||||
import {ChevronRight_Stroke2_Corner0_Rounded as ChevronIcon} from '#/components/icons/Chevron'
|
import {ChevronRight_Stroke2_Corner0_Rounded as ChevronIcon} from '#/components/icons/Chevron'
|
||||||
import {PlusLarge_Stroke2_Corner0_Rounded as PlusIcon} from '#/components/icons/Plus'
|
import {PlusLarge_Stroke2_Corner0_Rounded as PlusIcon} from '#/components/icons/Plus'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
|
|
||||||
export function AccountList({
|
export function AccountList({
|
||||||
@@ -53,18 +51,26 @@ export function AccountList({
|
|||||||
a.border,
|
a.border,
|
||||||
t.atoms.border_contrast_low,
|
t.atoms.border_contrast_low,
|
||||||
]}>
|
]}>
|
||||||
{accounts.map(account => (
|
{accounts
|
||||||
<React.Fragment key={account.did}>
|
.map(account => ({
|
||||||
<AccountItem
|
account,
|
||||||
profile={profiles?.profiles.find(p => p.did === account.did)}
|
profile: profiles?.profiles.find(p => p.did === account.did),
|
||||||
account={account}
|
}))
|
||||||
onSelect={onSelectAccount}
|
.filter(item => {
|
||||||
isCurrentAccount={account.did === currentAccount?.did}
|
return !!item.profile
|
||||||
isPendingAccount={account.did === pendingDid}
|
})
|
||||||
/>
|
.map(({account, profile}) => (
|
||||||
<View style={[a.border_b, t.atoms.border_contrast_low]} />
|
<React.Fragment key={account.did}>
|
||||||
</React.Fragment>
|
<AccountItem
|
||||||
))}
|
profile={profile!}
|
||||||
|
account={account}
|
||||||
|
onSelect={onSelectAccount}
|
||||||
|
isCurrentAccount={account.did === currentAccount?.did}
|
||||||
|
isPendingAccount={account.did === pendingDid}
|
||||||
|
/>
|
||||||
|
<View style={[a.border_b, t.atoms.border_contrast_low]} />
|
||||||
|
</React.Fragment>
|
||||||
|
))}
|
||||||
<Button
|
<Button
|
||||||
testID="chooseAddAccountBtn"
|
testID="chooseAddAccountBtn"
|
||||||
style={[a.flex_1]}
|
style={[a.flex_1]}
|
||||||
@@ -109,7 +115,7 @@ function AccountItem({
|
|||||||
isCurrentAccount,
|
isCurrentAccount,
|
||||||
isPendingAccount,
|
isPendingAccount,
|
||||||
}: {
|
}: {
|
||||||
profile?: AppBskyActorDefs.ProfileViewDetailed
|
profile: AppBskyActorDefs.ProfileViewDetailed
|
||||||
account: SessionAccount
|
account: SessionAccount
|
||||||
onSelect: (account: SessionAccount) => void
|
onSelect: (account: SessionAccount) => void
|
||||||
isCurrentAccount: boolean
|
isCurrentAccount: boolean
|
||||||
@@ -117,7 +123,6 @@ function AccountItem({
|
|||||||
}) {
|
}) {
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
const {_} = useLingui()
|
const {_} = useLingui()
|
||||||
const verification = useSimpleVerificationState({profile})
|
|
||||||
const {isActive: live} = useActorStatus(profile)
|
const {isActive: live} = useActorStatus(profile)
|
||||||
|
|
||||||
const onPress = useCallback(() => {
|
const onPress = useCallback(() => {
|
||||||
@@ -165,19 +170,11 @@ function AccountItem({
|
|||||||
profile?.displayName || profile?.handle || account.handle,
|
profile?.displayName || profile?.handle || account.handle,
|
||||||
)}
|
)}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges
|
||||||
<View>
|
profile={profile}
|
||||||
<VerificationCheck
|
size="sm"
|
||||||
width={12}
|
style={[{marginTop: -2}]}
|
||||||
verifier={verification.role === 'verifier'}
|
/>
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
{profile && (
|
|
||||||
<View style={{marginTop: -2}}>
|
|
||||||
<BotBadge profile={profile} />
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
</View>
|
</View>
|
||||||
<Text
|
<Text
|
||||||
style={[
|
style={[
|
||||||
|
|||||||
@@ -3,23 +3,27 @@ import {msg} from '@lingui/core/macro'
|
|||||||
import {useLingui} from '@lingui/react'
|
import {useLingui} from '@lingui/react'
|
||||||
import {Trans} from '@lingui/react/macro'
|
import {Trans} from '@lingui/react/macro'
|
||||||
|
|
||||||
|
import {useSession} from '#/state/session'
|
||||||
import {atoms as a, useTheme, web} from '#/alf'
|
import {atoms as a, useTheme, web} from '#/alf'
|
||||||
import {Button, ButtonText} from '#/components/Button'
|
import {Button, ButtonText} from '#/components/Button'
|
||||||
import * as Dialog from '#/components/Dialog'
|
import * as Dialog from '#/components/Dialog'
|
||||||
import {Robot_Filled_Corner2_Rounded as RobotIcon} from '#/components/icons/Robot'
|
import {Robot_Filled_Corner2_Rounded as RobotIcon} from '#/components/icons/Robot'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {navigate} from '#/Navigation'
|
import {navigate} from '#/Navigation'
|
||||||
|
import type * as bsky from '#/types/bsky'
|
||||||
|
|
||||||
export function BotAccountAlert({
|
export function BotAccountAlert({
|
||||||
control,
|
control,
|
||||||
isSelf,
|
profile,
|
||||||
}: {
|
}: {
|
||||||
control: Dialog.DialogControlProps
|
control: Dialog.DialogControlProps
|
||||||
isSelf: boolean
|
profile: bsky.profile.AnyProfileView
|
||||||
}) {
|
}) {
|
||||||
const {_} = useLingui()
|
const {_} = useLingui()
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
|
const {currentAccount} = useSession()
|
||||||
|
|
||||||
|
const isSelf = profile.did === currentAccount?.did
|
||||||
const description = isSelf
|
const description = isSelf
|
||||||
? 'You have marked this account as automated. You can remove it at any time from your account settings.'
|
? 'You have marked this account as automated. You can remove it at any time from your account settings.'
|
||||||
: 'This account has been marked as automated by its owner'
|
: 'This account has been marked as automated by its owner'
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
import {View} from 'react-native'
|
import {View} from 'react-native'
|
||||||
import {type ComAtprotoLabelDefs} from '@atproto/api'
|
|
||||||
import {msg} from '@lingui/core/macro'
|
import {msg} from '@lingui/core/macro'
|
||||||
import {useLingui} from '@lingui/react'
|
import {useLingui} from '@lingui/react'
|
||||||
|
|
||||||
@@ -8,17 +7,19 @@ import {atoms as a, useBreakpoints, useTheme} from '#/alf'
|
|||||||
import {BotAccountAlert} from '#/components/BotAccountAlert'
|
import {BotAccountAlert} from '#/components/BotAccountAlert'
|
||||||
import {Button} from '#/components/Button'
|
import {Button} from '#/components/Button'
|
||||||
import {useDialogControl} from '#/components/Dialog'
|
import {useDialogControl} from '#/components/Dialog'
|
||||||
|
import {type Props} from '#/components/icons/common'
|
||||||
import {Robot_Filled_Corner2_Rounded as RobotIcon} from '#/components/icons/Robot'
|
import {Robot_Filled_Corner2_Rounded as RobotIcon} from '#/components/icons/Robot'
|
||||||
import {useAnalytics} from '#/analytics'
|
import {useAnalytics} from '#/analytics'
|
||||||
|
import type * as bsky from '#/types/bsky'
|
||||||
|
|
||||||
export function BotBadge({
|
export function BotBadge({
|
||||||
profile,
|
profile,
|
||||||
alwaysShow = false,
|
alwaysShow = false,
|
||||||
size = 14,
|
size,
|
||||||
}: {
|
}: {
|
||||||
profile: {did: string; labels?: ComAtprotoLabelDefs.Label[]}
|
profile: bsky.profile.AnyProfileView
|
||||||
alwaysShow?: boolean
|
alwaysShow?: boolean
|
||||||
size?: number
|
size: Props['size']
|
||||||
}) {
|
}) {
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
|
|
||||||
@@ -28,7 +29,7 @@ export function BotBadge({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<View>
|
<View>
|
||||||
<RobotIcon width={size} fill={t.atoms.text_contrast_medium.color} />
|
<RobotIcon size={size} fill={t.atoms.text_contrast_medium.color} />
|
||||||
</View>
|
</View>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@@ -36,11 +37,9 @@ export function BotBadge({
|
|||||||
export function BotBadgeButton({
|
export function BotBadgeButton({
|
||||||
profile,
|
profile,
|
||||||
size,
|
size,
|
||||||
isSelf = false,
|
|
||||||
}: {
|
}: {
|
||||||
profile: {did: string; labels?: ComAtprotoLabelDefs.Label[]}
|
profile: bsky.profile.AnyProfileView
|
||||||
size: 'lg' | 'md' | 'sm'
|
size: 'lg' | 'md' | 'sm'
|
||||||
isSelf?: boolean
|
|
||||||
}) {
|
}) {
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
const ax = useAnalytics()
|
const ax = useAnalytics()
|
||||||
@@ -52,6 +51,7 @@ export function BotBadgeButton({
|
|||||||
return null
|
return null
|
||||||
}
|
}
|
||||||
|
|
||||||
|
console.log({size})
|
||||||
let dimensions = 12
|
let dimensions = 12
|
||||||
if (size === 'lg') {
|
if (size === 'lg') {
|
||||||
dimensions = gtPhone ? 20 : 18
|
dimensions = gtPhone ? 20 : 18
|
||||||
@@ -88,7 +88,7 @@ export function BotBadgeButton({
|
|||||||
</View>
|
</View>
|
||||||
)}
|
)}
|
||||||
</Button>
|
</Button>
|
||||||
<BotAccountAlert control={control} isSelf={isSelf} />
|
<BotAccountAlert control={control} profile={profile} />
|
||||||
</>
|
</>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -15,12 +15,10 @@ import {useListConvosQuery} from '#/state/queries/messages/list-conversations'
|
|||||||
import {useSession} from '#/state/session'
|
import {useSession} from '#/state/session'
|
||||||
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {atoms as a, tokens, useTheme} from '#/alf'
|
import {atoms as a, tokens, useTheme} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {Button} from '#/components/Button'
|
import {Button} from '#/components/Button'
|
||||||
import {useDialogContext} from '#/components/Dialog'
|
import {useDialogContext} from '#/components/Dialog'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {useAnalytics} from '#/analytics'
|
import {useAnalytics} from '#/analytics'
|
||||||
import type * as bsky from '#/types/bsky'
|
import type * as bsky from '#/types/bsky'
|
||||||
|
|
||||||
@@ -112,7 +110,6 @@ function RecentChatItem({
|
|||||||
profile.displayName || sanitizeHandle(profile.handle),
|
profile.displayName || sanitizeHandle(profile.handle),
|
||||||
moderation.ui('displayName'),
|
moderation.ui('displayName'),
|
||||||
)
|
)
|
||||||
const verification = useSimpleVerificationState({profile})
|
|
||||||
|
|
||||||
if (isBlockedOrBlocking(profile) || isMuted(profile)) {
|
if (isBlockedOrBlocking(profile) || isMuted(profile)) {
|
||||||
return null
|
return null
|
||||||
@@ -142,15 +139,7 @@ function RecentChatItem({
|
|||||||
numberOfLines={1}>
|
numberOfLines={1}>
|
||||||
{name}
|
{name}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges profile={profile} size="sm" style={[a.pl_xs]} />
|
||||||
<View style={[a.pl_2xs]}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={10}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={profile} />
|
|
||||||
</View>
|
</View>
|
||||||
</Button>
|
</Button>
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -0,0 +1,48 @@
|
|||||||
|
import {View} from 'react-native'
|
||||||
|
|
||||||
|
import {isBotAccount} from '#/lib/bots'
|
||||||
|
import {useProfileShadow} from '#/state/cache/profile-shadow'
|
||||||
|
import {atoms as a, type ViewStyleProp} from '#/alf'
|
||||||
|
import {BotBadge, BotBadgeButton} from '#/components/BotBadge'
|
||||||
|
import {useSimpleVerificationState} from '#/components/verification'
|
||||||
|
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
||||||
|
import {VerificationCheckButton} from '#/components/verification/VerificationCheckButton'
|
||||||
|
import type * as bsky from '#/types/bsky'
|
||||||
|
|
||||||
|
export function ProfileBadges({
|
||||||
|
profile,
|
||||||
|
interactive = false,
|
||||||
|
size,
|
||||||
|
style,
|
||||||
|
}: ViewStyleProp & {
|
||||||
|
profile: bsky.profile.AnyProfileView
|
||||||
|
interactive?: boolean
|
||||||
|
size: 'lg' | 'md' | 'sm'
|
||||||
|
}) {
|
||||||
|
const shadowed = useProfileShadow(profile)
|
||||||
|
const verification = useSimpleVerificationState({profile})
|
||||||
|
|
||||||
|
// if nothing to show, don't render the container at all
|
||||||
|
if (!verification.showBadge && !isBotAccount(shadowed)) return null
|
||||||
|
|
||||||
|
return (
|
||||||
|
<View style={[a.flex_row, a.align_center, a.gap_xs, style]}>
|
||||||
|
{interactive ? (
|
||||||
|
<>
|
||||||
|
<VerificationCheckButton profile={shadowed} size={size} />
|
||||||
|
<BotBadgeButton profile={shadowed} size={size} />
|
||||||
|
</>
|
||||||
|
) : (
|
||||||
|
<>
|
||||||
|
{verification.showBadge && (
|
||||||
|
<VerificationCheck
|
||||||
|
verifier={verification.role === 'verifier'}
|
||||||
|
size={size}
|
||||||
|
/>
|
||||||
|
)}
|
||||||
|
<BotBadge profile={shadowed} size={size} />
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</View>
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -31,7 +31,6 @@ import {
|
|||||||
useTheme,
|
useTheme,
|
||||||
type ViewStyleProp,
|
type ViewStyleProp,
|
||||||
} from '#/alf'
|
} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {
|
import {
|
||||||
Button,
|
Button,
|
||||||
ButtonIcon,
|
ButtonIcon,
|
||||||
@@ -42,10 +41,9 @@ import {Check_Stroke2_Corner0_Rounded as Check} from '#/components/icons/Check'
|
|||||||
import {PlusLarge_Stroke2_Corner0_Rounded as Plus} from '#/components/icons/Plus'
|
import {PlusLarge_Stroke2_Corner0_Rounded as Plus} from '#/components/icons/Plus'
|
||||||
import {Link as InternalLink, type LinkProps} from '#/components/Link'
|
import {Link as InternalLink, type LinkProps} from '#/components/Link'
|
||||||
import * as Pills from '#/components/Pills'
|
import * as Pills from '#/components/Pills'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {RichText} from '#/components/RichText'
|
import {RichText} from '#/components/RichText'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {type Metrics} from '#/analytics'
|
import {type Metrics} from '#/analytics'
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
import type * as bsky from '#/types/bsky'
|
import type * as bsky from '#/types/bsky'
|
||||||
@@ -243,7 +241,6 @@ function InlineNameAndHandle({
|
|||||||
moderationOpts: ModerationOpts
|
moderationOpts: ModerationOpts
|
||||||
}) {
|
}) {
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
const verification = useSimpleVerificationState({profile})
|
|
||||||
const moderation = moderateProfile(profile, moderationOpts)
|
const moderation = moderateProfile(profile, moderationOpts)
|
||||||
const name = sanitizeDisplayName(
|
const name = sanitizeDisplayName(
|
||||||
profile.displayName || sanitizeHandle(profile.handle),
|
profile.displayName || sanitizeHandle(profile.handle),
|
||||||
@@ -263,27 +260,15 @@ function InlineNameAndHandle({
|
|||||||
numberOfLines={1}>
|
numberOfLines={1}>
|
||||||
{forceLTR(name)}
|
{forceLTR(name)}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges
|
||||||
<View
|
profile={profile}
|
||||||
style={[
|
size="sm"
|
||||||
a.pl_2xs,
|
|
||||||
a.self_center,
|
|
||||||
{marginTop: platform({default: 0, android: -1})},
|
|
||||||
]}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={platform({android: 13, default: 12})}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<View
|
|
||||||
style={[
|
style={[
|
||||||
a.pl_2xs,
|
a.pl_2xs,
|
||||||
a.self_center,
|
a.self_center,
|
||||||
{marginTop: platform({default: 0, android: -1})},
|
{marginTop: platform({default: 0, android: -1})},
|
||||||
]}>
|
]}
|
||||||
<BotBadge profile={profile} />
|
/>
|
||||||
</View>
|
|
||||||
<Text
|
<Text
|
||||||
emoji
|
emoji
|
||||||
style={[
|
style={[
|
||||||
@@ -314,7 +299,6 @@ export function Name({
|
|||||||
profile.displayName || sanitizeHandle(profile.handle),
|
profile.displayName || sanitizeHandle(profile.handle),
|
||||||
moderation.ui('displayName'),
|
moderation.ui('displayName'),
|
||||||
)
|
)
|
||||||
const verification = useSimpleVerificationState({profile})
|
|
||||||
return (
|
return (
|
||||||
<View style={[a.flex_row, a.align_center, a.max_w_full, style]}>
|
<View style={[a.flex_row, a.align_center, a.max_w_full, style]}>
|
||||||
<Text
|
<Text
|
||||||
@@ -330,17 +314,7 @@ export function Name({
|
|||||||
numberOfLines={1}>
|
numberOfLines={1}>
|
||||||
{name}
|
{name}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges profile={profile} size="sm" style={[a.pl_xs]} />
|
||||||
<View style={[a.pl_xs]}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={14}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<View style={[a.pl_xs]}>
|
|
||||||
<BotBadge profile={profile} />
|
|
||||||
</View>
|
|
||||||
</View>
|
</View>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,7 +23,6 @@ import {formatCount} from '#/view/com/util/numeric/format'
|
|||||||
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {ProfileHeaderHandle} from '#/screens/Profile/Header/Handle'
|
import {ProfileHeaderHandle} from '#/screens/Profile/Header/Handle'
|
||||||
import {atoms as a, useTheme} from '#/alf'
|
import {atoms as a, useTheme} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
||||||
import {useFollowMethods} from '#/components/hooks/useFollowMethods'
|
import {useFollowMethods} from '#/components/hooks/useFollowMethods'
|
||||||
import {useRichText} from '#/components/hooks/useRichText'
|
import {useRichText} from '#/components/hooks/useRichText'
|
||||||
@@ -37,10 +36,9 @@ import {InlineLinkText, Link} from '#/components/Link'
|
|||||||
import {Loader} from '#/components/Loader'
|
import {Loader} from '#/components/Loader'
|
||||||
import * as Pills from '#/components/Pills'
|
import * as Pills from '#/components/Pills'
|
||||||
import {Portal} from '#/components/Portal'
|
import {Portal} from '#/components/Portal'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {RichText} from '#/components/RichText'
|
import {RichText} from '#/components/RichText'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {IS_WEB_TOUCH_DEVICE} from '#/env'
|
import {IS_WEB_TOUCH_DEVICE} from '#/env'
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
import {LiveStatus} from '#/features/liveNow/components/LiveStatusDialog'
|
import {LiveStatus} from '#/features/liveNow/components/LiveStatusDialog'
|
||||||
@@ -460,7 +458,6 @@ function Inner({
|
|||||||
[currentAccount, profile],
|
[currentAccount, profile],
|
||||||
)
|
)
|
||||||
const isLabeler = profile.associated?.labeler
|
const isLabeler = profile.associated?.labeler
|
||||||
const verification = useSimpleVerificationState({profile})
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View>
|
<View>
|
||||||
@@ -528,21 +525,16 @@ function Inner({
|
|||||||
moderation.ui('displayName'),
|
moderation.ui('displayName'),
|
||||||
)}
|
)}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges
|
||||||
<View
|
profile={profile}
|
||||||
style={[
|
size="md"
|
||||||
a.pl_xs,
|
style={[
|
||||||
{
|
a.pl_xs,
|
||||||
marginTop: -2,
|
{
|
||||||
},
|
marginTop: -2,
|
||||||
]}>
|
},
|
||||||
<VerificationCheck
|
]}
|
||||||
width={16}
|
/>
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={profile} size={16} />
|
|
||||||
</View>
|
</View>
|
||||||
|
|
||||||
<ProfileHeaderHandle profile={profileShadow} disableTaps />
|
<ProfileHeaderHandle profile={profileShadow} disableTaps />
|
||||||
|
|||||||
@@ -15,15 +15,13 @@ import {isConvoActive, useConvo} from '#/state/messages/convo'
|
|||||||
import {type ConvoItem} from '#/state/messages/convo/types'
|
import {type ConvoItem} from '#/state/messages/convo/types'
|
||||||
import {PreviewableUserAvatar} from '#/view/com/util/UserAvatar'
|
import {PreviewableUserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {atoms as a, useTheme, web} from '#/alf'
|
import {atoms as a, useTheme, web} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {ConvoMenu} from '#/components/dms/ConvoMenu'
|
import {ConvoMenu} from '#/components/dms/ConvoMenu'
|
||||||
import {Bell2Off_Filled_Corner0_Rounded as BellStroke} from '#/components/icons/Bell2'
|
import {Bell2Off_Filled_Corner0_Rounded as BellStroke} from '#/components/icons/Bell2'
|
||||||
import * as Layout from '#/components/Layout'
|
import * as Layout from '#/components/Layout'
|
||||||
import {Link} from '#/components/Link'
|
import {Link} from '#/components/Link'
|
||||||
import {PostAlerts} from '#/components/moderation/PostAlerts'
|
import {PostAlerts} from '#/components/moderation/PostAlerts'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {IS_WEB} from '#/env'
|
import {IS_WEB} from '#/env'
|
||||||
|
|
||||||
const PFP_SIZE = IS_WEB ? 40 : Layout.HEADER_SLOT_SIZE
|
const PFP_SIZE = IS_WEB ? 40 : Layout.HEADER_SLOT_SIZE
|
||||||
@@ -113,9 +111,6 @@ function HeaderReady({
|
|||||||
const {_} = useLingui()
|
const {_} = useLingui()
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
const convoState = useConvo()
|
const convoState = useConvo()
|
||||||
const verification = useSimpleVerificationState({
|
|
||||||
profile,
|
|
||||||
})
|
|
||||||
|
|
||||||
const isDeletedAccount = profile?.handle === 'missing.invalid'
|
const isDeletedAccount = profile?.handle === 'missing.invalid'
|
||||||
const displayName = isDeletedAccount
|
const displayName = isDeletedAccount
|
||||||
@@ -162,15 +157,7 @@ function HeaderReady({
|
|||||||
numberOfLines={1}>
|
numberOfLines={1}>
|
||||||
{displayName}
|
{displayName}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges profile={profile} size="sm" style={[a.pl_xs]} />
|
||||||
<View style={[a.pl_xs]}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={14}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={profile} />
|
|
||||||
</View>
|
</View>
|
||||||
{!isDeletedAccount && (
|
{!isDeletedAccount && (
|
||||||
<Text
|
<Text
|
||||||
|
|||||||
@@ -31,7 +31,6 @@ import {TimeElapsed} from '#/view/com/util/TimeElapsed'
|
|||||||
import {PreviewableUserAvatar} from '#/view/com/util/UserAvatar'
|
import {PreviewableUserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {atoms as a, useBreakpoints, useTheme, web} from '#/alf'
|
import {atoms as a, useBreakpoints, useTheme, web} from '#/alf'
|
||||||
import * as tokens from '#/alf/tokens'
|
import * as tokens from '#/alf/tokens'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {useDialogControl} from '#/components/Dialog'
|
import {useDialogControl} from '#/components/Dialog'
|
||||||
import {ConvoMenu} from '#/components/dms/ConvoMenu'
|
import {ConvoMenu} from '#/components/dms/ConvoMenu'
|
||||||
import {LeaveConvoPrompt} from '#/components/dms/LeaveConvoPrompt'
|
import {LeaveConvoPrompt} from '#/components/dms/LeaveConvoPrompt'
|
||||||
@@ -42,9 +41,8 @@ import {Link} from '#/components/Link'
|
|||||||
import {useMenuControl} from '#/components/Menu'
|
import {useMenuControl} from '#/components/Menu'
|
||||||
import {PostAlerts} from '#/components/moderation/PostAlerts'
|
import {PostAlerts} from '#/components/moderation/PostAlerts'
|
||||||
import {createPortalGroup} from '#/components/Portal'
|
import {createPortalGroup} from '#/components/Portal'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {useAnalytics} from '#/analytics'
|
import {useAnalytics} from '#/analytics'
|
||||||
import {IS_NATIVE} from '#/env'
|
import {IS_NATIVE} from '#/env'
|
||||||
import type * as bsky from '#/types/bsky'
|
import type * as bsky from '#/types/bsky'
|
||||||
@@ -113,9 +111,6 @@ function ChatListItemReady({
|
|||||||
const playHaptic = useHaptics()
|
const playHaptic = useHaptics()
|
||||||
const queryClient = useQueryClient()
|
const queryClient = useQueryClient()
|
||||||
const isUnread = convo.unreadCount > 0
|
const isUnread = convo.unreadCount > 0
|
||||||
const verification = useSimpleVerificationState({
|
|
||||||
profile,
|
|
||||||
})
|
|
||||||
|
|
||||||
const blockInfo = useMemo(() => {
|
const blockInfo = useMemo(() => {
|
||||||
const modui = moderation.ui('profileView')
|
const modui = moderation.ui('profileView')
|
||||||
@@ -415,15 +410,11 @@ function ChatListItemReady({
|
|||||||
{displayName}
|
{displayName}
|
||||||
</Text>
|
</Text>
|
||||||
</View>
|
</View>
|
||||||
{verification.showBadge && (
|
<ProfileBadges
|
||||||
<View style={[a.pl_xs, a.self_center]}>
|
profile={profile}
|
||||||
<VerificationCheck
|
size="sm"
|
||||||
width={14}
|
style={[a.pl_xs, a.self_center]}
|
||||||
verifier={verification.role === 'verifier'}
|
/>
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={profile} />
|
|
||||||
{lastMessageSentAt && (
|
{lastMessageSentAt && (
|
||||||
<View style={[a.pl_xs]}>
|
<View style={[a.pl_xs]}>
|
||||||
<TimeElapsed timestamp={lastMessageSentAt}>
|
<TimeElapsed timestamp={lastMessageSentAt}>
|
||||||
|
|||||||
@@ -34,7 +34,6 @@ import {
|
|||||||
REPLY_LINE_WIDTH,
|
REPLY_LINE_WIDTH,
|
||||||
} from '#/screens/PostThread/const'
|
} from '#/screens/PostThread/const'
|
||||||
import {atoms as a, useTheme} from '#/alf'
|
import {atoms as a, useTheme} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {Button} from '#/components/Button'
|
import {Button} from '#/components/Button'
|
||||||
import {DebugFieldDisplay} from '#/components/DebugFieldDisplay'
|
import {DebugFieldDisplay} from '#/components/DebugFieldDisplay'
|
||||||
import {CalendarClock_Stroke2_Corner0_Rounded as CalendarClockIcon} from '#/components/icons/CalendarClock'
|
import {CalendarClock_Stroke2_Corner0_Rounded as CalendarClockIcon} from '#/components/icons/CalendarClock'
|
||||||
@@ -48,12 +47,12 @@ import {Embed, PostEmbedViewContext} from '#/components/Post/Embed'
|
|||||||
import {TranslatedPost} from '#/components/Post/Translated'
|
import {TranslatedPost} from '#/components/Post/Translated'
|
||||||
import {PostControls, PostControlsSkeleton} from '#/components/PostControls'
|
import {PostControls, PostControlsSkeleton} from '#/components/PostControls'
|
||||||
import {useFormatPostStatCount} from '#/components/PostControls/util'
|
import {useFormatPostStatCount} from '#/components/PostControls/util'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {ProfileHoverCard} from '#/components/ProfileHoverCard'
|
import {ProfileHoverCard} from '#/components/ProfileHoverCard'
|
||||||
import * as Prompt from '#/components/Prompt'
|
import * as Prompt from '#/components/Prompt'
|
||||||
import {RichText} from '#/components/RichText'
|
import {RichText} from '#/components/RichText'
|
||||||
import * as Skele from '#/components/Skeleton'
|
import * as Skele from '#/components/Skeleton'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {VerificationCheckButton} from '#/components/verification/VerificationCheckButton'
|
|
||||||
import {WhoCanReply} from '#/components/WhoCanReply'
|
import {WhoCanReply} from '#/components/WhoCanReply'
|
||||||
import {useAnalytics} from '#/analytics'
|
import {useAnalytics} from '#/analytics'
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
@@ -363,9 +362,12 @@ const ThreadItemAnchorInner = memo(function ThreadItemAnchorInner({
|
|||||||
</Text>
|
</Text>
|
||||||
|
|
||||||
<View style={[a.pl_xs]}>
|
<View style={[a.pl_xs]}>
|
||||||
<VerificationCheckButton profile={authorShadow} size="md" />
|
<ProfileBadges
|
||||||
|
profile={authorShadow}
|
||||||
|
size="md"
|
||||||
|
interactive
|
||||||
|
/>
|
||||||
</View>
|
</View>
|
||||||
<BotBadge profile={authorShadow} size={14} />
|
|
||||||
</View>
|
</View>
|
||||||
<Text
|
<Text
|
||||||
style={[
|
style={[
|
||||||
|
|||||||
@@ -24,7 +24,6 @@ import {useRequireAuth, useSession} from '#/state/session'
|
|||||||
import {ProfileMenu} from '#/view/com/profile/ProfileMenu'
|
import {ProfileMenu} from '#/view/com/profile/ProfileMenu'
|
||||||
import {atoms as a, platform, useBreakpoints, useTheme} from '#/alf'
|
import {atoms as a, platform, useBreakpoints, useTheme} from '#/alf'
|
||||||
import {SubscribeProfileButton} from '#/components/activity-notifications/SubscribeProfileButton'
|
import {SubscribeProfileButton} from '#/components/activity-notifications/SubscribeProfileButton'
|
||||||
import {BotBadgeButton} from '#/components/BotBadge'
|
|
||||||
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
||||||
import {DebugFieldDisplay} from '#/components/DebugFieldDisplay'
|
import {DebugFieldDisplay} from '#/components/DebugFieldDisplay'
|
||||||
import {useDialogControl} from '#/components/Dialog'
|
import {useDialogControl} from '#/components/Dialog'
|
||||||
@@ -34,11 +33,11 @@ import {
|
|||||||
KnownFollowers,
|
KnownFollowers,
|
||||||
shouldShowKnownFollowers,
|
shouldShowKnownFollowers,
|
||||||
} from '#/components/KnownFollowers'
|
} from '#/components/KnownFollowers'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import * as Prompt from '#/components/Prompt'
|
import * as Prompt from '#/components/Prompt'
|
||||||
import {RichText} from '#/components/RichText'
|
import {RichText} from '#/components/RichText'
|
||||||
import * as Toast from '#/components/Toast'
|
import * as Toast from '#/components/Toast'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {VerificationCheckButton} from '#/components/verification/VerificationCheckButton'
|
|
||||||
import {IS_IOS} from '#/env'
|
import {IS_IOS} from '#/env'
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
import {GermButton} from '../components/GermButton'
|
import {GermButton} from '../components/GermButton'
|
||||||
@@ -144,10 +143,7 @@ let ProfileHeaderStandard = ({
|
|||||||
moderation.ui('displayName'),
|
moderation.ui('displayName'),
|
||||||
)}
|
)}
|
||||||
<View style={[a.pl_xs, {marginTop: platform({ios: 2})}]}>
|
<View style={[a.pl_xs, {marginTop: platform({ios: 2})}]}>
|
||||||
<VerificationCheckButton profile={profile} size="lg" />
|
<ProfileBadges profile={profile} size="lg" interactive />
|
||||||
</View>
|
|
||||||
<View style={[a.pl_xs, {marginTop: platform({ios: 2})}]}>
|
|
||||||
<BotBadgeButton profile={profile} size="lg" isSelf={isMe} />
|
|
||||||
</View>
|
</View>
|
||||||
</Text>
|
</Text>
|
||||||
</View>
|
</View>
|
||||||
|
|||||||
@@ -10,14 +10,12 @@ import {useModerationOpts} from '#/state/preferences/moderation-opts'
|
|||||||
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {BlockDrawerGesture} from '#/view/shell/BlockDrawerGesture'
|
import {BlockDrawerGesture} from '#/view/shell/BlockDrawerGesture'
|
||||||
import {atoms as a} from '#/alf'
|
import {atoms as a} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {Button, ButtonIcon} from '#/components/Button'
|
import {Button, ButtonIcon} from '#/components/Button'
|
||||||
import {TimesLarge_Stroke2_Corner0_Rounded as XIcon} from '#/components/icons/Times'
|
import {TimesLarge_Stroke2_Corner0_Rounded as XIcon} from '#/components/icons/Times'
|
||||||
import * as Layout from '#/components/Layout'
|
import * as Layout from '#/components/Layout'
|
||||||
import {Link} from '#/components/Link'
|
import {Link} from '#/components/Link'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {useAnalytics} from '#/analytics'
|
import {useAnalytics} from '#/analytics'
|
||||||
import type * as bsky from '#/types/bsky'
|
import type * as bsky from '#/types/bsky'
|
||||||
|
|
||||||
@@ -140,7 +138,6 @@ function RecentProfileItem({
|
|||||||
profile.displayName || sanitizeHandle(profile.handle),
|
profile.displayName || sanitizeHandle(profile.handle),
|
||||||
moderation.ui('displayName'),
|
moderation.ui('displayName'),
|
||||||
)
|
)
|
||||||
const verification = useSimpleVerificationState({profile})
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View style={[a.relative]}>
|
<View style={[a.relative]}>
|
||||||
@@ -166,15 +163,7 @@ function RecentProfileItem({
|
|||||||
<Text emoji style={[a.text_xs, a.leading_snug]} numberOfLines={1}>
|
<Text emoji style={[a.text_xs, a.leading_snug]} numberOfLines={1}>
|
||||||
{name}
|
{name}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges profile={profile} size="sm" style={[a.pl_xs]} />
|
||||||
<View style={[a.pl_2xs]}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={10}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={profile} />
|
|
||||||
</View>
|
</View>
|
||||||
</Link>
|
</Link>
|
||||||
<Button
|
<Button
|
||||||
|
|||||||
@@ -34,7 +34,6 @@ import * as SettingsList from '#/screens/Settings/components/SettingsList'
|
|||||||
import {atoms as a, platform, tokens, useBreakpoints, useTheme} from '#/alf'
|
import {atoms as a, platform, tokens, useBreakpoints, useTheme} from '#/alf'
|
||||||
import {AgeAssuranceDismissibleNotice} from '#/components/ageAssurance/AgeAssuranceDismissibleNotice'
|
import {AgeAssuranceDismissibleNotice} from '#/components/ageAssurance/AgeAssuranceDismissibleNotice'
|
||||||
import {AvatarStackWithFetch} from '#/components/AvatarStack'
|
import {AvatarStackWithFetch} from '#/components/AvatarStack'
|
||||||
import {BotBadgeButton} from '#/components/BotBadge'
|
|
||||||
import {Button, ButtonText} from '#/components/Button'
|
import {Button, ButtonText} from '#/components/Button'
|
||||||
import {useIsFindContactsFeatureEnabledBasedOnGeolocation} from '#/components/contacts/country-allowlist'
|
import {useIsFindContactsFeatureEnabledBasedOnGeolocation} from '#/components/contacts/country-allowlist'
|
||||||
import {useDialogControl} from '#/components/Dialog'
|
import {useDialogControl} from '#/components/Dialog'
|
||||||
@@ -62,13 +61,9 @@ import * as Layout from '#/components/Layout'
|
|||||||
import {Loader} from '#/components/Loader'
|
import {Loader} from '#/components/Loader'
|
||||||
import * as Menu from '#/components/Menu'
|
import * as Menu from '#/components/Menu'
|
||||||
import {ID as PolicyUpdate202508} from '#/components/PolicyUpdateOverlay/updates/202508/config'
|
import {ID as PolicyUpdate202508} from '#/components/PolicyUpdateOverlay/updates/202508/config'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import * as Prompt from '#/components/Prompt'
|
import * as Prompt from '#/components/Prompt'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useFullVerificationState} from '#/components/verification'
|
|
||||||
import {
|
|
||||||
shouldShowVerificationCheckButton,
|
|
||||||
VerificationCheckButton,
|
|
||||||
} from '#/components/verification/VerificationCheckButton'
|
|
||||||
import {useAnalytics} from '#/analytics'
|
import {useAnalytics} from '#/analytics'
|
||||||
import {IS_INTERNAL, IS_IOS, IS_NATIVE} from '#/env'
|
import {IS_INTERNAL, IS_IOS, IS_NATIVE} from '#/env'
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
@@ -322,9 +317,6 @@ function ProfilePreview({
|
|||||||
const {gtMobile} = useBreakpoints()
|
const {gtMobile} = useBreakpoints()
|
||||||
const shadow = useProfileShadow(profile)
|
const shadow = useProfileShadow(profile)
|
||||||
const moderationOpts = useModerationOpts()
|
const moderationOpts = useModerationOpts()
|
||||||
const verificationState = useFullVerificationState({
|
|
||||||
profile: shadow,
|
|
||||||
})
|
|
||||||
const {isActive: live} = useActorStatus(profile)
|
const {isActive: live} = useActorStatus(profile)
|
||||||
|
|
||||||
if (!moderationOpts) return null
|
if (!moderationOpts) return null
|
||||||
@@ -365,24 +357,16 @@ function ProfilePreview({
|
|||||||
]}>
|
]}>
|
||||||
{displayName}
|
{displayName}
|
||||||
</Text>
|
</Text>
|
||||||
{shouldShowVerificationCheckButton(verificationState) && (
|
<ProfileBadges
|
||||||
<View
|
profile={shadow}
|
||||||
style={[
|
size="lg"
|
||||||
{
|
interactive
|
||||||
marginTop: platform({web: 8, ios: 8, android: 10}),
|
|
||||||
},
|
|
||||||
]}>
|
|
||||||
<VerificationCheckButton profile={shadow} size="lg" />
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<View
|
|
||||||
style={[
|
style={[
|
||||||
{
|
{
|
||||||
marginTop: platform({web: 8, ios: 8, android: 10}),
|
marginTop: platform({web: 8, ios: 8, android: 10}),
|
||||||
},
|
},
|
||||||
]}>
|
]}
|
||||||
<BotBadgeButton profile={shadow} size="lg" isSelf />
|
/>
|
||||||
</View>
|
|
||||||
</View>
|
</View>
|
||||||
<Text style={[a.text_md, a.leading_snug, t.atoms.text_contrast_medium]}>
|
<Text style={[a.text_md, a.leading_snug, t.atoms.text_contrast_medium]}>
|
||||||
{sanitizeHandle(profile.handle, '@')}
|
{sanitizeHandle(profile.handle, '@')}
|
||||||
|
|||||||
@@ -15,11 +15,9 @@ import {sanitizeHandle} from '#/lib/strings/handles'
|
|||||||
import {type ComposerOptsPostRef} from '#/state/shell/composer'
|
import {type ComposerOptsPostRef} from '#/state/shell/composer'
|
||||||
import {PreviewableUserAvatar} from '#/view/com/util/UserAvatar'
|
import {PreviewableUserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {atoms as a, useTheme, web} from '#/alf'
|
import {atoms as a, useTheme, web} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {QuoteEmbed} from '#/components/Post/Embed'
|
import {QuoteEmbed} from '#/components/Post/Embed'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {parseEmbed} from '#/types/bsky/post'
|
import {parseEmbed} from '#/types/bsky/post'
|
||||||
|
|
||||||
export function ComposerReplyTo({replyTo}: {replyTo: ComposerOptsPostRef}) {
|
export function ComposerReplyTo({replyTo}: {replyTo: ComposerOptsPostRef}) {
|
||||||
@@ -71,8 +69,6 @@ export function ComposerReplyTo({replyTo}: {replyTo: ComposerOptsPostRef}) {
|
|||||||
}
|
}
|
||||||
}, [embed])
|
}, [embed])
|
||||||
|
|
||||||
const verification = useSimpleVerificationState({profile: replyTo.author})
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Pressable
|
<Pressable
|
||||||
style={[
|
style={[
|
||||||
@@ -110,15 +106,7 @@ export function ComposerReplyTo({replyTo}: {replyTo: ComposerOptsPostRef}) {
|
|||||||
sanitizeHandle(replyTo.author.handle),
|
sanitizeHandle(replyTo.author.handle),
|
||||||
)}
|
)}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges profile={replyTo.author} size="sm" style={[a.pl_xs]} />
|
||||||
<View style={[a.pl_xs]}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={14}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={replyTo.author} />
|
|
||||||
</View>
|
</View>
|
||||||
<View style={[a.flex_row, a.gap_md]}>
|
<View style={[a.flex_row, a.gap_md]}>
|
||||||
<View style={[a.flex_1, a.flex_grow]}>
|
<View style={[a.flex_1, a.flex_grow]}>
|
||||||
|
|||||||
@@ -9,10 +9,8 @@ import {sanitizeHandle} from '#/lib/strings/handles'
|
|||||||
import {useActorAutocompleteQuery} from '#/state/queries/actor-autocomplete'
|
import {useActorAutocompleteQuery} from '#/state/queries/actor-autocomplete'
|
||||||
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {atoms as a, platform, useTheme} from '#/alf'
|
import {atoms as a, platform, useTheme} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
|
|
||||||
export function Autocomplete({
|
export function Autocomplete({
|
||||||
prefix,
|
prefix,
|
||||||
@@ -78,7 +76,6 @@ function AutocompleteProfileCard({
|
|||||||
onPress: () => void
|
onPress: () => void
|
||||||
}) {
|
}) {
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
const state = useSimpleVerificationState({profile})
|
|
||||||
const displayName = sanitizeDisplayName(
|
const displayName = sanitizeDisplayName(
|
||||||
profile.displayName || sanitizeHandle(profile.handle),
|
profile.displayName || sanitizeHandle(profile.handle),
|
||||||
)
|
)
|
||||||
@@ -116,20 +113,15 @@ function AutocompleteProfileCard({
|
|||||||
numberOfLines={1}>
|
numberOfLines={1}>
|
||||||
{displayName}
|
{displayName}
|
||||||
</Text>
|
</Text>
|
||||||
{state.isVerified && (
|
<ProfileBadges
|
||||||
<View
|
profile={profile}
|
||||||
style={[
|
size="sm"
|
||||||
{
|
style={[
|
||||||
marginTop: platform({android: -2}),
|
{
|
||||||
},
|
marginTop: platform({android: -2}),
|
||||||
]}>
|
},
|
||||||
<VerificationCheck
|
]}
|
||||||
width={12}
|
/>
|
||||||
verifier={state.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={profile} />
|
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
<Text
|
<Text
|
||||||
|
|||||||
@@ -47,7 +47,6 @@ import {TimeElapsed} from '#/view/com/util/TimeElapsed'
|
|||||||
import * as Toast from '#/view/com/util/Toast'
|
import * as Toast from '#/view/com/util/Toast'
|
||||||
import {PreviewableUserAvatar, UserAvatar} from '#/view/com/util/UserAvatar'
|
import {PreviewableUserAvatar, UserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {atoms as a, platform, useTheme} from '#/alf'
|
import {atoms as a, platform, useTheme} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
||||||
import {BellRinging_Filled_Corner0_Rounded as BellRingingIcon} from '#/components/icons/BellRinging'
|
import {BellRinging_Filled_Corner0_Rounded as BellRingingIcon} from '#/components/icons/BellRinging'
|
||||||
import {Check_Stroke2_Corner0_Rounded as CheckIcon} from '#/components/icons/Check'
|
import {Check_Stroke2_Corner0_Rounded as CheckIcon} from '#/components/icons/Check'
|
||||||
@@ -64,12 +63,11 @@ import {StarterPack} from '#/components/icons/StarterPack'
|
|||||||
import {VerifiedCheck} from '#/components/icons/VerifiedCheck'
|
import {VerifiedCheck} from '#/components/icons/VerifiedCheck'
|
||||||
import {InlineLinkText, Link} from '#/components/Link'
|
import {InlineLinkText, Link} from '#/components/Link'
|
||||||
import * as MediaPreview from '#/components/MediaPreview'
|
import * as MediaPreview from '#/components/MediaPreview'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {ProfileHoverCard} from '#/components/ProfileHoverCard'
|
import {ProfileHoverCard} from '#/components/ProfileHoverCard'
|
||||||
import {Notification as StarterPackCard} from '#/components/StarterPack/StarterPackCard'
|
import {Notification as StarterPackCard} from '#/components/StarterPack/StarterPackCard'
|
||||||
import {SubtleHover} from '#/components/SubtleHover'
|
import {SubtleHover} from '#/components/SubtleHover'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import * as bsky from '#/types/bsky'
|
import * as bsky from '#/types/bsky'
|
||||||
|
|
||||||
const MAX_AUTHORS = 5
|
const MAX_AUTHORS = 5
|
||||||
@@ -174,9 +172,6 @@ let NotificationFeedItem = ({
|
|||||||
|
|
||||||
const niceTimestamp = niceDate(i18n, item.notification.indexedAt)
|
const niceTimestamp = niceDate(i18n, item.notification.indexedAt)
|
||||||
const firstAuthor = authors[0]
|
const firstAuthor = authors[0]
|
||||||
const firstAuthorVerification = useSimpleVerificationState({
|
|
||||||
profile: firstAuthor.profile,
|
|
||||||
})
|
|
||||||
const firstAuthorName = sanitizeDisplayName(
|
const firstAuthorName = sanitizeDisplayName(
|
||||||
firstAuthor.profile.displayName || firstAuthor.profile.handle,
|
firstAuthor.profile.displayName || firstAuthor.profile.handle,
|
||||||
)
|
)
|
||||||
@@ -247,25 +242,20 @@ let NotificationFeedItem = ({
|
|||||||
emoji
|
emoji
|
||||||
label={_(msg`Go to ${firstAuthorName}'s profile`)}>
|
label={_(msg`Go to ${firstAuthorName}'s profile`)}>
|
||||||
{forceLTR(firstAuthorName)}
|
{forceLTR(firstAuthorName)}
|
||||||
{firstAuthorVerification.showBadge && (
|
<ProfileBadges
|
||||||
<View
|
profile={firstAuthor.profile}
|
||||||
style={[
|
size="sm"
|
||||||
a.relative,
|
style={[
|
||||||
{
|
a.relative,
|
||||||
paddingTop: platform({android: 2}),
|
{
|
||||||
marginBottom: platform({ios: -7}),
|
paddingTop: platform({android: 2}),
|
||||||
top: platform({web: 1}),
|
marginBottom: platform({ios: -7}),
|
||||||
paddingLeft: 3,
|
top: platform({web: 1}),
|
||||||
paddingRight: 2,
|
paddingLeft: 3,
|
||||||
},
|
paddingRight: 2,
|
||||||
]}>
|
},
|
||||||
<VerificationCheck
|
]}
|
||||||
width={14}
|
/>
|
||||||
verifier={firstAuthorVerification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={firstAuthor.profile} />
|
|
||||||
</InlineLinkText>
|
</InlineLinkText>
|
||||||
</ProfileHoverCard>
|
</ProfileHoverCard>
|
||||||
)
|
)
|
||||||
@@ -1019,9 +1009,6 @@ function ExpandedAuthorsList({
|
|||||||
function ExpandedAuthorCard({author}: {author: Author}) {
|
function ExpandedAuthorCard({author}: {author: Author}) {
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
const {_} = useLingui()
|
const {_} = useLingui()
|
||||||
const verification = useSimpleVerificationState({
|
|
||||||
profile: author.profile,
|
|
||||||
})
|
|
||||||
return (
|
return (
|
||||||
<Link
|
<Link
|
||||||
key={author.profile.did}
|
key={author.profile.did}
|
||||||
@@ -1057,15 +1044,11 @@ function ExpandedAuthorCard({author}: {author: Author}) {
|
|||||||
author.profile.displayName || author.profile.handle,
|
author.profile.displayName || author.profile.handle,
|
||||||
)}
|
)}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
<ProfileBadges
|
||||||
<View style={[a.pl_xs, a.self_center]}>
|
profile={author.profile}
|
||||||
<VerificationCheck
|
size="sm"
|
||||||
width={14}
|
style={[a.pl_xs, a.self_center]}
|
||||||
verifier={verification.role === 'verifier'}
|
/>
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<BotBadge profile={author.profile} />
|
|
||||||
<Text
|
<Text
|
||||||
numberOfLines={1}
|
numberOfLines={1}
|
||||||
style={[
|
style={[
|
||||||
|
|||||||
@@ -14,12 +14,10 @@ import {niceDate} from '#/lib/strings/time'
|
|||||||
import {useProfileShadow} from '#/state/cache/profile-shadow'
|
import {useProfileShadow} from '#/state/cache/profile-shadow'
|
||||||
import {unstableCacheProfileView} from '#/state/queries/profile'
|
import {unstableCacheProfileView} from '#/state/queries/profile'
|
||||||
import {atoms as a, platform, useTheme, web} from '#/alf'
|
import {atoms as a, platform, useTheme, web} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {WebOnlyInlineLinkText} from '#/components/Link'
|
import {WebOnlyInlineLinkText} from '#/components/Link'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {ProfileHoverCard} from '#/components/ProfileHoverCard'
|
import {ProfileHoverCard} from '#/components/ProfileHoverCard'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {IS_ANDROID} from '#/env'
|
import {IS_ANDROID} from '#/env'
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
import {TimeElapsed} from './TimeElapsed'
|
import {TimeElapsed} from './TimeElapsed'
|
||||||
@@ -56,7 +54,6 @@ let PostMeta = (opts: PostMetaOpts): React.ReactNode => {
|
|||||||
}, [queryClient, author])
|
}, [queryClient, author])
|
||||||
|
|
||||||
const timestampLabel = niceDate(i18n, opts.timestamp)
|
const timestampLabel = niceDate(i18n, opts.timestamp)
|
||||||
const verification = useSimpleVerificationState({profile: author})
|
|
||||||
const {isActive: live} = useActorStatus(author)
|
const {isActive: live} = useActorStatus(author)
|
||||||
|
|
||||||
const MaybeLinkText = opts.linkDisabled ? Text : WebOnlyInlineLinkText
|
const MaybeLinkText = opts.linkDisabled ? Text : WebOnlyInlineLinkText
|
||||||
@@ -110,31 +107,17 @@ let PostMeta = (opts: PostMetaOpts): React.ReactNode => {
|
|||||||
),
|
),
|
||||||
)}
|
)}
|
||||||
</MaybeLinkText>
|
</MaybeLinkText>
|
||||||
{verification.showBadge && (
|
<ProfileBadges
|
||||||
<View
|
profile={author}
|
||||||
style={[
|
size="sm"
|
||||||
a.pl_2xs,
|
|
||||||
a.self_center,
|
|
||||||
{
|
|
||||||
marginTop: platform({web: 0, ios: 0, android: -1}),
|
|
||||||
},
|
|
||||||
]}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={platform({android: 13, default: 12})}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
<View
|
|
||||||
style={[
|
style={[
|
||||||
a.pl_xs,
|
a.pl_2xs,
|
||||||
a.self_center,
|
a.self_center,
|
||||||
{
|
{
|
||||||
marginTop: -1,
|
marginTop: platform({web: 0, ios: 0, android: -1}),
|
||||||
},
|
},
|
||||||
]}>
|
]}
|
||||||
<BotBadge profile={author} />
|
/>
|
||||||
</View>
|
|
||||||
<MaybeLinkText
|
<MaybeLinkText
|
||||||
emoji
|
emoji
|
||||||
numberOfLines={1}
|
numberOfLines={1}
|
||||||
|
|||||||
@@ -23,7 +23,6 @@ import {formatCount} from '#/view/com/util/numeric/format'
|
|||||||
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
import {UserAvatar} from '#/view/com/util/UserAvatar'
|
||||||
import {NavSignupCard} from '#/view/shell/NavSignupCard'
|
import {NavSignupCard} from '#/view/shell/NavSignupCard'
|
||||||
import {atoms as a, tokens, useTheme, web} from '#/alf'
|
import {atoms as a, tokens, useTheme, web} from '#/alf'
|
||||||
import {BotBadge} from '#/components/BotBadge'
|
|
||||||
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
import {Button, ButtonIcon, ButtonText} from '#/components/Button'
|
||||||
import {Divider} from '#/components/Divider'
|
import {Divider} from '#/components/Divider'
|
||||||
import {
|
import {
|
||||||
@@ -54,9 +53,8 @@ import {
|
|||||||
UserCircle_Stroke2_Corner0_Rounded as UserCircle,
|
UserCircle_Stroke2_Corner0_Rounded as UserCircle,
|
||||||
} from '#/components/icons/UserCircle'
|
} from '#/components/icons/UserCircle'
|
||||||
import {InlineLinkText} from '#/components/Link'
|
import {InlineLinkText} from '#/components/Link'
|
||||||
|
import {ProfileBadges} from '#/components/ProfileBadges'
|
||||||
import {Text} from '#/components/Typography'
|
import {Text} from '#/components/Typography'
|
||||||
import {useSimpleVerificationState} from '#/components/verification'
|
|
||||||
import {VerificationCheck} from '#/components/verification/VerificationCheck'
|
|
||||||
import {IS_WEB} from '#/env'
|
import {IS_WEB} from '#/env'
|
||||||
import {useActorStatus} from '#/features/liveNow'
|
import {useActorStatus} from '#/features/liveNow'
|
||||||
|
|
||||||
@@ -72,7 +70,6 @@ let DrawerProfileCard = ({
|
|||||||
const {_, i18n} = useLingui()
|
const {_, i18n} = useLingui()
|
||||||
const t = useTheme()
|
const t = useTheme()
|
||||||
const {data: profile} = useProfileQuery({did: account.did})
|
const {data: profile} = useProfileQuery({did: account.did})
|
||||||
const verification = useSimpleVerificationState({profile})
|
|
||||||
const {isActive: live} = useActorStatus(profile)
|
const {isActive: live} = useActorStatus(profile)
|
||||||
|
|
||||||
return (
|
return (
|
||||||
@@ -98,18 +95,7 @@ let DrawerProfileCard = ({
|
|||||||
numberOfLines={1}>
|
numberOfLines={1}>
|
||||||
{profile?.displayName || account.handle}
|
{profile?.displayName || account.handle}
|
||||||
</Text>
|
</Text>
|
||||||
{verification.showBadge && (
|
{profile && <ProfileBadges profile={profile} size="md" />}
|
||||||
<View
|
|
||||||
style={{
|
|
||||||
top: 0,
|
|
||||||
}}>
|
|
||||||
<VerificationCheck
|
|
||||||
width={16}
|
|
||||||
verifier={verification.role === 'verifier'}
|
|
||||||
/>
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
{profile && <BotBadge profile={profile} size={16} />}
|
|
||||||
</View>
|
</View>
|
||||||
<Text
|
<Text
|
||||||
emoji
|
emoji
|
||||||
|
|||||||
Reference in New Issue
Block a user