I needed to define a component which wraps TextInput because I have a lot of text inputs in my App and I want them to have a trash-can icon to clear text and a common style.
My component is this:
import React from 'react';
import {
TextInput,
TouchableOpacity,
StyleSheet,
View,
ReturnKeyTypeOptions,
Platform,
} from 'react-native';
import Numerics from '../constants/Numerics';
import { Ionicons } from '@expo/vector-icons';
import Colors from '../constants/Colors';
interface Props {
placeholder?: string;
iconName?: string;
returnKeyType?: ReturnKeyTypeOptions;
backgroundColor?: string;
margin?: number;
marginBottom?: number;
onTextChanged?(text: string): void;
onFinishedEditing?(text: string): void;
onClearTextInput?(): void;
}
const defaultProps: Props = {
backgroundColor: Colors.textInputBackgroundColor,
placeholder: '',
iconName: '',
returnKeyType: 'none',
margin: 0,
onTextChanged: (text) => {},
onFinishedEditing: (text) => {},
marginBottom: 0,
};
const CustomTextInput: React.FC<Props> = (props) => {
const [inputText, setInputText] = React.useState('');
const onCancelSearchHandler = () => {
setInputText('');
if (props.onTextChanged) {
props.onTextChanged('');
}
if (props.onClearTextInput) props.onClearTextInput();
};
let clearTextComponent = <View></View>;
if (inputText) {
clearTextComponent = (
<TouchableOpacity onPress={onCancelSearchHandler}>
<Ionicons
name='trash-outline'
color={Colors.greyColor}
size={Numerics.iconsSize}
/>
</TouchableOpacity>
);
}
return (
<View
style={[
styles.searchBarContainer,
{
backgroundColor: props.backgroundColor,
margin: props.margin,
marginBottom: props.marginBottom,
},
]}>
<Ionicons
name={props.iconName}
color={Colors.greyColor}
size={Numerics.iconsSize}
/>
<TextInput
style={styles.textInput}
keyboardType='default'
returnKeyType={props.returnKeyType}
value={inputText}
onChangeText={(text) => {
setInputText(text);
if (props.onTextChanged) {
props.onTextChanged(text);
}
}}
onEndEditing={(event) => {
if (props.onFinishedEditing) {
props.onFinishedEditing(event.nativeEvent.text);
}
}}
placeholder={props.placeholder}
autoCorrect={false}
/>
{clearTextComponent}
</View>
);
};
CustomTextInput.defaultProps = defaultProps;
const styles = StyleSheet.create({
searchBarContainer: {
flexDirection: 'row',
backgroundColor: Colors.textInputBackgroundColor,
borderRadius: 10,
height: 50,
padding: 5,
alignItems: 'center',
},
textInput: {
flex: 1,
marginLeft: 10,
},
});
export default CustomTextInput;
The main features are:
- At the left of the TextInput there is customizable icon
- At the right of the TextInput there is a "clear text" button icon, which disappears if there's no text
- An handler that fires when text editing is ended
- The
CustomTextInputhas its own state to make the clear text button work
Everything works fine, but I really don't know how can I clear the text from the outside! Consider that I use my CustomTextInput in an App page, and when the App navigates to another page, I want to clear my CustomTextInput.
How would you do that?