WPF DataGridTemplateColumn.我错过了什么吗?

iLe*_*ing 6 wpf datagrid focus wpftoolkit wpfdatagrid

     <data:DataGridTemplateColumn Header="Name">
        <data:DataGridTemplateColumn.CellTemplate>
            <DataTemplate>
                <TextBlock Text="{Binding Name}">
            </DataTemplate>
        </data:DataGridTemplateColumn.CellTemplate> 
        <data:DataGridTemplateColumn.CellEditingTemplate>
            <DataTemplate>
                <TextBox Text="{Binding Name}">
            </DataTemplate>
        </data:DataGridTemplateColumn.CellEditingTemplate> 
    </data:DataGridTemplateColumn>              
Run Code Online (Sandbox Code Playgroud)

这是模板列的明显例子,对吧?这可能有什么问题?所以,这就是事情 - 当用户通过点击TAB键导航DataGrid时,它需要点击TAB两次(!)才能编辑TextBox中的文本.一旦用户获得列焦点,我怎么能让它可编辑,我的意思是即使他刚刚开始打字?

好.我找到了一种方法 - 进入Grid.KeyUp()我把代码放在下面:

 if (Grid.CurrentColumn.Header.ToString() == "UserName")
        {
            if (e.Key != Key.Escape) 
            {
                Grid.BeginEdit();

                // Simply send another TAB press
                if (Keyboard.FocusedElement is Microsoft.Windows.Controls.DataGridCell)
                {
                    var keyEvt = new KeyEventArgs(Keyboard.PrimaryDevice, Keyboard.PrimaryDevice.ActiveSource, 0, Key.Tab) { RoutedEvent = Keyboard.KeyDownEvent };
                    InputManager.Current.ProcessInput(keyEvt);
                }
            }
        } 
Run Code Online (Sandbox Code Playgroud)

Nal*_*iya 9

您遇到的问题是DataGridTemplateColumn中的控件(例如TextBox)包含在DataGridCell中.默认情况下,DataGridCell具有制表位功能.因此,必须按两次TAB以获得焦点到TextBox控件的原因.解决方案是禁用DataGridCell的制表位功能.这可以通过DataGridCell的样式完成.

这是解决方案:

<Style TargetType="{x:Type DataGridCell}">
     <Setter Property="KeyboardNavigation.IsTabStop" Value="False" />
</Style>
Run Code Online (Sandbox Code Playgroud)


Ara*_*and 8

你的问题源于这样一个事实,即每个单元格将其编辑器放在首先获得焦点的内容控件中,然后你必须再次选择标签.如果您在GenerateEditingElement方法中查看DataGridTemplateColumn的代码,它会调用一个方法LoadTemplateContent来执行此操作:

private FrameworkElement LoadTemplateContent(bool isEditing, object dataItem, DataGridCell cell)
{
    DataTemplate template = ChooseCellTemplate(isEditing);
    DataTemplateSelector templateSelector = ChooseCellTemplateSelector(isEditing);
    if (template != null || templateSelector != null)
    {
        ContentPresenter contentPresenter = new ContentPresenter();
        BindingOperations.SetBinding(contentPresenter, ContentPresenter.ContentProperty, new Binding());
        contentPresenter.ContentTemplate = template;
        contentPresenter.ContentTemplateSelector = templateSelector;
        return contentPresenter;
    }

    return null;
}
Run Code Online (Sandbox Code Playgroud)

看看它如何创建一个新的内容演示者来放入模板.其他人以各种方式处理这个问题,我派生自己的列类型来处理这些东西.(所以我不创建额外的元素或设置内容演示者不接收焦点)在这个例子中他们使用焦点管理器来处理相同的问题(我还没有测试过这段代码)

<tk:DataGridTemplateColumn.CellEditingTemplate>
   <DataTemplate>
      <Grid FocusManager.FocusedElement="{Binding ElementName=txt1}">
         <TextBox Name="txt1" Text="{Binding XPath=@ISBN}" 
                  BorderThickness="0" GotFocus="TextBox_GotFocus"/>
      </Grid>
   </DataTemplate>
</tk:DataGridTemplateColumn.CellEditingTemplate>
Run Code Online (Sandbox Code Playgroud)

如果您有一个用户控件作为编辑器,那么您可以将模式与焦点管理器一起使用,或者为OnLoaded事件使用事件处理程序.