이번 강좌에서는 리액트 네이티브(React Native)로 단순한 할 일 관리앱(To-Do App)을 만들어 봅니다.
expo-cli 설치
이전에는 create-react-native-app 도구를 사용해서 리액트 네이티브 프로젝트를 생성했다. 하지만, 지금은 expo-cli를 사용하여 프로젝트를 생성한다. 아래와 같이 expo-cli를 설치하자.
$ npm install -g expo-cli
Node v6 이상 버전이 설치되어 있어야 한다.
프로젝트 생성
expo init 를 사용하여 프로젝트를 생성한다.
$ expo init todo-app
$ cd todo-app/
$ npm start
npm start명령은 Expo CLI 서버를 시작한다. 그리고 Expo 모바일 앱을 사용하면 개발 중인 앱을 스마트폰에서 테스트해 볼 수 있다.
앱 설계하기
오래전에 사용했던 무료 mock-up 서비스가 있었는데, 오랜만에 찾아보니 없어졌다. 그래서 앱인벤터를 이용하여 간단하게 화면 설계를 하였다.
기능은 매우 간단하다.
- 텍스트 박스에 할 일을 입력하고 저장 버튼을 누르면 할 일 목록에 추가된다.
- 체크 박스를 누르면 할 일이 체크(완료)된다.
- 삭제 버튼을 클릭하면 할 일 목록에서 삭제된다.
화면은 한 개다. 그리고 화면에 3개의 컴포넌트가 있다. App 컴포넌트, Header 컴포넌트, Body 컴포넌트이다. 리액트는 보통 컴포넌트 단위로 각각 개발하여 조립하는 식으로 구현한다. 이렇게 하면 컴포넌트를 재활용하여 다른 화면을 구현하는데 사용할 수 있다.
컴포넌트 구현하기
이제 컴포넌트를 하나씩 구현해보자. 우선은 UI 만 구현한다. 기능은 다음 강좌에서 구현할 것이다. 그리고 소스 코드에 대한 자세한 설명은 생략한다. 기능을 구현할때는 소스 코드를 자세하게 설명할 것이다.
todo-app
├─ App.js
├─ Header.js
└─ Body.js
Header 컴포넌트
Header.js
import React, { Component } from 'react';
import { StyleSheet, View, TextInput, TouchableOpacity } from 'react-native'
import { MaterialCommunityIcons } from '@expo/vector-icons';
class Header extends Component {
render() {
return (
<View style={styles.container}>
<View style={styles.input}>
<TextInput
style={styles.inputText}
placeholder='Enter new todo'
autoCorrect={ false }
/>
<TouchableOpacity>
<MaterialCommunityIcons style={styles.addBtn} size={30} name='plus-circle' />
</TouchableOpacity>
</View>
</View>
)
}
}
const styles = StyleSheet.create({
container: {
marginLeft: 20,
marginRight: 20,
},
input: {
borderRadius: 10,
backgroundColor: "#FFF",
paddingLeft: 10,
paddingRight: 10,
height: 50,
alignItems: "center",
flexDirection: 'row',
justifyContent: 'space-between',
borderBottomColor: "#bbb",
borderBottomWidth: StyleSheet.hairlineWidth,
},
inputText: {
flex: 1,
},
addBtn: {
color: '#4169E1'
}
});
export default Header;
TouchableOpacity컴포넌트는 터치하면 투명도가 증가한다. 그래서 버튼 대신 많이 사용된다.
Body 컴포넌트
Body.js
import React, { Component } from 'react';
import { MaterialCommunityIcons } from '@expo/vector-icons';
import { StyleSheet, Text, View, TouchableOpacity } from 'react-native';
class Body extends Component {
state = [
{
text: '할일1',
completed: false,
},
{
text: '할일2',
completed: true,
},
{
text: '할일3',
completed: false,
},
]
render() {
return (
<View style={styles.container}>
{
this.state.map(data => (
<View style={styles.todo}>
<View style={styles.todoText}>
<TouchableOpacity style={styles.todoCheckbox}>
{
data.completed
? <MaterialCommunityIcons size={20} name='checkbox-marked-circle-outline' />
: <MaterialCommunityIcons size={20} name='checkbox-blank-circle-outline' />
}
</TouchableOpacity>
<Text>{data.text}</Text>
</View>
<TouchableOpacity>
<MaterialCommunityIcons style={styles.todoDelBtn} size={30} name='delete-outline' />
</TouchableOpacity>
</View>
))
}
</View>
)
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
marginVertical: 5,
marginHorizontal: 20,
padding: 10,
backgroundColor: "#FFF",
borderRadius: 10,
},
todo: {
flexDirection: 'row',
alignItems: "center",
justifyContent: 'space-between',
height: 50,
borderBottomColor: "#bbb",
borderBottomWidth: StyleSheet.hairlineWidth,
},
todoCheckbox: {
marginRight: 5,
},
todoText: {
flexDirection: 'row',
},
todoDelBtn: {
color: '#777'
}
});
export default Body;
data.completed값(True/False)에 따라 할 일 목록의 체크박스 아이콘이 바뀐다.
App 컴포넌트
App.js
import React from 'react';
import { StyleSheet, View, Text } from 'react-native';
import Header from './Header'
import Body from './Body'
export default class App extends React.Component {
render() {
return (
<View style={styles.container}>
<Text style={styles.title}>Todo App</Text>
<Header />
<Body />
</View>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
flexDirection: 'column',
paddingTop: 50,
backgroundColor: "#EEE",
},
title: {
fontWeight: "800",
fontSize: 30,
marginLeft: 20,
marginBottom: 20,
}
});
App 컴포넌트에서는 Header 컴포넌트와 Body 컴포넌트를 보여준다.
이제 앱을 실행 해보자.
앱이 실행되면, 아래와 같은 화면이 나타나야 한다.
다음 강좌에서 할 일을 텍스트박스에 입력하고, 목록에 추가하는 기능을 구현할 것이다.
처음에 낯설고 어려웠던 리액트가 이제는 조금씩 익숙해지고 있습니다. 플러터로 모바일앱을 개발할때와 비교하면, 오류나 문제가 발생했을 때 플러터보다는 빨리 해결 할 수 있었습니다. 리액트 네이티브는 오류 내용을 구글 검색하면 해결 방법을 쉽게 찾을 수 있습니다.
여기까지 읽어주셔서 감사합니다.