UNPKG

@hackplan/polaris

Version:

Shopify’s product component library

70 lines (69 loc) 3.17 kB
import React from 'react'; import { MinusMinor, TickSmallMinor } from '@shopify/polaris-icons'; import { createUniqueIDFactory } from '@shopify/javascript-utilities/other'; import { classNames } from '../../utilities/css'; import { withAppProvider } from '../AppProvider'; import Choice, { helpTextID } from '../Choice'; import Icon from '../Icon'; import { Key } from '../../types'; import styles from './Checkbox.scss'; const getUniqueID = createUniqueIDFactory('Checkbox'); class Checkbox extends React.PureComponent { constructor() { super(...arguments); this.inputNode = React.createRef(); this.handleInput = () => { const { onChange, id, disabled } = this.props; if (onChange == null || this.inputNode.current == null || disabled) { return; } onChange(!this.inputNode.current.checked, id); this.inputNode.current.focus(); }; this.handleKeyUp = (event) => { const { keyCode } = event; if (keyCode !== Key.Space) return; this.handleInput(); }; } render() { const { id = getUniqueID(), label, labelHidden, helpText, checked = false, error, disabled, onFocus, onBlur, name, value, } = this.props; const describedBy = []; if (error) { describedBy.push(`${id}Error`); } if (helpText) { describedBy.push(helpTextID(id)); } const ariaDescribedBy = describedBy.length ? describedBy.join(' ') : undefined; const wrapperClassName = classNames(styles.Checkbox, error && styles.error); const isIndeterminate = checked === 'indeterminate'; const isChecked = !isIndeterminate && Boolean(checked); const indeterminateAttributes = isIndeterminate ? { indeterminate: 'true', 'aria-checked': 'mixed' } : { 'aria-checked': isChecked }; const iconSource = isIndeterminate ? MinusMinor : TickSmallMinor; const inputClassName = classNames(styles.Input, isIndeterminate && styles['Input-indeterminate']); return ( /* eslint-disable jsx-a11y/no-redundant-roles */ <Choice id={id} label={label} labelHidden={labelHidden} helpText={helpText} error={error} disabled={disabled} onClick={this.handleInput}> <span className={wrapperClassName}> <input onKeyUp={this.handleKeyUp} ref={this.inputNode} id={id} name={name} value={value} type="checkbox" checked={isChecked} disabled={disabled} className={inputClassName} onFocus={onFocus} onBlur={onBlur} onClick={stopPropagation} onChange={noop} aria-invalid={error != null} aria-describedby={ariaDescribedBy} role="checkbox" {...indeterminateAttributes}/> <span className={styles.Backdrop}/> <span className={styles.Icon}> <Icon source={iconSource}/> </span> </span> </Choice> /* eslint-enable jsx-a11y/no-redundant-roles */ ); } } function noop() { } function stopPropagation(event) { event.stopPropagation(); } export default withAppProvider()(Checkbox);