0

我在该主题上进行了很多搜索,但在没有代码的情况下无法真正找到解决方案。我知道有些人会说为这个视图相关的事情使用代码隐藏是完全可以的,但我还是想避免它。

我有一个用户控件,它显示一个带有单个文本框和一个确定按钮的“对话框”。该对话框是一个简单的用户控件,位于所有其他控件之上。默认情况下,用户控件的可见性设置为折叠。如果用户控件可见,我想将键盘焦点设置为对话框用户控件上的文本框。有没有办法在 xaml 中完全做到这一点?由于在加载控件时我的对话框控件不可见,因此只需设置

FocusManager.FocusedElement="{Binding ElementName=tbID}"

不管用。我尝试使用某种可见性触发器:

   <TextBox Grid.Column="3"
             Grid.Row="5"
             Name="tbID"
             VerticalAlignment="Center">
        <TextBox.Style>
            <Style TargetType="{x:Type TextBox}">
                <Style.Triggers>
                    <Trigger Property="Visibility" Value="Visible">
                        <Setter Property="FocusManager.FocusedElement" Value="{Binding ElementName=tbID}" />
                    </Trigger>
                </Style.Triggers>
            </Style>
        </TextBox.Style>
    </TextBox>

但这也不起作用。触发器被触发,但文本框没有获得焦点。我真的很感激对此的任何建议。提前致谢!

4

2 回答 2

3

您可以尝试使用附加行为来设置焦点。这是一些示例代码:

public static class Focus
{
    public static readonly DependencyProperty ShouldFocusWhenVisibleProperty =
        DependencyProperty.RegisterAttached("ShouldFocusWhenVisible", typeof (bool), typeof (Focus), new PropertyMetadata(default(bool), ShouldFocusWhenVisibleChanged));

    private static void ShouldFocusWhenVisibleChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
    {
        var uiElement = sender as UIElement;
        if (uiElement == null) return;

        var shouldFocus = GetShouldFocusWhenVisible(uiElement);
        if (shouldFocus)
        {
            UpdateFocus(uiElement);
            uiElement.IsVisibleChanged += UiElementOnIsVisibleChanged;
        }
        else
            uiElement.IsVisibleChanged -= UiElementOnIsVisibleChanged;
    }

    private static void UiElementOnIsVisibleChanged(object sender, DependencyPropertyChangedEventArgs e)
    {
        var uiElement = sender as UIElement;
        if (uiElement == null) return;

        UpdateFocus(uiElement);
    }

    private static void UpdateFocus(UIElement uiElement)
    {
        if (!uiElement.IsVisible) return;

        Keyboard.PrimaryDevice.Focus(uiElement);
    }

    public static void SetShouldFocusWhenVisible(UIElement uiElement, bool value)
    {
        uiElement.SetValue(ShouldFocusWhenVisibleProperty, value);
    }

    public static bool GetShouldFocusWhenVisible(UIElement uiElement)
    {
        return (bool)uiElement.GetValue(ShouldFocusWhenVisibleProperty);
    }
}

然后,将以下代码应用于对话框中的 TextBox <TextBox local:Focus.ShouldFocusWhenVisible="True" />:请注意,这local:将需要是对上述 Focus 类的命名空间的引用。

于 2013-03-04T13:35:23.940 回答
2

我认为你想绑定到UserControl Visibility属性而不是TextBox

例子

<UserControl x:Class="WpfApplication7.IconButton"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             mc:Ignorable="d" 
             d:DesignHeight="100" d:DesignWidth="200" Name="_this">
    <Grid>
        <TextBox Name="tbID" Margin="0,12,0,0" VerticalAlignment="Top">
            <TextBox.Style>
                <Style TargetType="{x:Type TextBox}">
                    <Style.Triggers>
                        <DataTrigger Binding="{Binding ElementName=_this, Path=Visibility}" Value="Visible">
                            <Setter Property="FocusManager.FocusedElement" Value="{Binding ElementName=tbID}" />
                        </DataTrigger>
                    </Style.Triggers>
                </Style>
            </TextBox.Style>
        </TextBox>
    </Grid>
</UserControl>
于 2013-03-04T22:16:04.470 回答