【问题标题】:Pass props to React component dependent on route根据路由将 props 传递给 React 组件
【发布时间】:2017-11-01 20:28:00
【问题描述】:

我有一个使用 react-router 的根组件:

<HashRouter>
  <aside>
    <Sidebar />
  </aside>
  <main>
    <Switch>
      {/* -- routes go here -- */}
    </Switch>
  </main>
</HashRouter>

我希望我的Sidebar 组件根据我们所处的路线具有不同的内容。所以如果我有两条路线,foobar,当我去/foo 时,我希望Sidebar 拥有与访问/bar 时不同的道具。我尝试将location 作为道具传递:

<Sidebar location={this.context.router.location.pathname} />

但我很确定它不是这样工作的......果然它没有工作。

【问题讨论】:

  • 你尝试使用withRouter
  • 是的,行得通。如果你想把它放在答案中,我会标记它。

标签: reactjs react-router


【解决方案1】:

您可以使用withRouter 将值从路由传递到另一个组件。通过这种方式,您可以进行条件渲染或实现与组件的当前路由相关的任何其他逻辑。

您可以访问历史对象的属性和最近的 的匹配通过 withRouter 高阶组件。带路由器 每次路由更改时都会重新渲染其组件 与渲染道具相同的道具:{ match, location, history }。

示例 (来自官方文档)

// A simple component that shows the pathname of the current location
class ShowTheLocation extends React.Component {
  static propTypes = {
    match: PropTypes.object.isRequired,
    location: PropTypes.object.isRequired,
    history: PropTypes.object.isRequired
  }

  render() {
    const { match, location, history } = this.props

    return (
      <div>You are now at {location.pathname}</div>
    )
  }
}

// Create a new component that is "connected" (to borrow redux
// terminology) to the router.
const ShowTheLocationWithRouter = withRouter(ShowTheLocation)

【讨论】:

    【解决方案2】:

    这是一种使用 React Router 的 withRouter&lt;Sidebar /&gt; 组件“连接”到路由器的方法。

    使用withRouter,我们照常创建&lt;Sidebar /&gt; 组件,然后像这样“连接”它:

    //Sidebar
    class Sidebar extends React.Component {
      render() {
        const { location } = this.props;
    
        return (
          <div>
            <h1>Sidebar</h1> 
            <p>You are now at {this.props.location.pathname}</p>
          </div>
        )
      }
    }
    
    const SidebarWithRouter = withRouter(Sidebar);
    

    最后,我们有一个新的&lt;SidebarWithRouter /&gt; 组件连接到路由器,因此它可以访问matchlocationhistory

    不幸的是,由于 iframe 中的history,代码 sn-p 无法在 Stackoverflow 中运行,但这是代码,以及一个有效的 Codepen

    let { BrowserRouter, Link, Route } = ReactRouterDOM;
    let { Switch, withRouter } = ReactRouter;
    let Router = BrowserRouter;
    
    // App
    class App extends React.Component {
      render() {
        return (
          <Router>
            <div className="container">
              <ul>
                <li>
                  <Link to="/">Home</Link>
                </li>
                <li>
                  <Link to="/about">About</Link>
                </li>
              </ul>
              <hr />
              <aside>
                <SidebarWithRouter  />
              </aside>
              <Switch> 
                <Route exact path="/" component={Home} />
                <Route path="/about" component={About} />
              </Switch>
            </div>
          </Router>
        );
      }
    }
    
    //Home
    const Home = () => (
      <div>
        <h1>Home</h1>
        <p>This is the Home Page.</p>
      </div>
    );
    
    //About
    const About = () => (
      <div>
        <h1>About</h1>
        <p>This is about</p>
      </div>
    );
    
    //Sidebar
    class Sidebar extends React.Component {
      render() {
        const { location } = this.props;
    
        return (
          <div>
            <h1>Sidebar</h1> 
            <p>You are now at {this.props.location.pathname}</p>
          </div>
        )
      }
    }
    
    const SidebarWithRouter = withRouter(Sidebar);
    
    ReactDOM.render(<App />, document.getElementById("app"));
    

    【讨论】:

      猜你喜欢
      • 2019-06-20
      • 2015-10-30
      • 2020-04-02
      • 1970-01-01
      • 1970-01-01
      • 2017-08-19
      • 2018-08-28
      • 2017-11-17
      • 2017-09-14
      相关资源
      最近更新 更多