I'm looking to be able to open/close a nested list using React, so that when you click on the parent li the children are hidden? Here's what I used to create the list.
list.js
class List extends React.Component {
render(){
return (
<ul>
{this.props.list.map(function(item){
return (
<li>
<ListItem key={item.id} item={item} />
<List list={item.children} />
</li>
);
})}
</ul>
);
}
list-item.js
class ListItem extends React.Component {
handleCollapse(){
console.log('Open/Close: ' + this.props.item.display_name);
return false;
}
handleFilter(){
console.log('Filter id: ' + this.props.item.id);
return false;
}
render(){
return (
<div>
<a rel="{this.props.item.id}" onClick={this.handleCollapse.bind(this)}>
{this.props.item.display_name}
</a>
<input value="" type="checkbox" onClick={this.handleFilter.bind(this)} />
</div>
)
}
Are you trying to simulate accordion behaviour? If yes then you can modify your code like this. Use component's state and toggle it to open and close children. Instead of creating <List list={item.children} /> in List class, import(or use require) list.js in list-item.js and render the child List item on the basis of current ListItem's state.
list-item.js
class ListItem extends React.Component {
//Add this
constructor (){
super(...arguments);
this.state = { showChild:false};
}
handleCollapse(){
console.log('Open/Close: ' + this.props.item.display_name);
//Add this
this.setState({showChild:!this.state.showChild});
return false;
}
handleFilter(){
console.log('Filter id: ' + this.props.item.id);
return false;
}
render(){
let children;
if(this.state.showChild) {
children = (<List list={this.props.item.children} />);
}
return (
<div>
<a rel="{this.props.item.id}" onClick={this.handleCollapse.bind(this)}>
{this.props.item.display_name}
</a>
<input value="" type="checkbox" onClick={this.handleFilter.bind(this)} />
//Add this
{children}
</div>
)
};
}
list.js
class List extends React.Component {
render(){
//Removed <List .../>, rest is same just other way of doing same stuff
let LI = this.props.list.map( (item) => {
return( <li> <ListItem key={item.id} item={item} /></li>);
}
);
return ( <ul>{LI}</ul>);
}
};
dummy data to test
var data=[
{
id:"1st of Level 1",
get display_name(){return _name(this.id,this.children)},
children: [
{
id:"1st of Level 1.2",
get display_name(){return _name(this.id,this.children)},
children: [
{
id:"1st of Level 1.2.1",
get display_name(){return _name(this.id,this.children)},
children:[]
}
]
},
{
id:"2nd of Level 1.2",
get display_name(){return _name(this.id,this.children)},
children:[]
}
]
},
{
id:"2nd of Level 1",
get display_name(){return _name(this.id,this.children)},
children:[]
},
{
id:"3rd of Level 1",
get display_name(){return _name(this.id,this.children)},
children:[]
},
{
id:"4th of Level1",
get display_name(){return _name(this.id,this.children)},
children:[]
}
];
function _name(id,child) {
if(child.length>0)
return("I am "+id+" I HAVE CHILDREN");
else {
return("I am "+id+" I DON'T HAVE CHILDREN ");
}
}
ReactDOM.render(<List list={data} />,document.getElementById('root'));
`
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