import * as React from 'react'; import classNames from 'classnames'; import Text from '../text/Text'; import useChipContext from './useChipContext'; import ChipGroup from './ChipGroup'; export const SIZE: { M: 'm'; S: 's'; } = { M: 'm', S: 's', }; type ChipSizeType = 'm' | 's'; type StyleType = Partial< React.CSSProperties & { '--chipBorderColor'?: string; '--chipCheckedBorderColor'?: string; } >; const isCheckedWithinGroup = ( groupValue?: string | Array, value?: string ) => { if (!value) { return; } if (Array.isArray(groupValue)) { return groupValue.includes(value); } return groupValue === value; }; export type ChipPropsType = { children: React.ReactNode; /** * Sets whether the chip is checked or unchecked. * @example */ checked?: boolean; /** * Sets whether the Chip is multi select or single select. * @example */ multiSelect?: boolean; /** * Optional string. Additional classnames. */ className?: string | null | undefined; /** * Sets whether the Chip is disabled. * @example */ disabled?: boolean; /** * Sets whether the Chip is required. * @example */ required?: boolean; /** * Sets size. * @example * @default m */ size?: ChipSizeType; /** * The name of the chip group. * @example */ name?: string; /** * Style applied to the container. * @example */ style?: StyleType; /** * Value of the input. * @example */ value: string; /** * You can render icon inside the chip on the left side * @example } * > * Math * */ icon?: React.ReactNode; /** * Function called with an object containing the react synthetic event, whenever the state of the chip changes. */ onChange?: (arg0: React.SyntheticEvent) => void; 'aria-describedby'?: string; } & Omit< React.AllHTMLAttributes, | 'checked' | 'children' | 'size' | 'name' | 'onChange' | 'style' | 'value' | 'icon' >; const Chip = ({ children, className, value, style, name, disabled, size = 'm', multiSelect, checked, required, icon, onChange, 'aria-describedby': ariaDescribedBy, ...props }: ChipPropsType) => { const chipClass = classNames('sg-chip', `sg-chip--${size}`, className); const inputClass = classNames('sg-chip__input'); const chipGroupContext = useChipContext(); const isWithinChipGroup = Boolean( chipGroupContext && Object.keys(chipGroupContext).length ); const isCheckbox = multiSelect || chipGroupContext.multiSelect; const inputType = isCheckbox ? 'checkbox' : 'radio'; const groupName = isWithinChipGroup ? chipGroupContext.name : name; const isRequired = isWithinChipGroup ? chipGroupContext.required : required; const isDisabled = isWithinChipGroup ? chipGroupContext.disabled : disabled; const isControlled = checked !== undefined || isWithinChipGroup; const isChecked = isControlled ? // @ts-ignore TS2345 checked ?? isCheckedWithinGroup(chipGroupContext.groupValue, value) : undefined; // @ts-ignore TS7006 const onInputChange = e => { if (isWithinChipGroup) { chipGroupContext.onChipChange(e, value); } if (onChange) { onChange(e); } }; return ( ); }; Chip.Group = ChipGroup; export default Chip;