안드로이드/정리(Android)

(Android) 카카오톡 프로필 앱 만들기

김염인 2022. 2. 14. 16:38
adapter를 이용한 RecyclerView의 재사용을 통해 간단한 앱을 만들어 봤다.
recyclerView에 들어갈 view는 firebase를 이용한 이메일 회원가입 기능을 이용하여 회원가입이 성공하면 유저 프로필이 뜨는 앱을 만들었다.

완성앱
최종 구현화면


1. firebase Login 기능 구현하기

firebase와 kotlin 연동은 기본적으로 간단한 작업이다.  firebase 콘솔에서 google.json 형식의 파일과 Kotlin 프로젝트를 연동해준다.

그리고 mainActivity에서 firebaseAuth를 전역으로 사용할 수 있게 불러주고,

 

private val auth: FirebaseAuth by lazy {
    Firebase.auth
}

private var userDB : DatabaseReference? = null
USER의 DB구조 또한 만들어 주어야 하기 때문에 User_DB도 DatabaseReferences형태로 전역으로 불러준다.

 

package com.example.recycler_view_practice

data class User_Model (
    val uid: String,
    val name: String,
    val age: String,
    val job: String,
    val gender : String,
    val key : Long
){
    constructor(): this("","","","","",0)
}
User Data Class 생성해주기 

 

package com.example.recycler_view_practice

class DBKey {
    companion object{
        const val DB_USERS = "Users"
    }
}
firebaseDb 구조를 이용할 users의 key 값을 정의해준다 Users로 설정

 

override fun onStart() {
    super.onStart()

    var currentUser = auth.currentUser

    if (currentUser != null) {
        signInButton.setText("로그아웃")
        signUpButton.isVisible = false
        currentUserName.setText("${currentUser.displayName.toString()} 님")
        currentUserName.isVisible = true
    } else {
        signInButton.setText("로그인")
        signUpButton.isVisible = true
        signUpButton.isEnabled = true
        currentUserName.isVisible = false
    }

}
Current User가 null 인경우는 로그인이 되지 않은 경우를 뜻한다. / 로그인 버튼이 보이도록 설정
Current User가 Notnull 인경우는 로그인이 된 경우를 뜻한다 / 로그아웃 버튼이 보이도록 설정, 회원가입 버튼은 안보이도록 설정

 

2. 앱의 핵심 RecyclerView 구현하기

recyclerView를 구현하기 위해서는 반복될 view를 먼저 만들어주어야 한다. 

item_recycler.xml

cardView를 통해 card형식의 view를 만들어 주었다. 이뷰를 이용해 recyclerview에 반복하여 넣어주며 사용해준다.

 

userDB = Firebase.database.reference.child(DB_USERS)
userDB?.addChildEventListener(object : ChildEventListener {
    override fun onChildAdded(snapshot: DataSnapshot, previousChildName: String?) {
        val usermodel = snapshot.getValue(User_Model::class.java)
        usermodel ?: return
        articleList.add(usermodel)
        userAdapter.submitList(articleList)
        userAdapter.notifyDataSetChanged()
    }

    override fun onChildChanged(snapshot: DataSnapshot, previousChildName: String?) {}
    override fun onChildRemoved(snapshot: DataSnapshot) {}
    override fun onChildMoved(snapshot: DataSnapshot, previousChildName: String?) {}
    override fun onCancelled(error: DatabaseError) {}
})

 

DB_USERS에 저장돼있는 reference의 child 값들을 가져온다.

가져욘 값들을 adapter에 넣어주어 view에 뿌려 준다

 

package com.example.recycler_view_practice

import android.content.Context
import android.view.LayoutInflater
import android.view.ViewGroup
import android.widget.Toast
import androidx.recyclerview.widget.DiffUtil
import androidx.recyclerview.widget.RecyclerView
import com.example.recycler_view_practice.DBKey.Companion.DB_USERS
import com.example.recycler_view_practice.databinding.ItemRecyclerBinding
import com.google.firebase.database.FirebaseDatabase
import com.google.firebase.ktx.Firebase

class MainAdapter(val context : Context, val onItemClicked: User_Model): androidx.recyclerview.widget.ListAdapter<User_Model, MainAdapter.ViewHolder>(diffUtil) {
    inner class ViewHolder(private val binding: ItemRecyclerBinding):
            RecyclerView.ViewHolder(binding.root){
                fun bind(userModel: User_Model){
                    if(userModel.gender == "남자"){
                        binding.itemImageView.setBackgroundResource(R.drawable.man)
                    }
                    else{
                        binding.itemImageView.setBackgroundResource(R.drawable.woman)
                    }
                    binding.ageTextView.text = userModel.age
                    binding.jobTextView.text = userModel.job
                    binding.nameTextView.text = userModel.name

                    binding.root.setOnClickListener {
                        Toast.makeText(context, "${userModel.name}님 환영합니다.", Toast.LENGTH_LONG).show()
                    }
                }


            }

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        return ViewHolder(ItemRecyclerBinding.inflate(LayoutInflater.from(parent.context), parent, false))
    }

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        holder.bind(currentList[position])
    }


    companion object {
        val diffUtil = object : DiffUtil.ItemCallback<User_Model>() {
            override fun areItemsTheSame(oldItem: User_Model, newItem: User_Model): Boolean {
                return oldItem.key == newItem.key
            }

            override fun areContentsTheSame(oldItem: User_Model, newItem: User_Model): Boolean {
                return oldItem == newItem
            }

        }
    }
}

adpater를 구현해주고 itemClicked 이벤트를 받아 아이템을 클릭하면 어떻게 될지 setonclickListner를 통해 구현해주었다. 남자인 경우와 여자인 경우를 drawable로 다르게 image를 넣어주었다.

 

최종 구현화면

 

느낀점

recyclerVeiw를 다루는 방법과 firebaseDB구조를 다루는 법을 익혀 놓으면 카카오톡과 같이 채팅 앱도 만들 수 있고 더욱더 커스터마이징해서 나중에 user Info를 가진 앱이나 많은 데이터를뿌려줄 수 있는 앱을 만들때 많이 유용할 것 같다. Firebase를 이용한 DB구조를 더욱더 익혀 여기서 발전해서 채팅기능 또한 넣어보고 싶다.