这是我的App.js
import React, {Component} from 'react';
import logo from './logo.svg';
import './App.css';
import {BrowserRouter as Router} from 'react-router-dom';
import Navbar from "./components/nav";
import firebase from './firebase';
import Questions from './components/questions';
import Stuff from './components/stuff';
class App extends Component {
constructor(p) {
super(p);
this.state = {user: null}
}
render() {
return (
<div className="App">
<Navbar/>
{this.state.user ? <Questions/> : <Stuff/>}
</div>
);
}
}
export default App;
这个想法是,它应该渲染导航栏,如果用户登录,它应该渲染Questions元素,否则,渲染其他东西。
这是我的<Navbar/>
元素:
import React from 'react';
import {Navbar as Bar, Nav, NavItem, Modal, Button, FormControl} from 'react-bootstrap';
import {BrowserRouter as Router, Link, Route} from 'react-router-dom';
import firebase, {auth} from '../firebase';
class Navbar extends React.Component {
constructor(props) {
super(props);
this.state = {};
this.login = this.login.bind(this);
this.logout = this.logout.bind(this);
this.openLogin = this.openLogin.bind(this);
this.handleClose = this.handleClose.bind(this);
}
componentDidMount() {
auth.onAuthStateChanged((user) => {
if (user) {
this.setState({user});
}
});
}
logout() {
auth.signOut()
.then(() => {
this.setState({
user: null
});
});
}
login() {
var email = document.getElementById('email').value;
var password = document.getElementById('password').value;
auth.signInWithEmailAndPassword(email, password)
.then(result => {
const user = result.user;
this.setState({user});
document.getElementById('close').click();
}
).catch(e => console.log(e));
}
openLogin() {
this.setState({show: true});
}
handleClose() {
this.setState({show: false});
}
render() {
return (
<React.Fragment>
<Router>
<Bar>
<Bar.Header>
<Bar.Brand>
<a href="/home">UczIchApp</a>
{/*<Route path='path' component=""/>*/}
</Bar.Brand>
<Bar.Brand>
</Bar.Brand>
</Bar.Header>
<Nav>
{
this.state.user ?
<NavItem onClick={this.logout}>Wyloguj się</NavItem>
:
<NavItem onClick={this.openLogin}>Zaloguj się</NavItem>
}
</Nav>
</Bar>
</Router>
<Modal show={this.state.show} onHide={this.handleClose}>
<Modal.Header closeButton>
<Modal.Title>Modal heading</Modal.Title>
</Modal.Header>
<Modal.Body>
<form>
<FormControl
id="email"
type="email"
label="Email address"
placeholder="Enter email"
/>
<FormControl id="password" label="Password" type="password"/>
<Button onClick={this.login}>Zaloguj</Button>
</form>
</Modal.Body>
<Modal.Footer>
<Button id="close" onClick={this.handleClose}>Close</Button>
</Modal.Footer>
</Modal>
</React.Fragment>
)
}
}
export default Navbar;
所以我想根据<App/>
元素中更改的用户状态更改<Navbar/>
元素中的内部。我怎样才能做到这一点?现在状态在<App.js/>
答案 0 :(得分:1)
在App Component中创建一个函数checkUserState
constructor(p) {
super(p);
this.state = {user: null}
this.checkUserState= this.checkUserState.bind(this);
}
checkUserState(user){
this.seState({user});
}
然后将Navbar组件中的props传递为
<Navbar {...this}/>
在您设置状态的Navbar Component内部,执行此操作
this.setState({
user: null
},function(){
this.props.checkUserState(this.state.user)
});
由于Navbar
是子组件,因此您需要反转。
答案 1 :(得分:0)
看起来你需要全局处理应用程序的状态。您可以尝试使用redux来管理该应用的状态。或者您可以将一个函数作为prop从您的父组件传递给导航器,该函数可以处理状态
const Nav = ({ handleClick }) => {
return (<button onClick={handleClick}>hello world</button>);
}
class HelloMessage extends React.Component {
constructor(props){
super(props);
this.state = {
checked: false
}
}
handleClick = (e) => {
e.preventDefault();
this.setState({checked: !this.state.checked});
}
render() {
return (
<div>
<Nav handleClick={this.handleClick}/>
<p><b>status:</b> {this.state.checked ? 'checked' : 'unchecked'}</p>
</div>
);
}
}
ReactDOM.render(
<HelloMessage name="Taylor" />,
document.getElementById('app')
);