【问题标题】:Using React Router with Switch and can't get the page to render different components when changing routes将 React Router 与 Switch 一起使用,并且在更改路由时无法让页面呈现不同的组件
【发布时间】:2019-04-26 18:48:00
【问题描述】:

我创建了一个 React 应用程序,它最终会根据 API 调用动态分配路由。现在我已经硬编码了组件,我只是试图切换页面视图以根据导航选择查看每个组件。我将 Nav 设置在 switch 视图之外,以便它始终呈现在页面上,但是当我尝试将 WelcomePage 设置为主路由时,它是唯一呈现在页面上的东西,即使我选择另一个组件也没有任何变化我的导航页面。关于为什么会发生这种情况以及我可以做些什么来解决它的任何建议/想法?

代码如下

Main App Component

import React from 'react'
import { Route, Redirect, Switch } from 'react-router-dom'
import ApplicationPage from './pages/ApplicationPage'
import FrameworkPage from './pages/FrameworkPage'
import WelcomePage from './pages/WelcomePage'
import Nav from './components/Nav'

const App = () => (
  <>
    <Route path={['/app/:appId', '/']} component={Nav} />
    <Switch>
    <Route path={['/app/:appId', '/']} component={WelcomePage} />
    <Route path={['/app', '/Framework']} component={FrameworkPage} />
      <Route
        path={['/app/:appId/setting/:settingKey', '/app/:appId', '/app']}
        component={ApplicationPage}
      />
      <Redirect to="/app/foo" />

    </Switch>

  </>
)

export default App

Nav Component

import React from 'react'
import styled from 'styled-components'
import { useAppState } from '../store'

const Nav = ({ match, history }) => {
  const [appState] = useAppState()

  return (
    <StyledNav>
      <h1>Title of Page</h1>
      <select
        defaultValue={match.params.appId}
        onChange={({ target }) => history.replace(`/app/${target.value}`)}
      >
        <option>Choose App</option>
        {appState.apps.map(opt => (
          <option key={opt}>{opt}</option>
        ))}
      </select>
    </StyledNav>
  )
}

const StyledNav = styled.nav`
  padding: 20px 10px;
  background: black;
  color: white;

  h1 {
    margin: 0;
  }
`

export default React.memo(
  Nav,
  (prevProps, nextProps) =>
    prevProps.match.params.appId === nextProps.match.params.appId
)

【问题讨论】:

  • 刚刚给你写了一个答案。如果您有任何问题,请告诉我。 :)

标签: reactjs react-router


【解决方案1】:

所以我认为正在发生的事情是,因为您在 Switch 之外定义了 Nav 路线并给了它一条路径。它总是会最终呈现在其他所有内容之上,因为您正在使路径成为要求,并且无论何时在其他地方导航时仍然满足该路径。您可以做的就是将 Nav 的路线全部删除并执行此操作。无论如何,这将使导航出现在顶部,而不会中断您的导航。您似乎也没有导入 BrowserRouter。

import React from 'react'
import { BrowserRouter, Route, Redirect, Switch } from 'react-router-dom'
import ApplicationPage from './pages/ApplicationPage'
import FrameworkPage from './pages/FrameworkPage'
import WelcomePage from './pages/WelcomePage'
import Nav from './components/Nav'

const App = () => (
  <BrowserRouter>
    <div>
       <Nav/>
       <Switch>
          <Route path={['/app/:appId', '/']} component={WelcomePage} />
          <Route path={['/app', '/Framework']} component={FrameworkPage} />
          <Route
        path={['/app/:appId/setting/:settingKey', '/app/:appId', '/app']}
        component={ApplicationPage}
      />
          <Redirect to="/app/foo" />

       </Switch>
    </div>
  <BrowserRouter/>
)

export default App

【讨论】:

  • 啊,我试过了,但现在它抛出了一个错误,因为我的 Nav 元素实际上依赖于道具。我有一个下拉导航器,它将根据 API 调用动态呈现选项。我将编辑我的原始帖子以包括上下文
  • 知道了,我认为你仍然可以将道具传递给导航,只是不要定义路线。 :)。编辑啊,好吧,我明白你要做什么了。
  • 嗯我试过了,但它又回到了同样的问题,没有任何视图从导航选择改变,它只显示 WelcomePage 组件
  • 我得到的错误是TypeError: Cannot read property 'params' of undefined Nav src/components/Nav.js:12 9 | &lt;StyledNav&gt; 10 | &lt;h1&gt;Comcast.BSD.Configuration&lt;/h1&gt; 11 | &lt;select &gt; 12 | defaultValue={match.params.appId} | ^ 13 | onChange={({ target }) =&gt; history.replace(`/app/${target.value}`)} 14 | &gt; 15 | &lt;option&gt;Choose App&lt;/option&gt;
  • @JCalkins89 嘿伙计。你能解释一下 appId 是从哪里生成的以及它是如何更新的,如果它确实得到了更新?我想到的是将该值保留在您的 redux-state 中并将该状态映射到您的 Navbar。
猜你喜欢
  • 2021-10-21
  • 1970-01-01
  • 2020-05-06
  • 1970-01-01
  • 2021-08-19
  • 2019-09-13
  • 2023-02-08
  • 2018-09-18
  • 1970-01-01
相关资源
最近更新 更多