1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
|
import React, { PureComponent } from 'react'
import PropTypes from 'prop-types'
import classnames from 'classnames'
import { removeLeadingZeroes } from '../send/send.utils'
/**
* Component that attaches a suffix or unit of measurement trailing user input, ex. 'ETH'. Also
* allows rendering a child component underneath the input to, for example, display conversions of
* the shown suffix.
*/
export default class UnitInput extends PureComponent {
static propTypes = {
children: PropTypes.node,
error: PropTypes.bool,
onBlur: PropTypes.func,
onChange: PropTypes.func,
placeholder: PropTypes.string,
suffix: PropTypes.string,
value: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
}
static defaultProps = {
placeholder: '0',
}
constructor (props) {
super(props)
this.state = {
value: props.value || '',
}
}
componentDidUpdate (prevProps) {
const { value: prevPropsValue } = prevProps
const { value: propsValue } = this.props
const { value: stateValue } = this.state
if (prevPropsValue !== propsValue && propsValue !== stateValue) {
this.setState({ value: propsValue })
}
}
handleFocus = () => {
this.unitInput.focus()
}
handleChange = event => {
const { value: userInput } = event.target
let value = userInput
if (userInput.length && userInput.length > 1) {
value = removeLeadingZeroes(userInput)
}
this.setState({ value })
this.props.onChange(value)
}
handleBlur = event => {
const { onBlur } = this.props
typeof onBlur === 'function' && onBlur(this.state.value)
}
getInputWidth (value) {
const valueString = String(value)
const valueLength = valueString.length || 1
const decimalPointDeficit = valueString.match(/\./) ? -0.5 : 0
return (valueLength + decimalPointDeficit + 0.75) + 'ch'
}
render () {
const { error, placeholder, suffix, children } = this.props
const { value } = this.state
return (
<div
className={classnames('unit-input', { 'unit-input--error': error })}
onClick={this.handleFocus}
>
<div className="unit-input__input-container">
<input
type="number"
className="unit-input__input"
value={value}
placeholder={placeholder}
onChange={this.handleChange}
onBlur={this.handleBlur}
style={{ width: this.getInputWidth(value) }}
ref={ref => { this.unitInput = ref }}
/>
{
suffix && (
<div className="unit-input__suffix">
{ suffix }
</div>
)
}
</div>
{ children }
</div>
)
}
}
|