Expo Google places autocomplete - listView not clicable - css

I am trying to use the GooglePlacesAutocomplete, but once I make the address query, for example: "São C" and the "listView" return something like: "São Caetano, São Paulo ...", but when I try to select one option it seems like the list is not visible, because and the selection do not affect the item list.
this is the code I am using:
import * as React from 'react';
import { Platform, StyleSheet, Text, View } from 'react-native';
import { GooglePlacesAutocomplete } from 'react-native-google-places-autocomplete';
import { colors, device, fonts } from '../constants';
// icons
import SvgTruck from './icons/Svg.Truck';
//const { onLocationSelected } = this.props
// constants
const GOOGLE_MAPS_APIKEY = '[API KEY]'
const WhereTo = () => (
<View style={styles.container}>
<View style={styles.containerBanner}>
<Text style={styles.bannerText}>15% off, up to $6.00</Text>
<Text style={styles.bannerMuted}>3 days</Text>
</View>
<View style={styles.containerInput} >
<View style={styles.containerSquare}>
<View style={styles.square} />
</View>
<GooglePlacesAutocomplete
styles={{
textInputContainer: {
flex: 1,
backgroundColor: 'transparent',
height: 54,
marginHorizontal: 20,
borderTopWidth: 0,
borderBottomWidth:0
},
textInput: {
height: 45,
left:0,
margin: 0,
borderRadius: 0,
paddingTop: 0,
paddingBottom: 0,
paddingLeft: 0,
paddingRight: 0,
padding: 0,
marginTop: 0,
marginLeft: 0,
marginRight: 0,
fontSize:18
},
listView: {
position:'absolute',
marginTop: 50
},
description: {
fontSize:16
},
row: {
padding: 18,
height:58
}
}}
placeholder="Para onde?"
onPress={(data, details) => {
// 'details' is provided when fetchDetails = true
console.log(data, details);
}}
query={{
key: GOOGLE_MAPS_APIKEY,
language: 'pt',
components: "country:br"
}}
textInputProps={{
autoCapitalize: "none",
autoCorrect: false
}}
fetchDetails
enablePoweredByContainer={false}
/>
<View style={styles.containerIcon}>
<SvgTruck />
</View>
</View>
</View>
);
const styles = StyleSheet.create({
container: {
top: Platform.select({ ios: 60, android: 40 }),
alignSelf: 'center',
position: 'absolute',
shadowColor: colors.black,
shadowOffset: { height: 2, width: 0 },
shadowOpacity: 0.2,
shadowRadius: 8,
top: device.iPhoneX ? 144 : 120,
width: device.width - 40
},
containerBanner: {
backgroundColor: colors.green,
borderTopLeftRadius: 4,
borderTopRightRadius: 4,
flexDirection: 'row',
justifyContent: 'space-between',
paddingHorizontal: 16,
paddingVertical: 8
},
bannerText: {
color: colors.white,
fontFamily: fonts.uberMedium,
fontSize: 12
},
bannerMuted: {
color: colors.mint,
fontFamily: fonts.uberMedium,
fontSize: 12
},
containerInput: {
alignItems: 'center',
backgroundColor: colors.white,
flexDirection: 'row',
height: 48
},
containerSquare: {
alignItems: 'center',
flex: 0.15
},
square: {
backgroundColor: colors.black,
height: 8,
width: 8
},
containerIcon: {
alignItems: 'center',
borderLeftColor: colors.greyMercury,
borderLeftWidth: 1,
flex: 0.2
}
});
export default WhereTo;
Can anyone trying to help me to solve it?

I recreated the Expo project and now it works, I could not found the root cause, but once that other project was made by other person and Expo make it easy to do and configure, it was fast enoght to create.
export default function AskForDriver () {
const [location, setLocation] = useState("");
const [errorMsg, setErrorMsg] = useState("");
useEffect(() => {
(async () => {
let { status } = await Location.requestPermissionsAsync();
if (status !== 'granted') {
setErrorMsg('Permission to access location was denied');
}
let location = await Location.getCurrentPositionAsync({});
setLocation(location);
})();
}, []);
let text = 'Waiting..';
if (errorMsg) {
text = errorMsg;
} else if (location) {
text = JSON.stringify(location);
console.log('location - latitude: ', location.coords.latitude)
console.log('location - longitude: ', location.coords.longitude)
}
return (
<View style={styles.container}>
<View style={styles.mainHeader}>
<Text style={styles.fontHeader}>Incluir flatlist com promoções e mensagens de incentivos</Text>
</View>
<View style={styles.searchHeader}>
<GooglePlacesAutocomplete
currentLocation
//styles={styles.placesautocomplete}
styles={{
textInputContainer: {
backgroundColor: 'grey',
},
placesautocomplete: {
flex:1,
},
textInput: {
height: 38,
color: '#5d5d5d',
fontSize: 16,
},
predefinedPlacesDescription: {
color: '#1faadb',
},
}}
placeholder='Search'
onPress={(data, details = null) => {
// 'details' is provided when fetchDetails = true
console.log(data, details);
}}
query={{
key: 'YOUR API KEY',
language: 'pt',
components: 'country:br',
}}
/>
</View>
<MapView
style={styles.mapStyle}
showsMyLocationButton
initialRegion={{
latitude: 37.78825,
longitude: -122.4324,
latitudeDelta: 0.0922,
longitudeDelta: 0.0421,
}}
>
</MapView>
{//<Text>{text}</Text>
}
</View>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
position: 'absolute',
alignContent:'center',
margin:0
},
mainHeader: {
backgroundColor: '#10002b',
padding:10,
},
fontHeader: {
color: '#e0aaff',
fontSize: 15,
},
searchHeader: {
borderColor: '#333',
borderWidth:5,
},
mapStyle: {
flex:1,
width: Dimensions.get('window').width,
height: Dimensions.get('window').height,
},
});

Related

React Native - Pressable is not clickable on Android

What I'm building:
I'm creating a card that will render with a question mark at top of it and when the user press it, the card will flip with animation and show some information.
Code:
From a code perspective it looks like this:
import { View, StyleSheet, Text, Pressable, Animated } from 'react-native';
import { FontAwesome } from '#expo/vector-icons';
import { GlobalStyles } from '../../constants/styles';
import { useTranslation } from 'react-i18next';
export default Card = ({ isSpy, guessingItem, onPress }) => {
const { t } = useTranslation();
let currentValue = 0;
const animatedValue = new Animated.Value(0);
animatedValue.addListener((v) => (currentValue = v.value));
const frontInterpolate = animatedValue.interpolate({
inputRange: [0, 180],
outputRange: ['0deg', '180deg'],
});
const backInterpolate = animatedValue.interpolate({
inputRange: [0, 180],
outputRange: ['180deg', '360deg'],
});
const frontAnimatedStyles = {
transform: [{ rotateY: frontInterpolate }],
};
const backAnimatedStyles = {
transform: [{ rotateY: backInterpolate }],
};
const flipCard = () => {
console.log(currentValue);
if (currentValue >= 90) {
Animated.spring(animatedValue, {
toValue: 0,
tension: 10,
friction: 8,
useNativeDriver: false,
}).start();
setTimeout(() => onPress(), 600);
} else {
Animated.spring(animatedValue, {
toValue: 180,
tension: 10,
friction: 8,
useNativeDriver: false,
}).start();
}
};
return (
<View style={styles.constainer}>
<Pressable onPress={flipCard} style={{ backgroundColor: 'red' }}>
<View style={GlobalStyles.styles.flexbox}>
<Animated.View style={[styles.innerContainer, frontAnimatedStyles]}>
<FontAwesome name="question" size={160} />
</Animated.View>
</View>
</Pressable>
<Pressable onPress={flipCard}>
<View style={GlobalStyles.styles.flexbox}>
<Animated.View style={[backAnimatedStyles, styles.innerContainer, styles.innerContainerBack]}>
<View style={styles.constainer}>
{!isSpy && (
<>
<FontAwesome name={guessingItem.section.icon} size={60} />
<Text style={styles.itemName}>{guessingItem.name}</Text>
</>
)}
{isSpy && (
<>
<FontAwesome name="user-secret" size={60} />
<Text style={styles.placeName}>{t('youAreSpy')}</Text>
</>
)}
</View>
</Animated.View>
</View>
</Pressable>
</View>
);
};
const styles = StyleSheet.create({
constainer: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
},
innerContainer: {
height: 300,
width: 230,
marginVertical: 50,
padding: 60,
borderWidth: 6,
borderColor: GlobalStyles.colors.primary50,
borderRadius: 20,
justifyContent: 'center',
alignItems: 'center',
backfaceVisibility: 'hidden',
},
innerContainerBack: {
position: 'absolute',
right: -115,
bottom: 0,
justifyContent: 'center',
alignItems: 'center',
},
itemName: {
marginTop: 20,
fontSize: 18,
alignItems: 'center',
color: GlobalStyles.colors.primary50,
},
pressed: {},
});
What is an issue:
On-screen below you can see a pressable element with red background.
If I click on any part of this red part, the card would flip. If I test it on Android, clicking on anything inside the white border would not trigger a flip. Only clicking outside of that white border but still inside the red background would trigger a flip.
The question is: Why it behaves differently when I am using basic react-native elements? How can I fix that so clicking would always work for the inside click?
I tested this component on my side and it works well. I think there is no problem with the Card component. Please check the parent component of the Card.
I only changed "right" value from -115 to 0 in the style of innerContainerBack.
innerContainerBack: {
position: 'absolute',
right: 0,
bottom: 0,
justifyContent: 'center',
alignItems: 'center',
}
And you'd better use only one Pressable Component and remove the View component in the Pressable. So my ultimate solution is
import { View, StyleSheet, Text, Pressable, Animated } from 'react-native';
import { FontAwesome } from '#expo/vector-icons';
import { GlobalStyles } from '../../constants/styles';
import { useTranslation } from 'react-i18next';
export default Card = ({ isSpy, guessingItem, onPress }) => {
const { t } = useTranslation();
let currentValue = 0;
const animatedValue = new Animated.Value(0);
animatedValue.addListener((v) => (currentValue = v.value));
const frontInterpolate = animatedValue.interpolate({
inputRange: [0, 180],
outputRange: ['0deg', '180deg'],
});
const backInterpolate = animatedValue.interpolate({
inputRange: [0, 180],
outputRange: ['180deg', '360deg'],
});
const frontAnimatedStyles = {
transform: [{ rotateY: frontInterpolate }],
};
const backAnimatedStyles = {
transform: [{ rotateY: backInterpolate }],
};
const flipCard = () => {
console.log(currentValue);
if (currentValue >= 90) {
Animated.spring(animatedValue, {
toValue: 0,
tension: 10,
friction: 8,
useNativeDriver: false,
}).start();
setTimeout(() => onPress(), 600);
} else {
Animated.spring(animatedValue, {
toValue: 180,
tension: 10,
friction: 8,
useNativeDriver: false,
}).start();
}
};
return (
<View style={styles.constainer}>
<Pressable onPress={flipCard} style={{ backgroundColor: 'red' }}>
<Animated.View style={[styles.innerContainer, frontAnimatedStyles]}>
<FontAwesome name="question" size={160} />
</Animated.View>
<Animated.View style={[backAnimatedStyles, styles.innerContainer, styles.innerContainerBack]}>
<View style={styles.constainer}>
{!isSpy && (
<>
<FontAwesome name={guessingItem.section.icon} size={60} />
<Text style={styles.itemName}>{guessingItem.name}</Text>
</>
)}
{isSpy && (
<>
<FontAwesome name="user-secret" size={60} />
<Text style={styles.placeName}>{t('youAreSpy')}</Text>
</>
)}
</View>
</Animated.View>
</Pressable>
</View>
);
};
const styles = StyleSheet.create({
constainer: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
},
innerContainer: {
height: 300,
width: 230,
marginVertical: 50,
padding: 60,
borderWidth: 6,
borderColor: GlobalStyles.colors.primary50,
borderRadius: 20,
justifyContent: 'center',
alignItems: 'center',
backfaceVisibility: 'hidden',
},
innerContainerBack: {
position: 'absolute',
right: 0,
bottom: 0,
justifyContent: 'center',
alignItems: 'center',
},
itemName: {
marginTop: 20,
fontSize: 18,
alignItems: 'center',
color: GlobalStyles.colors.primary50,
},
pressed: {},
});

Can't get this layout in react native:centering vertical text

this is a follow up question for my problem.
I have this layout and I want to use it as an component which will be more square shaped.
I am struggling trying to create this layout with css in react native.
Can someone help me? I really only need the style for centering the text on the left .
I appreciate your help.
type TeamsProps = {
name: string,
}
const TeamCard = (props: TeamsProps) => {
const [showOptions, setShowOptions] = useState<Boolean>(false)
const toggleOptions = () => {
setShowOptions(!showOptions)
}
return (
<View style={[styles.container, { height: (Dimensions.get("window").width - 3 * 15) / 2 }]}>
<TouchableOpacity onLongPress={toggleOptions} style={styles.card}>
<View style={styles.nameFlag}>
<Text style={styles.name}>{props.name}</Text>
</View>
<View style={styles.member}>
</View>
</TouchableOpacity>
{ showOptions ?
<TouchableOpacity onPress={toggleOptions} style={styles.options}>
<TextInput style={styles.input} value="Team Name"></TextInput>
<View style={styles.buttons}>
<TouchableOpacity style={[styles.button, styles.delete]}>
<Delete style={{ fontSize: 20, color: "white", margin: "auto" }} />
</TouchableOpacity>
<TouchableOpacity style={[styles.button, styles.confirm]}>
<Check style={{ fontSize: 20, color: "white", margin: "auto" }} />
</TouchableOpacity>
</View>
</TouchableOpacity>
: <></>
}
</View>
)
}
const styles = StyleSheet.create({
container: {
flexBasis: "calc(50% - 7.5px)"
},
card: {
backgroundColor: constants.mainColor,
borderRadius: 15,
shadowOpacity: 0.6,
shadowRadius: 10,
flex: 1,
flexDirection: "row",
alignItems: "center"
},
nameFlag: {
backgroundColor: constants.mainColorLight,
height: "calc(100% - 30px)",
width: "15%",
marginVertical: 15,
borderTopRightRadius: 30,
borderBottomRightRadius: 30,
justifyContent: "center"
},
name: {
position: "absolute",
// TODO: translateX needs to use -50%, translateY needs to use 50% of parent width
transform: [{ rotate: "-90deg" }, { translateX: -33 }, { translateY: 13 }],
transformOrigin: "left",
width: "max-content",
fontFamily: constants.fontFamilyHeader,
fontSize: constants.fontSizeHeader
},
member: {
backgroundColor: constants.mainColorLight,
height: "calc(100% - 30px)",
width: "calc(85% - 30px)",
margin: 15,
borderRadius: 30,
padding: 15,
flex: 1,
flexDirection: "row",
flexWrap: "wrap",
gap: 15,
justifyContent: "space-around",
alignItems: "center"
},
options: {
backgroundColor: constants.shadowColor,
position: "absolute",
top: 0,
left: 0,
zIndex: 100,
width: "100%",
height: "100%",
borderRadius: 15,
padding: 15,
flex: 1,
justifyContent: "center",
alignItems: "center",
gap: 25
},
input: {
backgroundColor: "white",
width: "100%",
borderRadius: 50,
padding: 5,
fontFamily: constants.fontFamilySubheader,
fontSize: constants.fontSizeHeader,
textAlign: "center"
},
buttons: {
flexDirection: "row",
gap: 25
},
button: {
borderRadius: 50,
width: 40,
height: 40
},
delete: {
backgroundColor: constants.alertColor
},
confirm: {
backgroundColor: constants.accentColor
}
})
weird shifting if text gets longer #Hammad Hassan
Try out this code and let me know
type CardProps= {
name: string
}
const Card = (props: CardProps) => {
return (
<View style={styles.container}>
<View style={styles.nameFlag}>
<Text style={styles.name}>{props.name}</Text>
</View>
<View style={styles.main}>
</View>
</View>
)
}
const styles = StyleSheet.create({
container: {
backgroundColor: constants.mainColor,
flex: 1,
flexDirection: "row"
},
nameFlag: {
backgroundColor: constants.mainColorLight,
height: "95%",
width: "15%",
marginVertical: "5%",
borderTopRightRadius: 50,
borderBottomRightRadius: 50,
justifyContent: "center"
},
name: {
transform: [{ rotate: "-90deg" }, { translateY: -12 }],
fontFamily: constants.fontFamily,
fontSize: constants.fonzSizeHeader,
textAlign: 'center',
marginRight: 'auto',
marginLeft: 'auto',
marginTop: 'auto',
marginBottom: 'auto'
},
main: {
backgroundColor: constants.mainColorLight,
height: "95%",
width: "75%",
margin: "5%",
borderRadius: 50
}
})
export { Card }

React Native Sticky Footer Input got covered by Keyboard even using KeyboardAvoidingView

I have a basic chat application and when I open the keyboard I want the Sticky Chat Footer to persist at the top of the keyboard but its still being covered even when I use KeyboardAvoidingView.
Here is the image below:
And here is the image when keyboard is open:
Here is my component code below:
<SafeAreaView style={styles.scrollWrapper}>
<KeyboardAvoidingView
style={styles.scrollWrapper}
behavior="height"
keyboardVerticalOffset={headerHeight + 20}
>
<View style={styles.chatBar}>
<IconButton Icon={ButtonAdd} size={32} onPress={() => {}} />
{isKeyboardVisible ? (
<>
<RoundedInput
ref={inputRef}
itemStyle={styles.chatInput}
placeholder="type something here..."
RightComponent={(
<IconButton
Icon={EmojiIcon}
size={normalize(16.5)}
onPress={() => {}}
/>
)}
/>
<TouchableOpacity
activeOpacity={0.4}
onPress={handleKeyboardVisibility}
>
<Icon
style={styles.icon}
name="send-circle"
size={normalize(34)}
color="#F48C2D"
/>
</TouchableOpacity>
</>
) : (
<>
<IconButton
Icon={KeyboardIcon}
size={32}
onPress={handleKeyboardVisibility}
/>
<IconButton Icon={ChatCamera} size={32} onPress={() => {}} />
<IconButton Icon={GalleryIcon} size={32} onPress={() => {}} />
<IconButton Icon={GifIcon} size={32} onPress={() => {}} />
<IconButton Icon={LocationIcon} size={32} onPress={() => {}} />
</>
)}
</View>
</KeyboardAvoidingView>
</SafeAreaView>
and here is my style
const styles = StyleSheet.create({
header: {
...headerStyles.homeHeaderWrapper,
backgroundColor: '#F9F9F9',
borderBottomColor: '#D0D1D1',
},
scrollWrapper: {
flexGrow: 1,
backgroundColor: 'white',
},
dateWrapper: {
marginTop: normalize(12),
...helpers.center,
},
dateTxt: {
...fontHelper(10, typographyFonts.openSansRegular, '#212121', 0).font,
},
messageWrapper: {
flexDirection: 'row',
padding: normalize(12),
},
image: {
height: normalize(33),
width: normalize(33),
overflow: 'hidden',
borderRadius: 100,
alignSelf: 'center',
marginTop: normalize(12),
},
chatBubble: {
marginLeft: normalize(8),
maxWidth: '75%',
// height: normalize(77),
backgroundColor: '#F2F5F8',
borderRadius: 14,
// ...helpers.center,
padding: normalize(12),
marginVertical: normalize(5),
},
chatMsg: {
...fontHelper(13, typographyFonts.openSansRegular, '#212121', 0).font,
},
chatBar: {
height: normalize(65),
shadowOffset: { width: normalize(0), height: normalize(-1.25) },
// borderWidth: 5,
// borderBottomColor: 'red',
borderTopWidth: normalize(0.3),
borderTopColor: colors.alternative,
shadowColor: 'rgba(186,190,214,0.70)',
shadowOpacity: normalize(0.2),
shadowRadius: 2,
elevation: 5,
position: 'absolute',
left: 0,
right: 0,
bottom: 0,
flexDirection: 'row',
alignItems: 'center',
justifyContent: 'space-around',
zIndex: 999,
},
chatInput: {
height: normalize(35),
backgroundColor: '#FFFFFF',
borderColor: '#F48C2D',
borderWidth: 1,
width: '70%',
},
icon: {
width: normalize(34),
height: normalize(34),
},
});
I also already tried using react-native-keyboard-aware-scrollview but it didn't help as well.
Appreciate if someone could help.
I got the same issue.
Try this workaround.
You need to position your component on the top of the keyboard,
but it will depend on the size of device keyboard
import { Keyboard, Animated } from 'react-native'
...
useEffect(() => {
Keyboard.addListener('keyboardWillShow', _keyboardWillShow);
Keyboard.addListener('keyboardWillHide', _keyboardWillHide);
return () => {
Keyboard.removeListener('keyboardWillShow', _keyboardWillShow);
Keyboard.removeListener('keyboardWillHide', _keyboardWillHide);
}
}, []);
const _keyboardWillShow = (event) => {
const height = event.endCoordinates.height;
posComponent(height);
};
const _keyboardWillHide = (event) => {
posComponent(0);
};
const animateButton = (value) => {
Animated.spring(your_variable, {
toValue: value,
tension: 50,
friction: 10,
}).start();
}
then on your view component chatbar
<Animated.View style={{
...styles.chatBar,
...(Platform.OS === 'ios' && { bottom: your_variable })}>
...
</Animated.View>

Attempt to invoke virtual method 'double java.lang.Double.doubleValue()' on a null object reference , react redux and when use connect

when i want to configuration react redux and set connect in my Routes
component i get this err ,
import React, { Component } from 'react';
import { connect } from 'react-redux'
import { Router, Scene, Actions } from 'react-native-router-flux';
import { Text, View, Image, TouchableOpacity, ImageBackground, AsyncStorage } from 'react-native';
import SendNumber from './src/container/SendNumber';
import EnterCode from './src/container/EnterCode';
import Home from './src/container/Home';
import Profile from './src/container/Profile';
import ResultItemsPage from './src/container/ResultItemsPage'
import Details from './src/container/Details'
//back button
const backButton = () => (
<TouchableOpacity
onPress={() => Actions.pop()}
style={{ width: 30, height: 20, marginLeft: 20 }}
>
<View style={{ alignItems: 'center' }}>
<Image
source={require('./Assets/Images/left-arrow.png')}
style={{ width: 30, height: 20 }}
/>
{/*
<Icon name='ios-arrow-round-back' style={{ color: '#fff' }} />
*/}
</View>
</TouchableOpacity>
);
const backButtonDetail = () => (
<TouchableOpacity
style={{
backgroundColor: '#33333320',
padding: 10,
width: 50,
height: 50,
borderRadius: 30,
justifyContent: 'center',
alignItems: 'center',
top: 10,
start: 10,
}} onPress={() => Actions.pop()} >
<Image style={{
width: 30,
resizeMode: 'contain'
}}
source={require('./Assets/Images/left-arrow-white.png')} />
</TouchableOpacity>
)
class Routes extends Component {
constructor(props) {
super(props)
this.state = {
login: false
}
}
_storeData = async () => {
try {
await AsyncStorage.setItem('login', 'true');
} catch (error) {
// Error saving data
}
};
_retrieveData = async () => {
try {
const value = await AsyncStorage.getItem('TASKS');
alert(value)
} catch (error) {
// Error retrieving data
}
};
componentWillMount() {
this._storeData();
this._retrieveData();
}
render() {
return (
<Router>
<Scene key="root" >
<Scene key="SendNumber"
component={SendNumber}
title="Send Number"
hideNavBar={true}
initial={true}
/>
<Scene key="EnterCode" component={EnterCode}
title=""
titleStyle={{ color: 'transparent' }}
renderBackButton={() => backButton()}
navigationBarStyle={styles.login_style_bar}
sceneStyle={styles.login_scene_style}
/>
<Scene key="Home"
component={Home}
title="home"
hideNavBar={true}
/>
<Scene key="Profile" component={Profile}
title=""
titleStyle={{ color: 'transparent' }}
renderBackButton={() => backButton()}
navigationBarStyle={styles.login_style_bar}
sceneStyle={styles.login_scene_style}
/>
<Scene key="ResultItemsPage" component={ResultItemsPage}
title=""
titleStyle={{ color: 'transparent' }}
renderBackButton={() => backButton()}
navigationBarStyle={styles.login_style_bar}
sceneStyle={styles.login_scene_style}
onRight={() => alert('right')}
// rightButtonImage={require('./Assets/Images/bell.png')}
renderRightButton={() => (
<TouchableOpacity style={styles.notification_box}
onPress={() => alert('توجهات')}>
<ImageBackground
style={styles.bell}
source={require('./Assets/Images/bell.png')}
>
<View style={styles.notification} >
<Text style={styles.notification_text} >3</Text>
</View>
</ImageBackground>
</TouchableOpacity>
)}
/>
<Scene key="Details" component={Details}
title=""
titleStyle={{ color: 'red' }}
renderBackButton={() => backButtonDetail()}
navigationBarStyle={styles.login_style_bar_detail}
sceneStyle={styles.login_scene_style}
/>
</Scene>
</Router >
)
}
}
const mapStateToProps = state => {
return {
status: state.number.loginStatus
}
}
export default connect(mapStateToProps)(Routes);
const styles = ({
login_style_bar: {
backgroundColor: '#f6f6f6',
shadowColor: "#f7f7f7",
elevation: 0,
height: 50,
},
login_style_bar_detail: {
backgroundColor: 'transparent',
shadowColor: "#f7f7f7",
elevation: 0,
height: 50,
},
bell: {
width: 30,
height: 30,
justifyContent: 'center',
alignItems: 'center',
},
notification: {
width: 14,
height: 14,
borderRadius: 7,
backgroundColor: '#B22850',
start: 10,
top: -10,
justifyContent: 'center',
alignItems: 'center',
},
notification_text: {
color: '#fff',
fontSize: 9,
fontFamily: 'ISFMedium',
},
notification_box: {
width: 40,
height: 40,
right: 20,
justifyContent: 'center',
alignItems: 'center',
},
bell: {
width: 30,
height: 30,
justifyContent: 'center',
alignItems: 'center',
},
notification: {
width: 14,
height: 14,
borderRadius: 7,
backgroundColor: '#B22850',
start: 10,
top: -10,
justifyContent: 'center',
alignItems: 'center',
},
notification_text: {
color: '#fff',
fontSize: 9,
fontFamily: 'ISFMedium',
},
})

how to fetch data from firebase using expo react native app

Problem:
I am very new to react native and firebase stuff. I am making a train timetable system. There I have implemented a search function. This is how that component looks.
import React, { Component } from "react";
import {
StyleSheet,
Text,
TextInput,
View,
TouchableOpacity,
Dimensions,
Picker,
ListView
} from "react-native";
import {
Ionicons,
Foundation,
Entypo,
MaterialCommunityIcons,
FontAwesome,
MaterialIcons
} from "#expo/vector-icons";
import app from "../../config/db";
import { Autocomplete } from "react-native-autocomplete-input";
import { addItem } from '../../services/stationService';
const { height, width } = Dimensions.get("window");
const box_width = width / 2 + 40;
export default class TicketForm extends React.Component {
constructor(props) {
super(props);
this.state = {
start: "",
end: "",
class: "",
isLoading:false
};
}
static navigationOptions = {
title: "Tickets",
headerStyle: {
backgroundColor: "#2b78fe"
},
headerTintColor: "#fff",
headerTitleStyle: {
color: "#ffff"
}
};
search =()=>{
app.database().ref('/trains').on("value").then(snapshot=>{
console.log(snapshot);
})
}
render() {
var ds = new ListView.DataSource({ rowHasChanged: (r1, r2) => r1 !== r2 });
return (
<View style={styles.form}>
<View style={styles.inputSection}>
<TextInput
style={styles.input}
placeholder="From"
onChangeText={start => {
this.setState({ start: start });
}}
underlineColorAndroid="transparent"
/>
<MaterialCommunityIcons
style={styles.inputicon}
name="backspace"
size={30}
color="#42a5f5"
/>
</View>
<View style={styles.inputSection}>
<TextInput
style={styles.input}
placeholder="To"
onChangeText={end => {
this.setState({ end: end });
}}
underlineColorAndroid="transparent"
/>
<MaterialCommunityIcons
style={styles.inputicon}
name="backspace"
size={30}
color="#42a5f5"
/>
</View>
<View style={styles.classSection}>
<Picker
selectedValue={this.state.class}
style={{ height: 50, width: box_width }}
onValueChange={(itemValue, itemIndex) =>
this.setState({ class: itemValue })
}
>
<Picker.Item label="1 st Class" value="1" />
<Picker.Item label="2 nd Class" value="2" />
<Picker.Item label="3 rd Class" value="3" />
</Picker>
</View>
<View style={styles.buttonCoontainer}>
<View style={styles.searchContainer}>
<TouchableOpacity onPress={this.search}>
<View style={styles.search}>
<Text style={styles.searchText}>Search</Text>
<Ionicons name="ios-search" size={30} color="#fff" />
</View>
</TouchableOpacity>
</View>
</View>
</View>
);
}
}
const styles = StyleSheet.create({
form: {
flex: 1,
borderWidth: 3,
borderRadius: 8,
borderColor: "#ffff",
backgroundColor: "#ffff",
marginTop: 15,
marginLeft: 15,
marginRight: 15,
marginBottom: 5,
paddingTop: 50,
paddingLeft: 20,
paddingRight: 20
},
input: {
width: box_width,
flex: 1,
paddingTop: 5,
paddingRight: 5,
paddingBottom: 5,
paddingLeft: 0,
backgroundColor: "#fff",
color: "#424242"
},
inputSection: {
flexDirection: "row",
justifyContent: "center",
alignItems: "center",
backgroundColor: "#fff",
borderColor: "#78909c",
borderWidth: 0.8,
paddingLeft: 5,
paddingRight: 5,
marginTop: 10,
marginBottom: 10
},
classSection: {
flexDirection: "row",
justifyContent: "center",
alignItems: "center",
backgroundColor: "#e9ebee",
borderColor: "#e9ebee",
borderWidth: 0.8,
paddingLeft: 5,
paddingRight: 5,
marginTop: 10,
marginBottom: 10
},
dateSection: {
justifyContent: "center",
alignItems: "center",
backgroundColor: "#fff",
paddingLeft: 5,
paddingRight: 5,
marginTop: 10,
marginBottom: 10,
width: 335
},
inputIcon: {
padding: 10
},
reverseContainer: {
flexDirection: "row",
marginTop: 30
},
reverse: {
flexDirection: "row",
borderWidth: 0.5,
borderColor: "#eff0f1",
borderRadius: 5,
width: box_width / 2,
paddingTop: 3,
paddingBottom: 3,
paddingLeft: 20,
paddingRight: 10,
marginLeft: 0,
marginRight: 20,
backgroundColor: "#eff0f1"
},
reset: {
flexDirection: "row",
borderWidth: 0.5,
borderColor: "#eff0f1",
borderRadius: 5,
width: box_width / 2,
paddingTop: 3,
paddingBottom: 3,
paddingLeft: 20,
paddingRight: 10,
marginLeft: box_width / 4,
marginRight: 0,
backgroundColor: "#eff0f1"
},
reverseText: {
marginTop: 3,
marginRight: 10
},
resetText: {
marginTop: 3,
marginRight: 10
},
searchContainer: {
flexDirection: "row",
marginTop: 30
},
search: {
alignItems: "center",
flexDirection: "row",
borderWidth: 0.5,
borderColor: "#2089dc",
borderRadius: 5,
width: box_width + 80,
paddingTop: 6,
paddingBottom: 6,
paddingLeft: box_width / 2,
paddingRight: 10,
marginLeft: 0,
marginRight: 20,
backgroundColor: "#2089dc"
},
searchText: {
marginTop: 3,
marginRight: 10,
fontSize: 15,
fontWeight: "700",
color: "#ffff"
},
searchIcon: {
fontWeight: "700"
}
});
When I hit the search button there it is giving me an error. Here I am specifying how I implemented the action inside the search function.
app.database().ref('/trains').on("value").then(snapshot=>{
console.log(snapshot);
})
This is how I configure the firebase in my app and have imported it to my current component.
import Firebase from 'firebase';
let config = {
apiKey: "My Key",
authDomain: "my domain",
databaseURL: "https://mytrain-5beba.firebaseio.com",
projectId: "mytrain-5beba",
storageBucket: "mytrain-5beba.appspot.com",
messagingSenderId: "305193513552"
};
let app = Firebase.initializeApp(config);
// export const db = app.database();
export default app;
This is how my database looks like in the console.
Can someone help me to query this database correctly from my react native app?. Thank you very much.
You can try something like this:
.database()
.ref('/trains/')
.on('value', snapshot => {
const trains = snapshot.val();
console.warn(trains);
});

Resources