Fixed Header horizontal ListView react-native - javascript

I have created a table view using react-native list view.
I want to fix the header and first column in this table.
Here is what I created:
This list view is scrollable horizontally as well as vertically and all the data is dynamic.
I want to freeze the header and first column of this table if possible
Here is my code:
import React, { Component } from 'react';
import {
AppRegistry,
StyleSheet,
Text,
ListView,
ScrollView,
Image,
TouchableOpacity,
Platform,
View
} from 'react-native';
import PMR from "../utilities/PMR";
import Spinner from 'react-native-loading-spinner-overlay';
import NavigationBar from 'react-native-navbar';
let bg = require('image!bg'),
back = require('image!back'),
Dimensions = require('Dimensions'),
windowSize = Dimensions.get('window'),
Screen = require('Dimensions').get('window');
class StationData extends Component {
constructor(props) {
super(props)
this.state = {
dataSource: new ListView.DataSource({
rowHasChanged: (row1, row2) => row1 !== row2,
}),
isVisible: true,
}
}
componentDidMount() {
let {username, password} = this.props.navigator.cerdentials;
let obj = {
'stXid':this.props.data.stationId,
'startTime':this.props.data.from,
'endTime':this.props.data.to
};
PMR.rawData(username, password, obj).then((rslt) => {
var RawData = [];
rslt.forEach(function(dataItem) {
if (dataItem.pointValue.length > 0)
RawData.push(dataItem);
});
RawData.unshift({name: 'Time', pointValue: rslt[0].pointValue})
// console.log(rslt)
this.setState({
dataSource: this.state.dataSource.cloneWithRows(RawData),
isVisible: false,
});
});
}
renderData(rowData) {
// console.log(rowData.pointValue);
if(rowData.name === 'Time'){
return (
<View>
<View style={{borderColor:'rgba(214, 214, 214,1)',borderWidth:1}}>
<View style={styles.names}>
<Text style={{marginHorizontal: 12, marginVertical:(Platform.OS === 'ios') ? 15 : 16}}>{rowData.name}</Text>
</View>
{rowData.pointValue.map((data) => <View style={{borderBottomWidth:1,borderColor:'rgba(214, 214, 214,1)',padding:8}}><Text>{data.time.split(" ")[1]}</Text></View>)}
</View>
</View>
);
} else {
return (
<View>
<View style={{borderColor:'rgba(214, 214, 214,1)',borderWidth:1}}>
<View style={styles.names}>
<Text style={{marginHorizontal: 12, marginVertical: 6.5}}>{rowData.name}</Text>
<Text>({rowData.engineeringUnit})</Text>
</View>
{rowData.pointValue.map((data) => <View style={{borderBottomWidth:1,borderColor:'rgba(214, 214, 214,1)',padding:8}}><Text>{isNaN(data.value) ? (data.value) : +(Math.round(data.value + "e+1") + "e-1")}</Text></View>)}
</View>
</View>
);
}
}
render() {
var titleConfig = {
title: `Station Data: ${this.props.data.stationName}`,
}
return (
<View style={styles.container}>
<Image style={styles.bg} source={bg} />
<Spinner visible={this.state.isVisible} />
<NavigationBar
title = {titleConfig}
leftButton={<TouchableOpacity onPress={() => this.props.navigator.pop()}>
<Image style={styles.back} source={back} />
</TouchableOpacity>}
style = {{backgroundColor:'rgba(244, 244, 244,1)'}} />
<ScrollView>
<View style={{position:'absolute', right:16, marginVertical:12}}>
<Text>{this.props.data.showDate}</Text>
</View>
<ListView
horizontal={true}
automaticallyAdjustContentInsets={false}
removeClippedSubviews={false}
enableEmptySections={true}
dataSource={this.state.dataSource}
renderRow={this.renderData}
style={styles.listView}
/>
</ScrollView>
</View>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
},
bg: {
position: 'absolute',
left: 0,
top: 0,
width: windowSize.width,
height: windowSize.height
},
names: {
backgroundColor:'rgba(219, 243, 207,1)',
borderBottomWidth:1,
borderColor:'rgba(214, 214, 214,1)',
alignItems:'center',
},
back:
{ marginTop:10,
marginLeft:10,
width:20,
height:20,
},
listView: {
marginVertical:(Screen.width/100)*10,
marginHorizontal:(Screen.width/100)*5
},
});
module.exports =StationData;

Related

Undefined is not an object-React Native

Hi I am new to react native i am facing this error TypeError:undefined is not an object (evaluating this.state.items)
Another problem is it is returning me the data in an array how do i display the data as a string
import React, { Component } from "react";
import {StyleSheet,View,ActivityIndicator,FlatList,Text,TouchableOpacity} from "react-native";
export default class Source extends React.Component {
static navigationOptions = ({ navigation }) => {
return {
title: "Source Listing",
headerStyle: {backgroundColor: "#fff"},
headerTitleStyle: {textAlign: "center",flex: 1}
};
};
constructor(props) {
super(props);
this.state = {
loading: false,
items:[]
};
this.fetchRequest=this.fetchRequest.bind.this
}
FlatListItemSeparator = () => {
return (
<View style={{
height: .5,
width:"100%",
backgroundColor:"rgba(0,0,0,0.5)",
}}
/>
);
}
componentDidMount()
{
fetchRequest();
}
renderItem=(data)=>
<TouchableOpacity style={styles.list}>
<Text style={styles.lightText}>{data.item.name}</Text>
<Text style={styles.lightText}>{data.item.email}</Text>
<Text style={styles.lightText}>{data.item.company.name}</Text>
</TouchableOpacity>
render(){
<FlatList
data= {this.state.dataSource}
ItemSeparatorComponent = {this.FlatListItemSeparator}
renderItem= {item=> this.renderItem(item)}
keyExtractor= {item=>item.id.toString()}
/>
fetchRequest()
{
const parseString = require('react-native-xml2js').parseString;
fetch('http://192.168.200.133/apptak_service/apptak.asmx/Get_Item_Master')
.then(response => response.text())
.then((response) => {
parseString(response, function (err, result) {
console.log(response)
});
}).catch((err) => {
console.log('fetch', err)
this.fetchdata();
})
if(this.state.loading){
return(
<View style={styles.loader}>
<ActivityIndicator size="large" color="#0c9"/>
</View>
)}}
return(
<View style={styles.container}>
</View>
)}
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: "#fff"
},
loader:{
flex: 1,
justifyContent: "center",
alignItems: "center",
backgroundColor: "#fff"
},
list:{
paddingVertical: 4,
margin: 5,
backgroundColor: "#fff"
}
});
Basically what i am trying to do is to get data from webservices and display the app on the screen

Getting JSON Parse error: Unexpected identifier "undefined" when using React native & React navigation?

I am pretty new to React Native, so if the question seems stupid i am sorry in advance, i have been trying for hours to get this to work before asking this question.
I am trying to pass data from a text input to the next screen using firebase database.
I keep getting the error JSON Parse error: Unexpected identifier "undefined", I have attached below my two files, one with the text input (InputForm.js) and the other one which i want to show that data on the screen (ASTConfig1screen)
If anyone can help with this you really are a superstar!
InputForm.js
import React, { Component } from 'react';
import { StyleSheet, ScrollView, ActivityIndicator, View, TextInput } from 'react-native';
import { Button } from 'react-native-elements';
import firebase from '../Firebase';
import { withNavigation } from 'react-navigation';
class InputForm extends Component {
constructor() {
super();
this.ref = firebase.firestore().collection('boards');
this.state = {
name: '',
inventoryclass: '',
outlet: '',
isLoading: false,
};
}
updateTextInput = (text, field) => {
const state = this.state
state[field] = text;
this.setState(state);
}
saveBoard() {
this.setState({
isLoading: true,
});
this.ref.add({
name: this.state.name,
inventoryclass: this.state.inventoryclass,
outlet: this.state.outlet,
}).then((docRef) => {
this.setState({
name: '',
outlet: '',
inventoryclass: '',
isLoading: false,
});
this.props.navigation.navigate('ASTConfig1');
})
.catch((error) => {
console.error("Error adding document: ", error);
this.setState({
isLoading: false,
});
});
}
render() {
if(this.state.isLoading){
return(
<View style={styles.activity}>
<ActivityIndicator size="large" color="#ffa500"/>
</View>
)
}
return (
<ScrollView style={styles.container}>
<View style={styles.subContainer}>
<TextInput style={styles.inputtext}
placeholder={'Name'}
placeholderTextColor="white"
value={this.state.name}
onChangeText={(text) => this.updateTextInput(text, 'name')}
/>
</View>
<View style={styles.subContainer}>
<TextInput style={styles.inputtext}
multiline={true}
numberOfLines={4}
placeholder={'Inventory Class'}
placeholderTextColor="white"
value={this.state.inventoryclass}
onChangeText={(text) => this.updateTextInput(text, 'inventoryclass')}
/>
</View>
<View style={styles.subContainer}>
<TextInput style={styles.inputtext}
placeholder={'Outlet'}
placeholderTextColor="white"
value={this.state.outlet}
onChangeText={(text) => this.updateTextInput(text, 'outlet')}
/>
</View>
<View style={styles.button}>
<Button
large
leftIcon={{name: 'save'}}
title='Save'
onPress={() => this.saveBoard()} />
</View>
</ScrollView>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
padding: 20
},
subContainer: {
flex: 1,
marginBottom: 20,
padding: 5,
borderBottomWidth: 2,
borderBottomColor: '#CCCCCC',
},
inputtext: {
color: 'white',
fontSize: 20
},
activity: {
position: 'absolute',
left: 0,
right: 0,
top: 0,
bottom: 0,
alignItems: 'center',
justifyContent: 'center'
}
})
export default withNavigation(InputForm);
and this is where i would like to show the data on this screen
ASTConfig1.js
import React from 'react';
import {
View,
Text,
StyleSheet,
Button,
ImageBackground,
StatusBar,
SafeAreaView,
TextInput,
ScrollView,
UIManager,
ActivityIndicator
}
from 'react-native';
import {AccordionList} from "accordion-collapse-react-native";
import { Separator } from 'native-base';
import {widthPercentageToDP as wp, heightPercentageToDP as hp} from 'react-native-responsive-screen';
import firebase from '../Firebase';
import Logo from '.././components/Logo';
import Colors from '.././constants/Colors';
import Search from '.././components/Search';
import InputForm from '.././components/InputForm';
class ASTConfig1Screen extends React.Component {
static navigationOptions = {
title: 'ASTConfig1',
};
constructor(props) {
super(props);
this.state= {
isLoading: true,
board: {},
key: '',
status:true,
text: '',
list:[
{
title: 'Getting Started',
body: 'React native Accordion/Collapse component, very good to use in toggles & show/hide content'
},
{
title: 'Components',
body: 'AccordionList,Collapse,CollapseHeader & CollapseBody'
},
{
title: 'Test',
body: 'AccordionList,Collapse,CollapseHeader & CollapseBody'
}
],
}
}
componentDidMount() {
const { navigation } = this.props;
const ref = firebase.firestore().collection('boards').doc(JSON.parse(navigation.getParam('boardkey')));
ref.get().then((doc) => {
if (doc.exists) {
this.setState({
board: doc.data(),
key: doc.id,
isLoading: false
});
} else {
console.log("No such document!");
}
});
}
_head(item){
return(
<Separator bordered style={{alignItems:'center'}}>
<Text>{item.title}</Text>
</Separator>
);
}
_body(item){
return (
<View style={{padding:10}}>
<Text style={{textAlign:'center'}}>{item.body}</Text>
</View>
);
}
ShowHideTextComponentView = () =>{
if(this.state.status == true)
{
this.setState({status: false})
}
else
{
this.setState({status: true})
}
}
render() {
if(this.state.isLoading){
return(
<View style={styles.activity}>
<ActivityIndicator size="large" color="#0000ff" />
</View>
)
}
return (
<View style={styles.screen}>
<ImageBackground
source={require('.././assets/Img/BackGround2.png')}
style={styles.background}>
</ImageBackground>
<SafeAreaView>
<View style={{flex: 1, justifyContent: 'space-between', width: wp('80%')}}>
<View style={styles.logotop}>
<Logo/>
</View>
<View style={styles.editstock}>
<Text style={styles.editstocktext}>EDIT STOCK LIST:</Text>
</View>
{/*Start of 3 buttons Firebase*/}
<View style={styles.three}>
<View style={styles.edit1}>
<Text style={styles.textheader}>{this.state.board.name}</Text>
<Button style={styles.edit} title='Edit' ></Button>
</View>
<View style={{padding: 3}}></View>
<View style={styles.edit2}>
<Text style={styles.text}>{this.state.board.inventoryclass}</Text>
<Button style={styles.edit} title='Edit' ></Button>
</View>
<View style={styles.edit3}>
<Text style={styles.text}>{this.state.board.outlet}</Text>
<Button style={styles.edit} title='Edit' ></Button>
</View>
</View>
{/*End of 3 buttons Firebase*/}
{/*Start of AccordionList*/}
<ScrollView>
<View style={styles.middle}>
<AccordionList
list={this.state.list}
header={this._head}
body={this._body}
/>
</View>
</ScrollView>
{/*End of AccordionList*/}
{/*Start of Search*/}
<View>
{
this.state.status ? null : <View style={styles.bottom}>
<Text style={styles.textbottom}>SEARCH FOR NEW ITEMS:</Text>
<Search />
</View>
}
<Button title="ADD" onPress={this.ShowHideTextComponentView} />
</View>
</View>
</SafeAreaView>
</View>
);
};
};
{/*End of Search*/}
export default ASTConfig1Screen;
but it returns the error - Error adding document: [SyntaxError: SyntaxError: SyntaxError: JSON Parse error: Unexpected identifier "undefined"
in inputform.js saveBoard function you should
this.props.navigation.navigate('Details', {
'ASTConfig1': docRef
});
and remove JSON.parse form other file

onpress stops working when loading new items react-native Android

the following code works fine on iOS, but on android after loading the orders array and rendering it, the onpress event stops working, at first I thought it was a problem with firebase but then I did it locally and I get the same issue.
import React from 'react';
import {
ActivityIndicator,
Alert,
Button,
Dimensions,
Image,
StatusBar,
StyleSheet,
ScrollView,
Text,
TouchableOpacity,
View,
Platform,
RefreshControl,
YellowBox } from 'react-native';
import { Ionicons as Icon } from '#expo/vector-icons';
import { Card, DefaultTheme } from 'react-native-paper';
import NavigationService from '../../Navigation/navigationService';
import _ from 'lodash';
YellowBox.ignoreWarnings(['Setting a timer']);
const _console = _.clone(console);
console.warn = message => {
if (message.indexOf('Setting a timer') <= -1) {
_console.warn(message);
}
};
import Firebase from '../../connection/to-firebase';
const LOGO_URL = 'https://i.imgur.com/BbYaucd.png';
const { width: SCREEN_WIDTH, height: SCREEN_HEIGHT } = Dimensions.get('window');
const styles = StyleSheet.create({
container: {
paddingTop: StatusBar.currentHeight,
width: SCREEN_WIDTH,
height: SCREEN_HEIGHT / 2,
backgroundColor: "#317AFA",
},
innerContainer: {width:SCREEN_WIDTH, alignItems: 'center', justifyContent: 'center' },
header: {position:'absolute', padding: 15, paddingTop: Platform.OS === 'ios' ? 13 : 7, marginTop:SCREEN_HEIGHT*0.05,zIndex:99 },
scrollView: {
position:'absolute',
top:SCREEN_HEIGHT*0.35,
marginHorizontal: 20,
width: SCREEN_WIDTH*0.90,
height: SCREEN_HEIGHT,
zIndex:9999
},
textHeader:{
marginTop:10,
color: 'white',
fontWeight: 'bold',
fontSize: 40,
}
});
const theme = {
colors: {
...DefaultTheme.colors,
primary: '#3498db',
accent: '#f1c40f',
}
}
export default class DefaultScreen extends React.Component {
constructor (props) {
super(props)
console.ignoredYellowBox = [
'Setting a timer'
];
this.state = {
orders: [],
refreshing: false,
timePassed: false
}
}
_onRefresh = () => {
this.setState({refreshing: true});
this.getOrders().then(() => {
this.setState({refreshing: false});
});
//setTimeout(()=>{this.setState({refreshing: false})},1000)
}
async getOrders(){
//let result = await Firebase.extractOrder();
let result = [
{
"Note": "",
"coords": {
"finalLatitude": 14.100751767597542,
"finalLongitude": -87.18541710839844,
"initialLatitude": 14.061113522979957,
"initialLongitude": -87.21807641015624
},
"createdAt": {
"nanoseconds": 686000000,
"seconds": 1576188983
},
"destinataryName": "Eliana Martínez",
"destinataryPhone": "97412032",
"idSubcategory": "1",
"idUsuario": 1,
"isTakenBySomeone": false,
"orderID": "rQAt5IEI687AkoI8rShh",
"products": [
{
"id": 93634,
"observation": "",
"price": "56.00",
"quantity": 1
},
{
"id": 29909,
"observation": "",
"price": "131.00",
"quantity": 97
}
],
"status": "Pending",
"telephone": 23456987,
"transportType": "Motocicleta"
}
]
this.setState({ orders: result});
}
componentDidMount(){
//this.getOrders();
}
renderOrders = (orders) =>{
return orders.map((a,b)=>{
return [
<MainOrders key={a.orderID} dName= {a.orderID} note ={a.Note} transType={a.transportType} orderDetails={a}
navigation={this.props.navigation}
/>
]
})
}
render() {
setTimeout(()=>{this.setState({timePassed: true})}, 1000);
if (!this.state.timePassed){
return (
<View style={styles.container}>
<StatusBar barStyle="dark-content" />
<View style={styles.header}>
<TouchableOpacity
onPress={() => {
this.props.navigation.openDrawer();
}}
style = {{marginTop:'10%'}}
>
<Icon name="md-menu" size={35} color={'#fff'}/>
</TouchableOpacity>
<Text style={styles.textHeader}>Home</Text>
</View>
<View style={styles.innerContainer}>
<ScrollView style={styles.scrollView}
refreshControl={ <RefreshControl refreshing={this.state.refreshing} onRefresh={this._onRefresh}/>}
>
<Card theme={theme}>
<Card.Title title="Order List" subtitle="" />
<Card.Content>
<ActivityIndicator size="small" color="#317AFA" />
</Card.Content>
<Card.Actions>
<Button title="View Order" style={{zIndex:9999, elevation:15}} onPress={()=>{
Alert.alert('Hello World')
}}>View Order</Button>
</Card.Actions>
</Card>
</ScrollView>
</View>
</View>
);
}
else{
const {orders,navigation} = this.state;
DefaultScreen.navigationOptions = {
title: ''
}
return (
<View style={styles.container}>
<StatusBar barStyle="dark-content" />
<View style={styles.header}>
<TouchableOpacity
onPress={() => {
this.props.navigation.openDrawer();
}}
style = {{marginTop:'10%'}}
>
<Icon name="md-menu" size={35} color={'#fff'}/>
</TouchableOpacity>
<Text style={styles.textHeader}>Home</Text>
</View>
<View style={styles.innerContainer}>
<ScrollView style={styles.scrollView}
refreshControl={ <RefreshControl refreshing={this.state.refreshing} onRefresh={this._onRefresh}/>}
>
<Card theme={theme}
>
<Card.Title title="Order List" subtitle="" />
<Card.Content>
{
orders.map((a,b)=>{
return [
<MainOrders key={a.orderID} dName= {a.orderID} note ={a.Note} transType={a.transportType} orderDetails={a}
navigation={this.props.navigation}
/>
]
})
}
</Card.Content>
<Card.Actions>
<Button title="Press me" style={{zIndex:9999}} onPress={()=>{
Alert.alert('Hello World')
}}> Press me</Button>
</Card.Actions>
</Card>
</ScrollView>
</View>
</View>
);
}
}
}
class MainOrders extends React.Component {
constructor() {
super();
}
render() {
return (
<View style={{marginTop:2,marginBottom:2}}>
<Card theme={theme}>
<Card.Title title={this.props.dName} subtitle={this.props.note} />
<Card.Content>
<Text>{this.props.transType}</Text>
</Card.Content>
<Card.Actions>
<Button title="view order" style={{zIndex:9999}} onPress={()=>{
this.props.navigation.navigate('orderDetails',{orderDetails: this.props.orderDetails})
}}> view order</Button>
</Card.Actions>
</Card>
</View>
);
}
}
I tried changing the execution orders,
setting timeout and when I manually filled out the order array was that I realized that the problem is at that point, but I can't see what I'm doing wrong.
"react-native": "0.59.8"
Thanks.

React Native Component doesn't re-render on state change

No matter what I try I can't seem to get my component to update. Below is my code:
import React, { Component } from "react";
import { StyleSheet, View, TouchableOpacity, Image, Text } from "react-native";
import PropTypes from "prop-types";
import { toggleSound } from "logic/Music.js";
import soundOn from "assets/img/swipe.png";
import soundOff from "assets/img/illum-triangle.png";
export default class GlobalSoundButton extends Component {
constructor(props) {
super(props);
this.state = {
audioOff: this.props.audioOff
};
}
componentDidUpdate = prevProps => {
if (prevProps.audioOff !== this.props.audioOff) {
this.setState({ audioOff: this.props.audioOff }, () => {
console.log("SWITCHING STATE", this.state);
};
this.forceUpdate();
}
};
render() {
return (
<View style={styles.soundButtonWrapper} key={this.props.name}>
<TouchableOpacity
style={styles.soundButtonPress}
activeOpacity={0.8}
onPress={() => {
toggleSound(this.props.sounds);
}}
>
<Image
style={styles.soundButton}
source={this.state.audioOff ? soundOff : soundOn}
></Image>
<Text style={styles.text}>
Audio {this.state.audioOff ? "off" : "on"}
</Text>
</TouchableOpacity>
</View>
);
}
}
const styles = StyleSheet.create({
soundButtonWrapper: {
width: "100%",
height: 40,
position: "absolute",
top: 20
},
soundButtonPress: {
width: 40,
height: 40,
position: "absolute",
right: 20
},
soundButton: {
width: 40,
height: 40,
tintColor: "#59BC92"
},
text: {
width: 120,
height: 40,
position: "absolute",
right: 80,
color: "white"
}
});
GlobalSoundButton.propTypes = {
sounds: PropTypes.array
};
The weird part is that I'm using this component in two different screens and in one case it works absolutely fine but in the other screen it doesn't re-render when the audio is changed.
Every time I press it the props get updated so I KNOW that the state updates. The console log always writes out different state so I know the state is updated. I also tried forceUpdate() and adding a key (you can see the key in the code) but it doesn't help.
I'm at a loss here. Has anyone bumped into the same issue or can help? I also know there are several questions quite like this one but no one answered my questions so I had to write my own.
I removed a lot of unrelated code here but basically I pass the props down the following way in my HomeScreen (it's the GlobalSoundButton, and in this case it works):
import GLOBAL from "logic/GlobalState.js";
export default class HomeScreen extends Component {
constructor(props) {
super(props);
this.state = {
audioOff: false,
};
}
async componentDidMount() {
let audioOff;
try {
audioOff = await retrieveData("audioOff");
} catch (err) {
console.error(err);
}
this.setState(
{
audioOff: audioOff === "true"
});
render() {
GLOBAL.homeScreen = this;
return (
<View style={styles.container}>
<View style={styles.bg}>
<ImageBackground
source={pattern}
style={styles.img}
resizeMode="repeat"
imageStyle={styles.innerImg}
/>
</View>
<View style={styles.container}>
<GlobalSoundButton
sounds={this.state.allSounds}
audioOff={this.state.audioOff}
name="HomeScreenKey"
></GlobalSoundButton>
<Text
style={[styles.smallText, styles.ppText]}
onPress={() =>
Linking.openURL(
"https://privacy-illuminati-flip.netlify.com"
).catch(err => console.error("An error occurred", err))
}
>
Privacy Policy
</Text>
<Text style={styles.welcome}>Illuminati Flip</Text>
<TouchableWithoutFeedback
onPressIn={evt => this.grabFinger(evt)}
onPressOut={evt => this.swipe(evt)}
pressRetentionOffset={{ top: 100, left: 0, bottom: 100, right: 0 }}
>
<View style={styles.swipeArea}>
<View style={styles.gridSelection}>
<Animated.View
pointerEvents={"none"}
style={{
...styles.innerGridSelection,
transform: [{ translateX: this.springValue }]
}}
>
{difficulties}
</Animated.View>
</View>
<View style={styles.margin}>
<Animated.Image
source={swipeFinger}
style={{
...styles.hand,
transform: [
{
translateX: this.fingerValue.interpolate({
inputRange: [-1, 1],
outputRange: [-15, 15]
})
}
]
}}
/>
<Text style={styles.smallText}>Swipe to change difficulty</Text>
</View>
</View>
</TouchableWithoutFeedback>
<TouchableOpacity
activeOpacity={0.8}
onPress={() => {
this.checkTutorial();
}}
>
<Text style={styles.button}>Begin Ceremony</Text>
</TouchableOpacity>
<Text
style={[styles.smallText, styles.musicText]}
onPress={() =>
Linking.openURL("https://fanlink.to/triobgame").catch(err =>
console.error("An error occurred", err)
)
}
>
Music by #triobelisk
</Text>
<Text
style={[styles.smallText, styles.devText]}
onPress={() =>
Linking.openURL("https://twitter.com/iamjohnhult").catch(err =>
console.error("An error occurred", err)
)
}
>
Developed by #iamjohnhult
</Text>
</View>
</View>
);
}
}
const styles = StyleSheet.create({
...
});
The difference in my other component where it doesn't work I render it like this:
import GLOBAL from "logic/GlobalState.js";
<GlobalSoundButton
sounds={this.state.allSounds}
audioOff={GLOBAL.homeScreen.state.audioOff}
name="GameScreenKey"
></GlobalSoundButton>
And the GlobalState.js is as follows:
module.exports = {
homeScreen: null
};

Custom Tabs using react-native

I have created custom tabs in react-native but I am unable to select a tab. I have initialized the state for the selected tab but do not know where to set the state.
here is my code:
'use strict';
import React, { Component } from 'react';
import {
AppRegistry,
StyleSheet,
Text,
Image,
View
} from 'react-native';
var Dimensions = require('Dimensions');
var windowSize = Dimensions.get('window');
var bg = require('image!bg');
class TabView extends Component {
constructor(props) {
super(props);
this.state = {
selectedTab: 'list',
selectedTab: 'map'
};
}
render() {
return (
<View style={styles.container}>
<Image style={styles.bg} source={bg} />
<View style={styles.tabView}>
<View style={[styles.listView,styles.selectedView]}>
<Text>List View</Text>
</View>
<View style={[styles.listView,{}]}>
<Text>Map View</Text>
</View>
</View>
</View>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
},
bg: {
position: 'absolute',
left: 0,
top: 0,
width: windowSize.width,
height: windowSize.height
},
tabView: {
flexDirection: 'row',
//bottom: 200,
borderWidth:2,
borderColor:'rgba(4, 193, 3,1)',
borderRadius: 5,
marginHorizontal: 20,
marginTop: 50
},
listView: {
flex: 2,
padding:7,
alignItems:'center'
},
mapView: {
flex: 2,
padding:7,
alignItems:'center'
},
selectedView: {
backgroundColor:'rgba(4, 193, 3,1)',
color: 'white'
}
});
module.exports = TabView
I just want to know where shall I add a check so that I can make a difference in the selected tab
Any help will be appreciated.
Please, check out the code here, to get an idea how it can be done
const Tab = (props) => {
let style = props.isSelected && styles.selectedTab || styles.normalTab;
return (
<View style={style}>
<TouchableHighlight onPress={() => props.onTabPress(props.id)}>
<Text>{props.title}</Text>
</TouchableHighlight>
</View>
)
}
class TabsView extends Component {
constructor(props) {
super(props)
this.state = {
selectedTab: 'one'
}
}
render() {
return (
<View>
<Tab onTabPress={this.onSelectTab.bind(this)} title="One" id="one" isSelected={this.state.selectedTab == "one"}/>
<Tab onTabPress={this.onSelectTab.bind(this)} title="Two" id="two" isSelected={this.state.selectedTab == "two"}/>
</View>
)
}
onSelectTab(selectedTab) {
this.setState({ selectedTab })
}
}
The above code splits your component in two parts, a logical part (TabsView) and a dumb presentational part (Tab)
The logical handles the clickHandler (onSelectTab) which is passed as a prop (onTabPress) to the dumb (Tab) Component.
I just want to know where shall I add a check so that I can make a difference in the selected tab
In the render method, it should go
example:
render() {
let FirstTabStyles = Object.assign(
defaultTabStyles,
(isFirstSelected && selectedStyles || {})
)
let SecondTabStyle = Object.assign(
defaultTabStyles,
(isSecondSelected && selectedStyles || {})
)
return (
<View>
<FirstTab style={FirstTabStyle} />
<SecondTab style={SecondTabStyle} />
</View>
)
}

Categories