Cet atelier de programmation fait partie du cours Principes de base d'Android en Kotlin. Vous tirerez pleinement parti de ce cours en suivant les ateliers de programmation dans l'ordre. Tous les ateliers de programmation du cours sont listés sur la page de destination des ateliers de programmation Principes de base d'Android en Kotlin.
Introduction
Dans l'atelier de programmation précédent, vous avez mis à jour l'application TrackMySleepQuality pour afficher des données sur la qualité du sommeil dans un RecyclerView
. Les techniques que vous avez apprises lorsque vous avez créé votre premier RecyclerView
suffisent pour la plupart des RecyclerViews
qui affichent des listes simples et pas trop longues. Toutefois, il existe un certain nombre de techniques qui rendent RecyclerView
plus efficace pour les listes volumineuses et qui facilitent la gestion et l'extension de votre code pour les listes et les grilles complexes.
Dans cet atelier de programmation, vous allez vous appuyer sur l'application de suivi du sommeil de l'atelier de programmation précédent. Vous apprendrez une méthode plus efficace pour mettre à jour la liste des données de sommeil et à utiliser la liaison de données avec RecyclerView
. (Si vous n'avez pas l'application de l'atelier de programmation précédent, vous pouvez télécharger le code de démarrage pour cet atelier de programmation.)
Ce que vous devez déjà savoir
- Créer une interface utilisateur de base à l'aide d'une activité, de fragments et de vues.
- Naviguer entre les fragments et utiliser
safeArgs
pour transmettre des données entre les fragments. - Affichez les modèles, les fabriques de modèles, les transformations et les
LiveData
, ainsi que leurs observateurs. - Création d'une base de données
Room
, d'un DAO et définition d'entités - Utiliser des coroutines pour les tâches de base de données et autres tâches de longue durée
- Implémenter un
RecyclerView
de base avec une mise en pageAdapter
,ViewHolder
et d'élément.
Points abordés
- Comment utiliser
DiffUtil
pour mettre à jour efficacement une liste affichée parRecyclerView
. - Utiliser la liaison de données avec
RecyclerView
- Utiliser des adaptateurs de liaison pour transformer des données.
Objectifs de l'atelier
- Utilisez l'application TrackMySleepQuality de l'atelier de programmation précédent de cette série.
- Mettez à jour
SleepNightAdapter
pour mettre à jour efficacement la liste à l'aide deDiffUtil
. - Implémentez la liaison de données pour
RecyclerView
, en utilisant des adaptateurs de liaison pour transformer les données.
L'application de suivi du sommeil comporte deux écrans, représentés par des fragments, comme illustré dans la figure ci-dessous.
Le premier écran, affiché à gauche, comporte des boutons permettant de démarrer et d'arrêter le suivi. L'écran affiche certaines données de sommeil de l'utilisateur. Le bouton Effacer supprime définitivement toutes les données que l'application a collectées pour l'utilisateur. Le deuxième écran, à droite, permet de sélectionner une note de qualité du sommeil.
Cette application est conçue pour utiliser un contrôleur d'UI, ViewModel
et LiveData
, ainsi qu'une base de données Room
pour conserver les données de sommeil.
Les données sur le sommeil sont affichées dans un RecyclerView
. Dans cet atelier de programmation, vous allez créer la partie DiffUtil
et la partie de liaison de données pour RecyclerView
. À la fin de cet atelier de programmation, votre application aura exactement la même apparence, mais elle sera plus efficace, plus facile à mettre à l'échelle et plus facile à gérer.
Vous pouvez continuer à utiliser l'application SleepTracker de l'atelier de programmation précédent ou télécharger l'application RecyclerViewDiffUtilDataBinding-Starter depuis GitHub.
- Si nécessaire, téléchargez l'application RecyclerViewDiffUtilDataBinding-Starter depuis GitHub et ouvrez le projet dans Android Studio.
- Exécutez l'application.
- Ouvrez le fichier
SleepNightAdapter.kt
. - Examinez le code pour vous familiariser avec la structure de l'application. Reportez-vous au diagramme ci-dessous pour récapituler l'utilisation de
RecyclerView
avec le modèle d'adaptateur pour afficher les données de sommeil à l'utilisateur.
- À partir des entrées utilisateur, l'application crée une liste d'objets
SleepNight
. Chaque objetSleepNight
représente une nuit de sommeil, sa durée et sa qualité. SleepNightAdapter
adapte la liste des objetsSleepNight
en un élément queRecyclerView
peut utiliser et afficher.- L'adaptateur
SleepNightAdapter
produit desViewHolders
qui contiennent les vues, les données et les métadonnées permettant à la vue du recyclage d'afficher les données. RecyclerView
utiliseSleepNightAdapter
pour déterminer le nombre d'éléments à afficher (getItemCount()
).RecyclerView
utiliseonCreateViewHolder()
etonBindViewHolder()
pour obtenir les supports de vue liés aux données à afficher.
La méthode notifyDataSetChanged() est inefficace
Pour indiquer à RecyclerView
qu'un élément de la liste a été modifié et doit être mis à jour, le code actuel appelle notifyDataSetChanged()
dans SleepNightAdapter
, comme indiqué ci-dessous.
var data = listOf<SleepNight>()
set(value) {
field = value
notifyDataSetChanged()
}
Toutefois, notifyDataSetChanged()
indique à RecyclerView
que la liste entière est potentiellement non valide. Par conséquent, RecyclerView
lie et redessine chaque élément de la liste, y compris ceux qui ne sont pas visibles à l'écran. Cela représente beaucoup de travail inutile. Pour les listes volumineuses ou complexes, ce processus peut prendre suffisamment de temps pour que l'affichage clignote ou saccade lorsque l'utilisateur fait défiler la liste.
Pour résoudre ce problème, vous pouvez indiquer à RecyclerView
exactement ce qui a changé. RecyclerView
peut alors mettre à jour uniquement les vues qui ont changé à l'écran.
RecyclerView
dispose d'une API riche pour mettre à jour un seul élément. Vous pouvez utiliser notifyItemChanged()
pour indiquer à RecyclerView
qu'un élément a été modifié. Vous pouvez utiliser des fonctions similaires pour les éléments ajoutés, supprimés ou déplacés. Vous pourriez tout faire manuellement, mais cette tâche serait loin d'être simple et pourrait impliquer pas mal de code.
Heureusement, il existe une meilleure solution.
DiffUtil est efficace et fait le gros du travail pour vous.
RecyclerView
comporte une classe appelée DiffUtil
, qui permet de calculer les différences entre deux listes. DiffUtil
prend une ancienne liste et une nouvelle liste, et identifie les différences. Il trouve les éléments qui ont été ajoutés, supprimés ou modifiés. Il utilise ensuite un algorithme appelé Eugene W. Myers pour déterminer le nombre minimal de modifications à apporter à l'ancienne liste pour produire la nouvelle.
Une fois que DiffUtil
a identifié les modifications, RecyclerView
peut utiliser ces informations pour ne mettre à jour que les éléments qui ont été modifiés, ajoutés, supprimés ou déplacés. C'est beaucoup plus efficace que de refaire toute la liste.
Dans cette tâche, vous allez mettre à niveau SleepNightAdapter
pour utiliser DiffUtil
afin d'optimiser RecyclerView
pour les modifications apportées aux données.
Étape 1 : Implémenter SleepNightDiffCallback
Pour utiliser la fonctionnalité de la classe DiffUtil
, étendez DiffUtil.ItemCallback
.
- Ouvrez
SleepNightAdapter.kt
. - Sous la définition complète de la classe
SleepNightAdapter
, créez une classe de premier niveau appeléeSleepNightDiffCallback
qui étendDiffUtil.ItemCallback
. TransmettezSleepNight
en tant que paramètre générique.
class SleepNightDiffCallback : DiffUtil.ItemCallback<SleepNight>() {
}
- Placez le curseur sur le nom de la classe
SleepNightDiffCallback
. - Appuyez sur
Alt+Enter
(Option+Enter
sur Mac), puis sélectionnez Implement Members (Implémenter les membres). - Dans la boîte de dialogue qui s'ouvre, cliquez sur OK en maintenant la touche Maj enfoncée pour sélectionner les méthodes
areItemsTheSame()
etareContentsTheSame()
.
Des stubs sont alors générés dansSleepNightDiffCallback
pour les deux méthodes, comme indiqué ci-dessous.DiffUtil
utilise ces deux méthodes pour déterminer comment la liste et les éléments ont changé.
override fun areItemsTheSame(oldItem: SleepNight, newItem: SleepNight): Boolean {
TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
}
override fun areContentsTheSame(oldItem: SleepNight, newItem: SleepNight): Boolean {
TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
}
- Dans
areItemsTheSame()
, remplacezTODO
par un code qui teste si les deux élémentsSleepNight
transmis,oldItem
etnewItem
, sont identiques. Si les éléments ont le mêmenightId
, ils sont identiques. Renvoie donctrue
. Sinon, renvoiefalse
.DiffUtil
utilise ce test pour déterminer si un élément a été ajouté, supprimé ou déplacé.
override fun areItemsTheSame(oldItem: SleepNight, newItem: SleepNight): Boolean {
return oldItem.nightId == newItem.nightId
}
- Dans
areContentsTheSame()
, vérifiez sioldItem
etnewItem
contiennent les mêmes données, c'est-à-dire s'ils sont égaux. Cette vérification d'égalité portera sur tous les champs, carSleepNight
est une classe de données. Les classesData
définissent automatiquementequals
et quelques autres méthodes pour vous. S'il existe des différences entreoldItem
etnewItem
, ce code indique àDiffUtil
que l'élément a été mis à jour.
override fun areContentsTheSame(oldItem: SleepNight, newItem: SleepNight): Boolean {
return oldItem == newItem
}
Il est courant d'utiliser un RecyclerView
pour afficher une liste qui change. RecyclerView
fournit une classe d'adaptateur, ListAdapter
, qui vous aide à créer un adaptateur RecyclerView
basé sur une liste.
ListAdapter
assure le suivi de la liste pour vous et avertit l'adaptateur lorsque la liste est mise à jour.
Étape 1 : Modifiez votre adaptateur pour étendre ListAdapter
- Dans le fichier
SleepNightAdapter.kt
, modifiez la signature de la classeSleepNightAdapter
pour étendreListAdapter
. - Si vous y êtes invité, importez
androidx.recyclerview.widget.ListAdapter
. - Ajoutez
SleepNight
comme premier argument àListAdapter
, avantSleepNightAdapter.ViewHolder
. - Ajoutez
SleepNightDiffCallback()
en tant que paramètre au constructeur.ListAdapter
utilisera ces informations pour identifier ce qui a changé dans la liste. La signature de votre classeSleepNightAdapter
terminée devrait se présenter comme suit.
class SleepNightAdapter : ListAdapter<SleepNight, SleepNightAdapter.ViewHolder>(SleepNightDiffCallback()) {
- Dans la classe
SleepNightAdapter
, supprimez le champdata
, y compris le setter. Vous n'en avez plus besoin, carListAdapter
garde la trace de la liste pour vous. - Supprimez le remplacement de
getItemCount()
, carListAdapter
implémente cette méthode pour vous. - Pour éliminer l'erreur dans
onBindViewHolder()
, modifiez la variableitem
. Au lieu d'utiliserdata
pour obtenir unitem
, appelez la méthodegetItem(position)
fournie parListAdapter
.
val item = getItem(position)
Étape 2 : Utilisez submitList() pour maintenir la liste à jour
Votre code doit indiquer à l'élément ListAdapter
quand une liste modifiée est disponible. ListAdapter
fournit une méthode appelée submitList()
pour indiquer à ListAdapter
qu'une nouvelle version de la liste est disponible. Lorsque cette méthode est appelée, ListAdapter
compare la nouvelle liste à l'ancienne et détecte les éléments qui ont été ajoutés, supprimés, déplacés ou modifiés. ListAdapter
met ensuite à jour les éléments affichés par RecyclerView
.
- Ouvrez
SleepTrackerFragment.kt
. - Dans
onCreateView()
, dans l'observateur sursleepTrackerViewModel
, recherchez l'erreur où la variabledata
que vous avez supprimée est référencée. - Remplacez
adapter.data = it
par un appel àadapter.submitList(it)
. Le code mis à jour est indiqué ci-dessous.
sleepTrackerViewModel.nights.observe(viewLifecycleOwner, Observer {
it?.let {
adapter.submitList(it)
}
})
- Exécutez votre application. Elle s'exécute plus rapidement, mais vous ne le remarquerez peut-être pas si votre liste est petite.
Dans cette tâche, vous allez utiliser la même technique que dans les ateliers de programmation précédents pour configurer la liaison de données et éliminer les appels à findViewById()
.
Étape 1 : Ajoutez la liaison de données au fichier de mise en page
- Ouvrez le fichier de mise en page
list_item_sleep_night.xml
dans l'onglet Texte. - Placez le curseur sur la balise
ConstraintLayout
, puis appuyez surAlt+Enter
(Option+Enter
sur un Mac). Le menu d'intention (le menu "Correction rapide") s'ouvre. - Sélectionnez Convert to data binding layout (Convertir en mise en page de liaison de données). Cela encapsule la mise en page dans
<layout>
et ajoute une balise<data>
à l'intérieur. - Si nécessaire, faites défiler l'écran vers le haut et, dans la balise
<data>
, déclarez une variable nomméesleep
. - Définissez
type
sur le nom complet deSleepNight
,com.example.android.trackmysleepquality.database.SleepNight
. Votre balise<data>
terminée devrait se présenter comme suit.
<data>
<variable
name="sleep"
type="com.example.android.trackmysleepquality.database.SleepNight"/>
</data>
- Pour forcer la création de l'objet
Binding
, sélectionnez Build > Clean Project (Compiler > Nettoyer le projet), puis Build > Rebuild Project (Compiler > Recompiler le projet). (Si vous rencontrez toujours des problèmes, sélectionnez File > Invalidate Caches / Restart (Fichier > Invalider les caches/Redémarrer).) L'objet de liaisonListItemSleepNightBinding
, ainsi que le code associé, sont ajoutés aux fichiers générés du projet.
Étape 2 : Développez la mise en page de l'élément à l'aide de la liaison de données
- Ouvrez
SleepNightAdapter.kt
. - Dans la classe
ViewHolder
, recherchez la méthodefrom()
. - Supprimez la déclaration de la variable
view
.
Code à supprimer :
val view = layoutInflater
.inflate(R.layout.list_item_sleep_night, parent, false)
- À l'emplacement de la variable
view
, définissez une nouvelle variable appeléebinding
qui augmente l'objet de liaisonListItemSleepNightBinding
, comme indiqué ci-dessous. Importez l'objet de liaison nécessaire.
val binding =
ListItemSleepNightBinding.inflate(layoutInflater, parent, false)
- À la fin de la fonction, au lieu de renvoyer
view
, renvoyezbinding
.
return ViewHolder(binding)
- Pour corriger l'erreur, placez votre curseur sur le mot
binding
. Appuyez surAlt+Enter
(Option+Enter
sur Mac) pour ouvrir le menu d'intention.
- Sélectionnez Modifier le type de paramètre "itemView" du constructeur principal de la classe "ViewHolder" en "ListItemSleepNightBinding". Cela met à jour le type de paramètre de la classe
ViewHolder
.
- Faites défiler l'écran vers le haut jusqu'à la définition de la classe
ViewHolder
pour voir la modification de la signature. Une erreur s'affiche pouritemView
, car vous avez remplacéitemView
parbinding
dans la méthodefrom()
.
Dans la définition de la classeViewHolder
, effectuez un clic droit sur l'une des occurrences deitemView
, puis sélectionnez Refactor > Rename (Refactoriser > Renommer). Remplacez le nom parbinding
. - Ajoutez le préfixe
val
au paramètre de constructeurbinding
pour en faire une propriété. - Dans l'appel à la classe parente,
RecyclerView.ViewHolder
, remplacez le paramètrebinding
parbinding.root
. Vous devez transmettre unView
, etbinding.root
est leConstraintLayout
racine dans la mise en page de votre élément. - Votre déclaration de classe terminée devrait ressembler au code ci-dessous.
class ViewHolder private constructor(val binding: ListItemSleepNightBinding) : RecyclerView.ViewHolder(binding.root){
Une erreur s'affiche également pour les appels à findViewById()
. Vous allez la corriger ensuite.
Étape 3 : Remplacer findViewById()
Vous pouvez désormais mettre à jour les propriétés sleepLength
, quality
et qualityImage
pour utiliser l'objet binding
au lieu de findViewById()
.
- Modifiez les initialisations de
sleepLength
,qualityString
etqualityImage
pour qu'elles utilisent les vues de l'objetbinding
, comme indiqué ci-dessous. Votre code ne devrait plus afficher d'erreurs.
val sleepLength: TextView = binding.sleepLength
val quality: TextView = binding.qualityString
val qualityImage: ImageView = binding.qualityImage
Avec l'objet de liaison en place, vous n'avez plus besoin de définir les propriétés sleepLength
, quality
et qualityImage
. DataBinding
mettra en cache les recherches, il n'est donc pas nécessaire de déclarer ces propriétés.
- Effectuez un clic droit sur les noms des propriétés
sleepLength
,quality
etqualityImage
. Sélectionnez Refactor > Inline (Refactoriser > Intégrer) ou appuyez surControl+Command+N
(Option+Command+N
sur Mac). - Exécutez votre application. (Vous devrez peut-être nettoyer et recompiler votre projet s'il comporte des erreurs.)
Dans cette tâche, vous allez mettre à niveau votre application pour qu'elle utilise la liaison de données avec des adaptateurs de liaison afin de définir les données dans vos vues.
Dans un atelier de programmation précédent, vous avez utilisé la classe Transformations
pour prendre des LiveData
et générer des chaînes mises en forme à afficher dans des vues de texte. Toutefois, si vous devez lier différents types ou des types complexes, vous pouvez fournir des adaptateurs de liaison pour aider la liaison de données à utiliser ces types. Les adaptateurs de liaison sont des adaptateurs qui prennent vos données et les transforment en un élément que la liaison de données peut utiliser pour lier une vue, comme du texte ou une image.
Vous allez implémenter trois adaptateurs de liaison, un pour l'image de qualité et un pour chaque champ de texte. En résumé, pour déclarer un adaptateur de liaison, vous devez définir une méthode qui reçoit un élément et une vue, et l'annoter avec @BindingAdapter
. Dans le corps de la méthode, vous implémentez la transformation. En Kotlin, vous pouvez écrire un adaptateur de liaison en tant que fonction d'extension sur la classe de vue qui reçoit les données.
Étape 1 : Créez des adaptateurs de liaison
Notez que vous devrez importer un certain nombre de cours lors de cette étape, mais qu'ils ne seront pas mentionnés individuellement.
- Ouvrez
SleepNightAdapater.kt
. - Dans la classe
ViewHolder
, recherchez la méthodebind()
et rappelez-vous ce qu'elle fait. Vous allez prendre le code qui calcule les valeurs debinding.sleepLength
,binding.quality
etbinding.qualityImage
, et l'utiliser à l'intérieur de l'adaptateur. (Pour l'instant, laissez le code tel quel. Vous le déplacerez à une étape ultérieure.) - Dans le package
sleeptracker
, créez et ouvrez un fichier appeléBindingUtils.kt
. - Déclarez une fonction d'extension sur
TextView
, appeléesetSleepDurationFormatted
, et transmettez unSleepNight
. Cette fonction sera votre adaptateur pour calculer et mettre en forme la durée du sommeil.
fun TextView.setSleepDurationFormatted(item: SleepNight) {}
- Dans le corps de
setSleepDurationFormatted
, liez les données à la vue comme vous l'avez fait dansViewHolder.bind()
. AppelezconvertDurationToFormatted()
, puis définissez letext
deTextView
sur le texte mis en forme. (Comme il s'agit d'une fonction d'extension surTextView
, vous pouvez accéder directement à la propriététext
.)
text = convertDurationToFormatted(item.startTimeMilli, item.endTimeMilli, context.resources)
- Pour informer la liaison de données de cet adaptateur de liaison, annotez la fonction avec
@BindingAdapter
. - Cette fonction est l'adaptateur pour l'attribut
sleepDurationFormatted
. Transmettez doncsleepDurationFormatted
en tant qu'argument à@BindingAdapter
.
@BindingAdapter("sleepDurationFormatted")
- Le deuxième adaptateur définit la qualité du sommeil en fonction de la valeur d'un objet
SleepNight
. Créez une fonction d'extension appeléesetSleepQualityString()
surTextView
et transmettez unSleepNight
. - Dans le corps, liez les données à la vue comme vous l'avez fait dans
ViewHolder.bind()
. AppelezconvertNumericQualityToString
et définisseztext
. - Annotez la fonction avec
@BindingAdapter("sleepQualityString")
.
@BindingAdapter("sleepQualityString")
fun TextView.setSleepQualityString(item: SleepNight) {
text = convertNumericQualityToString(item.sleepQuality, context.resources)
}
- Le troisième adaptateur de liaison définit l'image sur une vue d'image. Créez la fonction d'extension sur
ImageView
, appelezsetSleepImage
et utilisez le code deViewHolder.bind()
, comme indiqué ci-dessous.
@BindingAdapter("sleepImage")
fun ImageView.setSleepImage(item: SleepNight) {
setImageResource(when (item.sleepQuality) {
0 -> R.drawable.ic_sleep_0
1 -> R.drawable.ic_sleep_1
2 -> R.drawable.ic_sleep_2
3 -> R.drawable.ic_sleep_3
4 -> R.drawable.ic_sleep_4
5 -> R.drawable.ic_sleep_5
else -> R.drawable.ic_sleep_active
})
}
Étape 2 : Mettez à jour SleepNightAdapter
- Ouvrez
SleepNightAdapter.kt
. - Supprimez tout le contenu de la méthode
bind()
, car vous pouvez désormais utiliser la liaison de données et vos nouveaux adaptateurs pour effectuer ce travail à votre place.
fun bind(item: SleepNight) {
}
- Dans
bind()
, attribuez le sommeil àitem
, car vous devez informer l'objet de liaison de votre nouveauSleepNight
.
binding.sleep = item
- Sous cette ligne, ajoutez
binding.executePendingBindings()
. Cet appel est une optimisation qui demande à la liaison de données d'exécuter immédiatement toutes les liaisons en attente. Il est toujours recommandé d'appelerexecutePendingBindings()
lorsque vous utilisez des adaptateurs de liaison dans unRecyclerView
, car cela peut accélérer légèrement le dimensionnement des vues.
binding.executePendingBindings()
Étape 3 : Ajoutez des liaisons à la mise en page XML
- Ouvrez
list_item_sleep_night.xml
. - Dans
ImageView
, ajoutez une propriétéapp
portant le même nom que l'adaptateur de liaison qui définit l'image. Transmettez la variablesleep
, comme indiqué ci-dessous.
Cette propriété crée la connexion entre la vue et l'objet de liaison, via l'adaptateur. Chaque fois quesleepImage
est référencé, l'adaptateur adapte les données deSleepNight
.
app:sleepImage="@{sleep}"
- Procédez de la même façon pour les vues de texte
sleep_length
etquality_string
. Chaque fois quesleepDurationFormatted
ousleepQualityString
sont référencés, les adaptateurs adaptent les données deSleepNight
.
app:sleepDurationFormatted="@{sleep}"
app:sleepQualityString="@{sleep}"
- Exécutez votre application. Elle fonctionne exactement comme avant. Les adaptateurs de liaison se chargent de la mise en forme et de la mise à jour des vues lorsque les données changent, ce qui simplifie
ViewHolder
et donne au code une structure bien meilleure qu'auparavant.
Vous avez affiché la même liste pour les derniers exercices. C'est voulu, pour vous montrer que l'interface Adapter
vous permet d'architecturer votre code de nombreuses manières différentes. Plus votre code est complexe, plus il est important de bien l'architecturer. Dans les applications de production, ces modèles et d'autres sont utilisés avec RecyclerView
. Tous les modèles fonctionnent et présentent chacun des avantages. Le choix dépend de ce que vous créez.
Félicitations ! Vous êtes bien parti pour maîtriser RecyclerView
sur Android.
Projet Android Studio : RecyclerViewDiffUtilDataBinding.
DiffUtil
:
RecyclerView
comporte une classe appeléeDiffUtil
, qui permet de calculer les différences entre deux listes.DiffUtil
comporte une classe appeléeItemCallBack
que vous étendez pour déterminer la différence entre deux listes.- Dans la classe
ItemCallback
, vous devez remplacer les méthodesareItemsTheSame()
etareContentsTheSame()
.
ListAdapter
:
- Pour gérer des listes sans frais, vous pouvez utiliser la classe
ListAdapter
au lieu deRecyclerView.Adapter
. Toutefois, si vous utilisezListAdapter
, vous devez écrire votre propre adaptateur pour les autres mises en page. C'est pourquoi cet atelier de programmation vous montre comment procéder. - Pour ouvrir le menu d'intention dans Android Studio, placez le curseur sur n'importe quel élément de code et appuyez sur
Alt+Enter
(Option+Enter
sur Mac). Ce menu est particulièrement utile pour refactoriser le code et créer des stubs pour implémenter des méthodes. Le menu est contextuel. Vous devez donc placer le curseur exactement au bon endroit pour obtenir le menu approprié.
Liaison de données :
- Utilisez la liaison de données dans la mise en page de l'élément pour lier les données aux vues.
Adaptateurs de liaison :
- Vous avez déjà utilisé
Transformations
pour créer des chaînes à partir de données. Si vous devez lier des données de types différents ou complexes, fournissez des adaptateurs de liaison pour aider la liaison de données à les utiliser. - Pour déclarer un adaptateur de liaison, définissez une méthode qui prend un élément et une vue, puis annotez la méthode avec
@BindingAdapter
. En Kotlin, vous pouvez écrire l'adaptateur de liaison en tant que fonction d'extension surView
. Transmettez le nom de la propriété que l'adaptateur adapte. Exemple :
@BindingAdapter("sleepDurationFormatted")
- Dans la mise en page XML, définissez une propriété
app
portant le même nom que l'adaptateur de liaison. Transmettez une variable avec les données. Exemple :
.app:sleepDurationFormatted="@{sleep}"
Cours Udacity :
- Développer des applications Android avec Kotlin
- Kotlin Bootcamp for Programmers (Formation Kotlin pour les programmeurs)
Documentation pour les développeurs Android :
- Créer une liste avec RecyclerView
RecyclerView
DiffUtil
- Bibliothèque Data Binding
- Adaptateurs de liaison
notifyDataSetChanged()
Transformations
Autres ressources :
Cette section répertorie les devoirs possibles pour les élèves qui suivent cet atelier de programmation dans le cadre d'un cours animé par un enseignant. Il revient à l'enseignant d'effectuer les opérations suivantes :
- Attribuer des devoirs si nécessaire
- Indiquer aux élèves comment rendre leurs devoirs
- Noter les devoirs
Les enseignants peuvent utiliser ces suggestions autant qu'ils le souhaitent, et ne doivent pas hésiter à attribuer d'autres devoirs aux élèves s'ils le jugent nécessaire.
Si vous suivez cet atelier de programmation par vous-même, n'hésitez pas à utiliser ces devoirs pour tester vos connaissances.
Répondre aux questions suivantes
Question 1
Parmi les éléments suivants, lesquels sont nécessaires pour utiliser DiffUtil
? Plusieurs réponses possibles.
▢ Étendez la classe ItemCallBack
.
▢ Ignorer areItemsTheSame()
.
▢ Ignorer areContentsTheSame()
.
▢ Utiliser la liaison de données pour suivre les différences entre les éléments.
Question 2
Parmi les affirmations suivantes sur les adaptateurs de liaison, lesquelles sont vraies ?
▢ Un adaptateur de liaison est une fonction annotée avec @BindingAdapter
.
▢ L'utilisation d'un adaptateur de liaison vous permet de séparer le formatage des données du conteneur de la vue.
▢ Vous devez utiliser un RecyclerViewAdapter
si vous souhaitez utiliser des adaptateurs de liaison.
▢ Les adaptateurs de liaison constituent une excellente solution lorsque vous devez transformer des données complexes.
Question 3
Quand devriez-vous envisager d'utiliser Transformations
au lieu d'un adaptateur de liaison ? Plusieurs réponses possibles.
▢ Vos données sont simples.
▢ Vous mettez en forme une chaîne.
▢ Votre liste est très longue.
▢ Votre ViewHolder
ne contient qu'une seule vue.
Passez à la leçon suivante :