I am facing one problem regarding my textInput.My textInput is going out of the parent view when my app comes in foreground from background. This is happening very frequently.
This happens when I have multiple lines inside textInput before sending app to background.
here is the screenshot:
Here is the code:
import React from 'react';
import {useState,useRef} from 'react';
import {View, StyleSheet, Animated, TouchableOpacity, Image, TextInput, ScrollView, Platform} from 'react-native';
import GestureRecognizer, {swipeDirections} from 'react-native-swipe-gestures';
export default function ListItem() {
const [textInputHeight, setTextInputHeight] = useState(36);
const [text, onChangeText] = React.useState('Useless Text');
const height = useRef(new Animated.Value(1)).current;
const [isExpanded, setIsExpanded] = useState(false);
const componentHeight = 300;
const parentContainerExpandedHeight =
Platform.OS === "ios"
? (componentHeight) + textInputHeight - 45
: (componentHeight) + textInputHeight - 15;
const maxTextLengthWhenExpanded = 1000;
const maxTextLengthWhenCollapsed = 250;
useEffect(() => {
if (isKeyboardVisible) {
if (isExpanded) {
setIsExpanded(false);
Animated.timing(height, {
toValue: 1,
duration: 200,
useNativeDriver: false,
}).start();
}
} else {
if (inputRef && inputRef.current) {
inputRef.current.blur();
}
if (isExpanded) {
setIsExpanded(false);
Animated.timing(height, {
toValue: 1,
duration: 200,
useNativeDriver: false,
}).start();
}
}
}, [isKeyboardVisible]);
const onSwipeUp = () => {
setIsExpanded(true);
Animated.timing(height, {
toValue: parentContainerExpandedHeight,
duration: 400,
useNativeDriver: false,
}).start();
};
const onSwipeDown = () => {
setIsExpanded(false);
Animated.timing(height, {
toValue: 0,
duration: 400,
useNativeDriver: false,
}).start();
};
const getTextLayoutSize = (event: any) => {
setTextInputHeight(event.nativeEvent.layout.height);
};
return (
<GestureRecognizer onSwipeUp={() => onSwipeUp()} onSwipeDown={() => onSwipeDown()}>
<View style={styles.parentContainer}>
<View style={styles.handlebar} />
<Animated.View style={[styles.childContainer, { minHeight: height }]}>
<View style={styles.textInputContainer}>
<View style={styles.textImageWrapper}>
<ScrollView bounces={false}>
<TextInput
onLayout={getTextLayoutSize}
value={text}
onChangeText={onChangeText}
placeholder={'placeholder'}
placeholderTextColor="gray"
multiline
textAlignVertical="top"
style={{
textAlignVertical: 'top',
marginBottom: 10,
}}
maxLength={isExpanded ? maxTextLengthWhenExpanded : maxTextLengthWhenCollapsed
}
/>
</ScrollView>
</View>
</View>
<View style={styles.container}>
<TouchableOpacity
style={styles.submitButton}>
</TouchableOpacity>
<TouchableOpacity
onPress={() => {}}
style={styles.submitButton}
>
</TouchableOpacity>
</View>
</Animated.View>
</View>
</GestureRecognizer>
);
}
const styles = StyleSheet.create({
parentContainer: {
minHeight: 120,
width: "100%",
backgroundColor: "#FFFFFF",
borderTopLeftRadius: 8,
borderTopRightRadius: 8,
justifyContent: "center",
paddingHorizontal: 16,
paddingTop: 4,
},
handlebar: {
width: 47,
height: 4,
borderRadius: 10,
marginBottom: 8,
alignSelf: "center",
backgroundColor: "#808080",
},
childContainer: {
backgroundColor: "#FFFFFF",
borderTopLeftRadius: 4,
borderTopRightRadius: 4,
borderBottomLeftRadius: 4,
borderBottomRightRadius: 4,
borderColor: "#808080",
justifyContent: "flex-end",
borderBottomWidth: 1,
borderRightWidth: 1,
borderLeftWidth: 1,
borderTopWidth: 1,
padding: 8,
},
textImageWrapper: {
backgroundColor: "#FFFFFF",
paddingBottom: 10,
},
container: {
flexDirection: "row",
justifyContent: "space-between",
backgroundColor: "#FFFFFF",
},
submitButton: {
justifyContent: "center",
alignItems: "center",
width: 40,
height: 40,
backgroundColor: "#808080",
borderRadius: 100,
}
});