2016-08-03 17 views
3

ProblemFirebaseRecyclerAdapter - wie Datenbankabfrage nach der Erstellung

ich eine Liste von Elementen haben zu ändern, die in Android durch eine FirebaseRecyclerAdapter angezeigt. Ich erstelle diesen Adapter mit einer Datenbankreferenz auf der gesamten Liste der Elemente (sagen wir "Beiträge"). Der Post zeigt auch die Kategorie an und wenn der Benutzer auf die Kategorie klickt, möchte ich die Liste so aktualisieren, dass nur Objekte dieser Kategorie angezeigt werden. Ich

Lösung versucht, dass nicht funktioniert ich auf der „Kategorie“ Textview einen Klick Hörer setzen und wenn der Anwender auf das ich einen neuen Adapter mit der neuen Datenbankabfrage zu instanziieren versucht, aber es funktioniert nicht Arbeit.

Andere Ideen: es außerhalb der adpater Do: ein neues Intent erstellen das Fragment wieder aufzunehmen und einen neuen Adapter mit der neuen Abfrage

erstellen Frage Hat jemand mit der gleichen Situation umgehen, wo auf einem user click Sie möchten die ursprüngliche Liste der vom adpater abgerufenen Elemente filtern? Was ist die beste Lösung?

Einzelheiten

protected void populateViewHolder(final PostViewHolder viewHolder, final Post post, final int position) { 


    /* Set the post text, author and category */ 
    viewHolder.postText.setText(post.getText()); 
    viewHolder.postAuthor.setText(post.getAuthor()); 
    viewHolder.postCategory.setText(post.getCategory()); 

    /* Set a listener on category so that 
     I refresh data with only that category */ 
    viewHolder.quoteCategory.setOnClickListener(new View.OnClickListener() { 

     Post selectedPost = getItem(position); 

     @Override 
     public void onClick(View v) { 

      String category = selectedPost.getCategory(); 

      // !!!! NOW I HAVE TO CHANGE DATA SET !!! /// 

Ich denke, jetzt habe ich richtig Db Referenz erzeugen kann ein neues Fragment mit einem neuen Adapter mit ... aber ist dies der beste Weg? Gibt es eine Möglichkeit, den gleichen Adapater in der bevölkerten Ansicht zu verwenden und eine andere Abfrage zu übergeben?

Antwort

1

Versuchen Sie .notifyDatasetChanged() auf Ihrem Adapter, wenn der Klick auftritt. Nachdem Sie den Datensatz mit den neuen Firebase-Daten geändert haben.

+0

Vielen Dank für die Antwort, aber das Problem besteht nicht darin, eine Änderung im Datensatz zu melden ... das Problem ist, wie man den Datensatz ändert, nachdem der Adapter bereits erstellt wurde. "nachdem Sie den Datensatz geändert haben" ... wie kann ich das tun? – DavideN

0

Hier ist der Code für die Aktualisierung der Firebase-Daten. Hier aktualisiere ich zwei Parameter, die als Titel und Körper übergeben wurden.

private void writeNewPost(String userId, String username, String title, String body) { 

     String key = mDatabase.child("posts").push().getKey(); 
     Post post = new Post(userId, username, title, body); 
     Map<String, Object> postValues = post.toMap(); 

     Map<String, Object> childUpdates = new HashMap<>(); 
     childUpdates.put("/posts/" + key, postValues); 
     childUpdates.put("/user-posts/" + userId + "/" + key, postValues); 

     mDatabase.updateChildren(childUpdates); 
    } 

Ich denke, das wird Ihnen helfen.

+0

danke für die Antwort von Ich möchte keine Daten aktualisieren/ändern ...Ich möchte sie in der Benutzeroberfläche anders filtern. Die Lösung, die ich gefunden habe, ist es, ein neues Fragment zu erstellen und es mit einem neuen Firebaseadapter aufzurufen, wo ich als Argument eine weitere Firebase-Abfrage im Konstruktor ablege – DavideN

1

Sie ändern die Abfrage nicht, Sie erstellen einen neuen Adapter und Abfrage, ersetzen den Adapter in der Recycleransicht und bereinigen den alten. Hier

ist ein Beispiel, "Ändern der Abfrage" auf der Grundlage einer Auswahl in einem Spinner:

locationSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() { 
     @Override 
     public void onItemSelected(final AdapterView<?> adapterView, final View view, 
     final int i, final long l) { 
      if (locationSpinner.getSelectedItem() != null) { 
       final Location location = locationSpinner.getSelectedItem(); 
       final String indexString = String.format("open/%s/", location.getId()); 
       final Query query = FirebaseDatabase.getInstance() 
         .getReference("availabilities") 
         .orderByChild("statusLocationDateKey") 
         .startAt(indexString + "0") // simplified for example 
         .endAt(indexString + "9"); // simplified for example 
       adapter = new ListingAdapter(query); 
       final FirebaseRecyclerAdapter oldAdapter = 
         (FirebaseRecyclerAdapter) listing.getAdapter(); 
       listing.setAdapter(adapter); 
       if (oldAdapter != null) { 
        oldAdapter.cleanup(); 
       } 
      } 
     } 

Hinweis: ListingAdapter ist eine Unterklasse von FirebaseRecyclerAdapter und listing ein RecyclerView ist.

Auch sicher sein, einen Null-Check in dem auf für die Aktivität oder das Fragment zerstören aufzunehmen, da mit dem Code oben, gibt es keine Garantie, dass der Adapter immer initialisiert wurde, zum Beispiel:

@Override 
public void onDestroyView() { 
    if (adapter != null) { 
     adapter.cleanup(); 
    } 
    super.onDestroyView(); 
}