Skip to content

Commit e7cf95a

Browse files
committed
feat: feeds improve pager and repect user
1 parent 901efcb commit e7cf95a

File tree

1 file changed

+134
-75
lines changed

1 file changed

+134
-75
lines changed

src/views/feeds.tsx

Lines changed: 134 additions & 75 deletions
Original file line numberDiff line numberDiff line change
@@ -9,29 +9,10 @@ import { LikePost, OpenPost, UnlikePost } from '../components/actions/post'
99
import type { FollowingUpdatesMoreKey } from 'jike-sdk/dist/client/types'
1010
import type { Entity, JikeClient } from 'jike-sdk'
1111

12-
function Pager() {
13-
const { lastPage, nextPage } = useContext(FeedsContext)!
14-
return (
15-
<ActionPanel.Section>
16-
<Action
17-
icon="⬅️"
18-
title="上一页"
19-
shortcut={{ modifiers: ['opt'], key: 'arrowLeft' }}
20-
onAction={lastPage}
21-
/>
22-
<Action
23-
icon="➡️"
24-
title="下一页"
25-
shortcut={{ modifiers: ['opt'], key: 'arrowRight' }}
26-
onAction={nextPage}
27-
/>
28-
</ActionPanel.Section>
29-
)
30-
}
31-
3212
interface FeedsCtx {
3313
lastPage: () => void
3414
nextPage: () => void
15+
toLatest: () => void
3516
}
3617

3718
const FeedsContext = createContext<FeedsCtx | undefined>(undefined)
@@ -44,6 +25,7 @@ export function Feeds() {
4425
Awaited<ReturnType<JikeClient['queryFollowingUpdates']>>
4526
>([])
4627
const [lastKeys, setLastKeys] = useState<FollowingUpdatesMoreKey[]>([])
28+
const [lastKey, setLastKey] = useState<FollowingUpdatesMoreKey>(undefined)
4729

4830
const fetchFeeds = async () => {
4931
if (!client) return
@@ -52,11 +34,10 @@ export function Feeds() {
5234
setLoading(true)
5335
try {
5436
const updates = await client.queryFollowingUpdates({
55-
lastKey: lastKeys.at(-1),
37+
lastKey,
5638
limit: limit.limitMaxCount(40),
5739
onDone(_, key) {
58-
lastKeys.push(key)
59-
setLastKeys(lastKeys)
40+
setLastKeys([...lastKeys, key])
6041
},
6142
})
6243
setUpdates(updates)
@@ -70,7 +51,7 @@ export function Feeds() {
7051

7152
useEffect(() => {
7253
fetchFeeds()
73-
}, [client])
54+
}, [client, lastKey])
7455

7556
const context: FeedsCtx = {
7657
lastPage: () => {
@@ -82,12 +63,18 @@ export function Feeds() {
8263
return
8364
}
8465

85-
lastKeys.pop()
86-
lastKeys.pop()
87-
setLastKeys(lastKeys)
88-
fetchFeeds()
66+
setLastKey(lastKeys.at(-3))
67+
setLastKeys(lastKeys.slice(0, -2))
68+
},
69+
70+
nextPage: () => {
71+
setLastKey(lastKeys.at(-1))
72+
},
73+
74+
toLatest: () => {
75+
setLastKeys([])
76+
setLastKey(undefined)
8977
},
90-
nextPage: () => fetchFeeds(),
9178
}
9279

9380
const onSetUser = (userId: string) => {
@@ -128,6 +115,7 @@ export function Feeds() {
128115
<NotSupported
129116
key={(update as any).id}
130117
type={(update as any).type}
118+
object={update}
131119
/>
132120
)
133121
}
@@ -137,57 +125,74 @@ export function Feeds() {
137125
)
138126
}
139127

140-
const NotSupported = ({ type }: { type: string }) => (
141-
<List.Item title={`暂不支持 ${type}`} />
128+
const NotSupported = ({ type, object }: { type: string; object: unknown }) => (
129+
<List.Item
130+
title={`暂不支持 ${type}`}
131+
actions={
132+
<ActionPanel>
133+
<Pager />
134+
<CopyUpdate object={object} />
135+
</ActionPanel>
136+
}
137+
/>
142138
)
143139

144140
const PersonalUpdate = ({ update }: { update: Entity.PersonalUpdate }) => {
145-
if (update.action === 'USER_FOLLOW') {
146-
return <UserFollow update={update} />
141+
switch (update.action) {
142+
case 'USER_FOLLOW':
143+
return <UserInteract update={update} title="关注了即友" />
144+
case 'USER_RESPECT':
145+
return <UserInteract update={update} title="夸了夸即友🎉" />
146+
default:
147+
return <NotSupported type={update.action} object={update} />
147148
}
148-
return <NotSupported type={update.action} />
149149
}
150150

151-
const UserFollow = ({ update }: { update: Entity.PersonalUpdate }) => {
152-
return (
153-
<List.Item
154-
icon={pictureWithCircle(update.users[0].avatarImage.thumbnailUrl)}
155-
title={update.users[0].screenName}
156-
subtitle="关注了即友"
157-
actions={
158-
<ActionPanel>
159-
{update.targetUsers.map((user) => (
160-
<ActionPanel.Submenu
161-
key={user.id}
162-
icon={pictureWithCircle(user.avatarImage.thumbnailUrl)}
163-
title={`打开 ${user.screenName} 用户页`}
164-
>
165-
<OpenProfile username={user.username} split={false} />
166-
</ActionPanel.Submenu>
167-
))}
168-
<Pager />
169-
</ActionPanel>
170-
}
171-
detail={
172-
<List.Item.Detail
173-
metadata={
174-
<List.Item.Detail.Metadata>
175-
<List.Item.Detail.Metadata.Label title="关注了即友" />
176-
{update.targetUsers.map((user) => (
177-
<List.Item.Detail.Metadata.Label
178-
key={user.id}
179-
icon={pictureWithCircle(user.avatarImage.thumbnailUrl)}
180-
title=""
181-
text={user.screenName}
182-
/>
183-
))}
184-
</List.Item.Detail.Metadata>
185-
}
186-
/>
187-
}
188-
/>
189-
)
190-
}
151+
const UserInteract = ({
152+
update,
153+
title,
154+
}: {
155+
update: Entity.PersonalUpdate
156+
title: string
157+
}) => (
158+
<List.Item
159+
icon={pictureWithCircle(update.users[0].avatarImage.thumbnailUrl)}
160+
title={update.users[0].screenName}
161+
subtitle={title}
162+
actions={
163+
<ActionPanel>
164+
{update.targetUsers.map((user) => (
165+
<ActionPanel.Submenu
166+
key={user.id}
167+
icon={pictureWithCircle(user.avatarImage.thumbnailUrl)}
168+
title={`打开 ${user.screenName} 用户页`}
169+
>
170+
<OpenProfile username={user.username} split={false} />
171+
</ActionPanel.Submenu>
172+
))}
173+
<Pager />
174+
<CopyUpdate object={update} />
175+
</ActionPanel>
176+
}
177+
detail={
178+
<List.Item.Detail
179+
metadata={
180+
<List.Item.Detail.Metadata>
181+
<List.Item.Detail.Metadata.Label title={title} />
182+
{update.targetUsers.map((user) => (
183+
<List.Item.Detail.Metadata.Label
184+
key={user.id}
185+
icon={pictureWithCircle(user.avatarImage.thumbnailUrl)}
186+
title=""
187+
text={user.screenName}
188+
/>
189+
))}
190+
</List.Item.Detail.Metadata>
191+
}
192+
/>
193+
}
194+
/>
195+
)
191196

192197
const OriginalPost = ({ post }: { post: JikePostWithDetail }) => {
193198
const [liked, setLiked] = useState(post.detail.liked)
@@ -240,9 +245,63 @@ ${post.detail.pictures
240245
)}
241246
<OpenPost type={ApiOptions.PostType.ORIGINAL} id={post.id} />
242247
<Pager />
248+
<CopyUpdate object={post.detail} />
243249
</ActionPanel>
244250
}
245-
detail={<List.Item.Detail markdown={markdown} />}
251+
detail={
252+
<List.Item.Detail
253+
markdown={markdown}
254+
metadata={
255+
<List.Item.Detail.Metadata>
256+
{post.detail.topic && (
257+
<List.Item.Detail.Metadata.Label
258+
title="圈子"
259+
icon={pictureWithCircle(
260+
post.detail.topic.squarePicture.thumbnailUrl
261+
)}
262+
text={post.detail.topic.content}
263+
/>
264+
)}
265+
</List.Item.Detail.Metadata>
266+
}
267+
/>
268+
}
269+
/>
270+
)
271+
}
272+
273+
function Pager() {
274+
const { lastPage, nextPage, toLatest } = useContext(FeedsContext)!
275+
return (
276+
<ActionPanel.Section>
277+
<Action
278+
icon="⬅️"
279+
title="上一页"
280+
shortcut={{ modifiers: ['opt'], key: 'arrowLeft' }}
281+
onAction={lastPage}
282+
/>
283+
<Action
284+
icon="➡️"
285+
title="下一页"
286+
shortcut={{ modifiers: ['opt'], key: 'arrowRight' }}
287+
onAction={nextPage}
288+
/>
289+
<Action
290+
icon="🎬"
291+
title="查看最新"
292+
shortcut={{ modifiers: ['opt', 'shift'], key: 'arrowLeft' }}
293+
onAction={toLatest}
294+
/>
295+
</ActionPanel.Section>
296+
)
297+
}
298+
299+
function CopyUpdate({ object }: { object: unknown }) {
300+
return (
301+
<Action.CopyToClipboard
302+
title="复制动态 (JSON)"
303+
shortcut={{ modifiers: ['opt', 'cmd'], key: 'c' }}
304+
content={JSON.stringify(object, undefined, 2)}
246305
/>
247306
)
248307
}

0 commit comments

Comments
 (0)