reactjs - react-router-dom 链接在 app.js(父组件)中工作,但在子组件中不起作用

标签 reactjs redux react-router-v4 react-router-dom

我在'app.js'(父组件)和'home.js'中有'Nav'组件,有条件地通过设置header { height: 90vh }在主页的标题底部响应空白。 .

为了做到这一点,我在“Home.js”的标题标签中包含了

最佳答案

我将在这里制作一个我通常使用的设置的简化示例。那么,这种方法呢?

index.js

import React from 'react';
import ReactDOM from 'react-dom';
import App from './components/App';
import Provider from "react-redux/es/components/Provider";
import { createStore, applyMiddleware } from 'redux';
import rootReducer from '../reducers/rootReducer';
import thunk from 'redux-thunk';

// Usually I would do this in an external file, but here I'm configuring my store

const myStore = configureStore(initialState) {
  return createStore(
    rootReducer,
    initialState,
    applyMiddleware(thunk)
  );
}    

// After that, I'm wrapping my App component inside of the Provider and passing in the configured store

ReactDOM.render((
    <Provider store={myStore }>
        <App/>
    </Provider>
), document.getElementById('root'));

App.js
import React, { Component } from 'react';
import { BrowserRouter } from 'react-router-dom'
import PrimaryLayoutContainerComponent from "../containers/PrimaryLayoutContainer";

// In my App.js I'm wrapping my primary layout container with BrowserRouter to get access to the history and also passing in the props

class App extends Component {
    render() {
        return (
            <BrowserRouter>
                <PrimaryLayoutContainerComponent {...this.props}/>
            </BrowserRouter>
        );
    }
}
export default App;

PrimaryLayoutContainerComponent.js
在这个(主容器)中,我将充分利用我以前的配置以及 Redux 状态管理提供和需要的任何内容。我还在这个阶段使用 withRouter 来访问历史对象的属性。
import React from 'react';
import { connect } from 'react-redux';
import { bindActionCreators } from 'redux';
import * as myActions from '../actions';
import PrimaryLayout from "../components/layout/PrimaryLayout";
import { withRouter } from 'react-router';
import PropTypes from 'prop-types';


class PrimaryLayoutContainerComponent extends Component {
    render() {
        return (
            <div>
                 //Here we pass our history as props
                <PrimaryLayout  history={this.props.history} 
                                propsX={this.props.propsX}

                                propsY={this.props.actions.propsY}
                />
            </div>
        )
    }
}

// In these (and all other cases) I would highly recommend using propTypes.
// They could give you the answer in where the issues might be in your future development 

PrimaryLayoutContainerComponent.propTypes = {
    loggedUser: PropTypes.string,
    actions: PropTypes.object.isRequired
};

const mapStateToProps = (state) => {
    return { xxxx }
}

const mapDispatchToProps = (dispatch) => {
    return {
        actions: bindActionCreators(myActions, dispatch)
    };
}

export default withRouter(connect(mapStateToProps, mapDispatchToProps)(PrimaryLayoutContainerComponent));

...然后终于在我的 Primary Layout Component 我会像这样定义我所有的路线:

PrimaryLayoutComponent.js
import React, { Component } from 'react';
import { Switch, Route, Redirect, Link } from 'react-router-dom';
// ... import all my compoenents


class PrimaryLayout extends Component {
    constructor(props) {
        super(props);
        this.state = {
            currentRoute: '' // I would use the state to dynamically change the  
                             // routes depending on which one was clicked
        }
    }



    componentWillReceiveProps(nextProps) {
        this.setState({
            currentRoute: nextProps.history.location.pathname
        })
    }

    componentWillMount() {
        this.setState({
            currentRoute: this.props.history.location.pathname
        })
    }

    render() {

        const { currentRoute } = this.state;

        return (
            <div className="wrapper">
                <header className="xxxx" role="banner">
                    <div className="container">
                        <div className="xxxxx">


                           <Link to="/home">
                             <img src={logo} alt="your logo"/> Your App Name
                           </Link>
                            <ul className="navbar__menu">
                                    <li className={currentRoute === "/home" ? "active" : ""}>
                                        <Link to="/home"> Home </Link>
                                    </li>

                                    <li className={currentRoute === "/componentOne" ? "active" : ""}>
                                        <Link to="/componentOne"> componentOne</Link>
                                    </li>

                                    <li className={currentRoute === "/componentTwo" ? "active" : ""}>
                                        <Link to="/componentTwo"> componentTwo</Link>
                                    </li>
                            </ul>

                        </div>
                    </div>
              </header>

// At the very end, I'm using the Switch HOC and defining my routes inside of a main tag

               <main>
                <Switch>
                      <Route path='/home' component={HomeContainerComponent} />
                  <Route path='/componentOne' component={componentOne} />               
                  <Route path='/componentTwo' component={componentTwo} />
                  <Redirect to="/home"/>
                </Switch>
                </main>
            </div>
        )
    }
}

export default PrimaryLayout;

我希望我的方法对您有所帮助,如果您有任何其他问题,请告诉我。我会尽快回复

关于reactjs - react-router-dom 链接在 app.js(父组件)中工作,但在子组件中不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52158147/

相关文章:

html - 未知 Prop 警告 react js `iconClassNameRight`

javascript - 对对象使用 ... 运算符

reactjs - 如何修复 nextCreate 不是设置 useMemo 设置身份验证 react 路由器和 Hook 的函数

javascript - 什么是 React 路由器中的内联渲染以及它如何与路由内的 "render"一起工作/

reactjs - React Router 4 Match 返回未定义

node.js - 无法从React应用程序进行 Node API调用

javascript - .map 在更新状态后没有重新渲染

reactjs - 无法安装 @typescript-eslint/eslint-plugin

javascript - Firebase onAuthStateChanged 在登录时被调用两次

Redux:如何让两个 reducer 按一定顺序响应相同的操作?