Chakra-React-Select

This contains the[`chakra-react-select`](https://github.com/csandman/chakra-react-select#chakra-react-select), a wrapper for the popular react component [react-select](https://react-select.com/home) made using the UI library Chakra UI. It is customized with the Tidal design components, but full documentation can be found https://github.com/csandman/chakra-react-select#chakra-react-select.

    View Source@fluidtruck/core

This contains thechakra-react-select, a wrapper for the popular react component react-select made using the UI library Chakra UI. It is customized with the Tidal design components, but full documentation can be found https://github.com/csandman/chakra-react-select#chakra-react-select

For complete documentation, please refer to thechakra-react-select repo.

Thank-you @csandman for creating this wrapper and the great documentation.

CodeSandbox Examples:#

TypeScript: https://codesandbox.io/s/chakra-react-select-chakrastyles-5yh6q?file=/app.tsx

TypeScript: https://codesandbox.io/s/chakra-react-select-styled-like-a-default-chakra-select-qwq3o?file=/app.tsx

Import#

import {
ChakraReactSelect,
CreatableSelect,
AsyncCreatableSelect,
AsyncSelect,
} from '@fluidtruck/core'
  • ChakraReactSelect: react-select composed of chakra-ui components. The selectComponents are the customized components overriding react-select default components. This ChakraReactSelect component takes the Menu component theme file as part of it's component styles.. The tidalSelectComponents are the Tidal customized components overriding chakra-react-select default chakraComponents, Specifically the DropdownIndicator. Both are export and can be used as needed for customizing.
import {
ChakraReactSelect,
CreatableSelect,
AsyncCreatableSelect,
AsyncSelect,
selectComponents,
tidalSelectComponents,
} from '@fluidtruck/core'

Usage#

const options = [
{ label: 'Green', value: 'green', colorScheme: 'green' },
{ label: 'Green-Yellow', value: 'greenyellow' },
{ label: 'Red', value: 'red' },
{ label: 'Violet', value: 'violet' },
{ label: 'Forest', value: 'forest' },
{ label: 'Tangerine', value: 'tangerine' },
{ label: 'Blush', value: 'blush' },
{ label: 'Purple', value: 'purple' },
]
function SelectUsage() {
const [state, setState] = React.useState()
const [inputState, setInputState] = React.useState('')
handleState = (value) => setState(value.value)
return (
<HStack spacing={6}>
<FormControl>
<FormLabel>Color Palette</FormLabel>
<ChakraReactSelect
isMulti
closeMenuOnSelect={false}
defaultMenuIsOpen
defaultValue={options[0]}
options={options}
id="colorsOne"
onChange={handleState}
/>
<chakra.p py={4}>
<b>State:</b> {state}
</chakra.p>
</FormControl>
</HStack>
)
}
render(<SelectUsage />)

Custom Components & Styling#

const iconStyle = {
mr: 2,
w: 8,
h: 'auto',
}
const options = [
{
label: 'Purple',
value: 'purple, blue',
colorScheme: 'purple'
},
{
label: 'Yellow',
value: 'gold, yellow',
colorScheme: 'yellow'
},
{
label: 'Pink',
value: 'pink, red',
colorScheme: 'pink'
},
{
label: 'Forest',
value: 'green, forest',
colorScheme: 'green'
},
{
label: 'Sand',
value: 'brown, sand, dirt',
colorScheme: 'red'
},
{
label: 'Candy',
value: 'candy, pink',
colorScheme: 'pink'
},
{
label: 'Sky',
value: 'sky, blue',
colorScheme: 'blue'
},
]
const components = {
Option: ({
children,
...props
}) => (
<selectComponents.Option {...props}>
<Flex flexDir="column">
<Flex>{children}</Flex>
<Text fontSize="xs">{props.data.label}</Text>
</Flex>
</selectComponents.Option>
),
Menu: ({ children, ...props }) => (
<selectComponents.Menu {...props}>
<Box sx={{
bgColor: 'white',
color: 'black',
shadow: 'base',
'> *': {
shadow: 'base',
}
}}
>
{children}
</Box>
</selectComponents.Menu>
),
ValueContainer: ({ children, ...props }) => (
<selectComponents.ValueContainer {...props}>
<Flex px={2} align="center" gap={2}>
<SearchIcon color="fluidBlue" /> {children}
</Flex>
</selectComponents.ValueContainer>
),
MultiValueContainer: ({ children, ...props }) => (
<selectComponents.MultiValueContainer {...props}>
{children}
</selectComponents.MultiValueContainer>
),
};
const filterOptions = (inputValue) => {
return options.filter((i) =>
i.value.includes(inputValue.toLowerCase())
)
};
const promiseOptions = (inputValue) =>
new Promise((resolve) => {
setTimeout(() => {
resolve(filterOptions(inputValue));
}, 1000);
});
function SelectUsage() {
const [state, setState] = React.useState()
const [inputState, setInputState] = React.useState('')
handleState = (value) => setState(value.value)
return (
<HStack spacing={6}>
<FormControl>
<FormLabel>Color Palette</FormLabel>
<AsyncCreatableSelect
isMulti
defaultMenuIsOpen
closeMenuOnSelect={false}
defaultValue={options[0].value}
loadOptions={promiseOptions}
id="bank"
onChange={handleState}
components={{
...tidalSelectComponents,
...components
}}
/>
</FormControl>
</HStack>
)
}
render(<SelectUsage />)

Custom Components & Styling#

Notice the ...selectComponents, this must be passed if overriding any components.

const iconStyle = {
mr: 2,
w: 8,
h: 'auto',
}
const options = [
{
label: 'Visa 2300',
value: '2300',
icon: <Icon as={CardVisaIcon} {...iconStyle} />
},
{
label: 'Discover 7657',
value: '7657',
icon: <Icon as={CardDiscoverIcon} {...iconStyle} />
},
{
label: 'Amex 4775',
value: '4775',
icon: <Icon as={CardAmexIcon} {...iconStyle} />
},
{
label: 'CC 5535',
value: '5535',
icon: <Icon as={CardGenericIcon} {...iconStyle} />
},
]
const Option = ({ children, ...props }) => (
<selectComponents.Option {...props}>
<Flex justifyContent="center">
{props.data.icon} {children}
</Flex>
</selectComponents.Option>
);
const SingleValue = ({ children, ...props }) => (
<selectComponents.SingleValue pl={0} {...props}>
<Flex
sx={{ '& > .chakra-icon': { color: 'fluidBlue' } }}
>
{props.data.icon} {children}
</Flex>
</selectComponents.SingleValue>
);
function SelectUsage() {
const [state, setState] = React.useState()
const [inputState, setInputState] = React.useState('')
handleState = (value) => setState(value.value)
return (
<HStack spacing={6}>
<FormControl>
<FormLabel>Color Palette</FormLabel>
<ChakraReactSelect
defaultValue={options[0].value}
options={options}
id="bank"
onChange={handleState}
components={{
Option,
SingleValue,
}}
/>
</FormControl>
</HStack>
)
}
render(<SelectUsage />)

chakraStyleProps: Custom style props#

In case one of the variants is not the design you need, you can override any component you need.

Please Refer to the default variants.tsx file in the src code.

Full Documentation

chakraStyles#

  • NOTE: this overrides the default styles declared in the variants.ts file. It will fallback to the Menu's theme styles.
  • you can access the variants by importing selectVariants, which contains the default menuBase and variantOutline.
  • import { selectVariants } from '@fluidtruck/core'
  • (provided: SystemStyleObject) -- The component's default Chakra styles
  • (state: Object) -- The component's current state e.g. isFocused (this gives all of the same props that are passed into the component)
  • returns a SystemStyleObject -- An output style object which is forwarded to the component's sx prop
const options = [
{ label: 'Violet', value: 'violet' },
{ label: 'Forest', value: 'forest' },
{ label: 'Tangerine', value: 'tangerine' },
{ label: 'Blush', value: 'blush' },
{ label: 'Purple', value: 'purple' },
]
function SelectUsage() {
const [state, setState] = React.useState()
handleState = (value) => setState(value.value)
const styles = {
multiValue: (provided) => ({
...provided,
bgColor: 'blue.500',
color: 'white',
}),
input: (provided) => ({
...provided,
color: 'blue.600',
fontSize: 'lg',
fontWeight: 'bold',
}),
singleValue: (provided) => ({
...provided,
color: 'blue.600',
fontSize: 'lg',
fontWeight: 'bold',
}),
placeholder: (provided) => ({
...provided,
color: 'blue.600',
fontSize: 'lg',
fontWeight: 'bold',
}),
dropdownIndicator: (provided) => ({
...provided,
color: 'blue.600',
}),
control: (provided) => ({
...provided,
bg: 'transparent',
borderColor: 'blue.600'
}),
valueContainer: (provided) => ({
...provided,
paddingStart: 1,
paddingEnd: 1,
}),
...selectVariants.menuBase,
}
return (
<HStack padding={4} spacing={6}>
<FormControl>
<FormLabel color="blue.800">Color Palette</FormLabel>
<ChakraReactSelect
isMulti
defaultValue={options[0].value}
options={options}
id="custom-styles"
onChange={handleState}
chakraStyles={styles}
variant="default"
/>
</FormControl>
</HStack>
)
}
render(<SelectUsage />)

Variants#

Pass the variant: string - default, outline, & dark

  • default actually is rendered from the Menu component theme file
  • dark is actually on a transparent background, meant for dark-mode.
  • if you would like to create a new variant, add the new variant zobject styles to the variants file.
const options = [
{ label: 'Violet', value: 'violet' },
{ label: 'Forest', value: 'forest' },
{ label: 'Tangerine', value: 'tangerine' },
{ label: 'Blush', value: 'blush' },
]
function SelectUsage() {
const [state, setState] = React.useState()
const [inputState, setInputState] = React.useState('')
handleState = (value) => setState(value.value)
return (
<Grid gap={4}>
<HStack spacing={6}>
<FormControl>
<FormLabel>Default</FormLabel>
<ChakraReactSelect
defaultValue={options[0].value}
options={options}
id="default-light"
onChange={handleState}
/>
</FormControl>
</HStack>
<HStack spacing={6}>
<FormControl>
<FormLabel>Outline</FormLabel>
<ChakraReactSelect
defaultValue={options[0].value}
options={options}
id="outline-variant"
onChange={handleState}
variant="outline"
/>
</FormControl>
</HStack>
<HStack spacing={6}>
<FormControl>
<FormLabel>Dark BG</FormLabel>
<Box bgColor="blue.700" py={3}>
<ChakraReactSelect
defaultValue={options[0].value}
options={options}
id="outline-variant"
onChange={handleState}
variant="dark"
/>
</Box>
</FormControl>
</HStack>
</Grid>
)
}
render(<SelectUsage />)

AsycSelect, MulitValue Select and CreatableSelect#

const options = [
{ label: 'Green', value: 'green', colorScheme: 'green' },
{ label: 'Green-Yellow', value: 'greenyellow', colorScheme: 'yellow' },
{ label: 'Red', value: 'red', colorScheme: 'red' },
{ label: 'Violet', value: 'violet', colorScheme: 'purple' },
{ label: 'Forest', value: 'forest', colorScheme: 'green' },
{ label: 'Tangerine', value: 'tangerine', colorScheme: 'orange' },
{ label: 'Blush', value: 'blush', colorScheme: 'pink' },
{ label: 'Purple', value: 'purple', colorScheme: 'purple' },
]
function SelectUsage() {
const [stateOne, setStateOne] = React.useState()
const [stateTwo, setStateTwo] = React.useState()
const [stateThree, setStateThree] = React.useState()
handleStateOne = (value) => setStateOne(value.value)
handleStateTwo = (value) => setStateTwo(value.value)
handleStateThree = (value) => setStateThree(value.value)
const filterColors = (inputValue) => {
return options.filter((i) =>
i.label.toLowerCase().includes(inputValue.toLowerCase())
);
};
const promiseOptions = (inputValue) =>
new Promise((resolve) => {
setTimeout(() => {
resolve(filterColors(inputValue));
}, 1000);
});
return (
<Grid gap={6}>
<FormControl>
<FormLabel>AsyncSelect</FormLabel>
<AsyncSelect
loadOptions={promiseOptions}
onChange={handleStateOne}
/>
</FormControl>
<FormControl>
<FormLabel>CreateableSelect</FormLabel>
<CreatableSelect
options={options}
onChange={handleStateTwo}
closeMenuOnSelect={false}
/>
</FormControl>
<FormControl>
<FormLabel>MulitValue Select</FormLabel>
<ChakraReactSelect
isMulti
options={options}
onChange={handleStateThree}
// overrides the the variants style in variants.ts
// will fallback on the menu.ts styles in the theme
chakraStyles={{
...selectVariants.menuBase,
multiValue: (provided) => ({ ...provided })
}}
/>
</FormControl>
</Grid>
)
}
render(<SelectUsage />)