Come visualizzare sulla TextBox il contenuto della cella corrente.
Nell‘articolo precedente abbiamo usato i Converter e le DataGridTemplateColumn per modificare l’aspetto dei dati aggiungendo qualcosa che mostra a colpo d’occhio come i dati si evolvono. Proseguiamo lo sviluppo con qualcosa di più tecnico. Ovvero faremo in modo di copiare sulla TextBox in calce alla Window il contenuto della cella correntemente selezionata al click del mouse sulla cella. Ovviamente la funzionalità per se non ha un gran senso, ma il codice per rilevare il contenuto delle celle, ovviamente può essere applicato per funzionalità ben diverse e più utili.
Visualizzare il contenuto della cella corrente su una TextBox
Per iniziare, dobbiamo aggiungere alla DataGrid, un event handler per intercettare l’evento SelectedCellsChanged; nel suo codice metteremo il necessario a ottenere il risultato voluto.
<DataGrid Name="dgStat" Grid.Row="0" AutoGenerateColumns="False" CurrentItem="{Binding CurrentStatistic, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" ItemsSource="{Binding Statistics, UpdateSourceTrigger=PropertyChanged}" SelectedCellsChanged="DgStat_SelectedCellsChanged" SelectionUnit="Cell">
Modifichiamo per prima cosa la dichiarazione della DataGrid aggiungendo la riga relativa all’event handler. Posizioniamoci poi sul nome dell’event handler e premiamo F12 oppure Tasto Destro e sul menu contestuale “Go to Definition“. Così ci verrà generato il metodo relativo in modo automatico.
Usando il menu, o il tasto F12 otterremo il codice qui sotto riportato.
private void DgStat_SelectedCellsChanged(object sender, SelectedCellsChangedEventArgs e) { }
Come potete notare la DataGrid ci passa dei dati tramite il SelectedCellsChangedEventArgs. Una delle cose che ci viene restituita è la seguente:
e.AddedCells
Come il nome della variabile ci dice, all’interno di questa collezione troviamo le celle selezionate. Visto che abbiamo indicato alla DataGrid di usare la selezione per Cella, vi troveremo un unico elemento. Gli elementi della collection sono oggetti di tipo DataGridCellInfo, pertanto mi aspettavo di trovare una property che restituisse il valore della colonna selezionata. Sfortunatamente non è così, soprattutto per le colonne di tipo DataGridTemplateColumn che possono contenere qualsiasi numero e tipo di controllo e quindi non permettono di recuperare il contenuto della cella in modo semplice. Pertanto ho fatto vari test e il seguente metodo è stato quello che è risultato più semplice.
- Effettuo un ciclo su tutte le colonne della collection AddedCells (ce ne sarà sempre una, ma perché non gestire le cose in modo generico?).
- Dalla DataGridCellInfo recupero l’oggetto Item che contiene la riga della collezione corrispondente a questa cella, quindi un oggetto CustomerStats.
- Utilizzo poi la property Header della DataGridCellInfo che riporta la stringa di intestazione e con uno switch seleziono l’opportuna cella dell’oggetto Item e la inserisco su una string builder. (anche in questo caso per fare in modo funzioni anche per dati multipli).
- Pongo il valore (o i valori) trovati nella Property SelectedValue, che è stata posta in Binding con il campo Text della TextBlock, pertanto il valore viene visualizzato automaticamente.
Di seguito il codice che realizza i punti qui sopra indicati:
private void DgStat_SelectedCellsChanged(object sender, SelectedCellsChangedEventArgs e) { if (e.AddedCells != null) { StringBuilder sb = new StringBuilder(); foreach (var cell in e.AddedCells) { CustomerStats item = cell.Item as CustomerStats; if (item != null) { string value = ""; switch (cell.Column.Header) { case "Trend": value = item.Trend.ToString(); break; case "Year": value = item.Year.ToString(); break; case "Customer Name": value = item.CustomerName.ToString(); break; case "Sales": value = item.SalesTotal.ToString(); break; case "Budget": value = item.BudgetTotal.ToString(); break; case "% Sales": value = item.PercentSales.ToString(); break; case "% Budget": value = item.PercentSales.ToString(); break; } sb.AppendLine(value); } } SelectedCellValue = sb.ToString(); } }
Potrebbe non essere il codice più elegante ma non ho trovato nulla di più semplice per ottenere quanto mi serviva.
Come vedete, la cella selezionata (in blu) si riflette nella TextBox sottostante.
Ci fermiamo qui per oggi, nel prossimo articolo, vedremo qualcosa di più corposo ovvero come salvare la configurazione delle colonne della DataGrid per ripristinarle alla successiva apertura dell’applicazione.