1
0
mirror of https://github.com/checktheroads/hyperglass synced 2024-05-11 05:55:08 +00:00
Files
checktheroads-hyperglass/hyperglass/ui/components/select/select.tsx
2021-01-03 23:51:09 -07:00

83 lines
2.4 KiB
TypeScript

import { createContext, useContext, useMemo } from 'react';
import ReactSelect from 'react-select';
import { chakra, useDisclosure } from '@chakra-ui/react';
import { useColorMode } from '~/context';
import {
useRSTheme,
useMenuStyle,
useMenuPortal,
useOptionStyle,
useControlStyle,
useMenuListStyle,
useMultiValueStyle,
usePlaceholderStyle,
useSingleValueStyle,
useMultiValueLabelStyle,
useMultiValueRemoveStyle,
useIndicatorSeparatorStyle,
} from './styles';
import type { TSelectOption } from '~/types';
import type { TSelectBase, TSelectContext, TReactSelectChakra } from './types';
const SelectContext = createContext<TSelectContext>(Object());
export const useSelectContext = (): TSelectContext => useContext(SelectContext);
const ReactSelectChakra = chakra<typeof ReactSelect, TReactSelectChakra>(ReactSelect);
export const Select: React.FC<TSelectBase> = (props: TSelectBase) => {
const { options, multi, onSelect, isError = false, ...rest } = props;
const { isOpen, onOpen, onClose } = useDisclosure();
const { colorMode } = useColorMode();
const selectContext = useMemo<TSelectContext>(() => ({ colorMode, isOpen, isError }), [
colorMode,
isError,
isOpen,
]);
const defaultOnChange = (changed: TSelectOption | TSelectOption[]) => {
if (!Array.isArray(changed)) {
changed = [changed];
}
if (typeof onSelect === 'function') {
onSelect(changed);
}
};
const multiValue = useMultiValueStyle({ colorMode });
const multiValueLabel = useMultiValueLabelStyle({ colorMode });
const multiValueRemove = useMultiValueRemoveStyle({ colorMode });
const menuPortal = useMenuPortal();
const rsTheme = useRSTheme();
return (
<SelectContext.Provider value={selectContext}>
<ReactSelectChakra
onChange={defaultOnChange}
onMenuClose={onClose}
onMenuOpen={onOpen}
isClearable={true}
options={options}
isMulti={multi}
theme={rsTheme}
styles={{
menuPortal,
multiValue,
multiValueLabel,
multiValueRemove,
menu: useMenuStyle,
option: useOptionStyle,
control: useControlStyle,
menuList: useMenuListStyle,
singleValue: useSingleValueStyle,
placeholder: usePlaceholderStyle,
indicatorSeparator: useIndicatorSeparatorStyle,
}}
{...rest}
/>
</SelectContext.Provider>
);
};