【问题标题】:Issue with doubleclick on datagrid双击数据网格的问题
【发布时间】:2014-06-27 15:26:07
【问题描述】:

我的 C# 代码中的数据网格上有以下内容:

<DataGrid.InputBindings>  
    <MouseBinding Gesture="LeftDoubleClick" Command="{Binding CmdTransUnitFillerRowDblClick}" />  
</DataGrid.InputBindings>  

它在大多数情况下都有效,除非用户首先选择行(单击)然后尝试双击该行。在这种情况下,永远不会触发 CmdTransUnitFillerRowDblClick 代码进行处理。

那么,当行已被选中时,如何让 CmdTransUnitFillerRowDblClick 在双击时正确触发?
既然有人会问:

private void ExecutecmdTransUnitFillerRowDblClick(object parameter)  
{
    if (DgTransUnitFillerSelectedItem != null)
        TransUnitFillerDoubleClick(DgTransUnitFillerSelectedItem.CollectionRowId);
}

【问题讨论】:

    标签: c# wpf xaml wpfdatagrid


    【解决方案1】:

    my answer to another related question。问题是用户选择一行(或单元格,实际上)后数据网格不再具有焦点;用户在数据网格中单击 in 的单元格。因此,您必须将焦点更改回数据网格以允许这样做。

    变化:

    <DataGrid.InputBindings>  
        <MouseBinding Gesture="LeftDoubleClick" Command="{Binding CmdTransUnitFillerRowDblClick}" />  
    </DataGrid.InputBindings>
    

    收件人:

    <DataGrid.InputBindings>  
        <MouseBinding Gesture="LeftDoubleClick" Command="{Binding CmdTransUnitFillerRowDblClick}" />  
        <MouseBinding Gesture="LeftClick" Command="{Binding CmdTransUnitFillerRowClick}" />  
    </DataGrid.InputBindings>
    

    ...并添加:

    private void ExecutecmdTransUnitFillerRowClick(object parameter)  
    {
        if (DgTransUnitFillerSelectedItem != null)
            The_Name_Of_Your_DataGrid.Focus();
    }
    

    【讨论】:

    • 未经测试,但他就不能只听DoubleClick事件而忽略e.Handled吗?
    • @TroelsLarsen 如果单元格保持焦点,DataGrid 上的 DoubleClick 事件将永远不会触发,因此他必须在单元格上添加另一个 DoubleClick 事件或更改焦点。
    • 啊.. 我刚刚看到它是一个 InputBinding,而不是一个事件。 :)
    • 谢谢,解释后有道理。似乎对我有用
    • @klugerama,你如何使用 MVVM 格式做到这一点?
    【解决方案2】:

    在现有的 InputBinding 之上,您可以使用 Style 将 InputBinding 附加到每个单元格:

    <Style TargetType="DataGridCell">
        <Setter Property="local:MouseCommands.LeftDoubleClick" Value="ApplicationCommands.New" />
    </Style>
    

    这需要使用 here 中的 MouseCommands 类。

    public static class MouseCommands
    {
        private static void LeftDoubleClickChanged(DependencyObject sender, DependencyPropertyChangedEventArgs args)
        {
            var control = (Control)sender;
    
            if (args.NewValue != null && args.NewValue is ICommand)
            {
                var newBinding = new MouseBinding(args.NewValue as ICommand, new MouseGesture(MouseAction.LeftDoubleClick));
                control.InputBindings.Add(newBinding);
            }
            else
            {
                var oldBinding = control.InputBindings.Cast<InputBinding>().First(b => b.Command.Equals(args.OldValue));
                control.InputBindings.Remove(oldBinding);
            }
        }
    
        public static readonly DependencyProperty LeftDoubleClickProperty =
            DependencyProperty.RegisterAttached("LeftDoubleClick",
                typeof(ICommand),
                typeof(MouseCommands),
                new UIPropertyMetadata(LeftDoubleClickChanged));
    
        public static void SetLeftDoubleClick(DependencyObject obj, ICommand value)
        {
            obj.SetValue(LeftDoubleClickProperty, value);
        }
    
        public static ICommand GetLeftDoubleClick(DependencyObject obj)
        {
            return (ICommand)obj.GetValue(LeftDoubleClickProperty);
        }
    }
    

    虽然我认为更简洁的方法是在代码隐藏中处理 MouseDoubleClick 事件,并通过直接调用 ViewModel 或在命令上调用 .Execute() 手动引发命令执行。

    【讨论】:

    • 我想过走代码隐藏路线,但这是别人设置的东西,他们不想使用代码隐藏,所以我在尝试修复时一直试图保持这种理念这个问题。我会试试你的解决方案。
    • 这可能在某些情况下对我有用,但是对于我们在数据网格上使用的某些接口,它会像疯了一样抛出错误。将链接保存到我的收藏夹,以便我以后可以根据需要参考
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-22
    • 2014-04-04
    • 1970-01-01
    • 1970-01-01
    • 2012-07-23
    相关资源
    最近更新 更多