APP/React Native

[React Native] 지역 날씨 어플 만들기 3부 (NomadCoder)

isfp_yykkng 2024. 8. 14. 17:40

[React Native] 지역 날씨 어플 만들기 3부 (NomadCoder)

 

지난 게시물을 통해서 Expo-location API를 이용하여 도시 지역 정보를 받아와 적용해 보았다. 혹시 아직 이전 게시물들을 못 봤다면 아래 링크를 타고 보고 와주세요 🙏


지역 날씨 어플 만들기 2부

2024.08.14 - [APP/React Native] - [React Native] 지역 날씨 어플 만들기 2부 (NomadCoder RN)

 

[React Native] 지역 날씨 어플 만들기 2부 (NomadCoder RN)

[React Native] 지역 날씨 어플 만들기 2부 (NomadCoder RN) 지역 날씨 어플의 레이아웃, 외관을 1부에 만들어 보았다. 혹시 아직 1부를 못 봤다면 아래 링크를 타고 보고 와주세요 🙏지역 날씨 어

yy-kkang.tistory.com

 

이번 게시글은 openweathermap API를 통해서 우리가 설정한 지역의 시간대별 날씨 정보를 받아와 볼 것이다.

 

Openweatehrmap API  란

 

openweathermap API는 국내외의 날씨 정보를 제공하는 오픈 API 이다. 이 날씨 API는 완전 무료는 아니고, 부분 무료이기 때문에 다른 날씨 정보 API를 이용해도 된다. 

 

 

우리는 Free로 주어진 3-hour Forecast 5 days API 를 사용할 것이고 이 API를 사용하기 위해서 openweathermap 에 가입하여 API Key 를 얻어야 한다. 

 

Openweathermap API 로 날씨 정보 얻어오기

우리가 사용한 3-hour / 5 Day forecast data API 정보이다.

https://openweathermap.org/forecast5#name5 

 

5 day weather forecast - OpenWeatherMap

 

openweathermap.org

const API_KEY = "d61136ecb7cd16424edaaea7bcf43eab";

export default function App() {
    const [days, setDays] = useState([]);
    const ask = async () => {
    						...   
        const { list } = await (
            await fetch( 
            	`https://api.openweathermap.org/data/2.5/forecast?lat=${latitude}&lon=${longitude}&appid=${API_KEY}&units=metric`
            )
    	).json();
    	const filteredList = list.filter(({ dt_txt }) => dt_txt.endsWith("00:00:00"));
    	setDays(filteredList);
    };

 

요청을 보내기 위한 fetch 주소를 위 사이트에서 가져오면 된다. 요청값으로 들어갈 값들은 위 코드와 같이 " ${  } " 로 변수를 추가하면 된다. 이렇게 요청을 보내고 받은 정보를 .json() 을 통해서 json 객체로 받아 list 객체에 저장한다.

 

이렇게 받은 list 객체 중 dt_txt의 끝이 "00:00:00" 으로 끝나는 정시의 값들만 걸러서 filteredlist에 저장한 후 이를 days 리스트 변수에 저장한다. 

 

json 객체로 받은 날씨 정보 객체를 map으로 뿌리기

배열 리스트의 모든 원소값들을 가장 잘 뿌릴 수 있는 javascript 문법은 바로 Array.map() 이다. 우리는 이 map() 함수를 이용하여 날씨 정보들을 뿌릴 것이다. 

 

        {days.length === 0 ? (
          <View style={styles.day}></View>
        ) : (
          days.map((day, index) => (
            <View key={index} style={styles.day}>
              <Text style={styles.temp}>
                {parseFloat(day.main.temp).toFixed(1)}
              </Text>
              <Text style={styles.description}>{day.weather[0].main}</Text>
              <Text style={styles.tinyText}>{day.weather[0].description}</Text>
            </View>
          ))
        )}

 

위 코드를 보면 알 수 있듯이 삼항 연산자를 이용하여 days 안에 아무것도 없다면 아무 것도 없는 빈 View 를, 아니면 온도, 날씨, 이에 대한 추가 정보 들을 Text를 통해서 뿌린다. 

 

const styles = StyleSheet.create({
  					...
  day: {
    width: SCREEN_WIDTH,
    alignItems: "center",
  },
  temp: {
    marginTop: 50,
    fontSize: 178,
  },
  description: {
    marginTop: -30,
    fontSize: 60,
  },
  tinyText: {
    fontSize: 20,
  },
});

 

style 정보에 대한 코드들은 다음과 같다.

 

Days가 빈 배열일 때 ActivityIndicator로 로딩 화면 띄우기

ActivityIndicator 는 RN에서 제공하는 circular loading indicator 이다. 즉, 말 그대로 로딩 중에 대한 컴포넌트이다.

 

더 자세한 정보는 이 링크를 참고! https://reactnative.dev/docs/activityindicator

 

ActivityIndicator · React Native

Displays a circular loading indicator.

reactnative.dev

import {
  StyleSheet,
  Text,
  View,
  ScrollView,
  Dimensions,
  ActivityIndicator,
} from "react-native";
				
			...
            
        {days.length === 0 ? (
          <View style={styles.day}>
            <ActivityIndicator
              color="white"
              size="large"
              style={{ marginTop: 10 }}
            />

 

이렇게 days의 길이가 0일 때, 즉 빈 배열일 때 하얀색의 큰 ActivityIndicator 를 띄었다. 결과 화면은 아래와 같다.

 

 

이 사진은 빈 배열이 아닐 때의 사진이다.

 

아이콘으로 조금 더 화면 꾸미기

" expo init " 을 이용하여 프로젝트를 만들었다면 expo의 vector-icons는 모두 자동으로 깔려있을 것이다. 우리는 이 아이콘을 이용할 것이다. 이를 위해 먼저 import가 필요하다.

import { Ionicons } from "@expo/vector-icons";

 

import를 한 후 이 링크로 사용할 아이콘을 고른다. ( expo icons : https://icons.expo.fyi/Index )

 

@expo/vector-icons directory

 

icons.expo.fyi

 

여기서 사용할 아이콘들을 클릭하면 아래 사진과 같이 icon family를 import 하고 이를 렌더링 화면에 추가하면 된다.

 

우리가 사용할 아이콘들을 객체 key와 value를 통해서 사용하면 된다. 이에 대한 코드는 다음과 같다.

import Fontisto from "@expo/vector-icons/Fontisto";
const icons = {
  Clouds: "cloudy",
  Clear: "day-sunny",
  Atmosphere: "cloudy-gusts",
  Snow: "snow",
  Rain: "rains",
  Drizzle: "rain",
  Thunderstorm: "lightning",
};

export default function App() {

			...
            
          days.map((day, index) => (
            <View key={index} style={styles.day}>
              <View
                style={{
                  flexDirection: "row",
                  alignItems: "flex-end",
                  width: "80%",
                  justifyContent: "space-around",
                }}
              >
                <Text style={styles.temp}>
                  {parseFloat(day.main.temp).toFixed(1)}
                </Text>
                <Fontisto
                  name={icons[day.weather[0].main]}
                  size={68}
                  color="black"
                  style={{ marginBottom: 25 }}
                />
              </View>

 

더 자세한 코드는 밑에 Github 나 NomadCoder 강의를 통해 확인하는 것이 좋다!

 

이렇게 NomadCoder 의 React Native weather app 게시물 작성이 끝났다. 이후 더 꾸민다면 게시물을 통해서 볼 수 있을 것이다. 

 

⚠️이 게시물의 모든 자료의 출처와 저작권은 노마드코더 강의에 있습니다. ⚠️

 


<참고>

opnweathermap API로 날씨 정보 주기

https://github.com/hoyeol0513/react_native_practice_nomad_weather/commit/2de17a81adc28d0e0e063d33e165f3d66279c2a2

 

using openweathermap api, get timely weather · hoyeol0513/react_native_practice_nomad_weather@2de17a8

hoyeol0513 committed Aug 13, 2024

github.com

 

Icon 추가

https://github.com/hoyeol0513/react_native_practice_nomad_weather/commit/c1e3f6736070f3d13bf8a0dd67470ed6bd5fe710

 

using expo-icons, add weather icons · hoyeol0513/react_native_practice_nomad_weather@c1e3f67

hoyeol0513 committed Aug 13, 2024

github.com