How to add element in array - javascript

Hi all I have following code:
const category = useSelector(state => state.category.category);
const list = [];
const addlist = (id, name) => {
const data = {
id: name,
};
list.push(data);
};
I am getting from my state category. Then I am creating empty list array and finally I have addlist function who is added item in my list array.
here is my select options:
return(
<div>
<select name="cars" id="cars">
<option value="" selected disabled hidden>
choose category
</option>
{category?.map((item, idx) => (
<option
key={item.id}
value={idx}
disabled={active}
onClick={() => addlist(item.id, item.name)}
>
{item.name}
</option>
))}
</select>
</div>
)
I am trying to implement following, when some option will be clicked it should be automatically added in array. But after clicking nothing was happening. Please help to resolve this issue.

As suggested in the comment section, for similar scenarios where you'd like to keep values for example in an array in your component you should use useState hook.
You can import useState as:
import { useState } from 'react'
A basic idea would be the following - see how the onClick has changed:
const YourComponent = () => {
const category = useSelector(state => state.category.category);
// here you can create a list state with an initial empty array
const [list, setList] = useState([])
return(
<div>
<select name="cars" id="cars">
<option value="" selected disabled hidden>
choose category
</option>
{category?.map((item, idx) => (
<option
key={item.id}
value={idx}
disabled={false} // originally here was active
onClick={() => setList(prevState => [...prevState, {
id: item.name
}])}
>
{item.name}
</option>
))}
</select>
</div>
)
}
But the essential part other than creating a list state would be:
setList(prevState =>
[...prevState, { id: item.name }]
)
Suggested documentation to read is Using the State Hook.

Related

Display a list of users from a REST API and filter with React

I'm new here and also new to react js and I'm having trouble solving 1 exercise that asks to display a list of users coming from a REST API and then to be able to filter it.
I have managed to show it but I don't know how to do the filter.
EDIT:
Well Thanx I manage to use filters as you say :D.
But now I want the user to be able to select which columns are shown and which are not.
For this I have created a select from which I plan to remove the filter but I don't really know how to proceed :/
This is how I'm doing the filter, using a text input.
//Query
const [query, setQuery] = useState("");
const search = (data) => {
return data.filter(
item => item.name.toLowerCase().includes(query));
}
the select
<select className='select' onChange={changeFilter}>
<option value="">All</option>
<option value="name">Name</option>
<option value="username">Username</option>
<option value="email">Email</option>
<option value="phone">Phone</option>
</select>
So basically I pretend to change the
"name" here: item.name.toLowerCase().includes(query));
for filter and if All is selected its shows all.
Any help with this?
Code from the fetch:
// users from API.
const [users, setUsers] = useState([]);
useEffect(() => {
fetchData();
}, []);
// async function
const fetchData = async () => {
await fetch('https://jsonplaceholder.typicode.com/users')
.then(response => response.json())
.then(data => setUsers(data))
.catch((error) => {
console.log("ERROR:" + error);
})
}
I modified the way I call the component in App.js
<div className="App">
<h1>PRUEBA DE NIVEL</h1>
<select className='select' onChange={changeSelectedFilter}>
<option value="">All</option>
<option value="name">Name</option>
<option value="username">Username</option>
<option value="email">Email</option>
<option value="phone">Phone</option>
</select>
<input type="text"
placeholder='Search...'
className='search'
onChange={e => setQuery(e.target.value.toLowerCase())}
/>
<UserTable data={search(users)} filter={selectedFilter} />
</div>
You can use the filter method like this:
const isUserEligible = (user) => {
if(/* the condition that the user must have */) {
return true;
} else {
return false;
}
}
users.filter((user) => isUserEligible(user)).map((user) => (
<UsersList
key={user.id}
name={user.name}
username={user.username}
email={user.email}
phone={user.phone}
/>
))
Update:
I didn't understand your question completely.
But if you want to show only the selected column in the select box, you can define a state for your select like this:
const [selectedColumn, setSelectedColumn] = useState("");
const changeSelectedColumn = (event) => {
setSelectedColumn(event.target.value);
}
<select className='select' onChange={changeSelectedColumn}>
<option value="">All</option>
<option value="name">Name</option>
<option value="username">Username</option>
<option value="email">Email</option>
<option value="phone">Phone</option>
</select>
And then you can pass the selectedColumn to your UsersList component like this:
users.map((user) => (
<UsersList
key={user.id}
name={user.name}
username={user.username}
email={user.email}
phone={user.phone}
selectedColumn={selectedColumn}
/>
))
And finally in your UsersList component, show only the selected column by 'if, else' base on the value of the selectedColumn or show all if the selectedColumn value is "". (Means that the user selected All columns).
If you also want to filter by the query, you can use the filter method again as I said before.
You could use a state called filterInput for example and an input, and filter(). Like so:
const [users, setUsers] = useState([]);
const [filterInput, setFilterInput] = useState("");
<div>
<input type="text" value={filterInput} onChange={() => setFilterInput(e.target.value)} />
{users
.filter((user) => user.name.includes(filterInput) || user.username.includes(filterInput))
.map((user) => (
<UsersList
key={user.id}
name={user.name}
username={user.username}
email={user.email}
phone={user.phone}
/>
))}
</div>
.filter MDN
users.filter(user => user.name.startsWith('R')).map((user) => (
<UsersList
key={user.id}
name={user.name}
username={user.username}
email={user.email}
phone={user.phone}
/>
));

Is there a way in React to change option in select by clicking on another select?

So basically if I set country in second dropdown to let's say Spain and then want to change the option in first select dropdown, how can I set second dropdown to go back to default value, in this case All Countries?
<select onClick={handleRankingsRange}>
<option value='top 100'>top 100</option>
<option value='top 200'>top 100-200</option>
<option value='top 200+'>top 200+</option>
</select>
<select onClick={handleFilterCountry}>
<option defaultValue='All Countries'>All Countries</option>
{countries
.filter((country) => country !== '')
.sort()
.map((country, index) => {
return (
<option value={country} key={index}>
{country}
</option>
);
})}
</select>
You need to convert your select components to controlled components by using value and onChange like this:
import { useState } from "react";
const countries = ["Spain", "France", "Portugal", "Germany"];
export default function App() {
const [selectedRange, setSelectedRange] = useState();
const [selectedCountry, setSelectedCountry] = useState();
const handleRankingsRange = (e) => {
setSelectedRange(e.target.value);
setSelectedCountry("");
};
const handleFilterCountry = (e) => {
setSelectedCountry(e.target.value);
};
return (
<div>
<select value={selectedRange} onChange={handleRankingsRange}>
<option value="top 100">top 100</option>
<option value="top 200">top 100-200</option>
<option value="top 200+">top 200+</option>
</select>
<select value={selectedCountry} onChange={handleFilterCountry}>
<option value="">All Countries</option>
{countries
.filter((country) => country !== "")
.sort()
.map((country, index) => {
return (
<option value={country} key={index}>
{country}
</option>
);
})}
</select>
<br />
selectedRange = {selectedRange}
<br />
selectedCountry = {selectedCountry}
</div>
);
}
You can take a look at this sandbox for a live working example of this solution.
[Edit] Added the second part of your question to set back to default "all countries"
if using a list (the list in my example will be an array with objects)
let list = [
{
country: "Spain",
options: ["one", "two", "three"],
},
...
]
you could create a state (useState hook) based on the array.
Mapping that list for the options as you have done, you can also map the first selection based on the array that you would set in your state.
My render would look like this:
return (
<>
<select name="rankings" id="selectRankings">
{ranking.map((rank, index) => {
return (
<option key={index} value={rank}>{rank}</option>
)
})}
</select>
<br/>
<select onChange={(e)=>{handleSelection(e)}} name="countries" id="selectCountry">
<option value="All">All Countries</option>
{list.map((item, index) => {
return(
<option key={index} value={item.country}>{item.country}</option>
)
})}
</select>
< />
);
when selecting a country, on change it will execute handleSelection which will find the correct options and update them to your state.
secondly, if you want to reset the value of the second selection element, you can just set it back to "All" (see code below)
const [ranking, setRanking] = useState(["-- select country first --"]);
const handleSelection = (e) => {
list.find(item => {
if (item.country === e.target.value) {
setRanking(item.options)
}
})
e.target.value = "All";
}
sandbox example

React adding custom props to vanilla html elements

const handleChange = (e) => {
console.log(e.target.id);
};
return (
<div>
<select onChange={(e) => handleChange(e)}>
<option value="1-10" id="foo">
1-10
</option>
How can I make the id prop in the <option> tag accessible by the code above? e.target.id returns nothing, but e.target.value returns the selected value. How can I create these custom attributes with when using vanilla html elements?
One of the easiest method to achieve this is as follows:
const handleChange = (e) => {
const index = e.target.selectedIndex;
const id = e.target.childNodes[index].id;
console.log(id); // logs 'foo' or 'bar' depending on selection
};
return (
<div>
<select onChange={(e) => handleChange(e)}>
<option value="1-10" id="foo">
1-10
</option>
<option value="11-20" id="bar">
11-20
</option>
</select>
</div>
);
e.target is the select, not the option. And since the select does not have an id, you are getting nothing. One way to achieve what you want is by doing so :
export default function App() {
const handleChange = (e) => {
const selectedOption = e.target.querySelector(`option[value='${e.target.value}']`);
console.log(selectedOption.id);
};
return (
<select onChange={(e) => handleChange(e)}>
<option value="1-10" id="foo">
1-10
</option>
<option value="1-11" id="bar">
1-11
</option>
</select>
);
}
Here's another way to do so
import React from 'react';
const handleChange = (e) => {
const index = e.target.selectedIndex;
const el = e.target.childNodes[index]
const option = el.getAttribute('id');
console.log(option)
};
export function App(props) {
return (
<div className='App'>
<select onChange={(e) => handleChange(e)}>
<option value="1-10" id="foo">
1-10
</option>
<option value="2-10" id="zoo">
2-10
</option>
</select>
</div>
);
}

How to add items in select dynamically in react?

Could you please tell me How to add items in select dynamically in react ?
I am getting response from server (name , label etc).For example I just mock my response and after two second I fetch that .
In my example I have two select box or drop down .first dropdown have value “one” and “two”(which is given as options in json).
In json there is one more option dependentField it mean the field is dependent on another field (value mentioned is dependent).In my example second field is dependent on first field.
So the value of second select or dropdown field will be ["three", "four"] if first select box or dropdown value id one.
So the value of second select or dropdown field will be ["five", "six"] if first select box or dropdown value id two.
So I need to watch the value of field as mention in hook form
https://react-hook-form.com/get-started
Can we dynamically add options
here is code
https://codesandbox.io/s/stoic-benz-lxb8i
useEffect(() => {
console.log("====");
(async () => {
var a = await FETCH_API();
console.log("sssss");
setState(a);
console.log(a);
})();
}, []);
const getForm = () => {
try {
return state.map((i, index) => {
switch (i.type) {
case "text":
return (
<div key={index}>
<label>{i.label}</label>
<input type="text" ref={register()} name={i.name} />
</div>
);
case "select":
if (i.watch) {
watch(i.name, null);
}
return (
<div key={index}>
<label>{i.label}</label>
<select name={i.name} ref={register()}>
{i.options.map((i, idx) => {
return (
<option key={idx} value={i}>
{i}
</option>
);
})}
/
</select>
</div>
);
default:
return <div>ddd</div>;
}
});
return <div>ddd</div>;
} catch (e) {}
};
I don’t wan’t want to do any harcoading like
useEffect(()=>{
},[‘first’])
can we watch or add useeffect dynamically to watch change dynamically ?
Any update
this is a simpl two select. Where frist select depend on second
import React,{useState, useEffect} from "react"
const App = () => {
const [state,setState] = useState({
option1:["one","two"],
option2: []
})
useEffect(()=> {
(async () => {
var a = await FETCH_API();
console.log("sssss");
setState({
...state,
option2: a
});
console.log(a);
})();
},[state.option1])
return(
<div>
<select>
{
state.option1.map((i,idx)=>{
return(
<option key={idx} value={i}>
{i}
</option>
)
})
}
</select>
<select>
{
state.option2.map((i,idx)=>{
return(
<option key={idx} value={i}>
{i}
</option>
)
})
}
</select>
</div>
)
}
export default App

React JSX: selecting "selected" on selected <select> option

In a React component for a <select> menu, I need to set the selected attribute on the option that reflects the application state.
In render(), the optionState is passed from the state owner to the SortMenu component. The option values are passed in as props from JSON.
render: function() {
var options = [],
optionState = this.props.optionState;
this.props.options.forEach(function(option) {
var selected = (optionState === option.value) ? ' selected' : '';
options.push(
<option value={option.value}{selected}>{option.label}</option>
);
});
// pass {options} to the select menu jsx
However that triggers a syntax error on JSX compilation.
Doing this gets rid of the syntax error but obviously doesn't solve the problem:
var selected = (optionState === option.value) ? 'selected' : 'false';
<option value={option.value} selected={selected}>{option.label}</option>
I also tried this:
var selected = (optionState === option.value) ? true : false;
<option value={option.value} {selected ? 'selected' : ''}>{option.label}</option>
Is there a recommended way of solving this?
React makes this even easier for you. Instead of defining selected on each option, you can (and should) simply write value={optionsState} on the select tag itself:
<select value={optionsState}>
<option value="A">Apple</option>
<option value="B">Banana</option>
<option value="C">Cranberry</option>
</select>
For more info, see the React select tag doc.
Also, React automatically understands booleans for this purpose, so you can simply write (note: not recommended)
<option value={option.value} selected={optionsState == option.value}>{option.label}</option>
and it will output 'selected' appropriately.
You could do what React warns you when you try to set the "selected" property of the <option>:
Use the defaultValue or value props on <select> instead of setting selected on <option>.
So, you can use options.value on the defaultValue of your select
Here is a complete solution which incorporates the best answer and the comments below it (which might help someone struggling to piece it all together):
UPDATE FOR ES6 (2019) - using arrow functions and object destructuring
in main component:
class ReactMain extends React.Component {
constructor(props) {
super(props);
this.state = { fruit: props.item.fruit };
}
handleChange = (event) => {
this.setState({ [event.target.name]: event.target.value });
}
saveItem = () => {
const item = {};
item.fruit = this.state.fruit;
// do more with item object as required (e.g. save to database)
}
render() {
return (
<ReactExample name="fruit" value={this.state.fruit} handleChange={this.handleChange} />
)
}
}
included component (which is now a stateless functional):
export const ReactExample = ({ name, value, handleChange }) => (
<select name={name} value={value} onChange={handleChange}>
<option value="A">Apple</option>
<option value="B">Banana</option>
<option value="C">Cranberry</option>
</select>
)
PREVIOUS ANSWER (using bind):
in main component:
class ReactMain extends React.Component {
constructor(props) {
super(props);
// bind once here, better than multiple times in render
this.handleChange = this.handleChange.bind(this);
this.state = { fruit: props.item.fruit };
}
handleChange(event) {
this.setState({ [event.target.name]: event.target.value });
}
saveItem() {
const item = {};
item.fruit = this.state.fruit;
// do more with item object as required (e.g. save to database)
}
render() {
return (
<ReactExample name="fruit" value={this.state.fruit} handleChange={this.handleChange} />
)
}
}
included component (which is now a stateless functional):
export const ReactExample = (props) => (
<select name={props.name} value={props.value} onChange={props.handleChange}>
<option value="A">Apple</option>
<option value="B">Banana</option>
<option value="C">Cranberry</option>
</select>
)
the main component maintains the selected value for fruit (in state), the included component displays the select element and updates are passed back to the main component to update its state (which then loops back to the included component to change the selected value).
Note the use of a name prop which allows you to declare a single handleChange method for other fields on the same form regardless of their type.
I was making a drop-down menu for a language selector - but I needed the dropdown menu to display the current language upon page load. I would either be getting my initial language from a URL param example.com?user_language=fr, or detecting it from the user’s browser settings. Then when the user interacted with the dropdown, the selected language would be updated and the language selector dropdown would display the currently selected language.
Since this whole thread has been giving fruit examples, I got all sorts of fruit goodness for you.
First up, answering the initially asked question with a basic React functional component - two examples with and without props, then how to import the component elsewhere.
Next up, the same example - but juiced up with Typescript.
Then a bonus finale - A language selector dropdown component using Typescript.
Basic React (16.13.1) Functional Component Example. Two examples of FruitSelectDropdown , one without props & one with accepting props fruitDetector
import React, { useState } from 'react'
export const FruitSelectDropdown = () => {
const [currentFruit, setCurrentFruit] = useState('oranges')
const changeFruit = (newFruit) => {
setCurrentFruit(newFruit)
}
return (
<form>
<select
onChange={(event) => changeFruit(event.target.value)}
value={currentFruit}
>
<option value="apples">Red Apples</option>
<option value="oranges">Outrageous Oranges</option>
<option value="tomatoes">Technically a Fruit Tomatoes</option>
<option value="bananas">Bodacious Bananas</option>
</select>
</form>
)
}
Or you can have FruitSelectDropdown accept props, maybe you have a function that outputs a string, you can pass it through using the fruitDetector prop
import React, { useState } from 'react'
export const FruitSelectDropdown = ({ fruitDetector }) => {
const [currentFruit, setCurrentFruit] = useState(fruitDetector)
const changeFruit = (newFruit) => {
setCurrentFruit(newFruit)
}
return (
<form>
<select
onChange={(event) => changeFruit(event.target.value)}
value={currentFruit}
>
<option value="apples">Red Apples</option>
<option value="oranges">Outrageous Oranges</option>
<option value="tomatoes">Technically a Fruit Tomatoes</option>
<option value="bananas">Bodacious Bananas</option>
</select>
</form>
)
}
Then import the FruitSelectDropdown elsewhere in your app
import React from 'react'
import { FruitSelectDropdown } from '../path/to/FruitSelectDropdown'
const App = () => {
return (
<div className="page-container">
<h1 className="header">A webpage about fruit</h1>
<div className="section-container">
<h2>Pick your favorite fruit</h2>
<FruitSelectDropdown fruitDetector='bananas' />
</div>
</div>
)
}
export default App
FruitSelectDropdown with Typescript
import React, { FC, useState } from 'react'
type FruitProps = {
fruitDetector: string;
}
export const FruitSelectDropdown: FC<FruitProps> = ({ fruitDetector }) => {
const [currentFruit, setCurrentFruit] = useState(fruitDetector)
const changeFruit = (newFruit: string): void => {
setCurrentFruit(newFruit)
}
return (
<form>
<select
onChange={(event) => changeFruit(event.target.value)}
value={currentFruit}
>
<option value="apples">Red Apples</option>
<option value="oranges">Outrageous Oranges</option>
<option value="tomatoes">Technically a Fruit Tomatoes</option>
<option value="bananas">Bodacious Bananas</option>
</select>
</form>
)
}
Then import the FruitSelectDropdown elsewhere in your app
import React, { FC } from 'react'
import { FruitSelectDropdown } from '../path/to/FruitSelectDropdown'
const App: FC = () => {
return (
<div className="page-container">
<h1 className="header">A webpage about fruit</h1>
<div className="section-container">
<h2>Pick your favorite fruit</h2>
<FruitSelectDropdown fruitDetector='bananas' />
</div>
</div>
)
}
export default App
Bonus Round: Translation Dropdown with selected current value:
import React, { FC, useState } from 'react'
import { useTranslation } from 'react-i18next'
export const LanguageSelectDropdown: FC = () => {
const { i18n } = useTranslation()
const i18nLanguage = i18n.language
const [currentI18nLanguage, setCurrentI18nLanguage] = useState(i18nLanguage)
const changeLanguage = (language: string): void => {
i18n.changeLanguage(language)
setCurrentI18nLanguage(language)
}
return (
<form>
<select
onChange={(event) => changeLanguage(event.target.value)}
value={currentI18nLanguage}
>
<option value="en">English</option>
<option value="de">Deutsch</option>
<option value="es">Español</option>
<option value="fr">Français</option>
</select>
</form>
)
}
An invaluable resource for React/Typescript
Here is the latest example of how to do it. From react docs, plus auto-binding "fat-arrow" method syntax.
class FlavorForm extends React.Component {
constructor(props) {
super(props);
this.state = {value: 'coconut'};
}
handleChange = (event) =>
this.setState({value: event.target.value});
handleSubmit = (event) => {
alert('Your favorite flavor is: ' + this.state.value);
event.preventDefault();
}
render() {
return (
<form onSubmit={this.handleSubmit}>
<label>
Pick your favorite flavor:
<select value={this.state.value} onChange={this.handleChange}>
<option value="grapefruit">Grapefruit</option>
<option value="lime">Lime</option>
<option value="coconut">Coconut</option>
<option value="mango">Mango</option>
</select>
</label>
<input type="submit" value="Submit" />
</form>
);
}
}
Main Point - Controlled Component
You are looking to set up a "Controlled Component". This will require you to set the value on the element as well as handle the on change event to update the value.
https://reactjs.org/docs/forms.html#controlled-components
Examples
https://codepen.io/codyswartz/pen/QWqYNrY
Simple Functional Component Select Example
This also includes a default and grays it out.
const defaultSelectValue = "Select a fruit"
const SelectExample = () => {
const [selected, setSelected] = useState(defaultSelectValue)
return (
<>
<label htmlFor="fruits">Fruits</label>{' '}
<select
id="fruits"
name="fruits"
defaultValue={selected}
style={{ color: selected === defaultSelectValue ? "gray" : "black" }}
onChange={e => setSelected(e.target.value)}
>
<option>{defaultSelectValue}</option>
<option>Banana</option>
<option>Apple</option>
<option>Orange</option>
</select>
<h2>Selected: {selected}</h2>
</>
)
}
// Usage
<SelectExample />
Dynamic Reusable Example with Default
This would take a collection of strings using the first as a default.
const SelectExample = ({ name, items }) => {
const defaultSelectValue = items[0]
const [selected, setSelected] = useState(defaultSelectValue)
return (
<>
<label htmlFor={name}>{name}</label>{' '}
<select
id={name}
name={name}
defaultValue={selected}
style={{ color: selected === defaultSelectValue ? "gray" : "black" }}
onChange={e => setSelected(e.target.value)}
>
{items.map(item => (
<option key={item} value={item}>
{item}
</option>
))}
</select>
<h2>Selected: {selected}</h2>
</>
)
}
// Usage
<SelectExample
name="fruits"
items={['Select a fruit', 'Banana', 'Apple', 'Orange']}
/>
With React 16.8. We can do this with hooks like the following example
Codesandbox link
import React, { useState } from "react";
import "./styles.css";
export default function App() {
const options = [
"Monty Python and the Holy Grail",
"Monty Python's Life of Brian",
"Monty Python's The Meaning of Life"
];
const filmsByTati = [
{
id: 1,
title: "Jour de fête",
releasedYear: 1949
},
{
id: 2,
title: "Play time",
releasedYear: 1967
},
{
id: 3,
releasedYear: 1958,
title: "Mon Oncle"
}
];
const [selectedOption, setSelectedOption] = useState(options[0]);
const [selectedTatiFilm, setSelectedTatiFilm] = useState(filmsByTati[0]);
return (
<div className="App">
<h1>Select Example</h1>
<select
value={selectedOption}
onChange={(e) => setSelectedOption(e.target.value)}
>
{options.map((option) => (
<option key={option} value={option}>
{option}
</option>
))}
</select>
<span>Selected option: {selectedOption}</span>
<select
value={selectedTatiFilm}
onChange={(e) =>
setSelectedTatiFilm(
filmsByTati.find(film => (film.id == e.target.value))
)
}
>
{filmsByTati.map((film) => (
<option key={film.id} value={film.id}>
{film.title}
</option>
))}
</select>
<span>Selected option: {selectedTatiFilm.title}</span>
</div>
);
}
Simply add as first option of your select tag:
<option disabled hidden value=''></option>
This will become default and when you'll select a valid option will be setted on your state
***Html:***
<div id="divContainer"></div>
var colors = [{ Name: 'Red' }, { Name: 'Green' }, { Name: 'Blue' }];
var selectedColor = 'Green';
ReactDOM.render(<Container></Container>, document.getElementById("divContainer"));
var Container = React.createClass({
render: function () {
return (
<div>
<DropDown data={colors} Selected={selectedColor}></DropDown>
</div>);
}
});
***Option 1:***
var DropDown = React.createClass(
{
render: function () {
var items = this.props.data;
return (
<select value={this.props.Selected}>
{
items.map(function (item) {
return <option value={item.Name }>{item.Name}</option>;
})
}
</select>);
}
});
***Option 2:***
var DropDown = React.createClass(
{
render: function () {
var items = this.props.data;
return (
<select>
{
items.map(function (item) {
return <option value={item.Name} selected={selectedItem == item.Name}>{item.Name}</option>;
})
}
</select>);
}
});
***Option 3:***
var DropDown = React.createClass(
{
render: function () {
var items = this.props.data;
return (
<select>
{
items.map(function (item) {
if (selectedItem == item.Name)
return <option value={item.Name } selected>{item.Name}</option>;
else
return <option value={item.Name }>{item.Name}</option>;
})
}
</select>);
}
});
Use defaultValue to preselect the values for Select.
<Select defaultValue={[{ value: category.published, label: 'Publish' }]} options={statusOptions} onChange={handleStatusChange} />
if you store objects in a state.
class Studentinformation extends Component
{
constructor(props)
{
super(props);
this.handlechange=this.handlechange.bind(this);
this.handleSubmit=this.handleSubmit.bind(this);
this.state={Studentinfo:{
Name:'',
Skill:'Java',
Address:''
}};
}
handlechange(event)
{
const name=event.target.name;
const value=event.target.value;
this.setState({ Studentinfo:
{
...this.state.Studentinfo,
[name]:[value]
}});
}
handleSubmit(event)
{
event.preventDefault();
}
render(){
return (
<div>
<form onSubmit={this.handleSubmit}>
<label>Name: <input type="text" name="Name" value={this.state.Studentinfo.Name} onChange={this.handlechange}></input></label>
<br/>
<label>Skills:
<select value={this.state.Studentinfo.Skill} name="Skill" onChange={this.handlechange}>
<option value="C++" >C++</option>
<option value="C#">C#</option>
<option value="Java">Java</option>
</select>
</label>
<br/>
<textarea value={this.state.Studentinfo.Address} onChange={this.handlechange}/>
<br/>
<input type="submit" value="Submit"></input>
</form>
</div>
);
}
}
I've had a problem with <select> tags not updating to the correct <option> when the state changes. My problem seemed to be that if you render twice in quick succession, the first time with no pre-selected <option> but the second time with one, then the <select> tag doesn't update on the second render, but stays on the default first .
I found a solution to this using refs. You need to get a reference to your <select> tag node (which might be nested in some component), and then manually update the value property on it, in the componentDidUpdate hook.
componentDidUpdate(){
let selectNode = React.findDOMNode(this.refs.selectingComponent.refs.selectTag);
selectNode.value = this.state.someValue;
}
Posting a similar answer for MULTISELECT / optgroups:
render() {
return(
<div>
<select defaultValue="1" onChange={(e) => this.props.changeHandler(e.target.value) }>
<option disabled="disabled" value="1" hidden="hidden">-- Select --</option>
<optgroup label="Group 1">
{options1}
</optgroup>
<optgroup label="Group 2">
{options2}
</optgroup>
</select>
</div>
)
}
I have a simple solution is following the HTML basic.
<input
type="select"
defaultValue=""
>
<option value="" disabled className="text-hide">Please select</option>
<option>value1</option>
<option>value1</option>
</input>
.text-hide is a bootstrap's class, if you not using bootstrap, here you are:
.text-hide {
font: 0/0 a;
color: transparent;
text-shadow: none;
background-color: transparent;
border: 0;
}
if you use Stateless then
const IndexPage =({states, selectedState}) => {
return(
<select id="states" defaultValue={selectedState} name="state">
{states.map(state=> (
<option value={state.id} key={state.id}>{state.name}</option>
))
}
</select>
)
}
I got around a similar issue by setting defaultProps:
ComponentName.defaultProps = {
propName: ''
}
<select value="this.props.propName" ...
So now I avoid errors on compilation if my prop does not exist until mounting.

Categories