import * as React from 'react'; import { Platform, StyleSheet, TextInputProps, TextStyle, View, ViewStyle, } from 'react-native'; import { inputItem } from '../../_styles/themes/default.components'; import MDTextInput, { IMDtextInputProps } from '../text-input'; import MDInputLabel, { IMDInputLabelStyles, MDInputLabelStyles, } from './input-label'; interface IMDMaterialTextInputProps extends IMDtextInputProps { styles?: IMDMaterialTextInputStyles; duration?: number; textFocusColor?: string; textBlurColor?: string; highlightColor?: string; height?: number; } interface IMDMaterialTextInputStyles extends IMDInputLabelStyles { wrapper: ViewStyle; input: TextStyle; } interface IMDMaterialTextInputState { focused: boolean; height?: number; } export const MDMaterialTextInputStyles: IMDMaterialTextInputStyles = { wrapper: { width: '100%', height: 60, paddingTop: 28, paddingBottom: 4, position: 'relative', overflow: 'hidden', }, input: { width: '100%', position: 'absolute', color: '#111a34', fontSize: inputItem.fontSize, fontWeight: inputItem.fontWeight as TextStyle['fontWeight'], ...Platform.select({ android: { bottom: -5, left: -2, }, ios: { bottom: 8, }, }), }, ...MDInputLabelStyles, }; const styles = StyleSheet.create( MDMaterialTextInputStyles ); export default class MDMaterialTextInput extends React.Component< IMDMaterialTextInputProps, IMDMaterialTextInputState > { public static defaultProps = { styles, duration: 200, placeholderTextColor: inputItem.placeholder, value: '', dense: false, multiline: false, height: undefined, }; constructor (props: IMDMaterialTextInputProps) { super(props); this.state = { focused: false, height: props.height, }; } private inputLabel: MDInputLabel | null = null; private input: MDTextInput | null = null; public componentWillReceiveProps ( nextProps: IMDMaterialTextInputProps & TextInputProps ) { const { value, height } = this.props; const { value: nextValue, height: nextHeight } = nextProps; if (value !== nextValue || height !== nextHeight) { this.setState({ height: nextHeight || 0, }); } } public render () { const { styles: _styles, placeholder, ...newProps } = this.props; const { placeholderTextColor, highlightColor, duration, textFocusColor, textBlurColor, } = this.props; const { input, wrapper, ...label } = _styles!; const { focused, height } = this.state; const hasValue = !!(this.props.value && this.props.value.length > 0); const wrapperStyles = [wrapper, height ? { height: undefined } : {}]; const labelProps = { styles: label, label: placeholder, labelColor: placeholderTextColor, duration, highlightColor, dense: true, hasValue, focused, focusHandler: () => { this.input && this.input.focus(); }, }; const inputStyles = [ input, focused && textFocusColor ? { color: textFocusColor } : {}, !focused && textBlurColor ? { color: textBlurColor } : {}, ]; return ( (this.input = ref)} /> (this.inputLabel = ref)} {...labelProps} /> ); } public focus () { this.input && this.input.focus(); } public blur () { this.input && this.input.blur(); } private handleFocus (e: any) { this.setState({ focused: true }); const { onFocus } = this.props; onFocus && onFocus(e); } private handleBlur (e: any) { this.setState({ focused: false }); const { onBlur } = this.props; onBlur && onBlur(e); } }