feat: simplify account creation flow

This commit is contained in:
codytseng 2025-12-23 21:52:32 +08:00
parent cd7c52eda0
commit a880a92748
35 changed files with 1247 additions and 222 deletions

View file

@ -1,28 +1,79 @@
import NormalFeed from '@/components/NormalFeed'
import { useFeed } from '@/providers/FeedProvider'
import { Button } from '@/components/ui/button'
import { usePrimaryPage } from '@/PageManager'
import { useFollowList } from '@/providers/FollowListProvider'
import { useNostr } from '@/providers/NostrProvider'
import client from '@/services/client.service'
import { TFeedSubRequest } from '@/types'
import { useEffect, useState } from 'react'
import { Compass, Search, UserPlus } from 'lucide-react'
import { useEffect, useRef, useState } from 'react'
import { useTranslation } from 'react-i18next'
export default function FollowingFeed() {
const { t } = useTranslation()
const { pubkey } = useNostr()
const { feedInfo } = useFeed()
const { followingSet } = useFollowList()
const { navigate } = usePrimaryPage()
const [subRequests, setSubRequests] = useState<TFeedSubRequest[]>([])
const [hasFollowings, setHasFollowings] = useState<boolean | null>(null)
const [refreshCount, setRefreshCount] = useState(0)
const initializedRef = useRef(false)
useEffect(() => {
if (initializedRef.current) return
async function init() {
if (feedInfo?.feedType !== 'following' || !pubkey) {
if (!pubkey) {
setSubRequests([])
setHasFollowings(null)
return
}
const followings = await client.fetchFollowings(pubkey)
setHasFollowings(followings.length > 0)
setSubRequests(await client.generateSubRequestsForPubkeys([pubkey, ...followings], pubkey))
if (followings.length) {
initializedRef.current = true
}
}
init()
}, [feedInfo?.feedType, pubkey])
}, [pubkey, followingSet, refreshCount])
return <NormalFeed subRequests={subRequests} isMainFeed />
// Show empty state when user has no followings
if (hasFollowings === false && subRequests.length > 0) {
return (
<div className="flex flex-col items-center justify-center min-h-[60vh] px-6 text-center">
<UserPlus size={64} className="text-muted-foreground mb-4" strokeWidth={1.5} />
<h2 className="text-2xl font-semibold mb-2">{t('Welcome to Jumble!')}</h2>
<p className="text-muted-foreground mb-6 max-w-md">
{t(
'Your feed is empty because you are not following anyone yet. Start by exploring interesting content and following users you like!'
)}
</p>
<div className="flex flex-col sm:flex-row gap-3 w-full max-w-md">
<Button size="lg" onClick={() => navigate('explore')} className="w-full">
<Compass className="size-5" />
{t('Explore')}
</Button>
<Button size="lg" variant="outline" onClick={() => navigate('search')} className="w-full">
<Search className="size-5" />
{t('Search Users')}
</Button>
</div>
</div>
)
}
return (
<NormalFeed
subRequests={subRequests}
onRefresh={() => {
initializedRef.current = false
setRefreshCount((count) => count + 1)
}}
isMainFeed
/>
)
}

View file

@ -1,5 +1,4 @@
import NormalFeed from '@/components/NormalFeed'
import { useFeed } from '@/providers/FeedProvider'
import { useNostr } from '@/providers/NostrProvider'
import { usePinnedUsers } from '@/providers/PinnedUsersProvider'
import client from '@/services/client.service'
@ -8,7 +7,6 @@ import { useEffect, useRef, useState } from 'react'
export default function PinnedFeed() {
const { pubkey } = useNostr()
const { feedInfo } = useFeed()
const { pinnedPubkeySet } = usePinnedUsers()
const [subRequests, setSubRequests] = useState<TFeedSubRequest[]>([])
const initializedRef = useRef(false)
@ -17,7 +15,7 @@ export default function PinnedFeed() {
if (initializedRef.current) return
async function init() {
if (feedInfo?.feedType !== 'pinned' || !pubkey || pinnedPubkeySet.size === 0) {
if (!pubkey || pinnedPubkeySet.size === 0) {
setSubRequests([])
return
}
@ -28,7 +26,7 @@ export default function PinnedFeed() {
}
init()
}, [feedInfo?.feedType, pubkey, pinnedPubkeySet])
}, [pubkey, pinnedPubkeySet])
return <NormalFeed subRequests={subRequests} isMainFeed />
}

View file

@ -5,7 +5,7 @@ import relayInfoService from '@/services/relay-info.service'
import { useEffect, useState } from 'react'
export default function RelaysFeed() {
const { feedInfo, relayUrls } = useFeed()
const { relayUrls } = useFeed()
const [isReady, setIsReady] = useState(false)
const [areAlgoRelays, setAreAlgoRelays] = useState(false)
@ -22,10 +22,6 @@ export default function RelaysFeed() {
return null
}
if (!feedInfo || (feedInfo.feedType !== 'relay' && feedInfo.feedType !== 'relays')) {
return null
}
return (
<NormalFeed
subRequests={[{ urls: relayUrls, filter: {} }]}

View file

@ -199,7 +199,7 @@ function WelcomeGuide() {
<div className="flex flex-col sm:flex-row gap-3 w-full max-w-md">
<Button size="lg" className="w-full" onClick={() => navigate('explore')}>
<Compass className="size-5" />
{t('Explore Relays')}
{t('Explore')}
</Button>
<Button size="lg" className="w-full" variant="outline" onClick={() => checkLogin()}>