Created
November 18, 2019 21:10
-
-
Save saaage/25c9170b9faebfb85a4dd732ac0c7c5a to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { useState, useEffect, useRef } from 'react' | |
import get from 'lodash.get' | |
import { array, bool, func } from 'prop-types' | |
import Autocomplete from '@material-ui/lab/Autocomplete' | |
import Button from '@material-ui/core/Button' | |
import FormGroup from '@material-ui/core/FormGroup' | |
import FormLabel from '@material-ui/core/FormLabel' | |
import FormHelperText from '@material-ui/core/FormHelperText' | |
import TextField from '@material-ui/core/TextField' | |
import { contains, compareUsingKey, isEmpty } from 'utils' | |
import { Space } from 'shared/components' | |
import { useQuery } from 'react-apollo' | |
import { Container } from 'shared/components' | |
import CircularProgress from '@material-ui/core/CircularProgress' | |
import { useConceptLocations } from 'shared/hooks' | |
import GET_CATEGORY from 'pages/menu/graphql/queries/getCategory' | |
const AddSelections = ({ | |
setSelections, | |
categoryId, | |
owner, | |
ignore, | |
batchUpdate | |
}) => { | |
const { | |
loading: categoryLoading, | |
error: categoryError, | |
data: categoryData | |
} = useQuery(GET_CATEGORY, { | |
variables: { | |
categoryId: categoryId, | |
conceptLocationsFilter: useConceptLocations().filter, | |
recursiveChildCategories: true, | |
recursiveElements: true | |
} | |
}) | |
const [values, setValues] = useState([]) | |
const clearValues = () => setValues([]) | |
const ignoreRef = useRef(null) | |
useEffect(() => { | |
if (ignoreRef.current !== ignore) { | |
ignoreRef.current = ignore | |
clearValues() | |
} | |
}) | |
if (categoryError) throw new Error(categoryError) | |
if (categoryLoading || !categoryData) | |
return ( | |
<Container display="flex" justifyContent="center"> | |
<CircularProgress /> | |
</Container> | |
) | |
const category = get(categoryData, 'category', null) | |
const options = get(category, 'elements', []) | |
// re-render form whenever we get a new `ignore` prop | |
return ( | |
<FormGroup key={ignore}> | |
<FormLabel>Selections</FormLabel> | |
<FormHelperText> | |
The valid selections from {category.displayName} when ordering within | |
the context of {owner.displayName}. | |
</FormHelperText> | |
<Space value="one-and-half" /> | |
<Container display="flex" alignItems="center"> | |
<Container flex="1"> | |
<Autocomplete | |
disableCloseOnSelect | |
getOptionLabel={s => s.displayName} | |
multiple | |
onChange={(_, v) => { | |
batchUpdate ? setValues(v) : setSelections(v) | |
}} | |
options={options | |
.filter( | |
o => | |
!contains(ignore, o.elementId, i => | |
get(i, 'element.elementId') | |
) | |
) | |
.sort((a, b) => compareUsingKey(a, b, 'displayName'))} | |
renderInput={params => ( | |
<TextField | |
{...params} | |
fullWidth | |
variant="outlined" | |
label="add selections" | |
/> | |
)} | |
/> | |
</Container> | |
{batchUpdate && ( | |
<Container display="flex" alignItems="center"> | |
<Space value="one" direction="x" /> | |
<Button | |
disabled={isEmpty(values)} | |
onClick={() => { setSelections(values) }} | |
> | |
add | |
</Button> | |
</Container> | |
)} | |
</Container> | |
</FormGroup> | |
) | |
} | |
AddSelections.propTypes = { | |
// An array of selections to ignore | |
ignore: array, | |
// Function to call with current values | |
setSelections: func.isRequired, | |
// Should we add a confirm Button which calls `setSelections`? | |
batchUpdate: bool | |
} | |
AddSelections.defaultProps = { | |
ignore: [] | |
} | |
export default AddSelections |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment