Firebase:使用RecyclerView

时间:2017-02-08 14:05:39

标签: android firebase android-recyclerview firebase-realtime-database

我希望RecyclerView向用户显示随机问题。一旦问题得到解答(怀疑或错误),即使他关闭了应用程序,它也不会再次出现在该用户身上。之后,重新加载活动并出现一个新的随机问题。

当用户看到数据库中的所有问题时,它应显示一条消息,表示当时没有其他问题。

如果用户在点击后看到问题,我现在的代码就是放入Firebase数据库。

我试图发表一个if声明(但这似乎是一个愚蠢的想法)并且它的工作时间很短。基本上它说,如果孩子存在,重新加载活动。当数据库有数千个问题时,它会工作一段时间,但有一天会崩溃。

我的问题:

首先,我不想重新加载活动n次"发现"一个尚未出现的问题。

其次,我无法确定用户何时会看到所有问题以显示消息。

以下是代码:

  mDatabase = FirebaseDatabase.getInstance().getReference().child("Category").child(category_key).child("Questions");
query = mDatabase.orderByChild("randomId").startAt(randomValue).limitToFirst(1);

@Override
protected void onStart() {
    super.onStart();

    FirebaseRecyclerAdapter<Questions, QuestionViewHolder>
            firebaseRecyclerAdapter = new FirebaseRecyclerAdapter<Photos, QuestionViewHolder>(
            Question.class,
            R.layout.question_grid,
            QuestionViewHolder.class,
            query
    ) {
        @Override
        protected void populateViewHolder(final QuestionViewHolder viewHolder, final Question model, int position) {

            final String question_key = getRef(position).getKey();
            final String category_key = getIntent().getExtras().getString("category_id");

            mDatabase.addValueEventListener(new ValueEventListener() {
                @Override
                public void onDataChange(DataSnapshot dataSnapshot) {

                    if (dataSnapshot.child(question_key).child("ViwedBy").hasChild(mAuth.getCurrentUser().getUid())) {

                        finish();
                        startActivity(getIntent());


                    } else {

                        viewHolder.setQuestion(model.getQuestion());{

                            @Override
                            public void onClick (View v){


                                mDatabaseLike.addValueEventListener(new ValueEventListener() {
                                @Override
                                public void onDataChange(DataSnapshot dataSnapshot) {

                                    mDatabaseTest = FirebaseDatabase.getInstance().getReference().child("Category").child(category_key).child("Questions").child(question_key).child("ViewedBy").child(mAuth.getCurrentUser().getUid());
                                    mDatabaseTest.setValue(true);

                                     finish();
                                     startActivity(getIntent());


                                }


                                @Override
                                public void onCancelled(DatabaseError databaseError) {

                                }

                            });
                        }
                      }
                    }
                }


                @Override
                public void onCancelled (DatabaseError databaseError){

                }

            });


            mQuestionsList.setAdapter(firebaseRecyclerAdapter);


}

有没有更聪明的方法呢?

额外的问题:我是否需要重新加载整个活动,或者只能重新加载RecyclerView?

1 个答案:

答案 0 :(得分:0)

这将是解决问题的直接方法。您的活动将不再需要刷新,因为您的活动将由您的适配器处理。 按原样构建数据库

rootNode
L ...category/questions...
L answeredQuestions
  L userId
    L randomQuestionId:true
L questionsForUser
  L userId
    L randomQuestionId:true

当您的用户回答问题时:

add the questionId to answeredQuestions
remove the questionId from questionsForUser
call generateNewRandomQuestionForUser()

将FirebaseRecyclerAdapter替换为IndexedFirebaseRecyclerAdapter,如下所示:

new FirebaseIndexRecyclerAdapter<Question, QuestionHolder>(Question.class,
                                                   R.layout.question,
                                                   QuestionHolder.class,
                                                   keyRef, 
                                                   dataRef);

其中keyRef和dataRef都是

Query keyRef = FirebaseDatabase.getInstance().getReference().child("questionsForUser").child(userId);

Query DataRef  = FirebaseDatabase.getInstance().getReference().child("Category").child(category_key).child("Questions");

和generateNewRandomQuestionForUser()是这样的:

   public static void generateNewRandomQuestionForUser(final String userId, final String category_key) {
        FirebaseDatabase.getInstance().getReference().child("answeredQuestions").child(userId).addListenerForSingleValueEvent(new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                ArrayList<String> answeredQuestions = new ArrayList<String>();
                for (DataSnapshot questionId : dataSnapshot.getChildren()) {
                    answeredQuestions.add(questionId.getKey());
                }
                FirebaseDatabase.getInstance().getReference().child("Category").child(category_key).child("Questions").addListenerForSingleValueEvent(new ValueEventListener() {
                    @Override
                    public void onDataChange(DataSnapshot dataSnapshot) {
                        ArrayList<String> availableQuestionKeys = new ArrayList<String>();
                        for (DataSnapshot questionSnapshot : dataSnapshot.getChildren()) {
                            availableQuestionKeys.add(questionSnapshot.getKey());
                        }

                        // Using answeredQuestions, availableQuestionKeys, you can user your own algorithm
                        // to select one at random that the user has not seen yet.
                        // Here you can also determine whether a user has seen all possible questions and update UI accordingly.
                        // Once you have your random question as keyOfRandomQuestion:

                        FirebaseDatabase.getInstance().getReference().child("questionsForUser").child(userId).child(keyOfRandomQuestion).setValue(true);
                    }

                    @Override
                    public void onCancelled(DatabaseError databaseError) {}
                });
            }
            @Override
            public void onCancelled(DatabaseError databaseError) {}
        });
    }