forked from
jollywhoppers.com/witchsky.app
Bluesky app fork with some witchin' additions 馃挮
1import React from 'react'
2
3import {isWeb} from '#/platform/detection'
4import * as persisted from '#/state/persisted'
5import {type FeedDescriptor} from '#/state/queries/post-feed'
6
7type StateContext = FeedDescriptor | null
8type SetContext = (v: FeedDescriptor) => void
9
10const stateContext = React.createContext<StateContext>(null)
11stateContext.displayName = 'SelectedFeedStateContext'
12const setContext = React.createContext<SetContext>((_: string) => {})
13setContext.displayName = 'SelectedFeedSetContext'
14
15function getInitialFeed(): FeedDescriptor | null {
16 if (isWeb) {
17 if (window.location.pathname === '/') {
18 const params = new URLSearchParams(window.location.search)
19 const feedFromUrl = params.get('feed')
20 if (feedFromUrl) {
21 // If explicitly booted from a link like /?feed=..., prefer that.
22 return feedFromUrl as FeedDescriptor
23 }
24 }
25
26 const feedFromSession = sessionStorage.getItem('lastSelectedHomeFeed')
27 if (feedFromSession) {
28 // Fall back to a previously chosen feed for this browser tab.
29 return feedFromSession as FeedDescriptor
30 }
31 }
32
33 const feedFromPersisted = persisted.get('lastSelectedHomeFeed')
34 if (feedFromPersisted) {
35 // Fall back to the last chosen one across all tabs.
36 return feedFromPersisted as FeedDescriptor
37 }
38
39 return null
40}
41
42export function Provider({children}: React.PropsWithChildren<{}>) {
43 const [state, setState] = React.useState(() => getInitialFeed())
44
45 const saveState = React.useCallback((feed: FeedDescriptor) => {
46 setState(feed)
47 if (isWeb) {
48 try {
49 sessionStorage.setItem('lastSelectedHomeFeed', feed)
50 } catch {}
51 }
52 persisted.write('lastSelectedHomeFeed', feed)
53 }, [])
54
55 return (
56 <stateContext.Provider value={state}>
57 <setContext.Provider value={saveState}>{children}</setContext.Provider>
58 </stateContext.Provider>
59 )
60}
61
62export function useSelectedFeed() {
63 return React.useContext(stateContext)
64}
65
66export function useSetSelectedFeed() {
67 return React.useContext(setContext)
68}