UNPKG

wix-style-react

Version:
145 lines (129 loc) 4.22 kB
import React from 'react'; import PropTypes from 'prop-types'; import Heading from '../Heading'; import Input from '../Input/Input'; import { st, classes } from './EditableTitle.st.css'; import { WixStyleReactContext } from '../WixStyleReactProvider/context'; import { dataHooks } from './constants'; const DEFAULT_MAX_LENGTH = 100; class EditableTitle extends React.Component { constructor(props) { super(props); this.state = { focus: false, value: props.initialValue || '', }; } componentDidMount() { if (this.props.autoFocus) this.onFocus(); } onChange = e => { this.setState({ value: e.target.value }); }; showPlaceholder = () => !this.state.value && this.props.defaultValue; onFocus = () => { const value = this.state.value || this.props.defaultValue; const selectAll = !this.state.focus; this.setState({ focus: true, value }, () => { this.wsrInput.focus(); selectAll && this.wsrInput.select(); }); }; render() { const { dataHook, className, maxLength } = this.props; const focused = this.state.focus; return ( <WixStyleReactContext.Consumer> {({ reducedSpacingAndImprovedLayout }) => ( <div className={st( classes.root, { reducedSpacingAndImprovedLayout }, className, )} data-hook={dataHook} tabIndex={0} onFocus={this.onFocus} onClick={this.onFocus} > <div data-hook={dataHooks.heading} className={st(classes.headingWrapper, { focused, showPlaceholder: !!this.showPlaceholder(), })} > <Heading ellipsis appearance="H1" className={classes.heading}> {this.props.value || this.state.value || this.props.defaultValue} </Heading> </div> <div className={st(classes.activationIndicator, { focused, })} > {this.props.value || this.state.value || this.props.defaultValue} </div> <div className={st(classes.renamingField, { focused, })} data-hook={dataHooks.renamingField} onFocus={e => // input does not pass his event so we need to catch it e.stopPropagation() } > <Input autoSelect={false} textOverflow="clip" maxLength={maxLength || DEFAULT_MAX_LENGTH} onChange={ this.props.onChange ? this.props.onChange : this.onChange } value={this.props.value ? this.props.value : this.state.value} ref={wsrInput => (this.wsrInput = wsrInput)} onBlur={this.onValueSubmission} onEnterPressed={this.onEnterPressed} /> </div> </div> )} </WixStyleReactContext.Consumer> ); } onEnterPressed = () => { this.wsrInput.blur(); }; onValueSubmission = () => { const value = this.state.value || this.props.defaultValue; this.setState({ value, focus: false }, () => { if (typeof this.props.onSubmit === 'function') { this.props.onSubmit(value); } }); }; } EditableTitle.displayName = 'EditableTitle'; EditableTitle.defaultProps = { defaultValue: '', }; EditableTitle.propTypes = { /** Value - initial value to display */ initialValue: PropTypes.string, /** default - value to display when empty, when clicked the input gets this value */ defaultValue: PropTypes.string, /** onSubmit - invoked when done editing */ onSubmit: PropTypes.func, /** length - maximum chars the input can get */ maxLength: PropTypes.number, /** autoFocus - focus element on mount */ autoFocus: PropTypes.bool, /** onChange-invoked when editing */ onChange: PropTypes.func, /** value- the controlled value of the input */ value: PropTypes.string, }; export default EditableTitle;