0

我有一个主窗口,其中有很多用户控制。并使用导航我能够访问用户控件。但问题是如何在打开用户控件时将焦点设置在第一个文本框上。

我尝试使用依赖属性和布尔标志,我能够成功一点。当我第一次渲染 UserControl 时,我能够集中注意力,但是当我第二次打开时,我无法将焦点设置在 TextBox 上。

还有一件事,我对 TextBoxes 进行了验证,如果验证失败,则应该清空文本框,并且焦点应该放在相应的文本框上。

我如何在 WPF 中使用 MVVM 来实现这一点(CLR 3.5,VS2008)

提前致谢。

4

3 回答 3

1

如果您有 UserControl,那么您也有 CodeBehind。

把它放在你的代码隐藏中,你会做得很好。

this.Loaded += (o, e) => { Keyboard.Focus(textBox1) }

如果您希望收听验证错误,请将其放在您的 UserControl XAML 中。

<UserControl>
 <Grid Validation.Error="OnValidationError">
  <TextBox Text{Binding ..., NotifyOnValidationError=true } />
 </Grid>
<UserControl>

在 UserControl 的 CodeBehind 中,您将拥有如下内容:

public void OnValidationError(o , args)
{
  if(o is TextBox)
  {
    (TextBox)o).Text = string.Empty;
  }
}
于 2013-10-01T13:39:37.700 回答
0

您应该使用 AttachedProperty 来坚持 MVVM 模式,它将使您的视图模型独立于 UI 代码并且完全可单元测试。以下附加属性绑定一个布尔属性以聚焦并突出显示文本框,如果您不想要突出显示,则可以删除突出显示代码并仅使用焦点代码。

public class TextBoxBehaviors
    {
        #region HighlightTextOnFocus Property

        public static readonly DependencyProperty HighlightTextOnFocusProperty =
            DependencyProperty.RegisterAttached("HighlightTextOnFocus", typeof (bool), typeof (TextBoxBehaviors),
                                                new PropertyMetadata(false, HighlightTextOnFocusPropertyChanged));

        public static bool GetHighlightTextOnFocus(DependencyObject obj)
        {
            return (bool) obj.GetValue(HighlightTextOnFocusProperty);
        }

        public static void SetHighlightTextOnFocus(DependencyObject obj, bool value)
        {
            obj.SetValue(HighlightTextOnFocusProperty, value);
        }

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

            if ((bool) e.NewValue)
            {
                uie.GotKeyboardFocus += OnKeyboardFocusSelectText;
                uie.PreviewMouseLeftButtonDown += OnMouseLeftButtonDownSetFocus;
            }
            else
            {
                uie.GotKeyboardFocus -= OnKeyboardFocusSelectText;
                uie.PreviewMouseLeftButtonDown -= OnMouseLeftButtonDownSetFocus;
            }
        }

        private static void OnKeyboardFocusSelectText(object sender, KeyboardFocusChangedEventArgs e)
        {
            var textBox = sender as TextBox;
            if (textBox == null) return;

            textBox.SelectAll();
        }

        private static void OnMouseLeftButtonDownSetFocus(object sender, MouseButtonEventArgs e)
        {
            var textBox = sender as TextBox;
            if (textBox == null) return;

            if (!textBox.IsKeyboardFocusWithin)
            {
                textBox.Focus();
                e.Handled = true;
            }
        }

        #endregion
    }

您可以在要聚焦/突出显示的 TextBox 上使用此附加属性...

<TextBox ... local:TextBoxBehaviors.HighlightTextOnFocus="{Binding IsScrolledToEnd}" ... />
于 2013-10-01T16:19:30.367 回答
0

您也可以尝试使用FocusManager

<UserControl>
 <Grid FocusManager.FocusedElement="{Binding Path=FocusedTextBox, ElementName=UserControlName}">
  <TextBox x:Name="FocusedTextBox" />
 </Grid>
<UserControl>
于 2013-10-01T21:54:13.360 回答