I need to launch a function that I have in the child component of a parent button but I have not got it, someone knows some form, I have already seen some examples but I can not find something that can help me since they only handle property changes
this is my code parent:
import React from 'react';
import ReactDom from 'react-dom';
import AppBar from 'material-ui/AppBar';
import injectTapEventPlugin from 'react-tap-event-plugin';
import MuiThemeProvider from 'material-ui/styles/MuiThemeProvider';
import Menux from '../componentes/menux';
class App extends React.Component {
constructor(props) {
super(props);
}
render() {
return (
<div>
<AppBar
title="Aqui empezara todo"
onLeftIconButtonTouchTap = {Menuxr.handleToggle}
/>
<Menux />
</div>
);
}
}
injectTapEventPlugin();
ReactDom.render( <MuiThemeProvider><App/></MuiThemeProvider>,document.getElementById('workspace'));
child
import React from 'react';
import Drawer from 'material-ui/Drawer';
import AppBar from 'material-ui/AppBar';
import MenuItem from 'material-ui/MenuItem';
import RaisedButton from 'material-ui/RaisedButton';
export default class Menux extends React.Component {
constructor(props) {
super(props);
this.state = {openmenu: false};
}
handleClose = () => this.setState({openmenu: false});
handleToggle = () => this.setState({openmenu: !this.state.openmenu});
render() {
return (
<div>
<RaisedButton
label="Toggle Drawer"
ref="menu"
onTouchTap={this.handleToggle}/>
<Drawer width={200} openSecondary={false} open={this.state.openmenu} >
<AppBar title="menu"
onLeftIconButtonTouchTap = {this.handleClose}
/>
<MenuItem onTouchTap={this.handleClose}>Mi perfil</MenuItem>
<MenuItem onTouchTap={this.handleClose}>Mis usuarios</MenuItem>
<MenuItem onTouchTap={this.handleClose}>Mis unidades</MenuItem>
</Drawer>
</div>
);
}
To pass an onChange event handler to a child component in React: Define the event handler function in the parent component. Pass it as a prop to the child component, e.g. <Child handleChange={handleChange} /> . Set it to the onChange prop on the input field in the child.
In a parent component you can use @ViewChild() to access child component's method/variable. Use the @Input() decorator in your child component to allow the parent to bind to this input. To bind a property from parent to a child you must add in you template the binding brackets and the name of your input between them.
To add the click event in React using plain JavaScript, you need to use addEventListener() to assign the click event to an element. Create one <button> element as ref props so that it can be accessed to trigger the click event.
That's not how React functions, unfortunately. You are trying to use Menux.handleToggle
as the callback of the onLeftIconButtonTouchTap
prop, right? So when someone clicks the left icon button, you want the Menux
component to execute the handleToggle
function?
That won't work for two reasons:
Menux.handleToggle
, you are not calling it on an instance! Menux
is a reference to the class itself. It doesn't have the internal state that you are expecting. Moreover, handleToggle
is an instance method. This means it can only be executed on instances of the Menux
class.Menux
class, but as discussed above, that is not the same instance that React creates when you render the <Menux />
element.It's really hard to adequately articulate why it's wrong, it's just fundamentally wrong on a few levels hehe. Long story short: you just cannot call the function of a class like that and expect it to change an instance of that class that is not being specified.
Let's move past that. Now, there's a convoluted way of getting your code to work in the way you've written it, but I think it's better to help you understand a more idiomatic way of doing it. That is to say, a more "React way" of getting done what you want.
We want to "Lift the State Up". This concept is this article: https://facebook.github.io/react/docs/lifting-state-up.html
I highly recommend reading that article.
Why do we "lift state up?" Well in React, child nodes don't communicate with each other. Only children and parents communicate with each other. In fact, parents communicate by providing data and functions, children communicate only by calling the functions parents give them.
Imagine you're a kid, one of 5 siblings. You each have a cell phone, but you don't know the phone numbers of your siblings. You only have your parents phone number. But you need to convey some information to some of your siblings. What do you do? You call your parents phone number, relay them the information, and the parents will call your siblings and relay the data to them.
That's how React works.
So how do we apply this to your situation? Instead of the Menu determining itself when it's open, let's have the parent tell the Menu when it's open. This way, the parent can give both the Menux
component and the AppBar
component a function that they can use to say "Hey mom, can you close the menu?"
We will lift the state from the Menux component to the App component.
class App extends React.Component {
constructor(props) {
super(props);
this.state = {
openmenu: false
}
}
handleClose = () => this.setState({openmenu: false});
handleToggle = () => this.setState({openmenu: !this.state.openmenu});
render() {
return (
<div>
<AppBar
title="Aqui empezara todo"
onLeftIconButtonTouchTap = {this.handleToggle}
/>
<Menux openmenu={this.state.openmenu} handleToggle={this.handleToggle} handleClose={this.handleClose} />
</div>
);
}
}
Ah ha! Now our App determines when the menu is closed and when it's not. It is the single source of truth! But, it provides AppBar
and Menux
with some functions that they can call if they want to change the state in the parent. So how will Menux
change?
export default class Menux extends React.Component {
render() {
return (
<div>
<RaisedButton
label="Toggle Drawer"
ref="menu"
onTouchTap={this.props.handleToggle}/>
<Drawer width={200} openSecondary={false} open={this.props.openmenu} >
<AppBar title="menu"
onLeftIconButtonTouchTap = {this.props.handleClose}
/>
<MenuItem onTouchTap={this.props.handleClose}>Mi perfil</MenuItem>
<MenuItem onTouchTap={this.props.handleClose}>Mis usuarios</MenuItem>
<MenuItem onTouchTap={this.props.handleClose}>Mis unidades</MenuItem>
</Drawer>
</div>
);
}
It uses the functions that the parent passed it in order to set the state in the parent. A nice, easy, reusable component!
This is the React way of doing things. Parent-child only communication, state and functions passed down to children, children call those functions to change state higher up in the tree. Beautiful!
"But, but, but...I really don't want to do things the React way!"
Fiiiiine. Thankfully, someone else answered (so I don't have to :]) with a very simple way to accomplish what you want to do, without having to restructure your application to ahem a more idiomatic way.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With