Home / Android Nachrichten / Android DataBinding in RecyclerView – Profilbildschirm

Android DataBinding in RecyclerView – Profilbildschirm

In meinem vorherigen Artikel haben wir die Grundlagen von DataBinding gelernt. Heute werden wir die Grundlagen in die Tat umsetzen, indem wir einen Profilbildschirm mit datenbindenden Konzepten implementieren. Auf dem Profilbildschirm werden oben Profildetails angezeigt, und im unteren Abschnitt werden Post-Bilder im Rasterformat angezeigt. Das Raster wird mit einem RecyclerView erstellt, der die Datenbindung in einer Adapterklasse implementiert.

Durch die Verwendung von DataBinding in einer Adapterklasse wird der Code auf ein Minimum reduziert, da viele Dinge im Layout selbst berücksichtigt werden.

 android-recyclerview-databinding-example "width =" 720 "height =" 359 "class =" aligncenter size-full wp-image-41951 "srcset =" https://www.androidhive.info/wp-content /uploads/2018/04/android-recyclerview-databinding-example.jpg 720w, https://www.androidhive.info/wp-content/uploads/2018/04/android-recyclerview-databinding-example-300x150.jpg 300w "sizes =" (max-width: 720px) 100vw, 720px "/> <noscript><img src=Bindung von Android-Daten erforderlich. Beginnen Sie mit DataBinding, indem Sie das folgende Tutorial lesen.

Lesen: Android arbeitet mit DataBinding

2. Neues Projekt erstellen

1 . Erstellen Sie ein neues Projekt in Android Studio aus Datei ⇒ Neues Projekt und wählen Sie Grundaktivität aus Vorlagen.

2 . Aktivieren Sie DataBiding in app / build.gradle . Fügen Sie außerdem die Abhängigkeiten RecyclerView und Glide hinzu und synchronisieren Sie das Projekt.
















 android {
    dataBinding {
        enabled = true
    }
}

Abhängigkeiten {
    // ...

    Implementierung 'com.github.bumptech.glide: glide: 4.6.1'
    annotationProcessor 'com.github.bumptech.glide: compiler: 4.6.1'

    Implementierung 'com.android.support:recyclerview-v7:27.1.0'
}

3 . Fügen Sie die Berechtigung INTERNET in AndroidManifest.xml hinzu, da die Bilder von einer URL geladen werden müssen.


4 . Laden Sie res.zip herunter und fügen Sie es Ihren Projekten hinzu res . Diese Zeichenordner enthalten das für FAB erforderliche Plus-Symbol.

5 . Fügen Sie den entsprechenden strings.xml dimens.xml und colors.xml


 Datenbindung 
 Einstellungen 
 Profil 
POSTS [19659020]  FOLLOWERS
 FOLLOWING 


 16dp 
 16dp 
 8dp 
 100dp 
 30dp 
 15dp 
 13dp 
 24dp 10659022 ] # 111111 
 # fecb2f 
 # 333 

6 . Erstellen Sie drei Pakete mit den Namen model utils und view . Verschieben Sie nach dem Erstellen das Paket MainActivity in die Ansicht .

Nachfolgend finden Sie die endgültige Projektstruktur und die erforderlichen Dateien.

 android-databinding-project-structure "width =" 720 "height =" 436 "class =" aligncenter size-full wp-image-41935 "srcset =" https://www.androidhive.info/wp-content/uploads/2018/04/android-databinding-project-structure. png 720w, https://www.androidhive.info/wp-content/uploads/2018/04/android-databinding-project-structure-300x182.png 300w "sizes =" (maximale Breite: 720px) 100vw, 720px " /> <noscript><img src=Demonstration werden sowohl Observable als auch ObservableField in derselben Klasse verwendet.

  • Für die Variablen name, email, profileImage und about. Wird die Annotation @Bindable verwendet, und notifyPropertyChanged wird beim Festlegen neuer Daten aufgerufen
  • Variablen numberOfPosts numberOfFollowers numberOfFollowers werden als ObservableFields
  • @BindingAdapter wird verwendet, um profileImage an zu binden um das Bild über die Glide-Bibliothek von der URL zu laden.





















 import android.databinding.BaseObservable;
Import android.databinding.Bindable;
import android.databinding.BindingAdapter;
import android.databinding.ObservableField;
import android.widget.ImageView;

importieren com.bumptech.glide.Glide;
import com.bumptech.glide.request.RequestOptions;

import info.androidhive.databinding.BR;

public class User erweitert BaseObservable {
    String name;
    Zeichenfolge E-Mail;
    String profileImage;
    String über;


    // Die Metafelder des Profils sind ObservableField. Die Benutzeroberfläche wird aktualisiert
    // immer wenn ein neuer Wert gesetzt wird
    public ObservableField 
 numberOfFollowers = new ObservableField <> ();
    public ObservableField 
 numberOfPosts = new ObservableField <> ();
    public ObservableField 























































 numberOfFollowing = new ObservableField <> ();

    öffentlicher Benutzer () {
    }

    @Bindbar
    public String getName () {
        return name;
    }

    public void setName (String name) {
        this.name = name;
        notifyPropertyChanged (BR.name);
    }

    @Bindbar
    public String getEmail () {
        E-Mail zurücksenden;
    }

    public void setEmail (String email) {
        this.email = email;
        notifyPropertyChanged (BR.email);
    }

    @BindingAdapter ({"profileImage"})
    public static void loadImage (ImageView-Ansicht, String imageUrl) {
        Glide.with (view.getContext ())
                .load (imageUrl)
                .apply (RequestOptions.circleCropTransform ())
                .In Sicht);

        // Wenn Sie Picasso in Betracht ziehen, gehen Sie wie folgt vor
        // Picasso.with (view.getContext ()). Load (imageUrl) .placeholder (R.drawable.placeholder) .into (view);
    }

    @Bindbar
    public String getProfileImage () {
        return profileImage;
    }

    public void setProfileImage (String profileImage) {
        this.profileImage = profileImage;
        notifyPropertyChanged (BR.profileImage);
    }

    @Bindbar
    public String getAbout () {
        zurückkehren über;
    }

    public void setAbout (String about) {
        this.about = about;
        notifyPropertyChanged (BR.about);
    }

    public ObservableField 



 getNumberOfFollowers () {
        return numberOfFollowers;
    }

    public ObservableField 



 getNumberOfPosts () {
        return numberOfPosts;
    }

    public ObservableField 



 getNumberOfFollowing () {
        return numberOfFollowing;
    }
}

8 . Erstellen Sie eine weitere Klasse mit dem Namen Post.java unter dem Modellpaket . Diese Modellklasse stellt Daten für RecyclerView bereit.

























 import android.databinding.BindingAdapter;
import android.widget.ImageView;

importieren com.bumptech.glide.Glide;

public class Post {
    String imageUrl;

    @BindingAdapter ("imageUrl")
    public static void loadImage (ImageView-Ansicht, String imageUrl) {
        Glide.with (view.getContext ())
                .load (imageUrl)
                .In Sicht);
    }

    public String getImageUrl () {
        return imageUrl;
    }

    public void setImageUrl (String imageUrl) {
        this.imageUrl = imageUrl;
    }
}

9 . Erstellen Sie im Paket utils zwei Klassen mit den Namen BindingUtils.java und GridSpacingItemDecoration.java

  • convertToSuffix () menschenlesbares Format. Zum Beispiel wird 5500L als 5,5k und 5050890L als 5,1m konvertiert.
  • Wir binden diese Funktion zu TextViews, um die Posts, Follower und Follower in einem für Menschen lesbaren Format anzuzeigen.
















 package info.androidhive.databinding.utils;

public class BindingUtils {

    // https://stackoverflow.com/questions/9769554/how-to-convert-number-into-k-thousands-m-million-and-b-billion-suffix-in-jsp
    // Wandelt die Zahl in das Suffix K, M um
    // Beispiel: 5500 wird als 5.5k angezeigt
    public static String convertToSuffix (lange Zählung) {
        if (count <1000) return "" + count;
        int exp = (int) (Math.log (count) / Math.log (1000));
        Rückgabe von String.format ("%. 1f% c",
                count / Math.pow (1000, exp),
                "kmgtpe" .charAt (exp - 1));
    }
}

GridSpacingItemDecoration bietet Abstand zwischen RecyclerView-Rasterelementen.





























 package info.androidhive.databinding.utils;

android.graphics.Rect importieren;
import android.support.v7.widget.RecyclerView;
android.view.View importieren;

öffentliche Klasse GridSpacingItemDecoration erweitert RecyclerView.ItemDecoration {

    private int spanCount;
    privater int Abstand;
    private boolesche includeEdge;

    public GridSpacingItemDecoration (int spanCount, int spacing, boolesches includeEdge) {
        this.spanCount = spanCount;
        this.spacing = spacing;
        this.includeEdge = includeEdge;
    }

    @Override
    public void getItemOffsets (Rect outRect, Ansichtsansicht, RecyclerView-übergeordnetes Element, RecyclerView.State-Status) {
        int position = parent.getChildAdapterPosition (view);
        int column = position% spanCount;

        if (includeEdge) {
            outRect.left = spacing - Spalte * spacing / spanCount;
            outRect.right = (Spalte + 1) * spacing / spanCount;

            if (position 






< spanCount) {
                outRect.top = spacing;
            }
            outRect.bottom = spacing;
        } else {
            outRect.left = column * spacing / spanCount;
            outRect.right = spacing - (column + 1) * spacing / spanCount;
            if (position >





 = spanCount) {
                outRect.top = Abstand;
            }
        }
    }
}

2.1 Datenbindung in RecyclerView

Das Binden eines RecyclerView-Layouts ähnelt dem normalen Binden mit Ausnahme weniger Änderungen in den Methoden onCreateViewHolder und onBindViewHolder.

10 . Erstellen Sie ein Layout mit dem Namen post_row_item.xml . Dieses Layout enthält eine ImageView zum Rendern des Bildes in RecyclerView.

  • In diesem Layout wird die Datenbindung aktiviert, indem das Stammelement auf belassen wird. Das Post -Modell ist mit -Tag an dieses Layout gebunden.





    



        



    



    






        













    

11 . Erstellen Sie eine Klasse mit dem Namen PostsAdapter.java unter dem Paket view .

  • Da der Layoutname post_row_item.xml lautet, wird die generierte Bindungsklasse . PostRowItemBinding .
  • In der Methode onCreateViewHolder () wird das Layout von post_row_item mithilfe der Klasse PostRowItemBinding .
  • holder.binding. bindet das Modell Post an jede Zeile.















 package info.androidhive.databinding.view;

import android.databinding.DataBindingUtil;
import android.support.v7.widget.RecyclerView;
android.view.LayoutInflater importieren;
android.view.View importieren;
import android.view.ViewGroup;

import java.util.List;

import info.androidhive.databinding.R;
import info.androidhive.databinding.databinding.PostRowItemBinding;
import info.androidhive.databinding.model.Post;

public class PostsAdapter erweitert RecyclerView.Adapter 

 {

    private Liste 














 postList;
    privates LayoutInflater layoutInflater;
    private PostsAdapterListener Listener;

    öffentliche Klasse MyViewHolder erweitert RecyclerView.ViewHolder {

        private abschließende PostRowItemBinding-Bindung;

        public MyViewHolder (endgültiges PostRowItemBinding itemBinding) {
            super (itemBinding.getRoot ());
            this.binding = itemBinding;
        }
    }


    public PostsAdapter (List 




































 postList, PostsAdapterListener Listener) {
        this.postList = postList;
        this.listener = Listener;
    }

    @Override
    public MyViewHolder onCreateViewHolder (ViewGroup übergeordnet, int viewType) {
        if (layoutInflater == null) {
            layoutInflater = LayoutInflater.from (parent.getContext ());
        }
        PostRowItemBinding Bindung =
                DataBindingUtil.inflate (layoutInflater, R.layout.post_row_item, parent, false);
        neuen MyViewHolder zurückgeben (Bindung);
    }

    @Override
    public void onBindViewHolder (MyViewHolder-Inhaber, endgültige int-Position) {
        holder.binding.setPost (postList.get (position));
        holder.binding.thumbnail.setOnClickListener (neuer View.OnClickListener () {
            @Override
            public void onClick (View v) {
                if (Listener! = null) {
                    listener.onPostClicked (postList.get (position));
                }
            }
        });
    }

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

    öffentliche Schnittstelle PostsAdapterListener {
        void onPostClicked (Beitrag posten);
    }
}

2.2 Erstellen des Profilbildschirms

Jetzt sind alle Dateien vorhanden. Beginnen wir mit dem Aufbau der Hauptschnittstelle.

12 Öffnen Sie die Layoutdateien der Hauptaktivität, d. H. activity_main.xml und content_main.xml und aktivieren Sie die Datenbindung durch Hinzufügen der Tags und .






    



        



    



    








        







            








        



        






    






    



        



        





        



    



    








        









            









                






                    









                    










                





                













                











            



            









                









                    










                    







                



                









                    









                    







                



                









                    









                    







                

            



            




        



    

13 . Öffnen Sie schließlich MainActivity.java und führen Sie die folgenden Änderungen durch.

  • Da der Name des Hauptaktivitätslayouts activity_main lautet, lautet die generierte Bindungsklasse ActivityMainBinding . 19659042] renderProfile () gibt die Benutzerinformationen wie Name, Beschreibung, Posts, Follower und folgende Anzahl wieder.
  • initRecyclerView () initialisiert die RecyclerView mit Beispielbilddaten. [19659042] MyClickHandlers behandelt die Klickereignisse von UI-Elementen. Hier erfolgt die Bindung von Klickereignissen ausschließlich über das XML-Layout. Wir weisen dem Aktivitätscode nichts explizit zu.























































































 package info.androidhive.databinding.view;

android.content.Context importieren;
android.content.res.Resources importieren;
import android.databinding.DataBindingUtil;
android.os.Bundle importieren;
android.support.v7.app.AppCompatActivity importieren;
import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.GridLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.support.v7.widget.Toolbar;
import android.util.TypedValue;
android.view.View importieren;
android.widget.Toast importieren;

import java.util.ArrayList;

import info.androidhive.databinding.R;
import info.androidhive.databinding.databinding.ActivityMainBinding;
import info.androidhive.databinding.model.Post;
import info.androidhive.databinding.model.User;
import info.androidhive.databinding.utils.GridSpacingItemDecoration;

public class MainActivity erweitert AppCompatActivity implementiert PostsAdapter.PostsAdapterListener {

    private MyClickHandlers-Handler;
    private PostsAdapter mAdapter;
    private RecyclerView recyclerView;
    private ActivityMainBinding Bindung;
    privater Benutzer Benutzer;

    @Override
    protected void onCreate (Bundle savedInstanceState) {
        super.onCreate (savedInstanceState);

        binding = DataBindingUtil.setContentView (this, R.layout.activity_main);

        Toolbar toolbar = binding.toolbar;
        setSupportActionBar (Symbolleiste);
        getSupportActionBar (). setTitle (R.string.toolbar_profile);
        getSupportActionBar (). setDisplayHomeAsUpEnabled (true);

        handlers = new MyClickHandlers (this);

        renderProfile ();

        initRecyclerView ();
    }

    / **
     * Rendert RecyclerView mit Rasterbildern in 3 Spalten
     * /
    private void initRecyclerView () {
        recyclerView = binding.content.recyclerView;
        recyclerView.setLayoutManager (neuer GridLayoutManager (this, 3));
        recyclerView.addItemDecoration (neues GridSpacingItemDecoration (3, dpToPx (4), true));
        recyclerView.setItemAnimator (neuer DefaultItemAnimator ());
        recyclerView.setNestedScrollingEnabled (false);
        mAdapter = new PostsAdapter (getPosts (), this);
        recyclerView.setAdapter (mAdapter);
    }

    / **
     * Rendert Benutzerprofildaten
     * /
    private void renderProfile () {
        Benutzer = neuer Benutzer ();
        user.setName ("David Attenborough");
        user.setEmail ("david@natgeo.com");
        user.setProfileImage ("https://api.androidhive.info/images/nature/david.jpg");
        user.setAbout ("Naturforscher");

        // ObservableField hat keine Setter-Methode, stattdessen wird
        // mit der set () Methode aufgerufen werden
        user.numberOfPosts.set (3400L);
        user.numberOfFollowers.set (3050890L);
        user.numberOfFollowing.set (150L);


        // Benutzer anzeigen
        binding.setUser (user);

        // Click-Handler zuweisen
        binding.content.setHandlers (Handler);
    }

    private ArrayList 
 getPosts () {
        ArrayList 

































































 posts = new ArrayList <> ();
        für (int i = 1; i <10; i ++) {
            Post post = neuer Post ();
            post.setImageUrl ("https://api.androidhive.info/images/nature/" + i + ".jpg");

            posts.add (post);
        }

        Beiträge zurücksenden;
    }

    @Override
    public void onPostClicked (Beitrag posten) {
        Toast.makeText (getApplicationContext (), "Beitrag angeklickt!" + Post.getImageUrl (), Toast.LENGTH_SHORT) .show ();
    }

    öffentliche Klasse MyClickHandlers {

        Kontext Kontext;

        public MyClickHandlers (Kontext-Kontext) {
            this.context = context;
        }

        / **
         * Demonstration der Aktualisierung von Bindedaten
         * Profilname, Anzahl der Beiträge und Profilbild
         * wird bei Fab click aktualisiert
         * /
        public void onProfileFabClicked (Ansichtsansicht) {
            user.setName ("Sir David Attenborough");
            user.setProfileImage ("https://api.androidhive.info/images/nature/david1.jpg");

            // Aktualisierung von ObservableField
            user.numberOfPosts.set (5500L);
            user.numberOfFollowers.set (5050890L);
            user.numberOfFollowing.set (180L);
        }

        public boolean onProfileImageLongPressed (Ansichtsansicht) {
            Toast.makeText (getApplicationContext (), "Profilbild lange gedrückt!", Toast.LENGTH_LONG) .show ();
            falsch zurückgeben;
        }


        public void onFollowersClicked (Ansicht Ansicht) {
            Toast.makeText (Kontext, "Follower werden angeklickt!", Toast.LENGTH_SHORT) .show ();
        }

        public void onFollowingClicked (Ansichtsansicht) {
            Toast.makeText (Kontext, "Folgendes wird angeklickt!", Toast.LENGTH_SHORT) .show ();
        }

        public void onPostsClicked (Ansichtsansicht) {
            Toast.makeText (Kontext, "Beiträge angeklickt!", Toast.LENGTH_SHORT) .show ();
        }
    }

    / **
     * Umwandlung von dp in Pixel
     * /
    private int dpToPx (int dp) {
        Ressourcen r = getResources ();
        return Math.round (TypedValue.applyDimension (TypedValue.COMPLEX_UNIT_DIP, dp, r.getDisplayMetrics ());
    }
}

Führen Sie die App aus und testen Sie sie einmal. Stellen Sie sicher, dass das Gerät über eine Internetverbindung verfügt, da die Bilder vom Netzwerk heruntergeladen werden.

 android-data-binding-in-recyclerview-profile-screen "width =" 720 "height =" 625 "class =" aligncenter size-full wp -image-41914 "srcset =" https://www.androidhive.info/wp-content/uploads/2018/04/android-data-binding-in-recyclerview-profile-screen.png 720w, https: // www .androidhive.info / wp-content / uploads / 2018/04 / android-datenbindung-in-recyclerview-profile-screen-300x260.png 300w "sizes =" (max-width: 720px) 100vw, 720px "/> <noscript><img src=
Hallo! Ich bin Gründer bei androidhive und Programmierer. Meine Fähigkeiten umfassen Android, iOS, PHP, Ruby on Rails und vieles mehr. Wenn Sie eine Idee haben, die ich entwickeln soll? Reden wir: ravi@androidhive.info



About AndroidWeltEditor

Check Also

Chromebook artists can now level up their work with the One by Wacom

Source: Ara Wagoner / Android Central Wacom today announcedthe One By Wacom graphics tablet. It’s …

Leave a Reply

Your email address will not be published. Required fields are marked *