1
0
mirror of synced 2025-12-23 21:07:12 -05:00
Files
docs/components/ui/Picker/Picker.tsx
Grace Park 124f54eb0c Accessibility changes for Nav Menu (#24099)
* updating to nav landmark

* support keyboard esc to close mobile menu

* update to ChevronDown to remove nested div
2022-01-06 17:34:19 +00:00

86 lines
2.3 KiB
TypeScript

import { ReactNode } from 'react'
import cx from 'classnames'
import { useTranslation } from 'components/hooks/useTranslation'
import { Details, useDetails, Text, Dropdown, Box } from '@primer/components'
import { ChevronDownIcon } from '@primer/octicons-react'
export type PickerOptionsTypeT = {
text: string
item: ReactNode
selected?: boolean
}
export type PickerPropsT = {
variant?: 'inline'
defaultText: string
options: Array<PickerOptionsTypeT>
}
type PickerWrapperPropsT = {
variant?: 'inline'
children: ReactNode
}
function PickerSummaryWrapper({ variant, children }: PickerWrapperPropsT) {
if (variant === 'inline') {
return (
<div className="d-flex flex-items-center flex-justify-between">
{children}
<ChevronDownIcon size={24} className="arrow ml-md-1" />
</div>
)
}
return (
<>
{children}
<ChevronDownIcon size={16} className="arrow ml-md-1" />
</>
)
}
function PickerOptionsWrapper({ variant, children }: PickerWrapperPropsT) {
if (variant === 'inline') {
return <Box py="2">{children}</Box>
}
return (
<Dropdown.Menu direction="sw" style={{ width: 'unset' }}>
{children}
</Dropdown.Menu>
)
}
export function Picker({ variant, defaultText, options, ...restProps }: PickerPropsT) {
const { getDetailsProps, setOpen } = useDetails({ closeOnOutsideClick: true })
const selectedOption = options.find((option) => option.selected)
const { t } = useTranslation(['picker', 'toggle_picker_list'])
return (
<Details
{...getDetailsProps()}
className={cx(
'position-relative details-reset',
variant === 'inline' ? 'd-block' : 'd-inline-block'
)}
{...restProps}
>
<summary
className="d-block btn btn-invisible color-fg-default"
aria-haspopup="true"
aria-label={t('toggle_picker_list')}
>
<PickerSummaryWrapper variant={variant}>
<Text>{selectedOption?.text || defaultText}</Text>
</PickerSummaryWrapper>
</summary>
<PickerOptionsWrapper variant={variant}>
{options.map((option) => (
<Dropdown.Item onClick={() => setOpen(false)} key={option.text}>
{option.item}
</Dropdown.Item>
))}
</PickerOptionsWrapper>
</Details>
)
}