首页 > 解决方案 > 将 props 从另一个组件传递给一个组件,React Router v4

问题描述

我正在尝试使用 React Router v4 将道具从另一个组件传递给一个组件,但我没有得到我想要的结果。

这就是我试图传递道具的方式:

render() {
    const { selectedLanguage, repos, error, dashboard } = this.state

    return (
      <React.Fragment>
        <LanguagesNav
          selected={selectedLanguage}
          onUpdateLanguage={this.updateLanguage}
        />

        {error && <p>{error}</p>}

        {repos && <LoginForm repos={repos} selected={selectedLanguage} dashboard={dashboard} onUpdateLogin={this.updateLogin} />}

        <Route
          path='/dashboard'
          render={(props) => (
            <Dashboard {...props}
              repos={repos}
              selected={selectedLanguage}
            />
          )}
        />
      </React.Fragment>

我想从以下位置发送道具的整个组件:

登录.js

import React from 'react'
import PropTypes from 'prop-types'
import languagesdata from '../languagesdata.json'
import { fetchLanguageRepos } from '../utils/api'
import Dashboard from './Dashboard'
import {BrowserRouter as Router, Route } from 'react-router-dom'
import { Link } from 'react-router-dom'

function LanguagesNav ({ selected, onUpdateLanguage}) {
  const languages = ['EU', 'ES', 'EN']

  return (
    <div >
      <h1 className='center-text header-lg'>
        GAUR 2.0
      </h1>
      <ul className='flex-center'>
        {languages.map((language) => (
          <li key={language}>
            <button
              className='btn-clear nav-link'
              style={language === selected ? { color: 'rgb(187, 46, 31)' } : null }
              onClick={() => onUpdateLanguage(language)}>
              {language}
            </button>
          </li>
        ))}
      </ul>
    </div>
  )
}

LanguagesNav.propTypes = {
  selected: PropTypes.string.isRequired,
  onUpdateLanguage: PropTypes.func.isRequired
}

function LoginForm ({ repos, selected, dashboard, onUpdateLogin }) {
  var language = {}
  switch (selected) {
    case "EU":
      selected = "EU";
      language  = repos[0].terms;
      break;
    case "ES":
      selected = "ES";
      language = repos[1].terms;
      break;
    case "EN":
      selected = "EN";
      language = repos[2].terms;
      break;
  }

  return (
    <form className='column player'>
      <div className='row player-inputs'>
        <input
          type='text'
          id='username'
          className='input-light'
          placeholder={language.username}
          autoComplete='off'
        />
      </div>
      <div className='row player-inputs'>
        <input
          type='password'
          id='password'
          className='input-light'
          placeholder={language.password}
          autoComplete='off'
        />
      </div>
      <div className='row player-inputs'>
        <Link
          className='btn dark-btn'
          to={{
            pathname: '/dashboard',
          }}
          >
            {language.login}
        </Link>
      </div>
    </form>
  )
}

LoginForm.propTypes = {
  repos: PropTypes.array.isRequired
}

export default class Login extends React.Component {
  constructor(props) {
    super(props)

    this.state = {
      selectedLanguage: 'EU',
      repos: null,
      error: null,
      dashboard: false
    }

    this.updateLanguage = this.updateLanguage.bind(this)

  }
  componentDidMount () {
    this.updateLanguage(this.state.selectedLanguage)
  }
  updateLanguage (selectedLanguage) {
    this.setState({
      selectedLanguage,
      error: null
    })

    fetchLanguageRepos(selectedLanguage)
      .then((repos) => this.setState({
          repos,
          error: null,
      }))
      .catch(() => {
        console.warn('Error fetching repos: ', error)

        this.setState({
          error: 'There was an error fetching the repositories.'
        })
      })
  }

  render() {
    const { selectedLanguage, repos, error, dashboard } = this.state

    return (
      <React.Fragment>
        <LanguagesNav
          selected={selectedLanguage}
          onUpdateLanguage={this.updateLanguage}
        />

        {error && <p>{error}</p>}

        {repos && <LoginForm repos={repos} selected={selectedLanguage} dashboard={dashboard} onUpdateLogin={this.updateLogin} />}

        <Route
          path='/dashboard'
          render={(props) => (
            <Dashboard {...props}
              repos={repos}
              selected={selectedLanguage}
            />
          )}
        />
      </React.Fragment>
    )
  }
}

这是我要发送道具的组件:

仪表板.js

import React from 'react'
import PropTypes from 'prop-types'
import Card from './Card'
import Loading from './Loading'
import { fetchLanguageRepos } from '../utils/api'
import Profile from './Profile'
import { Link } from 'react-router-dom'

function ReposGrid ({ repos, selected, profile, onUpdateProfile }) {
  var language = {}
  switch (selected) {
    case "EU":
      selected = "EU";
      language  = repos[0].terms;
      break;
    case "ES":
      selected = "ES";
      language = repos[1].terms;
      break;
    case "EN":
      selected = "EN";
      language = repos[2].terms;
      break;
  }

  return (
    <ul className='grid space-around'>
      <li key={language.studyplan}>
        <button
          onClick={() => {onUpdateProfile(`${profile}`)}}
        >
          <Card
            header={language.studyplan}
          >
          </Card>
        </button>
      </li>
      <li key={language.careers}>
        <Link to='/'>
          <Card
            header={language.careers}
          >
          </Card>
        </Link>
      </li>
      <li key={language.census}>
        <Card
          header={language.census}
        >
        </Card>
      </li>
      <li key={language.sms}>
        <Card
          header={language.sms}
        >
        </Card>
      </li>
      <li key={language.tuitions}>
        <Card
          header={language.tuitions}
        >
        </Card>
      </li>
      <li key={language.surveys}>
        <Card
          header={language.surveys}
        >
        </Card>
      </li>
      <li key={language.titles}>
        <Card
          header={language.titles}
        >
        </Card>
      </li>
      <li key={language.exams}>
        <Card
          header={language.exams}
        >
        </Card>
      </li>
      <li key={language.record}>
        <Card
          header={language.record}
        >
        </Card>
      </li>
    </ul>
  )
}

export default class Dashboard extends React.Component {
  constructor(props) {
    super(props)

    this.state = {
      selectedLanguage: 'EU',
      repos: null,
      error: null,
      loading: true,
      profile: false
    }

    this.updateProfile = this.updateProfile.bind(this)
  }

  componentDidMount () {
    var { repos, selectedLanguage } = this.props
    this.setState({
      selectedLanguage,
      repos,
      error: null,
      loading: false,
      profile: false
    })
  }

  updateProfile (profile) {
    this.setState({
      error: null,
      profile: true
    })
  }

  render() {
    const { selectedLanguage, repos, error } = this.props
    const { profile } = this.state

   if (profile === true) {
     return (
       <React.Fragment>
         {repos && <Profile repos={repos} selectedLanguage={selectedLanguage} />}
       </React.Fragment>
     )
   }

    return (
      <React.Fragment>
        {repos && <ReposGrid repos={repos} selected={selectedLanguage} profile={profile} onUpdateProfile={this.updateProfile} />}
      </React.Fragment>
    )
  }
}

我应该得到这样的东西:

预期仪表板

相反,我得到了这个:

我得到的仪表板

只是为了提供更多信息,这是我为 Login.js 设置路由的 index.js:

index.js

import React from 'react'
import ReactDOM from 'react-dom'
import './index.css'
import Login from './components/Login'
import Dashboard from './components/Dashboard'
import Nav from './components/Nav'
import {BrowserRouter as Router, Route } from 'react-router-dom'

class App extends React.Component {
  render() {
    return (
      <Router>
        <div className='container'>
          <Nav />
          <Route exact path='/' component={Login} />
        </div>
      </Router>
    )
  }
}

ReactDOM.render(
  <App />,
  document.getElementById('app')
)

我试过在 index.js 中设置路由,但也没有用。正确的方法是什么?

标签: javascriptreactjsreact-routerjsx

解决方案


推荐阅读