본문 바로가기

Projects/React Native 위치 기반 날씨앱

#4. API 요청 중 로딩 화면 구현 및 새로고침 버튼

openweathermap에 비동기 요청을 하기 때문에 로딩 중 화면을 구현해야 한다. 이를 위해선 로딩 중인지를 확인하는 조건문이 필요하고, 로딩중이라면 로딩 UI를 띄우는 부분이 필요하다.

 

//로딩 중임을 표시할 수 있는 UI를 가져온다
import { ActivityIndicator, ActivityIndicatorBase } from 'react-native';

//기존코드와 동일한 부분
if(currentWeather){
    return (
      <View style={styles.container}>
        <StatusBar style="auto" />
        <View style={styles.main}>
          <UnitsPicker unitsSystem={unitsSystem} setUnitsSystem={setUnitsSystem} />
          <ReloadIcon load={load} />
          <WeatherInfo currentWeather={currentWeather} />
        </View>
        <WeatherDetails currentWeather={currentWeather} unitsSystem={unitsSystem} />
      </View>
    );
  }else if (errorMessage){
    return (
      <View style={styles.container}>
        <ReloadIcon load={load} />
        <Text style={styles.text}>{errorMessage}</Text>
        <StatusBar style="auto" />
      </View>
    );
  }else {
  //날씨정보가 있는 것도 아니고, 에러 메시지도 없다면, 로딩중이라 판별가능
    return (
      <View style={styles.container}>
      	
        //로딩중임을 표시하는 UI를 별도의 라이브러리를 활용하여 화면을 구성한다
        <ActivityIndicator size="large" color={colors.PRIMARY_COLOR} />
        <StatusBar style="auto" />
      </View>
    );
  }

비동기통신에서 로딩중이라는 상태는 에러 상태는 아니면서, 아직 정보가 들어오지 않은 상태를 말한다. 이 상태를 조건문으로 정의한 뒤, 로딩중일 때, 로딩 UI를 보여준다.

 

import React from 'react'
import { View, Text, Platform, StyleSheet } from 'react-native'
//새로고침에 사용할 아이콘을 가져온다
import { Ionicons } from '@expo/vector-icons'
import {colors} from '../utils/index'

export default function ReloadIcon({load}) {

	//안드로이드와 ios 상에서 새로고침 아이콘이 다르기 때문에
    //이를 판별할 수 있는 삼항연산자를 넣는다
    const reloadIconName = Platform.OS === "ios" ? 'ios-refresh' : 'md-refresh'

    return (
        <View style={styles.reloadIcon}>
        	//새로고침 아이콘을 누르면 api요청을 진행하는 load 함수가 재실행된다
            <Ionicons onPress={load} name={reloadIconName} size={24} color={colors.PRIMARY_COLOR} />
        </View>
    )
}

새로고침을 사용할 컴포넌트를 별도로 제작하였다. 이제 이 컴포넌트를 app.js에 넣어준다.

 

//export한 새로고침 컴포넌트를 import
import ReloadIcon from './components/ReloadIcon';

if(currentWeather){
    return (
      <View style={styles.container}>
        <StatusBar style="auto" />
        <View style={styles.main}>
          <UnitsPicker unitsSystem={unitsSystem} setUnitsSystem={setUnitsSystem} />
          //새로고침 컴포넌트를 메인화면에 띄우고 load함수를 전달해준다. 
          <ReloadIcon load={load} />
          <WeatherInfo currentWeather={currentWeather} />
        </View>
        <WeatherDetails currentWeather={currentWeather} unitsSystem={unitsSystem} />
      </View>
    );
  }