I'm trying to build a select component using react-select
plugin.
In the process of implementing this project, I have some kind of tricky problem with that. Check out my source code here: https://codesandbox.io/s/j148r99695
The problem that I have is I want to fetch all genresList data from the server and mapping them to select component. But somehow or I do wrong something, It's not working. Please see source code above to help me.
I fetch data from Movies
component. Its work well and I pass a props to FormFilter
component: <FormFilter genresList={this.state.genres} />
. And in the FormFilter
component, I check this.props.genresList
, it's available. But when I'm trying to assign it to FormFilter
state and console.log("state", this.state.genres);
that. It's empty. Anyone can tell me why?
Default react-select
using value
and label
to display data to select component. But you know some cases we have to custom that. I try it out by using map to transform to other arrays. But It's the best way? How can I custom valueKey
and labelKey
.
I'm using react-select
beta version2.
UPDATE: I was fixed my project. Please check out the link below. Somehow it's not working. I was commend inside source code.
So to make it works I have changed the FormFilter.js implementation:
import React, { Component } from "react";
import * as Animated from "react-select/lib/animated";
import AsyncSelect from "react-select/lib/Async";
class FormFilter extends Component {
constructor(props) {
super(props);
this.state = {
inputValue: "",
selectedOption: "",
genres: []
};
}
selectGenreHandleChange = newValue => {
const inputValue = newValue.replace(/\W/g, "");
this.setState({ inputValue });
console.log(inputValue);
};
componentDidMount() {
this.genresOption();
}
filterGenres = inputValue => {
const genres = this.genresOption();
//HERE - return the filter
return genres.filter(genre =>
genre.label.toLowerCase().includes(inputValue.toLowerCase())
);
};
promiseOptions = inputValue => {
return new Promise(resolve => { // HERE - you have to return the promise
setTimeout(() => {
resolve(this.filterGenres(inputValue));
}, 1000);
});
};
genresOption() {
const options = [];
const genres = this.props.genresList.genres; //HERE - array is genres in genresList
if (genres && genres instanceof Array) {
genres.map(genre => options.push({ value: genre.id, label: genre.name}));
}
return options;
}
render() {
const { inputValue } = this.state;
if (this.state.genres) console.log("state", this.state.genres);
if (this.props.genresList)
console.log("Movies props", this.props.genresList);
return (
<div className="filter_form">
<span className="search_element full">
<label htmlFor="genres">Genres</label>
<AsyncSelect
className="select genres"
classNamePrefix="tmdb_select"
isMulti
isSearchable="true"
isClearable="true"
cacheOptions
components={Animated}
value={inputValue}
defaultOptions
onInputChange={this.selectGenreHandleChange}
loadOptions={this.promiseOptions}
/>
</span>
</div>
);
}
}
export default FormFilter;
I have write a comment "HERE - something" to let you know what I changed. There are not big problems :)
I did some changed in your FIDDLE and it's works for me
Something like
import React, {Component} from "react";
import { render } from 'react-dom';
import Movies from './Movies';
import "./styles.css";
class App extends Component {
render() {
return (
<div className="App">
<Movies />
</div>
);
}
}
let a = document.getElementById("root");
render(<App />, a);
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.