17928: Adds storage classes checkboxes to collection create dialog.
[arvados-workbench2.git] / src / components / checkbox-field / checkbox-field.tsx
1 // Copyright (C) The Arvados Authors. All rights reserved.
2 //
3 // SPDX-License-Identifier: AGPL-3.0
4
5 import React from 'react';
6 import { WrappedFieldProps } from 'redux-form';
7 import {
8     FormControlLabel,
9     Checkbox,
10     FormControl,
11     FormGroup,
12     FormLabel,
13     FormHelperText
14 } from '@material-ui/core';
15
16 export const CheckboxField = (props: WrappedFieldProps & { label?: string }) =>
17     <FormControlLabel
18         control={
19             <Checkbox
20                 checked={props.input.value}
21                 onChange={props.input.onChange}
22                 disabled={props.meta.submitting}
23                 color="primary" />
24         }
25         label={props.label}
26     />;
27
28 type MultiCheckboxFieldProps = {
29     items: string[];
30     defaultValues?: string[];
31     label?: string;
32     minSelection?: number;
33     maxSelection?: number;
34     helperText?: string;
35     rowLayout?: boolean;
36 }
37
38 export const MultiCheckboxField = (props: WrappedFieldProps & MultiCheckboxFieldProps) => {
39     const isValid = (items: string[]) => (items.length >= (props.minSelection || 0)) &&
40         (items.length <= (props.maxSelection || items.length));
41     if (props.input.value.length === 0 && (props.defaultValues || []).length !== 0) {
42         props.input.value = props.defaultValues ? [...props.defaultValues] : [];
43     }
44     return <FormControl error={!isValid(props.input.value)}>
45         <FormLabel component='label'>{props.label}</FormLabel>
46         <FormGroup row={props.rowLayout}>
47         { props.items.map((item, idx) =>
48             <FormControlLabel
49                 key={`label-${idx}`}
50                 control={
51                     <Checkbox
52                         data-cy={`checkbox-${item}`}
53                         key={`control-${idx}`}
54                         name={`${props.input.name}[${idx}]`}
55                         value={item}
56                         checked={
57                             props.input.value.indexOf(item) !== -1 ||
58                             (props.input.value.length === 0 &&
59                                 (props.defaultValues || []).indexOf(item) !== -1)
60                         }
61                         onChange={e => {
62                             const newValue = [...props.input.value];
63                             if (e.target.checked) {
64                                 newValue.push(item);
65                             } else {
66                                 newValue.splice(newValue.indexOf(item), 1);
67                             }
68                             if (!isValid(newValue)) { return; }
69                             return props.input.onChange(newValue);
70                         }}
71                         disabled={props.meta.submitting}
72                         color="primary" />
73                 }
74                 label={item} />) }
75         </FormGroup>
76         <FormHelperText>{props.helperText}</FormHelperText>
77     </FormControl> };