Taxi App UI 4

윤수환·2025년 3월 16일

React Native

목록 보기
11/26

패키지
npm install @react-native-async-storage/async-storage

Async 비동기식
then, catch, finally
await - 앞에 async가 있을때만 사용가능 동기식 처럼 기다림

변경점
Main_Setting.tsx

import { JSX } from "react";
import { SafeAreaView, StyleSheet, Text, TouchableOpacity, FlatList } from "react-native";
import AsyncStorage from "@react-native-async-storage/async-storage";
import { useNavigation, ParamListBase } from "@react-navigation/native";
import { StackNavigationProp } from "@react-navigation/stack";

function Main_Setting() : JSX.Element {
    console.log("-- Main_Setting()")

    const navigation = useNavigation<StackNavigationProp<ParamListBase>>()

    const onLogout = () => {
        AsyncStorage.removeItem('userId').then(() => {
            navigation.popToTop()
        })
    }

    let arrSetMenu=[{id:0, name:'로그아웃'}]

    return (
        <SafeAreaView style={styles.container}>
            <FlatList style={{width:"100%"}}
            data={arrSetMenu}
            renderItem={(row:any) => {
                console.log("row =" + JSON.stringify(row))
                return (
                    <TouchableOpacity style={[styles.container]}>
                        <Text style={styles.textForm}>{row.item.name}</Text>
                    </TouchableOpacity>
                )
            }}
            keyExtractor={(item:any) => item.id}
            />
        </SafeAreaView>
    )
}

const styles = StyleSheet.create({
    container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center'
    },
    textForm: {
        borderWidth: 1,
        borderColor: '#3498db',
        padding: 20,
        width: '100%',
        fontSize: 18,
        textAlign: 'center',
        color: '#3498db',
        marginBottom: 2
    }
})

export default Main_Setting

Login.tsx

import { JSX } from "react";
import { SafeAreaView, StyleSheet, Text, TouchableOpacity, View } from "react-native";
import { useNavigation, ParamListBase } from "@react-navigation/native";
import { StackNavigationProp } from "@react-navigation/stack";
import Icon from 'react-native-vector-icons/FontAwesome';
import { TextInput } from "react-native-gesture-handler";
import { useState } from "react";
import AsyncStorage from "@react-native-async-storage/async-storage";

function Login() : JSX.Element {
    console.log("-- Login()")

    const navigation = useNavigation<StackNavigationProp<ParamListBase>>()

    const [userId, setUserId] = useState('')
    const [userPw, setUserPw] = useState('')
    const [disable, setDisable] = useState(true)

    const onIdChange = (newId:string) => {
        newId && userPw ? setDisable(false) : setDisable(true)
        setUserId(newId)
    }

    const onPwChange = (newPw:string) => {
        newPw && userPw ? setDisable(false) : setDisable(true)
        setUserPw(newPw)
    }

    const gotoRegister = () => {
        navigation.push('Register')
    }

    const gotoMain = () => {
        AsyncStorage.setItem('userId', userId)
        .then(() => {
            navigation.push('Main')
        })
        
    }

    return (
        <SafeAreaView style={styles.container}>
            <View style={styles.container}>
                <Icon name='taxi' size={80} color={'#3498db'}/>
            </View>
            <View style={styles.container}>
                <TextInput style={styles.input} placeholder={"아이디"}
                onChangeText={onIdChange}/>
                <TextInput style={styles.input} placeholder={"패스워드"}
                secureTextEntry={true}
                onChangeText={onPwChange}/>
            </View>

            <View style={styles.container}>
                <TouchableOpacity style={disable ? styles.buttonDisable : styles.button} disabled={disable} onPress={gotoMain}>
                    <Text style={styles.buttonText}>로그인</Text>
                </TouchableOpacity>
                <TouchableOpacity style={[styles.button, {marginTop:5}]} onPress={gotoRegister}>
                    <Text style={styles.buttonText}>회원가입</Text>
                </TouchableOpacity>
            </View>
            
        </SafeAreaView>
    )
}

const styles = StyleSheet.create({
    container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center',
        width: '100%'
    },
    button: {
        width: '70%',
        backgroundColor: '#3498db',
        paddingVertical: 10,
        paddingHorizontal: 20,
        borderRadius: 5
    },
    buttonDisable: {
        width: '70%',
        backgroundColor: 'gray',
        paddingVertical: 10,
        paddingHorizontal: 20,
        borderRadius: 5
    },
    buttonText: {
        color: 'white',
        fontSize: 16,
        textAlign: 'center'
    },
    input: {
        width: '70%',
        height: 40,
        borderWidth: 1,
        borderColor: 'gray',
        marginVertical: 10,
        padding: 10
    }
})

export default Login

Intro.tsx

import { JSX } from "react";
import React from "react";
import { SafeAreaView, StyleSheet, Text, TouchableOpacity } from "react-native";
import { useNavigation, ParamListBase } from "@react-navigation/native";
import { StackNavigationProp } from "@react-navigation/stack";
import Icon from 'react-native-vector-icons/FontAwesome';
import { useFocusEffect } from "@react-navigation/native";
import AsyncStorage from "@react-native-async-storage/async-storage";

function Intro() : JSX.Element {
    console.log("-- Intro()")

    const navigation = useNavigation<StackNavigationProp<ParamListBase>>()

    useFocusEffect(React.useCallback(() => {
        setTimeout(async () => {

            let userId = await AsyncStorage.getItem('userId')
            let isAutoLogin = false
            if (isAutoLogin) {
                navigation.push("Main")
            }
            else {
                navigation.push("Login")
            }
        }, 2000)
    }, []))

    return (
        <SafeAreaView style={styles.container}>
            <Icon name='taxi' size={100} color={'#3498db'}/>
        </SafeAreaView>
    )
}

const styles = StyleSheet.create({
    container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center'
    }
})

export default Intro

0개의 댓글