Files
med-notes/.pnpm-store/v10/files/1b/ef87fde58d2c4c81e87e26f5e9974fe909991ff9eb6e6408d6fae2a82bd2266786d9146029b1e131485581560456f1e6465aab85b2ff770f93be6ff3bca8da
2025-05-09 05:30:08 +02:00

60 lines
1.8 KiB
Plaintext

import { useStore } from '@tanstack/react-store'
import { useRef } from 'react'
import { replaceEqualDeep } from '@tanstack/router-core'
import { useRouter } from './useRouter'
import type {
AnyRouter,
RegisteredRouter,
RouterState,
} from '@tanstack/router-core'
import type {
StructuralSharingOption,
ValidateSelected,
} from './structuralSharing'
export type UseRouterStateOptions<
TRouter extends AnyRouter,
TSelected,
TStructuralSharing,
> = {
router?: TRouter
select?: (
state: RouterState<TRouter['routeTree']>,
) => ValidateSelected<TRouter, TSelected, TStructuralSharing>
} & StructuralSharingOption<TRouter, TSelected, TStructuralSharing>
export type UseRouterStateResult<
TRouter extends AnyRouter,
TSelected,
> = unknown extends TSelected ? RouterState<TRouter['routeTree']> : TSelected
export function useRouterState<
TRouter extends AnyRouter = RegisteredRouter,
TSelected = unknown,
TStructuralSharing extends boolean = boolean,
>(
opts?: UseRouterStateOptions<TRouter, TSelected, TStructuralSharing>,
): UseRouterStateResult<TRouter, TSelected> {
const contextRouter = useRouter<TRouter>({
warn: opts?.router === undefined,
})
const router = opts?.router || contextRouter
const previousResult =
useRef<ValidateSelected<TRouter, TSelected, TStructuralSharing>>(undefined)
return useStore(router.__store, (state) => {
if (opts?.select) {
if (opts.structuralSharing ?? router.options.defaultStructuralSharing) {
const newSlice = replaceEqualDeep(
previousResult.current,
opts.select(state),
)
previousResult.current = newSlice
return newSlice
}
return opts.select(state)
}
return state
}) as UseRouterStateResult<TRouter, TSelected>
}