React Native - issue with flexDirection - react-native

I am trying to put a button (custom component made from TouchableOpacity inside View) and an image in a view.....and have them sit side by side.
See code below
<View
style={{
borderColor: 'black',
borderWidth: 1,
flex: 1,
flexDirection: 'row',
}}
>
<MyButton
to_extraStyle={{
backgroundColor: '#03A9F4',
width: 100,
height: 60,
alignSelf: 'flex-start',
}}
onPress={this._imagePickHandler}
>
CHOOSE PIC
</MyButton>
<Image
source={{ uri: this.state.localImgUrl }}
style={{
width: 100,
height: 60,
borderColor: 'black',
borderWidth: 1,
alignSelf: 'flex-end',
}}
/>
</View>
When I remove flexDirection: 'row' you can see both the image and the button....they sit on top of each other....but with flexDirection: 'row' included, the image disappears and you can only see the button.
Any ideas?

Use the value of width as %.
<View
style={{
borderColor: 'black',
borderWidth: 1,
flex: 1,
flexDirection: 'row'
}}
>
<MyButton
to_extraStyle={{
backgroundColor: '#03A9F4',
width: "50%",
height: 60,
}}
onPress={this._imagePickHandler}
>
CHOOSE PIC
</MyButton>
<Image
source={{ uri: this.state.localImgUrl }}
style={{
width: "50%",
height: 60,
borderColor: 'black',
borderWidth: 1,
}}
/>
</View>
Example
export default class App extends Component {
render() {
return (
<View style={s.container}
>
<TouchableOpacity style={s.touchable}>
<Text style={{color:"#ffffff"}}>Button </Text>
</TouchableOpacity>
<Image source={{uri: 'http://i.imgur.com/IGlBYaC.jpg'}} style={s.backgroundImage} />
</View>
);
}
}
const s = StyleSheet.create({
backgroundImage: {
width: "50%",
height: 60,
borderColor: 'black',
borderWidth: 1,
},
touchable: {
backgroundColor: '#03A9F4',
width: "50%",
height: 60,
justifyContent:"center",
alignItems:"center"
},
container: {
borderColor: 'white',
borderWidth: 1,
flex: 1,
flexDirection: 'row'
}
});

Remove alignSelf on both MyButton and Image and they will sit side by side.
If what you wanted to obtain with alignSelf is to align MyButton at the very left and Image at the very right then add justifyContent: 'space-between' to your view.

Related

Touchable Opacity is half way through

My code is the following
My touchable opacity that does the d.onSelect is not being responsive, it only responds to the upper top half around the border, but nothing happens when I press on a players component from the bottom half. can any one explain or help
<>
<TouchableOpacity
onPress={
props.disabled === true
? () => null
: d.onSelect
}
style={{
backgroundColor: 'red'
}}
>
<LinearGradient
colors={[Colors.Player1, Colors.Player2]}
style={{
borderRadius: 10,
margin: 10,
paddingHorizontal: 3,
paddingVertical: 10,
justifyContent: 'center',
alignItems: 'center',
borderColor: Colors.Player1,
borderWidth: 3,
backgroundColor: Colors.NewBlue
}}
>
<ImageBackground
source={require('../assets/frame2.png')}
style={{
height: 40,
width: 40,
justifyContent: 'center',
alignItems: 'center',
overflow: 'hidden'
}}
>
<Image
source={{ uri: d.image }}
style={{
height: '75%',
width: '75%'
}}
resizeMode='contain'
/>
</ImageBackground>
<Text
style={{
textAlign: 'center',
color: '#fff',
textShadowColor:
'rgba(0, 0, 0, 0.75)',
textShadowOffset: {
width: 1,
height: 1
},
textShadowRadius: 1,
fontSize: 9,
fontFamily: 'Montserrat_semi_bold'
}}
>
{d.name && d.name.split(' ', 1)}
</Text>
</LinearGradient>
</TouchableOpacity>
</>
which results in the image
Without knowing all the context or having an expo snack, I'd say you need to ensure you have flex:1 set on the TouchableOpacity component. In addition, assure that the rest of your images fit within that flex:1

Keyboard moving view up in react native expo

I am new in react native and I please need help. When the keyboard appears , the whole view is pushed upwards.I do not want that to happen.I saw other answers but none of them is working for me.I do not want the view to be pushed up when the keyboard appears and want to remain where they are.I am using expo and has given the code below with the images.
import { StatusBar } from 'expo-status-bar';
import React from 'react';
import { Image, StyleSheet, View, TextInput, Text, TouchableOpacity, ScrollView, KeyboardAvoidingView } from 'react-native';
export default function LoginScreen({ navigation }) {
return (
<View style={styles.container}>
<Image style={styles.logo} source={
{
uri: "https://i.ibb.co/4JK4T3P/deale-logo.jpg",
}} />
<StatusBar style="auto" />
<View style={styles.inputContainer} >
<TextInput
style={styles.loginInput}
placeholder='Phone Number or Email'
/>
<TextInput
style={styles.passwordInput}
placeholder='Password'
/>
<TouchableOpacity
style={{
width: 280,
height: 50,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: 'rgb(255, 77, 77)',
elevation: 5,
borderRadius: 10,
top: 35
}}
activeOpacity={0.8}>
<Text
style={{
color: 'white',
fontSize: 15,
fontWeight: 'bold',
}} >
LOG IN
</Text>
</TouchableOpacity>
<Text
onPress={() => console.log('g')}
style={{
position: 'relative',
top: '23%',
fontWeight: 'bold',
}} >
OR LOGIN WITH SOCIAL MEDIA ACCOUNT?
</Text>
<View style={{
flex: 1,
flexDirection: 'row',
bottom: 30,
justifyContent: 'space-evenly',
top: '22%',
width: 300
}} >
<TouchableOpacity activeOpacity={0.5} >
<Image source={
{ uri: 'https://cdn3.iconfinder.com/data/icons/popular-services-brands/512/facebook-512.png' }}
style={{
width: 60,
height: 60,
}} />
</TouchableOpacity>
<TouchableOpacity activeOpacity={0.5} >
<Image source={
{ uri: 'https://lh3.googleusercontent.com/COxitqgJr1sJnIDe8-jiKhxDx1FrYbtRHKJ9z_hELisAlapwE9LUPh6fcXIfb5vwpbMl4xl9H9TRFPc5NOO8Sb3VSgIBrfRYvW6cUA' }}
style={{
width: 60,
height: 60,
}} />
</TouchableOpacity>
</View>
</View >
<View style={styles.loginButtonView} >
<TouchableOpacity
onPress={
() => navigation.navigate('Create')
}
style={{
width: '100%',
height: '100%',
justifyContent: 'center',
alignItems: 'center',
backgroundColor: 'rgb(145, 157, 230)',
top: 10,
elevation: 5,
borderRadius: 5
}}
activeOpacity={0.8}>
<Text
style={{ color: 'white', fontSize: 15, fontWeight: 'bold' }} >
CREATE ACCOUNT
</Text>
</TouchableOpacity>
<TouchableOpacity
style={{
justifyContent: 'center',
alignItems: 'center',
top: '40%'
}}
activeOpacity={0.1}>
<Text
style={{
color: 'black',
fontSize: 16,
top: 5
}} >
FORGOT PASSWORD
</Text>
</TouchableOpacity>
</View>
</View >
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#fff',
alignItems: 'center',
justifyContent: 'center',
},
logo: {
position: 'absolute',
height: 100,
width: 150,
resizeMode: "contain",
top: '3 %'
},
loginInput: {
position: 'relative',
height: 50,
borderColor: 'black',
backgroundColor: 'rgb(240, 240, 242)',
borderRadius: 10,
width: 280,
color: 'black',
textAlign: 'center',
justifyContent: 'center',
alignItems: 'center',
borderColor: 'white',
},
inputContainer: {
position: 'absolute',
top: '18%',
alignItems: 'center',
},
passwordInput: {
position: 'relative',
height: 50,
borderColor: 'black',
backgroundColor: 'rgb(240, 240, 242)',
borderRadius: 10,
width: 280,
color: 'black',
textAlign: 'center',
justifyContent: 'center',
alignItems: 'center',
borderColor: 'white',
top: 10
},
loginButtonView: {
position: 'absolute',
height: 46,
width: '70%',
top: '80%'
}
});
I figured out the reason myself.It was happening because i had set my positions based on percentage and the popping of keyboard changed the dimensions resulting in the change of position.
Try to use the component KeyboardAvoidingView like this:
<KeyboardAvoidingView behavior={'height'} enabled style={styles.container}>
<Image style={styles.logo} source={
{
uri: "https://i.ibb.co/4JK4T3P/deale-logo.jpg",
}} />
<StatusBar style="auto" />
<View style={styles.inputContainer} >
<TextInput
style={styles.loginInput}
placeholder='Phone Number or Email'
/>
<TextInput
style={styles.passwordInput}
placeholder='Password'
/>
<TouchableOpacity
style={{
width: 280,
height: 50,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: 'rgb(255, 77, 77)',
elevation: 5,
borderRadius: 10,
top: 35
}}
activeOpacity={0.8}>
<Text
style={{
color: 'white',
fontSize: 15,
fontWeight: 'bold',
}} >
LOG IN
</Text>
</TouchableOpacity>
<Text
onPress={() => console.log('g')}
style={{
position: 'relative',
top: '23%',
fontWeight: 'bold',
}} >
OR LOGIN WITH SOCIAL MEDIA ACCOUNT?
</Text>
<View style={{
flex: 1,
flexDirection: 'row',
bottom: 30,
justifyContent: 'space-evenly',
top: '22%',
width: 300
}} >
<TouchableOpacity activeOpacity={0.5} >
<Image source={
{ uri: 'https://cdn3.iconfinder.com/data/icons/popular-services-brands/512/facebook-512.png' }}
style={{
width: 60,
height: 60,
}} />
</TouchableOpacity>
<TouchableOpacity activeOpacity={0.5} >
<Image source={
{ uri: 'https://lh3.googleusercontent.com/COxitqgJr1sJnIDe8-jiKhxDx1FrYbtRHKJ9z_hELisAlapwE9LUPh6fcXIfb5vwpbMl4xl9H9TRFPc5NOO8Sb3VSgIBrfRYvW6cUA' }}
style={{
width: 60,
height: 60,
}} />
</TouchableOpacity>
</View>
</View >
<View style={styles.loginButtonView} >
<TouchableOpacity
onPress={
() => navigation.navigate('Create')
}
style={{
width: '100%',
height: '100%',
justifyContent: 'center',
alignItems: 'center',
backgroundColor: 'rgb(145, 157, 230)',
top: 10,
elevation: 5,
borderRadius: 5
}}
activeOpacity={0.8}>
<Text
style={{ color: 'white', fontSize: 15, fontWeight: 'bold' }} >
CREATE ACCOUNT
</Text>
</TouchableOpacity>
<TouchableOpacity
style={{
justifyContent: 'center',
alignItems: 'center',
top: '40%'
}}
activeOpacity={0.1}>
<Text
style={{
color: 'black',
fontSize: 16,
top: 5
}} >
FORGOT PASSWORD
</Text>
</TouchableOpacity>
</View>
</KeyboardAvoidingView >
Try to use different values in the position prop.
If you want less job, you can use the react-native-keyboard-aware-scroll-view. It's a very good lib to work with Keyboard in different layouts.

View over another view in percentage of screen width

I am new in react native and i want a view like attached image. I have no idea that how can achieved this..?
I have tried this:
app.js
<View style={styles.navSectionStyle}>
<TouchableOpacity
style={styles.SubmitButtonStyle}
activeOpacity = { .5 }
onPress={ this.ButtonClickCheckFunction }>
<Text style={styles.TextStyle}> Page 1 </Text>
</TouchableOpacity>
<View style={styles.BackStyle}>
<Text style={styles.TextStyle}> Test</Text>
</View>
</View>
style.js
SubmitButtonStyle: {
width:'70%',
height: 80 ,
justifyContent: 'center',
alignItems: 'center',
paddingTop:15,
paddingBottom:15,
backgroundColor:'#fff',
borderRadius:10,
borderWidth: 2,
borderColor: '#fff'
},
BackStyle:{
marginTop:10,
marginLeft:15,
position: 'absolute',
width: 30,
borderRadius:10,
borderWidth: 1,
borderColor: '#F53BBB',
backgroundColor: '#F53BBB',
justifyContent: 'center',
alignItems: 'center',
shadowColor: '#000000',
shadowOffset: {
width: 2,
height: 3
},
shadowRadius: 4,
shadowOpacity: 1.0
},
TextStyle:{
justifyContent: 'center',
alignItems: 'center'
}
Here's a basic template for the View
Get the Width of the screens using Dimensions api.
Mark the views as position: absolute and get position them according to the screen width.
15 % from both sides, 10% for overlapping view and 60% for the main view
render() {
return (
<View style={{flex: 1,
alignItems: 'center',
justifyContent: 'center',
backgroundColor: 'red'}}>
<View style={{width: Dimensions.get('window').width * 0.6,
height: 100,
backgroundColor: 'blue'}}/>
<View style={{position: 'absolute',
width: Dimensions.get('window').width * 0.1,
height: 80,
backgroundColor: 'black',
left: Dimensions.get('window').width * 0.15,
zIndex: 1}} />
<View style={{position: 'absolute',
width: Dimensions.get('window').width * 0.1,
height: 80,
backgroundColor: 'black',
right: Dimensions.get('window').width * 0.15,
zIndex: 1}} />
</View>
)
}

Component won't stay wrapped within bounds (React Native)

I am trying to make my own tab navigation like Instagram has instagram example. I noticed that the items within the footer view I made does not stay within the bounds and moves to the top left of the screen. Images shown - What I am trying to achieve What happens frequently
Here is the most important part of my code. I have done inline styles temporarily to try and figure out the issue. Here is the part where the issue lays <View style = {{ width: Dimensions.get('window').width, backgroundColor: '#fff', height: 80}} <TouchableOpacity onPress = {() => this.props.navigation.navigate('Profile')} style = {{justifyContent: 'flex-end'}}>
<Text style = {{justifyContent: 'flex-end'}}> Profile </Text>
</TouchableOpacity> </View>-
render() {
return (
<MapView style = {[style.container, style.map]}
region = {this.state.initialPosition}>
<MapView.Marker coordinate = {this.state.markerPosition}>
<View style = {style.radius}>
<View style = {style.marker}/>
</View>
</MapView.Marker>
<View style = {{ width: Dimensions.get('window').width, backgroundColor: '#fff', height: 80}} >
<TouchableOpacity onPress = {() => this.props.navigation.navigate('Profile')} style = {{justifyContent: 'flex-end'}}>
<Text style = {{justifyContent: 'flex-end'}}> Profile </Text>
</TouchableOpacity>
</View>
</MapView>
);
}
}
const style = StyleSheet.create({
container: {
flex: 1,
justifyContent: 'flex-end',
//alignItems: 'center',
},
text: {
color: '#fff'
},
map: {
left: 0,
right: 0,
top: 0,
bottom: 0,
position: 'absolute'
},
radius:{
height: 50,
width: 50,
borderRadius: 50 / 2,
overflow: 'hidden',
backgroundColor: 'rgba(1,213,106,0.3)',
borderWidth: 1,
borderColor: 'rgba(1,213,106,0.3)',
alignItems:'center',
justifyContent: 'center'
},
marker: {
height: 20,
width: 20,
borderWidth: 3,
borderColor: '#fff',
borderRadius: 20 / 2,
borderWidth: 3,
overflow: 'hidden',
backgroundColor: '#01D56A'
},
menuSection: {
backgroundColor: 'rgba(255, 255, 255, 0.7)',
width: Dimensions.get('window').width,
height: Dimensions.get('window').height/3,
justifyContent: 'flex-end',
alignItems: 'center'
},
icon:{
width: 50,
height: 50,
backgroundColor: 'black'
}
})

Vertical centering in React Native doesn't work

I use a ScrollView and I am not able to center an icon in one of inner Views.
import Icon from 'react-native-vector-icons/MaterialCommunityIcons';
<ScrollView>
...
<View style={styles.detailRowContainer}>
<View style={{flex: 1}}>
<Text style={styles.label} numberOfLines={1}>
{'Phone Number'}
</Text>
<Text style={styles.value} numberOfLines={1}>
{phone}
</Text>
</View>
<View style={styles.round}>
<TouchableWithoutFeedback onPress={this._onPressPhone}>
<Icon size={22} name="phone" />
</TouchableWithoutFeedback>
</View>
</View>;
...
</ScrollView>
detailRowContainer: {
flexDirection: 'row',
justifyContent: 'center',
flex: 1,
marginTop: 10,
paddingBottom: 10,
borderBottomWidth: 1,
borderBottomColor: Colors.lightGray,
},
label: {
color: Colors.glofoxDark,
marginBottom: 3,
},
value: {
color: Colors.glofoxDark,
fontWeight: '800',
borderBottomWidth: 1,
borderBottomColor: Colors.lightGray,
},
round: {
backgroundColor: Colors.lightBlue,
width: 30,
height: 30,
borderRadius: 30,
overflow: 'hidden',
justifyContent: 'center',
alignItems: 'flex-end',
flexDirection: 'row',
padding: 4,
},
The styles need to be modified in this way.
Right now you're doing
flexDirection: row along justifyContent: center. Since your first child element is taking complete parent flex, therefore it does not show its effect
paddingBottom is given but , for centering an equivalent paddingTop must be given
padding for the round style should be replaced with margin, otherwise it affects the position of the inner elements
alignItems in round , must not be flex-end, it should be replaced with center
Here are the styles that will fix the vertical centering
detailRowContainer: {
flexDirection: 'row',
alignItems: 'center',
flex: 1,
marginTop: 10,
paddingTop: 10,
paddingBottom: 10,
borderBottomWidth: 1,
borderBottomColor: Colors.lightGray,
},
round: {
backgroundColor: Colors.lightBlue,
width: 30,
height: 30,
borderRadius: 30,
overflow: 'hidden',
justifyContent: 'center',
alignItems: 'center',
margin: 4
},