Skip to content

WPF DataGrid 行双击事件中如何获取行数据

🏷️ WPF

因为双击 DataGrid 的空白区域也会出发双击事件(MouseDoubleClick),所以当前选中行并不一定就是事件触发行。

这里主要参考了 这篇博客 上的写法,但是该写法有时候会报 “System.Windows.Documents.Run”不是 Visual 或 Visual3D。 的错误。对于这个异常,参考 GitHub 上某个项目 issue 解决了。

修改后的示例代码如下:

1. 扩展方法类 VisualTreeExtensions.cs

csharp
using System.Windows;
using System.Windows.Media;
using System.Windows.Media.Media3D;

public static class VisualTreeExtensions
{
    public static DependencyObject FindVisualTreeRoot(this DependencyObject d)
    {
        var current = d;
        var result = d;

        while (current != null)
        {
            result = current;
            if (current is Visual || current is Visual3D)
            {
                break;
            }
            else
            {
                // If we're in Logical Land then we must walk 
                // up the logical tree until we find a 
                // Visual/Visual3D to get us back to Visual Land.
                current = LogicalTreeHelper.GetParent(current);
            }
        }

        return result;
    }
}

2. 双击事件代码

csharp
private void grdJobs_MouseDoubleClick(object sender, MouseButtonEventArgs e)
{
    var dg = sender as DataGrid;
    Point aP = e.GetPosition(dg);

    IInputElement obj = dg.InputHitTest(aP);
    DependencyObject target = obj as DependencyObject;

    while (target != null)
    {
        if (target is DataGridRow)
        {
            break;
        }
        target = VisualTreeHelper.GetParent(target.FindVisualTreeRoot());
    }

    if (target == null)
    {
        return;
    }

    if (row.GetIndex() >= 0)
    {
        // get row data
    }
    else
    {
        return;
    }
}