I am working on a React project and I am using Material UI.
Versions:
├─ react#15.6.1
├─ material-ui#0.19.4
I have in my code a component that makes use of Select Field component.
My code looks something like this:
<SelectField some_props>
{some_list.map(() => {return <MenuItem other_props/>})}
</SelectField>
On a desktop, this looks very good. However, I would like to get the native mobile select. The rolling one.
Basically, this:
How do I get a mobile friendly rolling select with Material UI?
Thanks!
Here is an example component which uses react-device-detect. If the user isMobile, the native select/options are rendered.
import React from 'react';
import {isMobile} from 'react-device-detect';
import FormControl from '#material-ui/core/FormControl';
import InputLabel from '#material-ui/core/InputLabel';
import Select from '#material-ui/core/Select';
import MenuItem from '#material-ui/core/MenuItem';
const ExampleSelect = () => {
const value = null;
const onChange = (e) => console.log(e.target.value);
const options = [
{value: 1, label: 'Option 1'},
{value: 2, label: 'Option 2'},
{value: 3, label: 'Option 3'}
];
return (
<FormControl>
<InputLabel>
Options
</InputLabel>
<Select
native={isMobile}
value={value}
onChange={onChange}
>
{options.map(option => (
isMobile ? (
<option key={option.value} value={option.value}>{option.label}</option>
) : (
<MenuItem key={option.value} value={option.value}>{option.label}</MenuItem>
)
))}
</Select>
</FormControl>
)
}
export default ExampleSelect;
Related
I spend almost half day but can't not found any solution to customize the title of week day of Material-ui DateRangePicker. Instead of "S", "M",..., I want to show the title as I expected.
Already tried to custom the dateAdapter but this not helps.
I see that Material-ui has component called MuiPickersUtilsProvider which I can customize the day title as I want but this component not support date-range picker.
I would highly appreciate any advices. Here is my code so far:
import * as React from 'react';
import TextField from '#mui/material/TextField';
import AdapterDateFns from '#mui/lab/AdapterDateFns';
import LocalizationProvider from '#mui/lab/LocalizationProvider';
import Box from '#mui/material/Box';
import MobileDateRangePicker from '#mui/lab/MobileDateRangePicker';
export class CustomDateFns extends AdapterDateFns {
getWeekdays() {
return ['AA', 'BB', 'CC', 'DD', 'EE', 'FF', 'GG'];
}
}
export default function ResponsiveDateRangePicker() {
const [value, setValue] = React.useState([null, null]);
return (
<LocalizationProvider dateAdapter={CustomDateFns}>
<MobileDateRangePicker
inputFormat="dd/MM/yyyy"
startText="Start date"
endText="End date"
value={value}
onChange={(newValue) => {
setValue(newValue);
}}
clearable={!!value[0] && !!value[1] ? true : false}
clearText="Reset"
cancelText=""
okText="Confirm"
toolbarTitle=""
renderInput={(startProps, endProps) => (
<React.Fragment>
<TextField {...startProps} />
<Box sx={{ mx: 2 }}> to </Box>
<TextField {...endProps} />
</React.Fragment>
)}
/>
</LocalizationProvider>
);
}
Here is what current it shows:
What I expect is:
The only way I found until now is manipulating the DOM, then set innerHTML. But I don't think this is a good way because we can't control DOM as this is generated by library, not by me.
I have the following component:
import React from 'react';
import PropTypes from 'prop-types';
import IconButton from '#material-ui/core/IconButton';
import TextField from '#material-ui/core/TextField';
import ClearIcon from '#material-ui/icons/Clear';
const InputSearch = ({ onClearSearch, onSearch, ...searchProps }) => {
const { id, value } = searchProps;
const onClear = (event) => {
onClearSearch(event, id);
};
return (
<TextField
id={id}
name={id}
onChange={onSearch}
value={value}
InputProps={{
endAdornment: value && (
<IconButton
className={classes.searchIcon}
onClick={onClear}
>
<ClearIcon fontSize={'small'} color={'primary'} />
</IconButton>
),
}}
/>
);
};
InputSearch.propTypes = {
onClearSearch: PropTypes.func.isRequired,
};
export default InputSearch;
As you can see, I'm trying to apply a required validation using propTypes. But then, when I try to use the component without the onClearSearch function, no error is being shown:
<InputSearch
value={searchBy}
onSearch={handleSearch}
/>
So what I'm doing wrong?
Your code is right... you can open developer tool of chrome by pressing F12 -> go to Console and you can see prop type error
for more detail you can see
https://blog.logrocket.com/validating-react-component-props-with-prop-types-ef14b29963fc/
If you want your project give prop-type error in terminal then you have to setup eslint in your project.
Below is the sample code, This sample working fine in all other browsers, except IE11. This dropdown closes immediately once after it clicked. The dropdown list does not show up.
import React, { useState } from "react";
import MultiSelect from "react-multi-select-component";
const Example: React.FC = () => {
const options = [{ label:"grpes", value: "grapes" },{ label:"mango",value: "mango" }];
const [selected, setSelected] = useState([]);
return (
<div>
<h1>Select Fruits</h1>
<pre>{JSON.stringify(selected)}</pre>
<MultiSelect
options={options}
value={selected}
onChange={setSelected}
labelledBy={"Select"}
/>
</div>
);
};
export default Example;
Since the react-multi-select-component dropdown is not compatible with IE I've used the below dropdown which has similar features as react-multi-select-component.
Component name : react-multiselect-checkboxes
https://www.npmjs.com/package/react-multiselect-checkboxes
I need to set multi selected value to autocomplete in reactjs. I'm using Material-UI components in my project.
F.e you can see above. First data is coming first user and second data is coming from another user. I want to fill in the value like that. Then, user can remove selected values or add new values.
If you can do it with dummy data, I can use with data from database. All i need how to do this.
import React from 'react';
import Chip from '#material-ui/core/Chip';
import Autocomplete from '#material-ui/lab/Autocomplete';
import { makeStyles } from '#material-ui/core/styles';
import TextField from '#material-ui/core/TextField';
const useStyles = makeStyles((theme) => ({
root: {
width: 500,
'& > * + *': {
marginTop: theme.spacing(3),
},
},
}));
export default function Multi({callbackFromMultiSelect,reference,favBooks}) {
const classes = useStyles();
return (
<div className={classes.root}>
<Autocomplete
multiple
id="tags-standard"
options={favBooks}
getOptionLabel={(option) => (option.name)}
// onClick={()=>alert('test')}
onChange={(event, value) =>callbackFromMultiSelect({value:value,reference:reference})}
// defaultValue={[top100Films[1]]}
renderInput={(params) => (
<TextField
{...params}
variant="standard"
label="favBooks"
placeholder="favBooks"
/>
)}
/>
</div>
);
}
And my parent component
import React from 'react'
import AutoCompleteTest from './AutoComplete'
export const Test = () => {
const callbackFromMultiSelect = (item) => {
console.log(item)
}
const favBooks=[
{name:"LOTR",from:"a",to:"a"},
{name:"GOT",from:"b",to:"b"},
{name:"HP",from:"c",to:"c"}
]
return (
<div className={'mainStore'}>
Test
<AutoCompleteTest callbackFromMultiSelect={callbackFromMultiSelect} reference={'test'} favBooks={favBooks}/>
<br />
<AutoCompleteTest callbackFromMultiSelect={callbackFromMultiSelect} reference={'test'} favBooks={favBooks}/>
</div>
)
}
I've made a codesandbox
https://codesandbox.io/s/wizardly-saha-gor3s?file=/src/App.js
You basicly have to make the component a controlled component.
https://material-ui.com/components/autocomplete/#playground
You can do this by using the 'getOptionSelected' prop
Following are the URL for the codesandbox for the react select menu item.
React select menu item
Here I am wrapping the menu item with div and change the values of select drop down but the values are not populating into the select drop down on change.
How to give runtime values to select dropdown on onChange event.
Could some one let me know the idea solutions for this?
Thanks
Is this what you wanted?
import React from "react";
import { makeStyles } from "#material-ui/core/styles";
import InputLabel from "#material-ui/core/InputLabel";
import MenuItem from "#material-ui/core/MenuItem";
import FormControl from "#material-ui/core/FormControl";
import Select from "#material-ui/core/Select";
const useStyles = makeStyles(theme => ({
formControl: {
margin: theme.spacing(1),
minWidth: 120
},
selectEmpty: {
marginTop: theme.spacing(2)
}
}));
export default function SimpleSelect() {
const classes = useStyles();
const [age, setAge] = React.useState(10);
const handleChange = event => {
setAge(event.target.value);
};
return (
<div>
<FormControl className={classes.formControl}>
<InputLabel id="demo-simple-select-label">Age</InputLabel>
<Select
labelId="demo-simple-select-label"
id="demo-simple-select"
value={age}
onChange={handleChange}
>
<MenuItem value={10}>Ten</MenuItem>
<MenuItem value={20}>Twenty</MenuItem>
<MenuItem value={30}>Thirty</MenuItem>
</Select>
</FormControl>
</div>
);
}
component needs directly as a child. Or else it wont populate. If you want to use a div then you can replace div with fragments. But I don't think we can style a fragment.
You need to provide a default value to the state.
Link to codesandbox which is working fine and I think its exactly what you wanted
Just let me know if this was what you wanted or if I'm missing anything.