Nextjs:侧边栏路由

IT技术 javascript reactjs next.js next-router
2022-07-11 01:13:04

我试图弄清楚如何使用 next.js 路由来使用路由指令填充侧边栏组件,以便在单击侧边栏选项时,主 div 会填充相关组件。

我可以找到显示侧栏菜单项的 CSS 的教程,但我找不到此任务的 next.js 路由说明。

到目前为止,我有一个侧边栏组件:

function Sidebar({}) {
// I also tried adding href inside the above {} but it didn't work
  // const { me, loading } = useMe()
  const { me, loading: meLoading } = useMe()


  if (meLoading)
    return (
      <Center>
        <Spinner />
      </Center>
    )
  return (
    
    <Flex as="section" minH="100vh" bg="bg-canvas" maxW="100%" p="0">
      <Flex
       
        // px={{ base: '4', sm: '6' }}
      >
        <Stack justify="space-between" spacing="1">
          <Stack spacing={{ base: '5', sm: '6' }} shouldWrapChildren>
            
            <InputGroup>
              <InputLeftElement pointerEvents="none">
                <Icon as={FiSearch} color="muted" boxSize="5" />
              </InputLeftElement>
              <Input placeholder="Search" />
            </InputGroup>
            <Stack spacing="1" >
              <NavButton label="Home"  fontWeight="normal"/>
              <Link href={Library} passHref>
                // I have tried several other versions of this without the passHref, using href="/Library" and a range of other things - but I cant find anything that works - or makes sense as way to put the content in the Container that currently displays lorem ipsum as below

                <NavButton label="Library" aria-current="page" fontWeight="normal" />
              </Link>
              <NavButton label="Tasks"  fontWeight="normal"  />
              
              
            </Stack>
          </Stack>

然后我有另一个名为 Dashbase 的组件,它应该是显示所选侧边栏选项的相关组件的位置(而不是 lorem ipsum)。

 const DashBase = () => {
    const isDesktop = useBreakpointValue({ base: false, lg: true })
    const router = useRouter()
    return (
      <Flex
        as="section"
        direction={{ base: 'column', lg: 'row' }}
        height="100vh"
        bg="white"
        mb="100px"
        overflowY="auto"
        minW="100%" 
        px={0}
        mx="0px"
        // minW="120em"
        // margin="auto"
      >
        {isDesktop ? <Sidebar /> : <Navbar />}
  
        <Container py="8" flex="none">
          <Text> lorem ipsum dolor sit amet, consectetur adipiscing lorem ipsum dolor sit amet, consectetur adipiscing
          </Text>
         
        </Container>
      </Flex>
    )
  }

  export default DashBase;
          <Stack spacing={{ base: '5', sm: '6' }}>
            <Stack spacing="1">
              
              <NavButton label="Help"  fontWeight="normal"/>
              <NavButton label="Settings"  fontWeight="normal"/>
            </Stack>
                         <UserProfile
              name={me.firstName + " " +  me.lastName}
              // image="h"
              bio={me.bio} 
            />
          </Stack>
        </Stack>
      </Flex>
    </Flex>
  
  )
}
1个回答

我至少可以想到两种方法:将两个组件包装在 aContext.Provider和 forward props中,正如您所提到的。

让我们看看我们如何实现后者,以便在单击DashBase时显示/隐藏里面的文本<NavButton label="Library" />为了便于阅读和理解,我省略了一些代码。

我们的第一步是boolean在我们的主要组件中创建一个状态,以便我们可以控制我们的子元素何时应该隐藏或可见。

dashbase.jsx

export const DashBase = () => {
  const isDesktop = useBreakpointValue({ base: false, lg: true })

  // assuming that the component should initially be hidden
  const [showLibrary, setShowLibrary] = React.useState(false)

  // state setter to switch between our `true` and `false` states
  const toggleLibrary = () => setShowLibrary(!showLibrary)

  return (
    <Flex>
      {/* forward the state setter to the `Sidebar` component */}
      {isDesktop ? <Sidebar toggleLibrary={toggleLibrary} /> : <Navbar />}
      <Container>
        {/* and render the text conditionally */}
        {showLibrary && (
          <Text>
            lorem ipsum dolor sit amet, consectetur adipiscing lorem ipsum dolor sit amet, consectetur adipiscing
          </Text>
        )}
      </Container>
    </Flex>
  )
}

然后我们可以将状态设置器助手传递toggleLibrary给我们的Sidebar组件。

sidebar.jsx

export const Sidebar = ({ toggleLibrary }) => {
  const { me, loading: meLoading } = useMe()

  if (meLoading)
    return (
      <Center>
        <Spinner />
      </Center>
    )

  return (
    <Stack>
      <Input placeholder="Search" />
      <Stack>
        <NavButton label="Home" />
        <NavButton label="Library" onClick={toggleLibrary} />
        <NavButton label="Tasks" />
        <NavButton label="Help" />
        <NavButton label="Settings" />
      </Stack>
      <UserProfile name={me.firstName + ' ' + me.lastName} bio={me.bio} />
    </Stack>
  )
}

我们现在应该能够通过单击来隐藏/显示<Text>...</Text>我们内部的组件DashBase<NavButton label="Library" />

如果我们想根据浏览器的当前位置显示/隐藏组件,我们可以将我们的状态移动到Sidebar组件并动态更新它useEffect

const router = useRouter()

React.useEffect(() => {
  if (router.pathname.includes('library')) {
    setShowLibrary(true)
  }
  return () => {}
}, [router.pathname])

这能解决你的问题吗?让我知道事情的后续。

干杯

以前的答案

一种基于某些元数据动态创建路由到其他页面的按钮的简单方法是:

const paths = ['about', 'home', 'login']

const Example = () => {
  const router = useRouter()
  return paths.map(p => <button onClick={router.push(`/{p}`)}>{p}</button>
}

上面的Example组件将创建三个按钮,每个按钮指向不同的路径。