Combining MUI’s Autocomplete component with customized features
https://mui.com/material-ui/react-autocomplete/

<Autocomplete
sx={{
width: '100%',
'& input': {
width: '100%',
bgcolor: 'background.paper',
color: theme =>
theme.palette.getContrastText(
theme.palette.background.paper,
),
},
}}
options={suggestedLocations}
onChange={(
event: React.SyntheticEvent<Element, Event>,
feature: MapboxFeature,
) => {
setFormCoordinates(feature.geometry.coordinates);
setPreviewLocation(feature.place_name);
}}
inputValue={formLocation}
onInputChange={(event: any, newInputValue: string) => {
setFormLocation(newInputValue);
}}
id="location-suggestion-input"
getOptionLabel={(feature: MapboxFeature) =>
`${feature.place_name}`
}
filterOptions={(options, state) => options}
freeSolo
loading={!!formLocation}
loadingText={
<div className="text-primary-accent-color">
<LinearProgress color="inherit" />
</div>
}
renderInput={params => (
<div ref={params.InputProps.ref}>
<input
type="text"
{...params.inputProps}
className="form-control"
required
placeholder="Start typing to search..."
/>
<Form.Control.Feedback type="valid">
Looks good!
</Form.Control.Feedback>
<Form.Control.Feedback type="invalid">
Location is required!
</Form.Control.Feedback>
</div>
)}
/>
Notes:
freeSolo: If true, the Autocomplete is free solo, meaning that the user input is not bound to provided options.filterOptions: get all the options without filteringloading and loadingText: condition to display UI for the loading staterenderInput: render a custom input, using Bootstrap stylings// Autocomplete Location Search
useEffect(() => {
if (!formLocation) {
setSuggestedLocations([]);
setFormCoordinates([]);
return;
}
// wait 0.5s before querying feature (location) data from mapbox
const queryLocationTimeOut = setTimeout(() => {
ogAxios
.get(
`https://api.mapbox.com/geocoding/v5/mapbox.places/${formLocation}.json?access_token=${
import.meta.env.VITE_MAPBOX_ACCESS_TOKEN
}`,
)
.then(res => {
const features: MapboxFeature[] = res.data.features;
setSuggestedLocations(features);
})
.catch(err => {
appContext.setSnackbar(
true,
"Error: Couldn't query location data from mapbox",
'error',
);
});
}, 500);
return () => clearTimeout(queryLocationTimeOut);
}, [formLocation]);