import React, { useState, useEffect } from 'react';
import { View, Text, Button, ActivityIndicator, StyleSheet } from 'react-native';
export default function DataFetchScreen() {
const [loading, setLoading] = useState(false);
const [error, setError] = useState(null);
const [data, setData] = useState(null);
async function fetchData() {
setLoading(true);
setError(null);
setData(null);
try {
const response = await fetch('https://jsonplaceholder.typicode.com/todos/1');
if (!response.ok) throw new Error('Network response was not ok');
const json = await response.json();
setData(json);
} catch (e) {
setError('Failed to load data.');
} finally {
setLoading(false);
}
}
useEffect(() => {
fetchData();
}, []);
return (
<View style={styles.container}>
{loading && <ActivityIndicator size="large" color="#0000ff" accessibilityLabel="Loading indicator" />}
{!loading && error && <Text accessibilityRole="alert" style={styles.errorText}>{error}</Text>}
{!loading && data && <Text style={styles.dataText}>{data.title}</Text>}
<Button title="Retry" onPress={fetchData} accessibilityLabel="Retry fetching data button" />
</View>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
padding: 16
},
errorText: {
color: 'red',
marginBottom: 12,
fontSize: 16
},
dataText: {
fontSize: 18,
marginBottom: 12
}
});This screen uses React Native hooks to manage loading, error, and data states.
The fetchData function is async. It sets loading to true and clears previous error and data. Then it fetches data from a fake API. If successful, it saves the data. If there is an error, it sets an error message. Finally, it sets loading to false.
The useEffect hook calls fetchData once when the screen loads.
The UI shows a spinner while loading, an error message if there was a problem, or the fetched data's title if successful. The Retry button lets the user try fetching again.
Accessibility labels and roles help screen readers understand the UI states.