3

I am trying to retrieve data from Firebase database. The top level node is messages and child nodes are author and message. After logging in, the chat messages are pulled from the database. ChatActivity calls the ChatListAdapter with the following code:-

    mAdapter = new ChatListAdapter(this, mDatabaseReference);
    mChatListView.setAdapter(mAdapter);

Here mChatListView is a RecyclerView. The adapter code is as following:-

    public class ChatListAdapter extends RecyclerView.Adapter<ChatListAdapter.ViewHolder> {
    private Activity mActivity;
    private DatabaseReference mDatabaseReference;
    private ArrayList<DataSnapshot> mSnapshotList;

    private ChildEventListener mListener = new ChildEventListener() {
        @Override
        public void onChildAdded(DataSnapshot dataSnapshot, String s) {
            mSnapshotList.add(dataSnapshot);
            notifyDataSetChanged();
        }

        @Override
        public void onChildChanged(DataSnapshot dataSnapshot, String s) {

        }

        @Override
        public void onChildRemoved(DataSnapshot dataSnapshot) {

        }

        @Override
        public void onChildMoved(DataSnapshot dataSnapshot, String s) {

        }

        @Override
        public void onCancelled(DatabaseError databaseError) {

        }
    };

    public class ViewHolder extends RecyclerView.ViewHolder {
        TextView authorName, body;

        public ViewHolder(View view) {
            super(view);
            authorName = (TextView) itemView.findViewById(R.id.author);
            body = (TextView) itemView.findViewById(R.id.message);

        }
    }

    public ChatListAdapter(Activity activity, DatabaseReference ref) {
        this.mActivity = activity;
        this.mDatabaseReference = ref.child("messages");
        mDatabaseReference.addChildEventListener(mListener);
        mSnapshotList = new ArrayList<>();
    }

    @Override
    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        View itemView = LayoutInflater.from(parent.getContext())
                .inflate(R.layout.chat_row, parent, false);

        return new ViewHolder(itemView);
    }

    @Override
    public void onBindViewHolder(ViewHolder holder, int position) {

        InstantMessage message = getItem(position);
        String author = message.getAuthor();
        holder.authorName.setText(author);
        String msg = message.getMessage();
        holder.body.setText(msg);
    }

    public InstantMessage getItem(int i) {
        DataSnapshot snapshot = mSnapshotList.get(i);
        return snapshot.getValue(InstantMessage.class);
    }

    @Override
    public int getItemCount() {
        return mSnapshotList.size();
    }    
}

The ChatActivity is as follows:-

    public class ChatActivity extends AppCompatActivity {

    private RecyclerView mChatListView;    
    private DatabaseReference mDatabaseReference;
    private ChatListAdapter mAdapter;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main_chat);    

        mDatabaseReference = FirebaseDatabase.getInstance().getReference();           
        mChatListView = (RecyclerView) findViewById(R.id.chat_list_view);        
    }

    @Override
    public void onStart(){
        super.onStart();
        mAdapter = new ChatListAdapter(this, mDatabaseReference);
        mChatListView.setAdapter(mAdapter);
    }

    @Override
    public void onStop() {
        super.onStop();
        mAdapter.cleanUp();
    }
}
Khaled Lela
  • 7,831
  • 6
  • 45
  • 73
John
  • 740
  • 5
  • 13
  • 36
  • Please post your full code including your activity. – Rajshree Tiwari Jul 26 '18 at 05:24
  • @RajshreeTiwari full code including activity has been added. – John Jul 26 '18 at 05:45
  • add this line `mSnapshotList = new ArrayList<>();` inside onChildAdded before `mSnapshotList.add(dataSnapshot);` – Peter Haddad Jul 26 '18 at 07:04
  • @PeterHaddad that line is already present in ChatListAdapter constructor. – John Jul 26 '18 at 07:23
  • @John If you are interested, **[this](https://stackoverflow.com/questions/49383687/how-can-i-retrieve-data-from-firebase-to-my-adapter/49384849)** is a recommended way in which you can retrieve data from a Firebase Realtime database and display it in a `RecyclerView` using `FirebaseRecyclerAdapter` and **[this](https://stackoverflow.com/questions/48622480/showing-firebase-data-in-listview)** is how you can use an `ArrayAdapter`. – Alex Mamo Jul 26 '18 at 09:16
  • @AlexMamo thank you. I will definitely check. But I am not sure what is wrong with my code. – John Jul 26 '18 at 09:24
  • @John Try do use one of the example above, which is more apropiate for you and then make the difference. – Alex Mamo Jul 26 '18 at 09:28
  • @AlexMamo For that, do I need FirebaseUI dependency ? – John Jul 26 '18 at 09:36
  • @John Yes, take a look [here](https://github.com/firebase/FirebaseUI-Android). – Alex Mamo Jul 26 '18 at 09:38
  • @AlexMamo it has worked sir !! Many many thanks. I want to accept your answer :-) – John Jul 26 '18 at 11:52
  • You're welcome! I'll write you an answer right away. – Alex Mamo Jul 26 '18 at 11:53
  • literally all u had to do was put this `mSnapshotList = new ArrayList<>();` inside onChildAdded – Peter Haddad Jul 26 '18 at 18:07

3 Answers3

1

Add Data in array list through Map, Example shoving the detail

Following method to fetch Data from Firebase :

public void getUsers(){
    final ArrayList arrayList=new ArrayList();
    DatabaseReference q1=FirebaseDatabase.getInstance().getReference();
    q1.addListenerForSingleValueEvent(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            collectiouser((Map<String,Object>)dataSnapshot.getValue());
        }

        @Override
        public void onCancelled(DatabaseError databaseError) {

        }
    });
    toolbar.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            Intent i=new Intent(ChatPage.this,FriendsProfile.class);
            i.putExtra("receiver",receiver);
            startActivity(i);
            finish();
        }
    });

}

Add Data into List :

private void collectiouser(Map<String, Object> value) {
    ArrayList<String> user=new ArrayList<>();
    for(Map.Entry<String,Object> entry : value.entrySet()){
        Map singleuser=(Map)entry.getValue();
        String u=entry.getKey();
        String s=singleuser.toString();
        user.add(u); // Add Data into List
    }
}
amit
  • 659
  • 1
  • 8
  • 21
  • you are not initializing the mSnapshotList, you need to initialize your array list like `private ArrayList mSnapshotList=new ArrayList<>();` – amit Jul 26 '18 at 07:44
  • I did it inside the ChatListAdapter constructor. – John Jul 26 '18 at 07:51
  • in this case write `mAdapter = new ChatListAdapter(this, mDatabaseReference); mChatListView.setAdapter(mAdapter);` code in onDatachange event of firebase – amit Jul 26 '18 at 07:54
1

There are two ways in which you can solve thos problem. This is a recommended way in which you can retrieve data from a Firebase Realtime database and display it in a RecyclerView using FirebaseRecyclerAdapter and this is how you can use an ArrayAdapter.

But note, in order to use those answers you need to add Firebase-UI dependency. See here the latest versions.

Alex Mamo
  • 130,605
  • 17
  • 163
  • 193
0
List<Insight> insightList = new ArrayList<>();
FirebaseData mFirebaseDatabase = FirebaseDatabase.getInstance().getReference(your reference key);
mFirebaseDatabase.addValueEventListener(new ValueEventListener() {
     @Override
     public void onDataChange(DataSnapshot dataSnapshot) {
         insightList.clear();
         for (DataSnapshot noteSnapshot:dataSnapshot.getChildren(){
               Insight note = noteSnapshot.getValue(Insight.class);
               insightList.add(note);
         }
         // pass list in recyclerview
       }
           @Override
            public void onCancelled(DatabaseError databaseError) {
                Log.d(TAG, databaseError.getMessage());
            }
        });