当打开Window时,如何将一个datatemplated TextBox聚焦在Window中ItemsControl的第一个元素中?(C#,WPF)

God*_*ark 4 c# wpf textbox focus itemscontrol

当用户单击应用程序中的按钮时,会打开一个窗口.我想要将属于ItemsControl中第一项的TextBox聚焦,这样用户可以在打开Window时立即开始输入,而无需手动选择TextBox.

如何才能做到这一点?

为简单起见,我们可以说Window看起来大致如下:

<Window>
    <Grid>
        <ItemsControl ItemsSource="{Binding MyItems}">
            <DataTemplate>
                <Grid>
                    <StackPanel>
                        <StackPanel>
                            <customControls:ValidationControl>
                                <TextBox Text="" />
                            </customControls:ValidationControl>
                        </StackPanel>
                    </StackPanel>
                </Grid>
            </DataTemplate>
        </ItemsControl>
    </Grid>
</Window>
Run Code Online (Sandbox Code Playgroud)

更新后查看提出的答案以及此链接: Window Loaded和WPF 修改后的解决方案如下:

<Window>
    <Grid>
        <ItemsControl x:Name="myItemsControl" ItemsSource="{Binding MyItems}">
            <DataTemplate>
                <Grid>
                    <StackPanel>
                        <StackPanel>
                            <customControls:ValidationControl>
                                <TextBox Text="" />
                            </customControls:ValidationControl>
                        </StackPanel>
                    </StackPanel>
                </Grid>
            </DataTemplate>
        </ItemsControl>
    </Grid>
</Window>
Run Code Online (Sandbox Code Playgroud)

在构造函数中:

this.Loaded += new RoutedEventHandler(ThisWindowLoaded);
Run Code Online (Sandbox Code Playgroud)

加载方法:

private void ThisWindowLoaded(object sender, RoutedEventArgs e)
{
    var textbox = FindVisualChild<TextBox>(myItemsControl.ItemContainerGenerator.ContainerFromIndex(0));
    FocusManager.SetFocusedElement(myItemsControl, textbox);
}
Run Code Online (Sandbox Code Playgroud)

超级方法:

public static T FindVisualChild<T>(DependencyObject depObj) where T : DependencyObject
{
    if (depObj != null)
    {
        for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
        {
            DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
            if (child != null && child is T)
            {
                return (T)child;
            }

            T childItem = FindVisualChild<T>(child);
            if (childItem != null)
                return childItem;
        }
    }
    return null;
}
Run Code Online (Sandbox Code Playgroud)

小智 6

FocusManager.SetFocusedElement()可能就是你所发现的.

XAML

   <ItemsControl x:Name="ItemsControl">
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <TextBox />
            </DataTemplate>
        </ItemsControl.ItemTemplate>
    </ItemsControl> 
Run Code Online (Sandbox Code Playgroud)

在Loaded事件中,您专注于第一个文本框:

   var textbox = ItemsControl.ItemContainerGenerator.ContainerFromIndex(0).FindChildByType<TextBox>();
   FocusManager.SetFocusedElement(ItemsControl, textbox);
Run Code Online (Sandbox Code Playgroud)

以下是我找到第一个孩子的方式:

  public static T FindVisualChild<T>(DependencyObject depObj) where T : DependencyObject
    {
        if (depObj != null)
        {
            for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
            {
                DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
                if (child != null
                    && child is T)
                {
                    return (T)child;
                }

                T childItem = FindVisualChild<T>(child);
                if (childItem != null)
                    return childItem;
            }
        }
        return null;
    }
Run Code Online (Sandbox Code Playgroud)