У меня есть следующий код реакции
. / App.js
import React from "react";
import Parent from "./components/Parent";
class App extends React.Component {
render() {
return (
<div className="App">
<Parent />
</div>
);
}
}
export default App;
. / Parent.js
import React, { Component } from "react";
import Child1 from "./Child1";
import Child2 from "./Child2";
class Parent extends Component {
state = {
age: ""
};
handleChange = value => {
this.setState({
age: value
});
};
render() {
console.log("Age: ", this.state.age);
return (
<div>
<h2>Parent</h2>
<Child1 onChange={this.handleChange} />
<Child2 value={this.state.age} />
</div>
);
}
}
export default Parent;
. / Child1.js
import React, { Component } from "react";
import CustomizedSelects from "./material-ui/CustomizedSelects";
class Child1 extends Component {
handleChange = value => {
this.props.onChange(value);
};
render() {
return (
<div>
<h3>Child1</h3>
<CustomizedSelects onChange={this.handleChange} />
</div>
);
}
}
export default Child1;
. / Child2.js
import React, { Component } from "react";
import ComposedTextField from "./material-ui/ComposedTextField";
class Child2 extends Component {
state = {
value: this.props.value
};
render() {
return (
<div>
<h3>Child2</h3>
<ComposedTextField value={this.props.value} />
</div>
);
}
}
export default Child2;
. /material-ui / ComposedTextField.js
import React from "react";
import ReactDOM from "react-dom";
import PropTypes from "prop-types";
import { withStyles } from "@material-ui/core/styles";
import FormControl from "@material-ui/core/FormControl";
import InputLabel from "@material-ui/core/InputLabel";
import OutlinedInput from "@material-ui/core/OutlinedInput";
const styles = theme => ({});
class ComposedTextField extends React.Component {
state = {
name: this.props.value
};
componentDidMount() {
this.forceUpdate();
}
handleChange = event => {
// this.setState({ name: event.target.value });
};
render() {
const { classes } = this.props;
return (
<div className={classes.container}>
<FormControl className={classes.formControl} variant="outlined">
<InputLabel
ref={ref => {
this.labelRef = ReactDOM.findDOMNode(ref);
}}
htmlFor="component-outlined"
>
Name
</InputLabel>
<OutlinedInput
id="component-outlined"
value={this.state.name}
onChange={this.handleChange}
labelWidth={this.labelRef ? this.labelRef.offsetWidth : 0}
/>
</FormControl>
</div>
);
}
}
ComposedTextField.propTypes = {
classes: PropTypes.object.isRequired
};
export default withStyles(styles)(ComposedTextField);
. / material-ui / CustomizedSelects.js
import React from "react";
import PropTypes from "prop-types";
import { withStyles } from "@material-ui/core/styles";
import InputLabel from "@material-ui/core/InputLabel";
import MenuItem from "@material-ui/core/MenuItem";
import FormControl from "@material-ui/core/FormControl";
import Select from "@material-ui/core/Select";
import InputBase from "@material-ui/core/InputBase";
const BootstrapInput = withStyles(theme => ({
root: {
"label + &": {
marginTop: theme.spacing.unit * 3
}
},
input: {
borderRadius: 4,
position: "relative",
backgroundColor: theme.palette.background.paper,
border: "1px solid #ced4da",
fontSize: 16,
width: "auto",
padding: "10px 26px 10px 12px",
transition: theme.transitions.create(["border-color", "box-shadow"]),
// Use the system font instead of the default Roboto font.
fontFamily: [
"-apple-system",
"BlinkMacSystemFont",
'"Segoe UI"',
"Roboto",
'"Helvetica Neue"',
"Arial",
"sans-serif",
'"Apple Color Emoji"',
'"Segoe UI Emoji"',
'"Segoe UI Symbol"'
].join(","),
"&:focus": {
borderRadius: 4,
borderColor: "#80bdff",
boxShadow: "0 0 0 0.2rem rgba(0,123,255,.25)"
}
}
}))(InputBase);
const styles = theme => ({
root: {
display: "flex",
flexWrap: "wrap"
},
margin: {
margin: theme.spacing.unit
},
bootstrapFormLabel: {
fontSize: 18
}
});
class CustomizedSelects extends React.Component {
state = {
age: ""
};
handleChange = event => {
this.setState({ age: event.target.value });
this.props.onChange(event.target.value);
};
render() {
const { classes } = this.props;
return (
<form className={classes.root} autoComplete="off">
<FormControl className={classes.margin}>
<InputLabel
htmlFor="age-customized-select"
className={classes.bootstrapFormLabel}
>
Age
</InputLabel>
<Select
value={this.state.age}
onChange={this.handleChange}
input={<BootstrapInput name="age" id="age-customized-select" />}
>
<MenuItem value="">
<em>None</em>
</MenuItem>
<MenuItem value={10}>Ten</MenuItem>
<MenuItem value={20}>Twenty</MenuItem>
<MenuItem value={30}>Thirty</MenuItem>
</Select>
</FormControl>
</form>
);
}
}
CustomizedSelects.propTypes = {
classes: PropTypes.object.isRequired
};
export default withStyles(styles)(CustomizedSelects);
Как связать Parent.stat.age к его дочернему состоянию, так что каждый раз, когда это значение изменяет, соответствующее значение вывода в Child также автоматически изменится.
Поскольку это позволит напрямую связываться между визуализированными значениями Child1 и Child2.Но здесь это вовсе не показывает каких-либо изменений.
Итак, чтобы справиться с этим, и, в более общем смысле, как работают состояния React, а также реагируют события, потому что я предполагаю, что все это связано вместе ...