UNPKG

wix-style-react

Version:
155 lines (147 loc) 4.97 kB
import React from 'react'; import StatusAlertSmall from 'wix-ui-icons-common/StatusAlertSmall'; import LabelledElement from '../LabelledElement'; import Input from '../Input'; import Text from '../Text'; import PropTypes from 'prop-types'; import { classes } from './InputWithLabel.st.css'; import dataHooks from './dataHooks'; const getSuffixContainer = suffix => suffix.map((item, index) => { return ( <div data-hook={`suffix-container`} key={`suffix-container-${index}`} className={classes.groupIcon} > {item} </div> ); }); class InputWithLabel extends React.Component { static propTypes = { /** Sets a default value for those who want to use this component uncontrolled */ dataHook: PropTypes.string, /** Pass a component you want to show as the suffix of the input, e.g., text string, icon. */ suffix: PropTypes.arrayOf(PropTypes.element), /** Sets the field label */ label: PropTypes.string, /** Sets input value */ value: PropTypes.oneOfType([PropTypes.string, PropTypes.number]), /** Specifies the status of a field */ status: PropTypes.oneOf(['error', 'warning', 'loading']), /** Defines the message displayed when you hover over the status icon. If not given or empty there will be no tooltip. */ statusMessage: PropTypes.node, /** Defines a standard input onFocus callback */ onFocus: PropTypes.func, /** Defines a standard input onBlur callback */ onBlur: PropTypes.func, /** Defines a standard input onChange callback */ onChange: PropTypes.func, /** Reference element data when a form is submitted */ name: PropTypes.string, /** Specifies the type of `<input/>` element to display. Default is text string. */ type: PropTypes.string, /** Define a string that labels the current element in case where a text label is not visible on the screen */ ariaLabel: PropTypes.string, /** Focus the element on mount (standard React input autoFocus). */ autoFocus: PropTypes.bool, /** Sets the value of native autocomplete attribute (consult the [HTML spec](https://html.spec.whatwg.org/multipage/form-control-infrastructure.html#attr-fe-autocomplete) for possible values) */ autocomplete: PropTypes.string, /** Specifies whether the input should be disabled or not */ disabled: PropTypes.bool, /** Specifies a CSS class name to be appended to the component’s root element */ className: PropTypes.string, /** Sets the maximum number of characters that can be entered into a field */ maxLength: PropTypes.number, /** Sets a placeholder message to display */ placeholder: PropTypes.string, /** Render a custom input component instead of the default html input tag */ customInput: PropTypes.elementType ? PropTypes.oneOfType([ PropTypes.func, PropTypes.node, PropTypes.elementType, ]) : PropTypes.oneOfType([PropTypes.func, PropTypes.node]), }; static defaultProps = { statusMessage: '', }; render() { const { label, suffix, value, dataHook, status, statusMessage, onChange, onFocus, onBlur, name, type, ariaLabel, autoFocus, autocomplete, disabled, className, maxLength, placeholder, customInput, } = this.props; return ( <div data-hook={dataHook} className={status ? undefined : classes.statusMessagePlaceholder} > <LabelledElement value={value} label={label} dataHook={dataHooks.labelledElement} > <Input name={name} type={type} ariaLabel={ariaLabel} autoFocus={autoFocus} autocomplete={autocomplete} disabled={disabled} maxLength={maxLength} placeholder={placeholder} onChange={onChange} onFocus={onFocus} onBlur={onBlur} dataHook={dataHooks.input} className={className} size="large" value={value} suffix={suffix ? getSuffixContainer(suffix) : []} status={status} customInput={customInput} hideStatusSuffix /> </LabelledElement> {status === Input.StatusError && statusMessage && ( <Text skin="error" size="small" weight="normal" className={classes.statusMessage} > <span className={classes.statusMessageIcon}> <StatusAlertSmall /> </span> <span data-hook={dataHooks.errorMessage} className={classes.errorMessageContent} > {statusMessage} </span> </Text> )} </div> ); } } export default InputWithLabel;