【问题标题】:How to TAB through a ListView with TextBoxes as TreeViewItems?如何通过带有 TextBoxes 作为 TreeViewItems 的 ListView 进行 TAB?
【发布时间】:2011-08-11 01:25:00
【问题描述】:

所以我基本上有这个 ListView,我想按 Tab 并遍历我的 TreeViewItems(最好只有我的 TextBoxes)

<ListView>
    <ListView.View>
        <GridView>
            <GridViewColumn  Header="number"  />
            <GridViewColumn Header="Selector">
                <GridViewColumn.CellTemplate>
                    <DataTemplate>
                        <TextBox Text="{Binding SelectorName}"/>
                    </DataTemplate>
                </GridViewColumn.CellTemplate>
            </GridViewColumn>
        </GridView>
    </ListView.View>
</ListView>

我看到的场景是在第一次按下选项卡后选择了整个第一个 TreeViewItem 并再次按下 Tab 选择了第一个 TextBox。最后第三个 TAB 离开 TreeView 到下一个控件,尽管有我想在“标签”到下一个控件之前捕获更多的文本框。 谢谢x

编辑: 问题在这里得到了回答: How to TAB through TextBoxes in a ListView

【问题讨论】:

    标签: wpf xaml listview textbox datatemplate


    【解决方案1】:

    【讨论】:

    • 这显然是我缺少的部分内容,现在如果您在选择时将焦点添加到文本框,那就完美了。
    【解决方案2】:

    也许我遗漏了一些东西,但我找不到任何简单的方法来做到这一点,以下是你可以做的概述:

    <ListView.InputBindings>
        <KeyBinding Key="Tab" Command="{Binding GoToNextItem}"
                CommandParameter="{Binding RelativeSource={RelativeSource AncestorType=ListView}}" />
        <KeyBinding Modifiers="Shift" Key="Tab" Command="{Binding GoToPreviousItem}"
                CommandParameter="{Binding RelativeSource={RelativeSource AncestorType=ListView}}" />
    </ListView.InputBindings>
    <ListView.ItemContainerStyle>
        <Style TargetType="{x:Type ListViewItem}">
            <EventSetter Event="Selected" Handler="ItemSelected" />
        </Style>
    </ListView.ItemContainerStyle>
    <ListView.View>
        <GridView>
            <GridViewColumn  Header="number"  />
            <GridViewColumn Header="Selector">
                <GridViewColumn.CellTemplate>
                    <DataTemplate>
                        <TextBox Name="_tb" Text="{Binding SelectorName}"/>
                    </DataTemplate>
                </GridViewColumn.CellTemplate>
            </GridViewColumn>
        </GridView>
    </ListView.View>
    

    我在这里做过的事情:

    • 覆盖选项卡行为以触发命令以选择另一个项目
    • 将事件处理程序添加到选定事件以聚焦文本框
    • 为 TextBox 命名,以便可以找到并聚焦

    代码:

    private readonly ICommand _GoToNextItem = new Command((p) =>
        {
            var lv = p as ListView;
            if (lv.SelectedIndex == -1 || lv.SelectedIndex == lv.Items.Count - 1)
            {
                lv.SelectedIndex = 0;
            }
            else
            {
                lv.SelectedIndex++;
            }
        });
    public ICommand GoToNextItem { get { return _GoToNextItem; } }
    
    private readonly ICommand _GoToPreviousItem = new Command((p) =>
    {
        var lv = p as ListView;
        if (lv.SelectedIndex <= 0)
        {
            lv.SelectedIndex = lv.Items.Count - 1;
        }
        else
        {
            lv.SelectedIndex--;
        }
    });
    public ICommand GoToPreviousItem { get { return _GoToPreviousItem; } }
    
    private void ItemSelected(object sender, RoutedEventArgs e)
    {
        var item = sender as ListBoxItem;
        (FindNamedChild(item, "_tb") as TextBox).Focus();
    }
    
    public static object FindNamedChild(DependencyObject container, string name)
    {
        if (container is FrameworkElement)
        {
            if ((container as FrameworkElement).Name == name) return container;
        }
        var ccount = VisualTreeHelper.GetChildrenCount(container);
        for (int i = 0; i < ccount; i++)
        {
            var child = VisualTreeHelper.GetChild(container, i);
            var target = FindNamedChild(child, name);
            if (target != null)
            {
                return target;
            }
        }
        return null;
    }
    

    这是非常粗略的,使用其中的任何部分需要您自担风险。 (我认为,如果不将选择纳入其中,聚焦也可以采用不同的方式

    Command 类只是ICommand 的一个通用实现,它接受一个在接口的Execute 方法中执行的lambda

    【讨论】:

    • 谢谢 H.B.实际上我最终没有使用它,因为当你有很多文本框时,虽然你想要,但你不会离开 ListView,这很烦人。而且我不知道 SHIFT + TAB 可以再次选择 TreeviewItem,然后您可以使用向上和向下箭头进行迭代,并且仍然可以选择按 Tab 退出 TreeView 到下一个控件。
    • @Mohamed Cheri:是的,被制表符困住不是很方便。我希望这对你仍然有用。
    【解决方案3】:

    在 GridViewColumn 和单元格模板上设置 IsTabStop="False"。它现在应该只选择 选项卡更改时数据模板内的文本框。

    试试这个:

    <ListView DataContext="List" IsTabStop="False" >
            <ListView.View>
                <GridView>
                    <GridViewColumn  Header="Name" />
                    <GridViewColumn Header="Selector">
                        <GridViewColumn.CellTemplate>
                            <DataTemplate  >
                                <TextBox Text="{Binding Name}" />
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                </GridView>
            </ListView.View>
        </ListView>
    

    【讨论】:

    • 不是有效的 XAML。你是这个意思吗?
    • 这不行,列不支持这样的属性,焦点仍然离开整个控件而不是转到下一项。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-07-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-09-04
    • 1970-01-01
    • 2021-11-15
    相关资源
    最近更新 更多