From a114c4486e2b5cd74686524d7e673ba7f2044eb4 Mon Sep 17 00:00:00 2001 From: John Ballesteros Date: Wed, 11 Dec 2024 16:23:14 +0800 Subject: [PATCH] refactor: restore hidden-item implementation for pillar-info and dropdown --- src/search/components/pillar-item.tsx | 41 +++++++++- .../pillar-items-dropdown-content.tsx | 22 ++++-- src/search/components/pillar-items.tsx | 15 +++- src/search/core/atoms.ts | 7 +- src/search/core/types.ts | 2 - src/search/data/get-pillar-info.ts | 79 +++++++++---------- src/search/pages/pillar-page.tsx | 6 +- .../state/contexts/pillar-items-context.tsx | 39 +++++++++ 8 files changed, 150 insertions(+), 61 deletions(-) create mode 100644 src/search/state/contexts/pillar-items-context.tsx diff --git a/src/search/components/pillar-item.tsx b/src/search/components/pillar-item.tsx index 7b63a35..97f89e1 100644 --- a/src/search/components/pillar-item.tsx +++ b/src/search/components/pillar-item.tsx @@ -2,26 +2,64 @@ import Link from 'next/link'; import { useRouter } from 'next/navigation'; +import { useInView } from 'react-intersection-observer'; import { Button } from '@nextui-org/button'; +import { useSetAtom } from 'jotai'; import { cn } from '@/shared/utils/cn'; import { TPillarItem } from '@/search/core/types'; +import { hiddenPillarItemsAtom } from '@/search/core/atoms'; import { usePillarRoutesContext } from '@/search/state/contexts/pillar-routes-context'; interface Props { isMainPillarItem: boolean; item: TPillarItem; + pillarSlug: string; } -export const PillarItem = ({ item, isMainPillarItem }: Props) => { +export const PillarItem = ({ item, isMainPillarItem, pillarSlug }: Props) => { const { isActive, label, href } = item; const router = useRouter(); const { isPendingPillarRoute, startTransition } = usePillarRoutesContext(); + const setHiddenItems = useSetAtom(hiddenPillarItemsAtom); + const { ref: inViewRef } = useInView({ + onChange: (inView) => { + setHiddenItems((prev) => { + const newState = { ...prev }; + + // Initialize Set if pillar doesn't exist + if (!newState[pillarSlug]) { + newState[pillarSlug] = []; + } + + // Update hidden items set + let pillarHiddenItems = [...newState[pillarSlug]]; + + if (!inView) { + pillarHiddenItems.unshift(label); + } else { + pillarHiddenItems = pillarHiddenItems.filter( + (itemLabel) => itemLabel !== label, + ); + } + + // Remove pillar key if empty + if (pillarHiddenItems.length > 0) { + newState[pillarSlug] = pillarHiddenItems; + } else { + delete newState[pillarSlug]; + } + + return newState; + }); + }, + }); + const onClick = () => { startTransition(() => { router.push(href); @@ -39,6 +77,7 @@ export const PillarItem = ({ item, isMainPillarItem }: Props) => {