I am new to react native and I am having trouble passing variables from one file to another.
module.exports works great when passing classes.
However is there any way in native to pass variables from file to file by exporting?
In the example below, one file (button) is creating an array of random numbers and I want to access that array in another file (genreSelector). Similarly I am trying to pass an array of strings from (genre to genreSelector).
I cant find an example of how to do this so I am under the impression that it isn't possible. How should I be passing information if this isn't possible?
Do I need to have all the functions in my main and call them from within the child classes, if so how do I reference the function of the parent class rather than its own this.function?
So main is rendered in index.android.js and it all works great. Bar of course the passing of arrays from file to file. I tried using states but still cant access the variables as desired.
Apologies for such a basic question asked in such a complicated way.
//this is button.js
import React, { Component } from 'react';
import {
Alert,
AppRegistry,
StyleSheet,
Text,
TouchableHighlight,
View
} from 'react-native';
import styles from '../styles/styles.js';
let rNumbers = [1,2,3];
var Button = React.createClass({
rNumberGen: function(){
let rNumbers = [Math.random(), Math.random(), Math.random()];
},
render: function(){
return(
<TouchableHighlight onPress={this.rNumberGen} style={styles.center}>
<Text style={styles.button}>Generate!</Text>
</TouchableHighlight>
);
}
});
module.exports = rNumbers;
module.exports = Button;
//this is genreSelector
import React, { Component } from 'react';
import {
Alert,
AppRegistry,
StyleSheet,
Text,
View
} from 'react-native';
import{
genre1,
genre2,
genre3
} from './genres.js';
import rNumbers from './button.js';
import styles from '../styles/styles.js';
let a = rNumbers.toString();
Alert.alert('This is', a);
var Genre = React.createClass({
render: function(){
let genre = this.props.selected;
return(
<View style={styles.genre}>
<Text style={styles.center}>{genre}</Text>
</View>
);
}
});
module.exports = Genre;
//This is main.js
import React, { Component } from 'react';
import {
AppRegistry,
StyleSheet,
Text,
View
} from 'react-native';
import
Button
from './button.js';
import
Genre
// genres
from './genreSelector.js';
import
styles
from '../styles/styles.js';
class Main extends React.Component {
render(){
return(
<View style={styles.container}>
<Text style={styles.title}>Genre Genrerator</Text>
<Text style={[styles.h2, styles.h21]}>I am listening to</Text>
<View style={styles.genreContainer}>
<Genre selected='{genres[1]}'/>
<Genre selected='{genres[2]}'/>
<Genre selected='{genres[3]}'/>
</View>
<Text style={styles.h2}>You filthy casual</Text>
<Button/>
</View>
);
}
}
module.exports = Main;
module.exports = rNumbers;
module.exports = Button;
You are overwriting it by assigning like that. You should use export keyword:
export {rNumbers};
export {Button};
then import like so:
import {rNumbers} from './button.js';
import {Button} from './button.js';
edit: error: expected { after export. Added in
Related
I'm trying to style a View in React-native but I keep getting this Error
(undefined is not an object (evaluating 'styles.screen))
I made a simple code ...
import React, {useState} from 'react';
import {StyleSheet, Text, View, Button, TextInput} from 'react-native';
export default function App() {
return (
<View style={styles.screen}>
<Text>I am testing</Text>
</View>
);
const styles = StyleSheet.create({
screen: {
padding: 50,
},
});
}
I spent two hours trying to fix this
This should fix it:
import React, { useState } from 'react';
import { StyleSheet, Text, View, Button, TextInput } from 'react-native';
export default function App() {
return (
<View style={styles.screen}>
<Text>I am testing</Text>
</View>
);
}
const styles = StyleSheet.create({
screen: {
padding: 50,
},
});
You need to move the const styles object outside of your App() function. The way you have it will return before initialising your stylesheet. An alternative is to place it before your return() inside App() but it is more standard to have it outside.
So, after troubleshooting for 3 hours and finding no info on this, I finally have the answer. I used a class template search bar React Native Search Bar and created custom styles for said search bar that was being exported from a file, in a folder named 'components' in a parent folder 'app' that was in my '[project]' folder. I imported the class to each screen as it was a header.
The following was an *incorrect import:
import {SearchComponent} from './app/components/searchComponent'
The correct import is:
import SearchComponent from './app/components/searchComponent'
(Because the SearchComponent was exported as a default component and not a named component in the searchComponent.js file.)
Quick reference to default vs named exports
After correctly importing the component, make sure your styles within that component's folder are named correctly and do not share style names with other styles in your destination file; i.e., name of fileA:styleA != name of fileB:styleA.
After checking your exports and imports very, very carefully and checking your style names with the same detail it worked – and it should work for you, as well.
I have design header, footer video player view, etc as a separate files.
How do I include those in every pages?
I tried this method. but doesn't work.
Follow the below steps:
Create a file eg: Header.js
import React, { Component } from 'react'
import { Text, View } from 'react-native'
class Header extends Component {
render() {
return (
<View>
<Text> Header Component </Text>
</View>
)
}
}
export that component or function to reuse that in other files.
export default Header;
by exporting that function or class you can import that in any js file by using this:
import Header from './Header.js'
OR
import Header from './Header'
Here is how you can use that imported component in other files:
import React, { Component } from 'react'
import { Text, View } from 'react-native'
import Header from './Header' // import that
class App extends Component {
render() {
return (
<View>
<Header /> // use like this
<Text> textInComponent </Text>
</View>
)
}
}
If you have multiple components or function to export in a single file you can't use export default in all of that. you just have to use export only.
like this: Common.js file
export Header;
export Button;
or you can use that like this.
import { Header, Button } from './Common';
I'm trying to make the UI for my app in the below picture:
My App's UI
I follow the instruction of React Navigation to make the Custom Navigator according to the UI but it doesn't work in Android. The red screen appears with the message "Cannot Add a child that doesn't have a YogaNode to a parent without a measure function". Here is my code:
import React, { Component } from 'react';
import { createStackNavigator } from 'react-navigation';
import TabAboutScreen from './TabAbout';
import TabMyLessonScreen from './TabMyLesson';
import TabTeacherScreen from './TabTeacher';
import { ScrollView, View, Text } from '../../../components';
import TabNavigator from './TabNavigator';
import TopBar from './TopBar';
import styles from './styles';
import CourseHeader from './CourseHeader';
import theme from '../../../theme';
import i18n from '../../../i18n';
export const CourseDetailStackNavigator = createStackNavigator({
TabAbout: TabAboutScreen,
TabMyLesson: TabMyLessonScreen,
TabTeacher: TabTeacherScreen,
}, {
headerMode: 'none',
initialRouteName: 'TabAbout',
});
export default class TabCourseDetail extends Component {
static router = CourseDetailStackNavigator.router;
constructor(props) {
super(props);
this._handleOnBackButtonPress = this._handleOnBackButtonPress.bind(this);
}
_handleOnBackButtonPress() {
// do something
}
render() {
return (
<View style={styles.container}>
<TopBar textButton={i18n.t('CMBack')} title={i18n.t('CDCourseDetail')} onPress={this._handleOnBackButtonPress} />
<ScrollView
style={styles.scrollContainer}
stickyHeaderIndices={[1]}
showsVerticalScrollIndicator={false}
alwaysBounceVertical={false}
>
<CourseHeader />
<TabNavigator />
<View style={styles.test}>
<CourseDetailStackNavigator navigation={this.props.navigation} />
</View>
</ScrollView>
</View>
);
}
}
My evironment: react-navigation: 2.12.1, react-native: 0.55.4
I found out that the problem was that I put inside component by following the document of react navigation. It works well in iOS but doesn't work in Android.
Have you ever faced this problem. I'm looking forward to your solutions. Best regard.
Make sure you have not left any commented code in the return method and also have not left any text (string) without Text tag of react native.
Hi I'm new to react so bear with me.
Below is my code...
import React from 'react';
import { StyleSheet, Text, View, TouchableHighlight, AsyncStorage} from 'react-native';
export default class App extends React.Component {
constructor(){
super();
this.state = {
myLeader: 'Joe',
};
}
onPress(){
alert({this.state.myLeader}); // 14
}
render() {
return (
<View>
<TouchableHighlight onPress={this.onPress.bind(this)}>
<Text>{this.state.myLeader}</Text>
</TouchableHighlight>
</View>
);
}
}
How to fix this problem?
error message is this. 'this is a reserved word(14.9) at Home.js:14.9'
I want to use {this.state.myLeader} in
onPress(){
alert({this.state.myLeader});
}
I tried 'bind(this)'
Any clue why?
Be careful with your usage of {}. In the context of JSX, {} can be used to "interpolate" a value within it. But if you're writing plain JavaScript code (as in alert({this.state.myLeader})) you don't need to interpolate anything, you just pass the value this.state.myLeader to alert, as in alert(this.state.myLeader).
Regarding the usage of alert within React Native, you'll probably want to follow #kytwb's advise and use Alert.alert.
Try to replace line 14 with:
console.log(this.state.myLeader)
To use Alert with React Native, take a look at the doc.
First, import Alert from react-native:
import { StyleSheet, Alert, Text, View, TouchableHighlight, AsyncStorage} from 'react-native';
Then, change the onPress function:
onPress(){
Alert.alert(this.state.myLeader); // 14
}
Another solution is to forget about the bind and do this:
onPress = () => {
alert({this.state.myLeader}); // 14
}
<TouchableHighlight onPress={this.onPress}>
I have extended the Text component in order to have a reusable text component with a custom font.
My custom component should accept the styles passed to it and add the custom font to it.
I'm currently doing this:
MyText.js
import React from 'react'
import {
Text,
StyleSheet
} from 'react-native';
export default class MyText extends React.Component {
render() {
const style =
Object.assign( {},
StyleSheet.flatten(this.props.style),
{fontFamily: "My Font"}
);
return (
<Text style={style}>
{this.props.children}
</Text>
);
}
}
While this works as expected, having to flatten the stylesheet every time seems wrong. The above is a trivial example, and I can think of other components on which I could use this pattern. For that reason, I want to make sure I'm not ignoring a more suitable approach.
Well it depends on how much you would want to customize. In this case , if it is just a different font, it could be something like
import React from 'react'
import {
Text,
StyleSheet
} from 'react-native';
import _ from 'lodash';
export default class MyText extends React.Component {
render() {
const filteredProps = _.omit(this.props, 'style');
return (
<Text style={[{fontFamily: "My Font"}, this.props.style]} {...filteredProps} />
);
}
}