reactjs ecmascript-6 es6-class

reactjs - TypeError no capturado: no se puede leer la propiedad ''estado o accesorios'' de indefinido



ecmascript-6 es6-class (2)

Entonces comencé a convertir mi aplicación de ES2015 a ES6 que usa React.

Tengo una clase para padres y una clase para niños así,

export default class Parent extends Component { constructor(props) { super(props); this.state = { code: '''' }; } setCodeChange(newCode) { this.setState({code: newCode}); } login() { if (this.state.code == "") { // Some functionality } } render() { return ( <div> <Child onCodeChange={this.setCodeChange} onLogin={this.login} /> </div> ); } }

Clase de niño,

export default class Child extends Component { constructor(props) { super(props); } handleCodeChange(e) { this.props.onCodeChange(e.target.value); } login() { this.props.onLogin(); } render() { return ( <div> <input name="code" onChange={this.handleCodeChange.bind(this)}/> </div> <button id="login" onClick={this.login.bind(this)}> ); } } Child.propTypes = { onCodeChange: React.PropTypes.func, onLogin: React.PropTypes.func };

Sin embargo, esto causa el siguiente error,

this.state no está definido

Se refiere a,

if (this.state.code == "") { // Some functionality }

¿Alguna idea de lo que podría estar causando esto?


Estoy de acuerdo con todas las diferentes soluciones dadas por @Shubham Kathri, excepto el enlace directo en render.

No se recomienda vincular sus funciones directamente en render. Se recomienda vincularlo siempre en el constructor porque si se vincula directamente en el renderizado, cada vez que se renderice su componente, Webpack creará una nueva función / objeto en un archivo empaquetado, por lo que el tamaño del archivo del paquete Webpack aumenta. Por muchas razones, su componente se vuelve a representar, por ejemplo: haciendo setState, pero si lo coloca en el constructor, se llama solo una vez.

No se recomienda la implementación a continuación.

<Child onCodeChange={this.setCodeChange.bind(this)} onLogin={this.login.bind(this)} />

Hazlo siempre en el constructor y usa la referencia siempre que sea necesario

constructor(props){ super(props); this.login = this.login.bind(this); this.setCodeChange = this.setCodeChange.bind(this); } <Child onCodeChange={this.setCodeChange} onLogin={this.login} />

Si está utilizando ES6, no es necesario el enlace manual, pero si lo desea, puede hacerlo. Puede usar las funciones de flecha si desea mantenerse alejado de los problemas relacionados con el alcance y los enlaces manuales de funciones / objetos.

Lo siento si hay algún error tipográfico que estoy respondiendo en mi móvil


Puede usar la función de flecha para unir sus funciones. Debe vincular sus funciones tanto en componentes secundarios como primarios.

Padre:

export default class Parent extends Component { constructor(props) { super(props); this.state = { code: '''' }; } setCodeChange = (newCode) => { this.setState({code: newCode}); } login = () => { if (this.state.code == "") { // Some functionality } } render() { return ( <div> <Child onCodeChange={this.setCodeChange} onLogin={this.login} /> </div> ); } }

Niño

export default class Child extends Component { constructor(props) { super(props); } handleCodeChange = (e) => { this.props.onCodeChange(e.target.value); } login = () => { this.props.onLogin(); } render() { return ( <div> <input name="code" onChange={this.handleCodeChange}/> </div> <button id="login" onClick={this.login}> ); } } Child.propTypes = { onCodeChange: React.PropTypes.func, onLogin: React.PropTypes.func };

También hay otras formas de vincular las funciones, como la que está utilizando, pero también debe hacerlo para el componente principal como <Child onCodeChange={this.setCodeChange.bind(this)} onLogin={this.login.bind(this)} />

o puede especificar el enlace en el constructor como

Padre:

constructor(props) { super(props); this.state = { code: '''' }; this.setCodeChange = this.setCodeChange.bind(this); this.login = this.login.bind(this); }

Niño

constructor(props) { super(props); this.handleCodeChange = this.handleCodeChange.bind(this); this.login = this.login.bind(this); }