TP 4 : Gestion d'une
liste de films
2LM
Développez une application Android permettant de gérer une liste de films avec les fonctionnalités suivantes :
Fonctionnalités principales :
1. Affichage de films
o Affichez une liste de films à l’aide d’un RecyclerView.
o Les données sont stockées dans une ArrayList.
2. Utilisation de ViewBinding
o Utilisez ViewBinding pour accéder aux vues de manière sécurisée et moderne.
3. Menu dans la barre d'action Ajoutez un menu dans la barre d'action contenant les options suivantes :
o About Us
Affiche un Toast contenant le message "isitcom".
Cette option doit apparaître directement dans la barre d’action avec une icône d'information.
o Visiter IMDB
Ouvre le site IMDB dans le navigateur.
Cette option doit apparaître dans le menu déroulant (trois points) avec une icône de navigateur.
oAppeler
Ouvre l'application téléphone avec le numéro "+216 12345678" pré-rempli.
Cette option doit également apparaître dans le menu déroulant (trois points) avec une icône de
téléphone.
4. Menu contextuel sur les éléments de la liste
o Lors d’un appui long sur un film dans le RecyclerView, un menu contextuel s’affiche avec deux
options :
o Modifier
Ouvre une boîte de dialogue personnalisée permettant de modifier le nom du film.
Cette boîte de dialogue doit être stylisée et contenir deux boutons :
▪ Confirmer : applique la modification
▪ Annuler : ferme la boîte de dialogue sans changement
o Supprimer
Affiche une AlertDialog pour confirmer la suppression du film sélectionné.
En cas de confirmation, le film est supprimé de la liste.
5. Afficher les détails d'un film sélectionné selon l'orientation de l’appareil Portrait et Landscape.
Figure 2 : Vue générale MainActivity
Figure 1 : menu contextuel avec deux options : Editer et Supprimer,
si l'utilisateur faire une longue presse sur un item du RecycleView
Figure 4 : modifier le nom du film Figure 3 : Confirmation de la
avec le Dialogue personnalisé suppression avec AlertDialog
Figure 5 : Structure du projet
🛠️ Étapes de réalisation
Partie 1 : Création du projet
• Créer un nouveau projet Android avec une activité vide.
• Activer ViewBinding dans le fichier [Link] (Module: app):
android {
…………………… rest of code
buildFeatures {
viewBinding = true
}
Then click "Sync Now" in Android Studio and wait until finish.
❑ ViewBinding is a feature in Android that helps you easily access views from your layout XML in a type-safe and
simple way without writing findViewById().
❑ When ViewBinding is enabled, Android Studio generates a binding class for each XML layout file.
Naming rule:
dialog_perso.xml → class name becomes DialogPersoBinding.
Partie 2 : Définition du modèle de données
• Créer une classe Film .
public class Film {
private int id;
private String nom;
private int annee;
private String directeur;
/* complete the code */ //////////// constructors
/* complete the code */ //////////// getters and setters
Partie 3 : Création du layout pour les éléments de la liste
• Créer un fichier item_film.xml dans le dossier res/layout avec un TextView pour afficher le
nom du film.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="[Link]
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:padding="16dp">
<TextView
android:id="@+id/tvNom"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="24sp"
android:textStyle="bold"
android:textColor="#D78223" />
<View
android:layout_width="match_parent"
android:layout_height="1dp"
android:layout_marginTop="12dp"
android:background="#2196F3" />
</LinearLayout>
Partie 4.1 : Modifier le thème(light and dark) de l’application pour afficher le bar d’action
Dans res/values/themes/[Link] et [Link] (night)
effacer “.NoActionBar”
<resources xmlns:tools="[Link]
<!-- Base application theme. -->
<style name="[Link]" parent="[Link]">
<!-- Customize your light theme here. -->
<!-- <item name="colorPrimary">@color/my_light_primary</item> -->
</style>
<style name="[Link]" parent="[Link]" />
</resources>
Notice : Make sure your [Link] uses this theme:
android:theme="@style/[Link] "
Partie 4.2 : Creé un dossier ‘menu’ dans res
Crée un fichier main_menu.xml
(res/menu/main_menu.xml)
o About Us
Cette option doit apparaître directement dans la barre d’action avec une icône d'information.
o Visiter IMDB
Cette option doit apparaître dans le menu déroulant (trois points) avec une icône de navigateur.
o Appeler
Cette option doit également apparaître dans le menu déroulant (trois points) avec une icône de
téléphone.
<!—complet the missing code with “……………….” -->
<menu xmlns:app="[Link]
xmlns:android="[Link]
<item android:id="@+id/about"
android:title="About Us"
app:showAsAction="…………." />
<item android:id="@+id/imdb"
android:title="Visiter IMDB"
app:showAsAction="………." />
<item android:id="@+id/call"
android:title="Appeler"
app:showAsAction="…………" />
</menu>
Partie 4.3 : Menu contextuel :
Crée un fichier menu_contextuel.xml dans (res/menu/menu_contextuel.xml)
o Lors d’un appui long sur un film dans le RecyclerView, un menu contextuel s’affiche avec deux
options :
❖ Edit
❖ Delete
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="[Link]
<item
android:id="@+id/action_edit"
android:title="Edit" />
<item
android:id="@+id/action_delete"
android:title="Delete" />
</menu>
Partie 5 : Création Boîte de dialogue personnalisée
Crée un fichier dialog_edit_movie.xml dans (res/layout/dialog_edit_movie.xml)
o Boîte de dialogue personnalisée permettant de modifier le nom du film.
Cette boîte de dialogue doit être stylisée et contenir deux boutons :
▪ Confirmer : applique la modification
▪ Annuler : ferme la boîte de dialogue sans changement
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="[Link]
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:padding="20dp"
>
<TextView
android:id="@+id/dialogTitle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Modifier le film"
android:textSize="20sp"
android:textStyle="bold"
android:layout_gravity="center"
android:textColor="#000000"
android:paddingBottom="10dp" />
<EditText
android:id="@+id/editTextMovieName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="Nom du film"
android:padding="12dp"
android:textColor="#000000"
android:textColorHint="#888888"
android:layout_marginBottom="20dp" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="end">
<Button
android:id="@+id/btnCancel"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Annuler"
android:backgroundTint="#B0BEC5"
/>
<Button
android:id="@+id/btnConfirm"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Confirmer"
android:backgroundTint="#4CAF50"
/> </LinearLayout> </LinearLayout>
Partie 6 : Ajoutez le layout activity_main.xml
Avec un RecyclerView avec l'id recyclerView .
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="[Link]
xmlns:app="[Link]
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<[Link]
android:id="@+id/recyclerView"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="8dp" />
</LinearLayout>
Partie 7 : Adapter du RecyclerView
Question : What is an Adapter in Android?
In Android, an Adapter is a bridge between a data source (like an ArrayList) and a UI component (like a RecyclerView,
ListView, or GridView).It takes your data (like a list of movies) and adapts it into views that can be displayed on the
screen.
➔When using a RecyclerView, we must create our own Adapter by extending [Link].
Créez une classe FilmAdapter :
package [Link];
/* complet the code */ // imports
// Adapter pour gérer l'affichage d'une liste de films dans un RecyclerView
public class FilmAdapter extends [Link]<[Link]> {
private List<Film> filmList; // Liste des films à afficher
private OnItemLongClickListener listener; // Listener pour les clics longs (menu contextuel)
// Interface pour capturer les événements de clic long
public interface OnItemLongClickListener {
void onItemLongClick(View view, int position);
}
// Méthode pour définir l'écouteur du clic long (depuis l'activité)
public void setOnItemLongClickListener(OnItemLongClickListener l) {
listener = l;
}
// Constructeur : on passe la liste des films à afficher
public FilmAdapter(List<Film> filmList) {
[Link] = filmList;
}
// Classe interne représentant chaque élément (ligne) du RecyclerView
public class FilmViewHolder extends [Link] implements
[Link] {
TextView nom; // Composant pour afficher le nom du film
public FilmViewHolder(View itemView) {
super(itemView);
// Lier la vue XML à l'objet Java
nom = [Link]([Link]);
// Permet d'associer un menu contextuel à chaque item
[Link](this);
// Gestion du clic long sur un item de la liste
[Link](v -> {
if (listener != null)
[Link](v, getAdapterPosition()); // Notifier l'activité
return false; // false : permet d'afficher le menu contextuel après
});
}
// Méthode appelée quand l'utilisateur effectue un clic long
@Override
public void onCreateContextMenu(ContextMenu menu, View v, [Link] menuInfo) {
// Titre du menu contextuel
[Link]("Movie Action");
// Ajouter deux options : Éditer et Supprimer
[Link](getAdapterPosition(), [Link].action_edit, 0, "Edit");
[Link](getAdapterPosition(), [Link].action_delete, 1, "Delete");
}
}
// Méthode appelée par RecyclerView pour créer une nouvelle "ligne" (ViewHolder)
@Override
public FilmViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
// Créer la vue à partir de l'XML item_film.xml
View view = [Link]([Link]()).inflate([Link].item_film, parent, false);
// Retourner un nouveau ViewHolder avec cette vue
return new FilmViewHolder(view);
}
// Méthode appelée pour afficher les données à une position donnée
@Override
public void onBindViewHolder(FilmViewHolder holder, int position) {
// Récupérer le film correspondant
Film f = [Link](position);
// Afficher uniquement le nom du film dans le TextView
[Link]([Link]());
}
// Indique combien d'éléments contient la liste
@Override
public int getItemCount() {
return [Link]();
}
}
Partie 8 : MainActivity avec ViewBinding
package [Link];
/* complet the code */ // imports
public class MainActivity extends AppCompatActivity {
private ActivityMainBinding binding; // Liaison avec le layout XML grâce au ViewBinding
private List<Film> filmList = new ArrayList<>(); // Liste contenant les films
private FilmAdapter adapter; // Adaptateur pour connecter la liste au RecyclerView
private int selectedPosition; // Position du film sélectionné (pour modifier/supprimer)
@Override
protected void onCreate(Bundle savedInstanceState) {
[Link](savedInstanceState);
binding = [Link](getLayoutInflater());
setContentView([Link]());
// Initialisation des films
[Link](new Film(1, "Interstellar", 2014, "Christopher Nolan"));
[Link](new Film(2, "Inception", 2010, "Christopher Nolan"));
[Link](new Film(3, "Breaking Bad", 2008, "Vince Gilligan and Peter Gould"));
[Link](new Film(4, "Game Of Thrones", 2011, " David Benioff and D. B. Weiss"));
[Link](new Film(5, "Better Call Saul", 2015, " Vince Gilligan and Peter Gould "));
// Configuration du RecyclerView : layout vertical + liaison avec l'adapter
adapter = new FilmAdapter(filmList);
[Link](new LinearLayoutManager(this));
[Link](adapter);
// Gestion du clic long pour afficher un menu contextuel sur un film
[Link]((view, position) -> {
selectedPosition = position;
[Link](); // Pour afficher le menu contextuel
});
// Enregistrement du RecyclerView pour qu'il puisse utiliser le menu contextuel
registerForContextMenu([Link]);
}
// Gestion des éléments sélectionnés dans le menu contextuel (clic long)
@Override
public boolean onContextItemSelected(MenuItem item) {
/* complete the code */ // actions when an item is selected
return [Link](item);
}
// Boîte de confirmation avant suppression
private void showDeleteConfirmation() {
new [Link](this)
.setTitle("Confirmation")
.setMessage("Voulez-vous vraiment supprimer ce film ?")
.setPositiveButton("Oui", (d, which) -> {
/* complete the code */ // supprimer le film
[Link](selectedPosition); // mise à jour graphique
})
.setNegativeButton("Non", null)
.show();
}
// Boîte de dialogue personnalisée pour modifier le nom d'un film
private void showEditDialog() {
Dialog dialog = new Dialog(this);
[Link]([Link].dialog_edit_movie);
EditText editText = [Link]([Link]);
Button btnConfirm = [Link]([Link]);
Button btnCancel = [Link]([Link]);
// Préremplir le champ avec le nom actuel
[Link]([Link](selectedPosition).getNom());
// Bouton de validation
[Link](v -> {
String newName = [Link]().toString().trim();
if (![Link]()) {
[Link](selectedPosition).setNom(newName);
[Link](selectedPosition);
[Link](this, "Nom modifié", Toast.LENGTH_SHORT).show();
[Link]();
} else {
[Link](this, "Veuillez entrer un nom", Toast.LENGTH_SHORT).show();
}
});
// Bouton d’annulation
[Link](v -> {
/* complete the code */ //Fermer le dialog sans rien faire
});
[Link](); // Afficher la boîte de dialogue
}
// Création du menu de l'action bar (menu supérieur)
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate([Link].main_menu, menu);
return true;
}
// Actions du menu principal (About, IMDB, Appeler)
@Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = [Link]();
/* complete the code */ // Gérer les actions selon l’élément sélectionné (about, call, imdb)
return [Link](item);
}
}
Partie 9 : Détails du film en fonction de l'orientation (Portrait / Paysage)
Objectif:
Ajouter la possibilité d'afficher les détails d'un film sélectionné selon l'orientation de l’appareil:
• En Portrait (Vertical) : ouvrir une nouvelle activité pour afficher les détails.
• En Landscape (Horizontal) : afficher directement les détails dans le même écran, dans un fragment situé à
droite de la liste des films.
Partie 9.1 : Adapter le layout pour gérer Portrait et Landscape
• Dans res/layout/activity_main.xml (portrait):
o Contenir seulement le RecyclerView.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="[Link]
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<[Link]
android:id="@+id/recyclerView"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</LinearLayout>
• Créez un dossier layout-land Dans res
Notice : If you create a folder with a name like “isitcom” instead of the conventional layout-land (or
other standard folder names), Android won't recognize it automatically.
Ensuit, Afficher tous les dossiers,
car Android Studio par défaut
n’affiche pas les dossier
personnalisé (ou bien vide)
• Dans res/ layout-land / activity_main.xml (paysage):
o Séparer l'écran en deux parties : liste à gauche, détails à droite.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="[Link]
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="horizontal">
<[Link]
android:id="@+id/recyclerView"
android:layout_width="0dp"
android:layout_weight="1"
android:layout_height="match_parent"/>
<FrameLayout
android:id="@+id/detail_container"
android:layout_width="0dp"
android:layout_weight="2"
android:layout_height="match_parent"/>
</LinearLayout>
Partie 9.2 : modifier l’adaptateur :
public class FilmAdapter extends [Link]<[Link]> {
// 2. Déclaration des variables
private List<Film> filmList; // Liste des films à afficher
private OnItemLongClickListener longClickListener; // Gestion des clics longs (menu contextuel)
private OnItemClickListener clickListener; // Gestion des clics simples (ouvrir détails)
// 3. Interface pour écouter un clic long (press long)
public interface OnItemLongClickListener {
void onItemLongClick(View view, int position);
}
// 4. Interface pour écouter un clic simple (press normal)
public interface OnItemClickListener {
void onItemClick(View view, int position);
}
// 5. Permet de définir le listener de clic long
public void setOnItemLongClickListener(OnItemLongClickListener listener) {
longClickListener = listener;
}
// 6. Permet de définir le listener de clic simple
public void setOnItemClickListener(OnItemClickListener listener) {
clickListener = listener;
}
// 7. Constructeur de FilmAdapter (on lui passe la liste de films)
public FilmAdapter(List<Film> filmList) {
[Link] = filmList;
}
// 8. Classe interne qui représente un item (un film)
public class FilmViewHolder extends [Link] implements
[Link] {
TextView nom; // TextView qui affichera le nom du film
public FilmViewHolder(View itemView) {
super(itemView);
// 8.1. Lier la vue XML à la variable Java
nom = [Link]([Link]);
// 8.2. Activer le menu contextuel quand on appuie longtemps
[Link](this);
// 8.3. Gérer un clic simple (ouvrir détails)
[Link](v -> {
if (clickListener != null)
[Link](v, getAdapterPosition());
});
// 8.4. Gérer un clic long (ouvrir menu contextuel Modifier/Supprimer)
[Link](v -> {
if (longClickListener != null)
[Link](v, getAdapterPosition());
return false; // false pour permettre aussi d'afficher le menu contextuel
});
}
// 8.5. Méthode pour créer le menu contextuel (quand clic long)
@Override
public void onCreateContextMenu(ContextMenu menu, View v, [Link] menuInfo) {
[Link]("Options");
[Link](getAdapterPosition(), [Link].action_edit, 0, "Editer"); // option éditer
[Link](getAdapterPosition(), [Link].action_delete, 1, "Supprimer"); // option supprimer
}
}
// 9. Méthode appelée quand RecyclerView a besoin d'un nouveau ViewHolder
@Override
public FilmViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
// 9.1. Créer une vue à partir de XML (item_film.xml)
View view = [Link]([Link]())
.inflate([Link].item_film, parent, false);
return new FilmViewHolder(view);
}
// 10. Méthode appelée pour afficher les données dans un ViewHolder
@Override
public void onBindViewHolder(FilmViewHolder holder, int position) {
// 10.1. Récupérer le film actuel
Film film = [Link](position);
// 10.2. Afficher uniquement le nom du film
[Link]([Link]());
}
// 11. Retourne le nombre total d'éléments dans la liste
@Override
public int getItemCount() {
return [Link]();
}
}
Partie 9.3 : afficher les détails du film en mode paysage
Créez un fichier fragment_detail.xml dans res/layout/ pour afficher les informations du film :
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="[Link]
android:layout_width="match_parent"
android:layout_height="match_parent"
android:backgroundTint="#03A9F4"
android:orientation="vertical"
android:padding="16dp">
<TextView
android:id="@+id/tvId"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="ID: "
android:textSize="24sp"
android:textStyle="bold" />
<TextView
android:id="@+id/tvNom"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:paddingTop="8dp"
android:text="Nom: "
android:textSize="24sp"
android:textStyle="bold" />
<TextView
android:id="@+id/tvAnnee"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:paddingTop="8dp"
android:text="Année: "
android:textSize="24sp"
android:textStyle="bold" />
<TextView
android:id="@+id/tvDirecteur"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:paddingTop="8dp"
android:text="Directeur: "
android:textSize="24sp"
android:textStyle="bold" />
</LinearLayout>
Créez une classe DetailFragment :
public class DetailFragment extends Fragment {
private TextView tvId, tvNom, tvAnnee, tvDirecteur;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = [Link]([Link].fragment_detail, container, false);
tvId = [Link]([Link]);
tvNom = [Link]([Link]);
tvAnnee = [Link]([Link]);
tvDirecteur = [Link]([Link]);return view;
}
public void afficherInformations(Film film) {
if (getView() != null) {
TextView tvId = getView().findViewById([Link]);
TextView tvNom = getView().findViewById([Link]);
TextView tvAnnee = getView().findViewById([Link]);
TextView tvDirecteur = getView().findViewById([Link]);
[Link]("ID: "+ ……….. ); /* complete the code */
[Link]("Nom: " + …………. ); /* complete the code */
[Link]("Année: " + ……………….. ); /* complete the code */
[Link]("Directeur: " ……………… ); /* complete the code */ }
} }
Partie 9.4 : afficher les détails du film en mode portrait
Créer une activité DetailActivity pour afficher les détails en mode portrait :
public class DetailActivity extends AppCompatActivity {
private ActivityDetailBinding binding;
@Override
protected void onCreate(Bundle savedInstanceState) {
[Link](savedInstanceState);
binding = [Link](getLayoutInflater());
setContentView([Link]());
[Link]("ID: " + getIntent().getIntExtra("id",0));
[Link]("Nom: " + getIntent().getStringExtra("nom"));
[Link]("Année: " + getIntent().getIntExtra("annee",0));
[Link]("Directeur: " + getIntent().getStringExtra("directeur"));
} }
activity_detail.xml:
<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="[Link]
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="20dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView android:id="@+id/tvId"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="ID: "
android:textStyle="bold"
android:textSize="24sp"/>
<TextView android:id="@+id/tvNom"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Nom: "
android:textSize="24sp"
android:textStyle="bold"
android:paddingTop="8dp"/>
<TextView android:id="@+id/tvAnnee"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Année: "
android:paddingTop="8dp"
android:textStyle="bold"
android:textSize="24sp"/>
<TextView android:id="@+id/tvDirecteur"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Directeur: "
android:paddingTop="8dp"
android:textStyle="bold"
android:textSize="24sp"/>
</LinearLayout>
</ScrollView>
Partie 9.5 : Modifier MainActivity
Dans [Link], implémentez le comportement suivant :
• Si l'écran est landscape, afficher les détails dans DetailFragment.
• Sinon, ouvrir une nouvelle activité DetailActivity.
public class MainActivity extends AppCompatActivity implements [Link] {
private ActivityMainBinding binding; // ViewBinding pour accéder aux vues de activity_main.xml
private List<Film> filmList = new ArrayList<>(); // Liste des films
private FilmAdapter adapter; // Adaptateur pour le RecyclerView
private int selectedPosition; // Position du film sélectionné pour edit/supprimer
private boolean isLandscape; // Indique si l'orientation est en paysage (landscape)
@Override
protected void onCreate(Bundle savedInstanceState) {
[Link](savedInstanceState);
binding = [Link](getLayoutInflater());
setContentView([Link]());
// Remplir la liste des films
[Link](new Film(1, "Interstellar", 2014, "Christopher Nolan"));
[Link](new Film(2, "Inception", 2010, "Christopher Nolan"));
[Link](new Film(3, "Breaking Bad", 2008, "Vince Gilligan and Peter Gould"));
[Link](new Film(4, "Game Of Thrones", 2011, "David Benioff and D. B. Weiss"));
[Link](new Film(5, "Better Call Saul", 2015, "Vince Gilligan and Peter Gould"));
// Configurer le RecyclerView
adapter = new FilmAdapter(filmList);
[Link](new LinearLayoutManager(this)); // Layout vertical
[Link](adapter);
// Relier l'adaptateur à l'interface d'écoute de clics
[Link](this);
// Vérifier si on est en landscape en cherchant le conteneur du fragment
isLandscape = (findViewById([Link].detail_container) != null);
if (isLandscape) {
// Si landscape, ajouter un fragment vide au démarrage pour éviter les erreurs plus tard
getSupportFragmentManager()
.beginTransaction()
.replace([Link].detail_container, new DetailFragment())
.commit();
}
}
// Gestion des clics longs (menu contextuel Modifier/Supprimer)
@Override
public boolean onContextItemSelected(MenuItem item) {
if ([Link]() == [Link].action_edit) {
showEditDialog(); // Modifier un film
return true;
} else if ([Link]() == [Link].action_delete) {
showDeleteConfirmation(); // Supprimer un film
return true;
}
return [Link](item);
}
// Afficher une boîte de confirmation pour supprimer un film
private void showDeleteConfirmation() {
new [Link](this)
.setTitle("Confirmation")
.setMessage("Voulez-vous vraiment supprimer ce film ?")
.setPositiveButton("Oui", (d, which) -> {
[Link](selectedPosition); // Supprimer le film de la liste
[Link](selectedPosition); // Notifier l'adaptateur
})
.setNegativeButton("Non", null) // Annuler
.show();
}
// Afficher une boîte de dialogue personnalisée pour éditer le nom du film
private void showEditDialog() {
Dialog dialog = new Dialog(this);
[Link]([Link].dialog_edit_movie);
EditText editText = [Link]([Link]);
Button btnConfirm = [Link]([Link]);
Button btnCancel = [Link]([Link]);
// Pré-remplir le champ avec le nom actuel
[Link]([Link](selectedPosition).getNom());
// Lorsque l'utilisateur confirme la modification
[Link](v -> {
String newName = [Link]().toString().trim();
if (![Link]()) {
[Link](selectedPosition).setNom(newName); // Mettre à jour le nom
[Link](selectedPosition); // Notifier l'adaptateur
[Link](this, "Nom modifié", Toast.LENGTH_SHORT).show();
[Link]();
} else {
[Link](this, "Veuillez entrer un nom", Toast.LENGTH_SHORT).show();
}
});
// Annuler la modification
[Link](v -> {
[Link](); // Fermer le dialog sans rien faire
});
[Link]();
}
// Créer le menu principal dans l'Action Bar
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate([Link].main_menu, menu);
return true;
}
// Gérer les actions du menu principal
@Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = [Link]();
if (id == [Link]) {
[Link](this, "isitcom", Toast.LENGTH_SHORT).show(); // About Us
return true;
} else if (id == [Link]) {
startActivity(new Intent(Intent.ACTION_VIEW, [Link]("[Link] // Ouvrir IMDB
return true;
} else if (id == [Link]) {
Intent intent = new Intent(Intent.ACTION_DIAL, [Link]("[Link] // Appeler
startActivity(intent);
return true;
}
return [Link](item);
}
// Quand l'utilisateur clique sur un item du RecyclerView
@Override
public void onItemClick(View view, int position) {
Film film = [Link](position);
FragmentManager manager = getSupportFragmentManager();
DetailFragment fragDetail = (DetailFragment) [Link]([Link].detail_container);
if (fragDetail != null && [Link]()) {
// En landscape : afficher directement dans le fragment
[Link](film);
} else {
// in portrait mode:
//ouvrir une nouvelle activité et transmettre les donnes id , nom , annee et directeur vers DetailActivity
/* complete the code */
}
}
}
Figure 6: portrait mode: select "Breaking Bad" Figure 7: portrait mode: show "Breaking Bad"
Details in DetailActivity Activity
Figure 8: landscape mode: show the details of "Game Of Thrones" when it's selected from the recycle view