Reputation: 327
I'm making a custom dropdown list in reactjs. When I click on any element in the dropdown list I get it's value and put it inside an input and it works just fine. The problem is that the first element returns nothing and I can't get it's value. Also I developed the dropdown list to disappear when I choose any element inside of it. But like I said it works just fine on all elements except the first one.
I solved the problem by setTimeOut and hide the dropdown list in 50 milliseconds. But I don't think this's a right solution.
//Select Component
class Select extends Component {
showList = (e) => {
e.target.closest('.select').classList.add('active');
}
hideList = (e) => {
setTimeout(() => {
e.target.closest('.select').classList.remove('active');
}, 100);
}
selectValue = (e) => {
let value = e.target.getElementsByTagName('span')[0].innerHTML;
this.setState({ selectValue: value })
}
render() {
return (
<input
{...this.props}
type="text"
placeholder={this.props['placeholder']}
onFocus={this.showList}
onBlur={this.hideList}
value={this.state.selectValue}
onChange={this.changeSelectValue}
required
/>
<div className="select">
<div className="select-options menu full-width">
{
this.props.list.map(element => {
return (
<MenuItem text={element} onClick={(e) => this.selectValue(e)} />
)
})
}
</div>
</div>
);
}
}
==================
class MenuItem extends Component {
constructor(props) {
super(props);
this.state = {}
}
render() {
return (
<p className={"menu-item " + this.props['type'] } {...this.props}>
{this.props['icon'] ? <i className={this.props['icon']} ></i> : null}
<span>{this.props['text']}</span>
</p>
);
}
}
Upvotes: 0
Views: 612
Reputation: 21
1.use key prop for every MenuItem Component when you are using the list to create a list of MenuItems. 2.Instead of getting value from target in selectValue function directly pass the value from onClick handler.
selectValue = (e , element) => {
this.setState({ selectValue: element })
}
<MenuItem text={element} key={element} onClick={(e) => this.selectValue(e , element)} />
Editted:- Remove the onBlur handler and put the functionality of hideList inside selectValue function after setState,you can use setState with callback if normal setState doesn't work
selectValue = (e) => {
let value = e.target.getElementsByTagName('span')[0].innerHTML;
this.setState({ selectValue: value })
e.target.closest('.select').classList.remove('active');
}
Upvotes: 1