Ajouter un nouvel élément à recyclerview par programme?

115

J'essaie toujours de comprendre le recyclage. J'ai une arraylist, que j'utilise pour initialiser une vue de recycleur avec.

Comment puis-je ajouter de nouveaux éléments au poste de vue du recycleur en définissant un adaptateur et un gestionnaire de disposition?

private void initData() {
        mItems = new ArrayList<String>();
        for (int i = 0; i < ITEMS_COUNT; i++) {
            mItems.add("Item " + (i + 1));
        }
    }

    private void initRecyclerView() {
        mRecentRecyclerView = (RecyclerView) findViewById(R.id.recentrecyclerView);
        mRecentRecyclerView.setHasFixedSize(true);
        mRecentLayoutManager = new LinearLayoutManager(this);
        mRecentRecyclerView.setLayoutManager(mRecentLayoutManager);



        mAdapter = new RecyclerView.Adapter<CustomViewHolder>() {
            @Override
            public CustomViewHolder onCreateViewHolder(ViewGroup viewGroup, int i) {
                View view = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.notice_snippet
                        , viewGroup, false);
                return new CustomViewHolder(view);
            }

            @Override
            public void onBindViewHolder(CustomViewHolder viewHolder, int i) {
                viewHolder.noticeSubject.setText(mItems.get(i));
            }

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

        };
        mRecentRecyclerView.setAdapter(mAdapter);

    private class CustomViewHolder extends RecyclerView.ViewHolder {

        private TextView noticeSubject;

        public CustomViewHolder(View itemView) {
            super(itemView);

            noticeSubject = (TextView) itemView.findViewById(R.id.notice_subject);
        }
    }

Donc, fondamentalement, après moi initdata()et initRecyclerView(), comment puis-je ajouter un nouvel élément à RecyclerView ??

Shubham Kanodia
la source
Vous pouvez voir cet exemple dans le code Github Happy !!!
Cabezas

Réponses:

272

Ajoutez d'abord votre article à mItems, puis utilisez:

mAdapter.notifyItemInserted(mItems.size() - 1);

cette méthode est meilleure que d'utiliser:

mAdapter.notifyDataSetChanged();

en performance.

Mostafa
la source
11
Bonne réponse. Cela signifie également que cela ne cassera pas les animations
Ben Pearson
7
Cela devrait être accepté comme une bonne réponse, l'autre casse les animations et est moins efficace que celle-ci.
Massimo du
27
C'est moi qui ai répondu à la réponse acceptée et je pense que celle-ci devrait être celle acceptée: D
Abdelrahman Elkady
2
@AJW oui. L'index du dernier élément de mItems est mItems.size () - 1.
Mostafa
2
Merci! J'ai des images qui devraient être chargées depuis Internet dans onBindViewHolder. Chaque fois que je reçois des données, je dois les ajouter à la liste et appeler notifyDataSetChanged (). Mais cela a fait un effet de scintillement d'image. Ci-dessus se trouvait la bonne solution que je recherchais. Vous pouvez également utiliser mAdapter.notifyItemRangeInserted (mItems.size () - 1, new_array_of_items_to_be_added.size ());
Vignesh Bala
38

ajoutez simplement à votre structure de données (mItems), puis informez votre adaptateur du changement de jeu de données

private void addItem(String item) {
  mItems.add(item);
  mAdapter.notifyDataSetChanged();
}

addItem("New Item");
Abdelrahman Elkady
la source
2
Et si ce n'est pas une chaîne que je veux ajouter, mais un ViewGroup?
IgorGanapolsky
1
@IgorGanapolsky J'ai aussi le même doute. Avez-vous trouvé une solution à cela?
Sash_KP
même doute ici aussi! de l'aide?
Srujan Barai
5
@IgorGanapolsky Le type d'élément serait spécifié par votre adaptateur, il pourrait donc s'agir de n'importe quel objet. Mais gardez à l'esprit que l'élément que vous ajoutez est simplement censé être les données. Le RecyclerView a des fonctions intégrées pour gonfler et lier une vue, ce qui se produira lorsque vous notifiezDataSetChanged (). Vous pouvez déboguer le onBindViewHolder pour voir la vue en cours de modification.
Chris
1
@IgorGanapolsky Vous ArrayList<T>devrez utiliser le type d'objet que vous souhaitez ajouter, par exemple ArrayList<ViewGroup>au lieu de ArrayList<String>. Ensuite, vous pouvez simplement changer le type d'argument de Stringà ViewGroup. (Désolé pour necro).
Eric Reed
14

si vous ajoutez plusieurs éléments à la liste, utilisez ceci:

mAdapter.notifyItemRangeInserted(startPosition, itemcount);

Cela informe tous les observateurs enregistrés que les éléments itemCount actuellement reflétés à partir de positionStart ont été nouvellement insérés. L'élément précédemment situé à positionStart et au-delà peut maintenant être trouvé à partir de la position positinStart + itemCount

élément existant dans l'ensemble de données toujours considéré à jour.

Nitin Anand
la source