0

I'm trying to re-fetch new data on Button Click in React Native. How to do that?

This is my current code and It's not fetching new content on Button Click, Instead nothing happening.

I have done until it's fetching content from API but can't implement refresh on button click because Flatlist is not loading again and again.

Thanks in Advance.

import React, { useEffect, useState } from 'react';
import { ActivityIndicator, FlatList, StyleSheet, View, Text, Button } from 'react-native';

import {
  Colors
} from 'react-native/Libraries/NewAppScreen';


const App: () => React$Node = () => {

  
  const [isLoading, setLoading] = useState(true);
  const [data, setData] = useState([]);


  useEffect(() => {
    fetch('https://exampleapi.dev/')
      .then((response) => response.json())
      .then((json) => setData(json))
      .catch((error) => console.error(error))
      .finally(() => setLoading(false));
  }, []);


  return (
    <>
    <View style={styles.container}>
      {isLoading ? <ActivityIndicator/> : (
        <FlatList
          data={data}
          keyExtractor={({ id }, index) => id}
          renderItem={({ item }) => (
            <Text style={styles.content}>{item.content}</Text>
          )}
        />
      )}
      
    </View>
     <View style={styles.buttonBottom}> 
    <Button
        title="🔀 Refresh"
        onPress={() => this.FlatList}
        style={styles.buttonShare}
        color="#66BB6A" />
     </View>       
    </>
    
  );
};

const styles = StyleSheet.create({
  container: {
    flex: 1,
    justifyContent: 'space-between',
    backgroundColor: '#1b262c',
    padding: 30,
    flexDirection:'row',
    alignItems:'center'
  },
  FlatList: {
    backgroundColor: Colors.aquamarine,
  },
  content: {
    fontSize: 22,
    textAlign: 'left',
    color: '#bbe1fa'
  },
  buttonBottom: {
    fontSize: 22,
    padding: 10,
    backgroundColor: '#1b262c',
  }
});

export default App;

2 Answers 2

2

Give useEffect dependency on which it will trigger when the button will be clicked.

Add new state which will toggle when the button will be clicked:

const App: () => React$Node = () => {
  const [isLoading, setLoading] = useState(true);
  const [data, setData] = useState([]);
  const [refetch, setRefetch] = useState(false); // <= this

Now set refetch as a dependency to useEffect:

useEffect(() => {
    fetch("https://exampleapi.dev/")
      .then((response) => response.json())
      .then((json) => setData(json))
      .catch((error) => console.error(error))
      .finally(() => setLoading(false));
  }, [refetch]);

and in the end, just toggle the state of refetch:

<Button
          title="🔀 Refresh"
          onPress={() => setRefetch(!refetch)}
          style={styles.buttonShare}
          color="#66BB6A"
        />

Final changes should look like this:

import React, { useEffect, useState } from "react";
import {
  ActivityIndicator,
  FlatList,
  StyleSheet,
  View,
  Text,
  Button,
} from "react-native";

import { Colors } from "react-native/Libraries/NewAppScreen";

const App: () => React$Node = () => {
  const [isLoading, setLoading] = useState(true);
  const [data, setData] = useState([]);
  const [refetch, setRefetch] = useState(false);

  useEffect(() => {
    fetch("https://exampleapi.dev/")
      .then((response) => response.json())
      .then((json) => setData(json))
      .catch((error) => console.error(error))
      .finally(() => setLoading(false));
  }, [refetch]);

  return (
    <>
      <View style={styles.container}>
        {isLoading ? (
          <ActivityIndicator />
        ) : (
          <FlatList
            data={data}
            keyExtractor={({ id }, index) => id}
            renderItem={({ item }) => (
              <Text style={styles.content}>{item.content}</Text>
            )}
          />
        )}
      </View>
      <View style={styles.buttonBottom}>
        <Button
          title="🔀 Refresh"
          onPress={() => setRefetch(!refetch)}
          style={styles.buttonShare}
          color="#66BB6A"
        />
      </View>
    </>
  );
};

const styles = StyleSheet.create({
  container: {
    flex: 1,
    justifyContent: "space-between",
    backgroundColor: "#1b262c",
    padding: 30,
    flexDirection: "row",
    alignItems: "center",
  },
  FlatList: {
    backgroundColor: Colors.aquamarine,
  },
  content: {
    fontSize: 22,
    textAlign: "left",
    color: "#bbe1fa",
  },
  buttonBottom: {
    fontSize: 22,
    padding: 10,
    backgroundColor: "#1b262c",
  },
});

export default App;
Sign up to request clarification or add additional context in comments.

2 Comments

You saved me. Thanks a ton.
Welcome, Happy Coding. :)
0

-> Create func to getData from API like:

    useEffect(() => {
        getData()
      }, []);

const getData = ()=>{
    fetch('https://exampleapi.dev/')
      .then((response) => response.json())
      .then((json) => setData(json))
      .catch((error) => console.error(error))
      .finally(() => setLoading(false))
  }

-> and when click on Button, just call:

<Button
          title="🔀 Refresh"
          onPress={getData}
          style={styles.buttonShare}
          color="#66BB6A"
        />

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.