book-openListBox

ListBox afișează o listă verticală de elemente din care utilizatorul poate selecta unul sau mai multe. Este controlul potrivit oriunde ai o colecție de obiecte pe care vrei să le afișezi și să permiți interacțiunea cu ele.

Există o distincție fundamentală pe care trebuie să o înțelegi de la început: ListBox-ul și colecția ta din memorie sunt două lucruri complet separate. ListBox-ul afișează elemente; el nu stochează datele aplicației și nu este sursa de adevăr. Sursa de adevăr este colecția din cod, de exemplu List<Contact> contacte. Ori de câte ori colecția se modifică, ListBox-ul trebuie actualizat manual pentru a reflecta schimbarea.

Această separare este intenționată și valoroasă. Operațiile de filtrare sau căutare pot modifica ce afișează ListBox-ul fără a modifica datele din memorie, exact comportamentul dorit pentru o funcție de căutare.

Adăugarea și eliminarea elementelor

ListBox-ul expune colecția sa de elemente prin proprietatea Items, de tip ListBox.ObjectCollection. Aceasta acceptă orice obiect de tip object.

// Adaugare un element
lstContacte.Items.Add(contact);

// Adaugare mai multor elemente dintr-o colectie
lstContacte.Items.AddRange(contacte.ToArray());

// Eliminare un element specific (prin referinta)
lstContacte.Items.Remove(contact);

// Eliminare dupa index
lstContacte.Items.RemoveAt(0);

// Stergere completa a tuturor elementelor
lstContacte.Items.Clear();

Când adaugi un obiect, ListBox-ul apelează automat ToString() pe el pentru a determina textul afișat. Acesta este motivul pentru care suprascriem ToString() pe clasele al căror obiect vrem să apară în liste:

Fără această suprascriere, ListBox-ul ar afișa numele complet al tipului, ceva de genul RegistruContacte.Contact, care nu este util.

Patternul RefreshLista()

Cel mai clar și mai predictibil mod de a ține ListBox-ul sincronizat cu lista din memorie este o metodă dedicată care golește ListBox-ul și îl repopulează complet la fiecare apel:

Această metodă se apelează după orice operație care modifică lista din memorie:

Alternativa de a adăuga direct în ListBox cu Items.Add în paralel cu modificarea listei din memorie funcționează pentru cazuri simple, dar devine dificil de gestionat în prezența funcționalităților de căutare sau filtrare. Patternul RefreshLista() este mai explicit și mai ușor de urmărit.

Selectarea elementelor

ListBox-ul expune mai multe proprietăți pentru a determina ce element este selectat în momentul curent:

Verificarea dacă ceva este selectat se face prin SelectedItem != null sau prin SelectedIndex != -1. Ambele sunt echivalente; SelectedItem != null este mai explicit:

O subtilitate importantă: dacă obții indexul selectat cu SelectedIndex și folosești acel index pentru a accesa lista din memorie cu contacte[index], trebuie să te asiguri că ListBox-ul afișează exact aceleași elemente în aceeași ordine ca lista din memorie. Dacă ai aplicat filtrare, indexul din ListBox nu mai corespunde indexului din lista completă. Varianta mai sigură este să lucrezi direct cu referința obiectului prin SelectedItem as Contact.

Evenimentul SelectedIndexChanged

Se declanșează de fiecare dată când selecția din ListBox se schimbă, fie prin click, fie prin taste. Util pentru a reactiona la selecția utilizatorului: afișarea detaliilor elementului selectat sau activarea și dezactivarea butoanelor în funcție de starea selecției.

Această abordare este preferabilă față de verificarea selecției în handler-ul butonului: butonul este dezactivat când nu există selecție și activat când există, astfel că utilizatorul primește feedback vizual imediat.

Selecție multiplă

Implicit, ListBox-ul permite selectarea unui singur element. Proprietatea SelectionMode controlează acest comportament:

Când SelectionMode nu este One, proprietatea SelectedItem returnează doar ultimul element selectat. Pentru accesul la toate elementele selectate, folosești SelectedItems:

În exercițiu se lucrează cu SelectionMode.One, care este implicit și suficient pentru cerințele aplicației.

Last updated