【问题标题】:How to pass props from child component to parent component to another child component in ReactJS?如何将道具从子组件传递到父组件到 ReactJS 中的另一个子组件?
【发布时间】:2020-05-11 07:58:13
【问题描述】:

我目前正在创建一个搜索栏,其中App 是父级,HeaderHome 是子级。我正在尝试通过App 将输入从Header 传递给Home,但似乎当我尝试加载{this.state.searchValue} 时它什么也没做。

我不知道我的代码哪里出错了。我还使用Route 将道具从Header 路由到Home

这是我的代码:

Header.js(孩子 1)

class Header extends Component {
  constructor(props) {
    super(props);
    this.state = {
      search: "",
    };
  }

  onChange = (event) => {
    this.setState({ search: event.target.value });
  };

  submitSearch = (event) => {
    event.preventDefault();
    console.log(this.state.search);
    this.props.passSearchData(this.state.search);
  };

  render() {
    return (
      <React.Fragment>
        <nav className="navbar navbar-expand-lg navbar-light bg-light">
          <form className="form-inline">
                <input
                  className="form-control mr-sm-2"
                  type="text"
                  placeholder="Search"
                  onChange={this.onChange}
                />
                <button
                  className="btn btn-danger"
                  type="submit"
                  onClick={this.submitSearch}
                >
                  Search
                </button>
              </form>
        </nav>
      </React.Fragment>
    );
  }
}

export default Header;

App.js(父)

class App extends Component {
  constructor() {
    super();
    this.state = {
      searchValue: "",
    };
  }

  handleSearchData = (search) => {
    this.setState({ searchValue: search });
  };

  componentDidMount() {
    this.props.getItems();
  }

  render() {
    return (
      <div className="App">
        <Router>
          <Header passSearchData={this.handleSearchData} />
          <Route
            exact
            path="/"
            render={(props) => (
              <Home {...props} searchValue={this.state.searchValue} />
            )}
          />
        </Router>
        <Footer />
      </div>
    );
  }
}

Home.js

class Catalog extends Component {
  constructor(props) {
    super(props);
    this.state = {
    };
  }
render() {
return (
      <div>
        <p>{this.props.searchValue}</p>
      </div>
    );
  }
}

【问题讨论】:

    标签: javascript reactjs react-native react-router react-component


    【解决方案1】:

    我认为使用反应上下文更好地解决这个问题,因为在路由之间传递状态非常痛苦

    首先你声明你自己的 Provider 作为组件之间的中介。 上下文将保存所有应用程序状态。要在您的组件中使用,只需使用useContext 并传递您想要使用的上下文,在这个用例中,我称之为AppContext。通过使用相同的上下文,您的组件会获得相同的状态并立即触发更新

    我提供的解决方案是使用功能组件。如果你正在使用类组件,只需简单地创建一个功能组件,然后将上下文传递给类组件

    import React, { useContext, useState } from 'react'
    
    const AppContext = React.createContext({})
    
    const AppProvider = props => {
      const [currentState, setCurrentState] = useState(null)
      
      const handleState = value => {
        setCurrentState(value)
      }
      
      const contextValue = { handleState, currentState }
      
      return (
        <AppContext.Provider value={contextValue}>
          {props.children}
        </AppContext.Provider>
      )
    }
    
    const Child1 = props => {
      const { handleState } = useContext(AppContext)
      
      const handleClick = e => {
        handleState(e.target.values)
      }
      
      return (
        <button onClick={handleClick}>Change State</button>
      )
    }
    
    const Child2 = props => {
      const { currentState } = useContext(AppContext)
      
      return (
        <h1>{currentState}</h1>
      )
    }
    
    const Parent = props => {
      
      return (
        <Router>
          <AppProvider>
            <Route component={Child1} />
            <Route component={Child2} />
          </AppProvider>
        </Router>
      )
    }
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

    【讨论】:

    • 谢谢,你的回答听起来很有趣。我会尝试使用上下文。
    • 不客气。顺便说一句,我只是编辑了一些错误的代码,在根目录下从 useContext 更改为 React.createContext
    猜你喜欢
    • 1970-01-01
    • 2020-07-30
    • 2019-01-04
    • 1970-01-01
    • 2017-04-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多