Caleb Bird
Caleb Bird

Reputation: 65

set.State is undefined

I have a variable in state called isLoading. The idea is to display a loading message while the program is communicating the server, then display the data. However, at ling 24, I get an error:

TypeError: This.setState is not a function (in 'this.setState({ isloadin: false});

import React from "react";
import { StyleSheet, Text, View, AsyncStorage } from "react-native";

var text;

export default class App extends React.Component {
  constructor(props) {
    super(props);
    state = {
      isLoading: true
    };
  }

  componentDidMount = () => {
    AsyncStorage.getItem("accessToken").then(token => {
      postdata(
        "http://1.0.0.0:1337/loadTransactions",
        { UserID: 69 },
        function(result) {
          text = toString(result.Data[1].ID);
          text = result.Data[1].Label;
          console.log(result.Data[1].Label);
          this.setState({
            isLoading: false
          });
        }
      );
    });
  };
  render() {
    console.log(this.setState.isLoading);

    if (this.setState.isLoading) {
      console.log(this.setState.isLoading);
      return (
        <View style={styles.container}>
          <Text>Loading....</Text>
        </View>
      );
    } else {
      return (
        <View style={styles.container}>
          <Text>Hi, {text}</Text>
          <Text>Test</Text>
        </View>
      );
    }
  }
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: "#fff",
    alignItems: "center",
    justifyContent: "center"
  }
});

Upvotes: 0

Views: 178

Answers (2)

Fawaz
Fawaz

Reputation: 3560

this (ref to the instance of class) might not be available inside the context of AsyncStorage. Save this as another variable and use inside:

componentDidMount = () => {
  const self = this;
  AsyncStorage.getItem("accessToken").then(token => {
    postdata(
      "http://204.48.23.161:1337/loadTransactions",
      { UserID: 69 },
      function(result) {
        text = toString(result.Data[1].ID);
        text = result.Data[1].Label;
        console.log(result.Data[1].Label);
        self.setState({
          isLoading: false
        });
      }
    );
  });
};

Upvotes: 0

nem035
nem035

Reputation: 35481

To maintain the context of a function as the same context where the function was lexically defined, you have to use an arrow function:

componentDidMount = () => {
  AsyncStorage.getItem("accessToken").then(token => {
    postdata(
      "http://204.48.23.161:1337/loadTransactions",
      { UserID: 69 },
      function(result) {
    // ^^^^^^^ use `result => ` here
        text = toString(result.Data[1].ID);
        text = result.Data[1].Label;
        console.log(result.Data[1].Label);
        this.setState({
          isLoading: false
        });
      }
    );
  });
};

Upvotes: 2

Related Questions