web-dev-qa-db-fra.com

WPF DataGrid: comment déterminer l'index de ligne actuel?

J'essaie d'implémenter une fonctionnalité de feuille de calcul très simple basée sur un DataGrid.

  1. L'utilisateur clique sur une cellule

  2. L'utilisateur tape une valeur et appuie sur Retour

  3. La ligne actuelle est analysée et toute formule de cellule qui dépend de la cellule cliquée est mise à jour.

Cela semble être le meilleur gestionnaire d'événements pour mes besoins:

private void my_dataGrid_CurrentCellChanged(object sender, EventArgs e)

Question: Comment détecter l'index de ligne de la ligne actuelle?

16
Travis Banger

Essayez ceci (en supposant que le nom de votre grille est "my_dataGrid"):

var currentRowIndex = my_dataGrid.Items.IndexOf(my_dataGrid.CurrentItem);

Normalement, vous pourrez utiliser my_dataGrid.SelectedIndex, mais il semble qu'avec l'événement CurrentCellChanged, la valeur de SelectedIndex affiche toujours l'index sélectionné précédemment. Cet événement particulier semble se déclencher avant que la valeur de SelectedIndex ne change réellement.

38
Grant

Salut, vous pouvez faire quelque chose comme ça pour faire votre feuille de calcul

 //not recomended  as it always  return the previous index of the selected row 
 void dg1_CurrentCellChanged(object sender, EventArgs e)
    {

       int rowIndex = dg1.SelectedIndex;   
     }

mais si vous voulez un exemple plus élaboré, voici comment vous pouvez le faire

namespace WpfApplication2
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
    ObservableCollection<Tuple<string,string>> observableCollection = new ObservableCollection<Tuple<string,string>>();  
    public MainWindow()
    {
        InitializeComponent();            
        for (int i = 0; i < 100; i++)
        {
            observableCollection.Add( Tuple.Create("item " + i.ToString(),"=sum (c5+c4)"));
        }

        dg1.ItemsSource = observableCollection; 

        dg1.CurrentCellChanged += dg1_CurrentCellChanged;

    }

    void dg1_CurrentCellChanged(object sender, EventArgs e)
    {
        //int rowIndex = dg1.SelectedIndex;   
        Tuple<string, string> Tuple = dg1.CurrentItem as Tuple<string, string>; 
        //here as you have your datacontext you can loop through and calculate what you want 

    }
}
}

J'espère que cette aide

3
BRAHIM Kamel

La solution de Grant fonctionnera jusqu'à ce que vous n'ayez pas de doublons de référence dans le ItemsSource, sinon vous obtiendrez l'index de la première occurrence de l'objet.

La solution de BRAHIM Kamel fonctionnera jusqu'à ce que vous ayez une sélection, sinon (si vous cliquez deux fois et désélectionnez une cellule/ligne) vous n'aurez pas de SelectedIndex.

Avec YourDataGrid.ItemContainerGenerator.ContainerFromItem( _dataItemFromCurentCell ) as DataGridRow vous obtiendrez toujours en double la dernière occurrence de la donnée.

je voudrais gérer l'événement DataGrid.PreviewMouseLeftButtonDown Et rechercher dans le gestionnaire l'arborescence visuelle jusqu'à DatagridRow, qui a la méthode DatagridRow.GetIndex(). Vous obtiendrez donc toujours le bon index de ligne.

<DataGrid ... PreviewMouseLeftButtonDown="Previe_Mouse_LBtnDown" >
    ...
</DataGrid>

private void Previe_Mouse_LBtnDown(object sender, MouseButtonEventArgs e)
{
    DataGridRow dgr = null;
    var visParent = VisualTreeHelper.GetParent(e.OriginalSource as FrameworkElement);
    while (dgr == null && visParent != null)
    {
        dgr = visParent as DataGridRow;
        visParent = VisualTreeHelper.GetParent(visParent);
    }
    if (dgr == null) { return; }

    var rowIdx=dgr.GetIndex();
}
2
Rekshino