state property undefined in render function - react-native

In the render function on one of my views I am trying to have the opacity of a view be tied to a state property: this.state.infoOpacity.
This is turning an error "undefined is not an object (evaluating 'this.state.infoOpacity')"
Any guidance would be helpful.
export default class BookView extends Component
{
constructor(props) {
super(props);
this.state = {
hideInfo:false,
infoOpacity:0.80,
swiperWidth:Dimensions.get('window').width,
swiperHeight:Dimensions.get('window').height
};
}
render() {
pages.forEach(function(ranPage){
photoViews.push(
<View key={ranPage.letter} style={{width: Dimensions.get('window').width, height: Dimensions.get('window').height}}>
<View style={[styles.meow,{opacity: this.state.infoOpacity}]}>
<Text style={styles.text}>{ranPage.name}</Text>
<Text style={styles.text}>{ranPage.phonetic}</Text>
<Text style={styles.text2}>{ranPage.description}</Text>
</View>
</View>
)
});
return (
<View style={{flex:1}}>
<Swiper showsButtons={false} style={{backgroundColor:'#000'}} width={this.state.swiperWidth} height={this.state.swiperHeight}>
{photoViews}
</Swiper>
</View>
);
}
}

The context changed in your forEach function. Use an arrow function to fix your issue. So instead of
pages.forEach(function(ranPage){ ... });
write this
pages.forEach((ranPage) => { ... });

Related

React native collapsible malformed calls from JS: field sizes are different

I'm using oblador/react-native-collapsible
and when I try to toggle the collapsible component I get a warning message Malformed calls from JS: field sizes are different.
Here is my code:
constructor(props) {
super(props);
this.toggle = this.toggle.bind(this);
this.state = {
isCollapsed: true
};
}
toggle() {
this.setState({ isCollapsed: !this.state.isCollapsed });
}
render() {
return (
<SafeAreaView style={{ flex: 1 }}>
<TouchableOpacity onPress={this.toggle}>
<Icon
active
type="FontAwesome"
name="caret-down"
/>
</TouchableOpacity>
<Collapsible collapsed={this.state.isCollapsed}>
<View>
<Text>Hello World!</Text>
</View>
</Collapsible>
</SafeAreaView>
);
}
I followed the example code here
Can anyone help me solve this? Thank you!

How to change text in sibling component in react-native?

I have an 'OutputBox' component and want to change the text being displayed in the component when I click a button.
I've read about props and state and i can't seem to get them working the way i need them too. I just started react-native and have a heavy background c++. I thought i could just declare a variable, 'text' in the 'OutputBox' component and then call a 'setOutputBoxText' function and change the 'text' var. Getters and Setters paradigm. I just cant wrap my head around how to use props to 'pass args' to components and the such.
export default class HelloWorldApp extends Component {
render() {
return (
<View style={{ flex: 1, alignItems: "flex-end" }}>
<CustomButton
text="N"
onPress={() => {
OutputBox.setOutputBox('You head North');
alert("You head North");
}}
/>
<OutputBox></OutputBox>
</View>
);
}
}
class CustomButton extends Component {
render() {
const { text, onPress} = this.props;
return (
<TouchableOpacity style={styles.buttonStyle}
onPress={() => onPress()}
>
<Text style={styles.textStyle}>{text}</Text>
</TouchableOpacity>
);
}
}
class OutputBox extends Component {
constructor( props ) {
super( props );
var displayText = 'Hello Traveller';
}
setOutputBox( newText ){
displayText = newText;
}
render() {
return (
<View style={ styles.outputBox }>
<Text>{this.displayText}</Text>
</View>
);
}
}
I would expect to be able to do something similar to what i have, however i just keep getting a typeError: OutputBox.setOutputBox is not a function. I know this is the wrong paradigm for react-native. I can't seem to wrap my head around doing something like this with props and state.
UPDATE: I no longer get the error typeError: OutputBox.setOutputBox is not a function. Now, the OutputBox just doesn't display anything. How I do I get the <Text/> component of the OutputBox to change and display.
Here is the correct way to do it.
export default class HelloWorldApp extends Component {
constructor( props ) {
super( props );
this.state={
displayText : 'Hello Traveller',
}
}
render() {
return (
<View style={{ flex: 1, alignItems: "flex-end" }}>
<CustomButton
text="N"
onPress={() => {
this.setState({displayText:'You head North'})
}}
/>
<OutputBox text={this.state.displayText}/>
</View>
);
}
}
class CustomButton extends Component {
render() {
const { text, onPress} = this.props;
return (
<TouchableOpacity style={styles.buttonStyle}
onPress={() => onPress()}
>
<Text style={styles.textStyle}>{text}</Text>
</TouchableOpacity>
);
}
}
class OutputBox extends Component {
render() {
return (
<View style={ styles.outputBox }>
<Text>{this.props.displayText}</Text>
</View>
);
}
}
I just removed the OutputBox component and put a <Text> component in there. I realized i didn't need the OutputBox component, since it's only purpose was to display text. This is what i ended up with
export default class HelloWorldApp extends Component {
constructor( props ) {
super( props );
this.state={
displayText : 'Hello Traveller',
}
}
render() {
return (
<View style={{ flex: 1, alignItems: "flex-end" }}>
<CustomButton
text="N"
onPress={() => {
this.setState({displayText:'You head North'})
}}
/>
<Text>{this.state.displayText}</Text>
</View>
);
}
}
class CustomButton extends Component {
render() {
const { text, onPress} = this.props;
return (
<TouchableOpacity style={styles.buttonStyle}
onPress={() => onPress()}
>
<Text style={styles.textStyle}>{text}</Text>
</TouchableOpacity>
);
}
}

undefined not an object ->react native JS

my Code is:
import Note from './Note';
export default class Main extends React.Component {
constructor(props) {
super(props);
this.state = {
noteArray: [],
noteText: '',
}
}
render() {
let notes = this.state.noteArray.map((val, key)=>{
return <Note key={key} keyval={key} val={val}
deleteMethod={()=>this.deleteNote(key)}></Note>
});
return (
<View style={styles.container}>
<View style={styles.header}>
<Text style={styles.headerText}>Yapılacaklar Listesi</Text>
</View>
<ScrollView style={styles.scrollContainer}>
{notes}
</ScrollView>
<View style={styles.footer}>
<TextInput
style={styles.textInput}
placeholder='Notunuz...'
placeholderTextColor='white'
underlineColorAndroid='transparent'
onChangeText={(noteText)=> this.setState({noteText})}
value={this.state.noteText}>
</TextInput>
</View>
<TouchableOpacity onPress={ this.addNote.bind(this) } style={styles.addButton} >
<Text style={styles.addButtonText}>+</Text>
</TouchableOpacity>
</View>
);
}
addNote()
{
if (this.state.noteText){
var d=new Date;
this.state.noteArray.push({
'date':d.getFullYear()
+'/'+(d.getMonth()+1)
+'/'+d.getDate()
});
this.setState({ noteArray: this.state.NoteArray })
this.setState({ noteText: '' })
}
}
}
My error is:undefined not an object (evaluating 'this.state.noteArray.map')
how can i solve this?
i started learn react. The error's screen is
Error Screen
it's my first example. :)
You have to make sure your array is existent:
let notes = !!this.state.noteArray && this.state.noteArray.map((val, key)=>{
should do the job.
The !! is a double negation to avoid another typical error.
This way if noteArray doesn´t exist, the second part after the && is not executed. You could go further and add security checks like checking that it actually is an array etc. but with the above line it should work as long as you actually have an array.

Unexpected token, expected; When calling a function in react native

I am trying to call a function when a button is pressed.
After I add the function, it errors out with the Unexpected token error.
I followed instructions from all previous similar questions but it doesn't solve my case. Please help.
_handlePress: function() {
console.log("Butto GO!")
}
export default class fun extends Component {
render() {
return (
<View style={styles.container}>
<TouchableHighlight onPress={() => this._handlePress()}>
<Image style={{width: 50, height: 50}} source={require('./go.png')} />
</TouchableHighlight>
</View>
);
}
}
Also, Should the called function be defined before the default class?
Put the function behind render, after the class and I don't know if u do test : function() it works there so try my example and give feedback
export default class fun extends Component {
_handlePress() {
console.log("Butto GO!")
}
render() {
return (
<View style={styles.container}>
<TouchableHighlight onPress={() => this._handlePress()}>
<Image style={{width: 50, height: 50}} source={require('./go.png')} />
</TouchableHighlight>
</View>
);
}
}
or if you want to do behind the export class you can use _handlePress() instead of this._handlePress() and it should work!
Example:
'use strict';
import React, {Component} from 'react';
import {View,Text,TouchableOpacity,Alert,Dimensions} from 'react-native';
const windows = Dimensions.get('window');
export default class Feed extends Component {
_test(){
Alert.alert("Test");
console.log("It worked!");
}
render() {
return (
<View style={{flex: 1}}>
<TouchableOpacity onPress={() => this._test()}>
<Image source={require('../image/2.jpg')} style={{height: windows.height, width: windows.width, }} />
</TouchableOpacity>
</View>
);
}
}

React Native - Error navigating to child components

I am able to define the initial route(Home) and the app navigates to that route. Inside Home I am calling another component called BoxLists which is displayed as expected. The issue I am having is when calling another component called StationOne from inside BoxLists.
I am getting the following error: uncaught error: undefined is not an object (evaluating 'this.props.navigator.push'
So the question is: How can I navigate from BoxLists to StationOne?
Note: I am planning to navigate to additional components(StationOne, StationTwo, StationN+1) from BoxLists.
Here is the code although you can go to RNPlayground at https://rnplay.org/apps/rLB5HQ. Thanks!
class App extends React.Component {
navigatorRenderScene(route,navigator){
if (route.title == "Home")
{
return( <Home navigator={navigator} /> );
}
if (route.title == "StationOne")
{
return( <StationOne navigator={navigator} /> );
}
}
render() {
return (
<Navigator
initialRoute = {{ title: "Home" }}
renderScene = {this.navigatorRenderScene.bind(this)}
/>
);
}
}
class Home extends React.Component {
render() {
return (
<View style={{flex: 1}}>
<View style={styles.header}>
<Text style={styles.headerText}>AdView</Text>
</View>
<BoxLists author="station one" navigator={navigator} />
</View>
);
}
}
class BoxLists extends React.Component {
_goToStation(){
this.props.navigator.push({
title: 'StationOne'
});
}
render() {
return (
<View>
<Text>You are in BoxList. The passed prop is: {this.props.author}</Text>
<TouchableHighlight onPress={this._goToStation.bind(this)}>
<Text>Press here to go to StationOne</Text>
</TouchableHighlight>
</View>
);
}
}
class StationOne extends React.Component {
render() {
return (
<View style={{flex: 1}}>
<Text> This is station one </Text>
</View>
);
}
}
class Home extends React.Component {
render() {
return (
<View style={{flex: 1}}>
<View style={styles.header}>
<Text style={styles.headerText}>AdView</Text>
</View>
<BoxLists author="station one" navigator={this.props.navigator} />
</View>
);
}
}
You need to pass this.props.navigator for the BoxLists component as shown above