안드로이드

안드로이드 + Firebase Realtime Database 실시간 채팅 앱 만들기 Firebase realtime database android firebase database realtime chatting

알통몬_ 2017. 4. 28. 19:04
반응형



안녕하세요 알통몬입니다.

공감 및 댓글은 포스팅 하는데 아주아주 큰 힘이 됩니다!!

포스팅 내용이 찾아주신 분들께 도움이 되길 바라며

더 깔끔하고 좋은 포스팅을 만들어 나가겠습니다^^

 

예전에 했던 포스팅에 이어집니다.

2017/03/19 - [안드로이드] - 안드로이드 앱, 안드로이드 프로젝트에 firebase 추가하는 방법

위 포스팅에서 안드로이드 프로젝트에 firebase를 추가하는 방법에 대해 알아봤는데요.

이번 포스팅부터 드디어 안드로이드 + firebase 의 database를 사용해 실시간 채팅 앱을 만들어보도록 하겠습니다.

권한 설정 부분인데요.

간단한 테스트를 할 것이기 때문에  read 와 write 모두 true 로 바꿔줍니다.

아래 사진에서 위의 빨간 표시를 한 코드를 추가해 주시면 됩니다.

1. Build.Gragle(Module:app) 에 추가하기

2.Build.Gradle(Project:app) 에 추가하기


3. 메시지 객체 만들기

채팅을 하기위해 메시지 객체를 만들어야합니다.

저는 간단하게 사용자 이름, 메시지 내용을 가지는 객체를 만들었습니다.

Msg.java

 class Msg {

    private String user;

    private String msg;


    public Msg() {

        // 빈 생성자가 없으면 에러를 뱉어서 만들었어요~

    }


    Msg(String user, String msg) {

        this.user = user;

        this.msg = msg;

    }


    String getUser() {

        return user;

    }


    String getMsg() {

        return msg;

    }

}

4. Msg.java 메시지 객체에 대응하는 msg_item.xml

채팅 내용을 구성할 xml입니다.

recyclerview의 아이템에 해당하는 레이아웃으로 유저이름과 메시지 내용을 표시하도록 구성했어요.

<?xml version="1.0" encoding="utf-8"?>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

    android:orientation="vertical" android:layout_width="match_parent"

    android:layout_height="wrap_content">

    <TextView

        android:layout_width="wrap_content"

        android:layout_height="wrap_content"

        android:gravity="center"

        android:id="@+id/userTv"/>

    <TextView

        android:id="@+id/msgTv"

        android:textColor="#000000"

        android:gravity="center|start"

        android:layout_width="wrap_content"

        android:layout_height="36dp" />

</LinearLayout> 


5. activity_main.xml 구성

저는 하나의 RecyclerView, EditText, Button 으로 간단하게 구성했어요.

<?xml version="1.0" encoding="utf-8"?>

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"

    android:layout_width="match_parent"

    android:layout_height="match_parent">


    <android.support.v7.widget.RecyclerView

        android:id="@+id/msgLv"

        android:layout_width="match_parent"

        android:layout_height="match_parent"

        android:layout_marginBottom="56dp" />


    <LinearLayout

        android:layout_width="match_parent"

        android:layout_height="48dp"

        android:layout_alignParentBottom="true"

        android:orientation="horizontal">


        <EditText

            android:id="@+id/msgEt"

            android:layout_width="0dp"

            android:layout_height="match_parent"

            android:layout_weight="8" />


        <Button

            android:id="@+id/sendMsgBtn"

            android:layout_width="0dp"

            android:layout_height="match_parent"

            android:layout_weight="2"

            android:text="Send" />

    </LinearLayout>

</RelativeLayout>

 


6. 마지막으로 MainActivity.java 입니다.

package com.my.app;


import android.os.Bundle;

import android.support.v7.app.AppCompatActivity;

import android.support.v7.widget.LinearLayoutManager;

import android.support.v7.widget.RecyclerView;

import android.text.TextUtils;

import android.view.View;

import android.widget.Button;

import android.widget.EditText;

import android.widget.TextView;


import com.firebase.ui.database.FirebaseRecyclerAdapter;

import com.google.firebase.database.DatabaseReference;

import com.google.firebase.database.FirebaseDatabase;


public class MainActivity extends AppCompatActivity {


    LinearLayoutManager mLinearLayoutManager;

    FirebaseRecyclerAdapter<Msg, ViewHolder> mFirebaseAdapter;

    Button msgSendBtn;

    RecyclerView recyclerView;

    EditText msgEt;

    DatabaseReference databaseReference;

    @Override

    protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

        databaseReference = FirebaseDatabase.getInstance().getReference();

        mLinearLayoutManager = new LinearLayoutManager(this);

        mLinearLayoutManager.setStackFromEnd(true);

        recyclerView = (RecyclerView) findViewById(R.id.msgLv);

        msgSendBtn = (Button) findViewById(R.id.sendMsgBtn);

        msgEt = (EditText) findViewById(R.id.msgEt);


        // 이 어뎁터는 Firebase의 database를 지속적으로 감시하며 메시지가 추가됐을 때 혹은

           액티비티가 처음 로딩됐을 때 메시지들을 레이아웃에 추가해줍니다.

        mFirebaseAdapter = new FirebaseRecyclerAdapter<Msg,

                ViewHolder>(

                Msg.class,

                R.layout.msg_item,

                ViewHolder.class,

                databaseReference.child("sample")) {


            @Override

            protected void populateViewHolder(ViewHolder viewHolder,

                                              Msg chatData, int position) {

                viewHolder.userTv.setText(chatData.getUser());

                viewHolder.msgTv.setText(chatData.getMsg());

                // 메시지를 레이아웃에 추가하는 동작들을 여기에 

                    코드로 작성하시면 됩니다. 위 코드처럼

            }

        };


         onItemRangeInserted()안의 코드는 메시지가 많이 와서 화면에 표시할 수 있는 양보다

        더 많은 양의 아이템들이 추가됐을 때 스크롤을 가장 아래로 내려주는 코드입니다.

        mFirebaseAdapter.registerAdapterDataObserver(new RecyclerView.AdapterDataObserver() {

            @Override

            public void onItemRangeInserted(int positionStart, int itemCount) {

                super.onItemRangeInserted(positionStart, itemCount);

                int friendlyMessageCount = mFirebaseAdapter.getItemCount();

                int lastVisiblePosition =

                        mLinearLayoutManager.findLastCompletelyVisibleItemPosition();

                if (lastVisiblePosition == -1 ||

                        (positionStart >= (friendlyMessageCount - 1) &&

                                lastVisiblePosition == (positionStart - 1))) {

                    recyclerView.scrollToPosition(positionStart);

                }

            }

        });

        recyclerView.setLayoutManager(mLinearLayoutManager);

        recyclerView.setAdapter(mFirebaseAdapter);


       메시지를 보낼 버튼의 리스너입니다.

        msgSendBtn.setOnClickListener(new View.OnClickListener() {

            @Override

            public void onClick(View v) {

                String msg = msgEt.getText().toString();

                if (!TextUtils.isEmpty(msg)) {

                    Msg chatData = new Msg("userName", msg);  // 유저 이름과 메세지로 chatData 만들기)

                    databaseReference.child("sample").push().setValue(chatData);  // 기본 database 하위 message라는 child에 chatData를 list로 만들기

                    msgEt.setText("");

                }


            }

        });

    }



    public static class ViewHolder extends RecyclerView.ViewHolder {

        //뷰홀더 패턴에 사용할 ViewHolder입니다.

        TextView msgTv;

        TextView userTv;

        public ViewHolder(View v) {

            super(v);

            msgTv = (TextView) v.findViewById(R.id.msgTv);

            userTv = (TextView) v.findViewById(R.id.userTv);

        }

    }

}

 



이렇게 간단하게 실시간으로 메시지가 등록되는 채팅 기능을 구현해 봤는데요.

실행 영상 보겠습니다.


근데 사실 이건 채팅이라고 하긴 좀 그렇죠?

그냥 내가 올린 메시지가 실시간으로 등록된다는 것만 빼면

다음 포스팅에서는 나와 상대방을 구분해 카카오톡처럼 왼쪽은 상대방 이름과 메시지

오른쪽에는 내 이름과 메시지가 뜨는 실시간 1대1 채팅 앱을 만들어보겠습니다.

Firebase Database 에 대한 기본적인 설명들은 

https://firebase.google.com/docs/database/android/structure-data?hl=ko

위 url 에서 확인할 수 있습니다.




반응형