2011-06-06 9 views
9

SaludosEn Silverlight, ¿cómo encuentro el primer campo vinculado a un modelo que tiene un error para poder enfocarlo?

Tengo un formulario de Silverlight vinculado a un objeto modelo que implementa INotifyDataErrorInfo y realiza la validación al hacer clic en el botón Guardar. Si algunas de las propiedades en el modelo vuelven inválidas, Silverlight resaltará automáticamente el campo de entrada encuadernado.

¿Hay alguna manera de establecer el foco en el primer campo no válido?

ACTUALIZACIÓN: ¿Hay alguna forma de ver si un campo de entrada se encuentra en ese estado de visualización no válido? Si puedo detectar eso, puedo recorrer mis campos y establecer el enfoque manualmente.

Gracias, Mateo

Respuesta

1

he implementado este comportamiento. Primero debe suscribirse a los métodos de ViewModel ErrorsChanged y PropertyChanged. Estoy haciendo esto en mi constructor:

/// <summary> 
    /// Initializes new instance of the View class. 
    /// </summary> 
    public View(ViewModel viewModel) 
    { 
     if (viewModel == null) 
      throw new ArgumentNullException("viewModel"); 

     // Initialize the control 
     InitializeComponent(); // exception 

     // Set view model to data context. 
     DataContext = viewModel; 

     viewModel.PropertyChanged += new PropertyChangedEventHandler(_ViewModelPropertyChanged); 
     viewModel.ErrorsChanged += new EventHandler<DataErrorsChangedEventArgs>(_ViewModelErrorsChanged); 
    } 

Luego escribir controladores para este tipo de eventos:

/// <summary> 
    /// If model errors has changed and model still have errors set flag to true, 
    /// if we dont have errors - set flag to false. 
    /// </summary> 
    /// <param name="sender">Ignored.</param> 
    /// <param name="e">Ignored.</param> 
    private void _ViewModelErrorsChanged(object sender, DataErrorsChangedEventArgs e) 
    { 
     if ((this.DataContext as INotifyDataErrorInfo).HasErrors) 
      _hasErrorsRecentlyChanged = true; 
     else 
      _hasErrorsRecentlyChanged = false; 
    } 

    /// <summary> 
    /// Iterate over view model visual childrens. 
    /// </summary> 
    /// <param name="sender">Ignored.</param> 
    /// <param name="e">Ignored.</param> 
    private void _ViewModelPropertyChanged(object sender, PropertyChangedEventArgs e) 
    { 
     if ((this.DataContext as INotifyDataErrorInfo).HasErrors) 
      _LoopThroughControls(this); 
    } 

Y, por último método Add:

/// <summary> 
    /// If we have error and we haven't already set focus - set focus to first control with error. 
    /// </summary> 
    /// <remarks>Recursive.</remarks> 
    /// <param name="parent">Parent element.</param> 
    private void _LoopThroughControls(UIElement parent) 
    { 
     // Check that we have error and we haven't already set focus 
     if (!_hasErrorsRecentlyChanged) 
      return; 

     int count = VisualTreeHelper.GetChildrenCount(parent); 

     // VisualTreeHelper.GetChildrenCount for TabControl will always return 0, so we need to 
     // do this branch of code. 
     if (parent.GetType().Equals(typeof(TabControl))) 
     { 
      TabControl tabContainer = ((TabControl)parent); 
      foreach (TabItem tabItem in tabContainer.Items) 
      { 
       if (tabItem.Content == null) 
        continue; 

       _LoopThroughControls(tabItem.Content as UIElement); 
      } 
     } 

     // If element has childs. 
     if (count > 0) 
     { 
      for (int i = 0; i < count; i++) 
      { 
       UIElement child = (UIElement)VisualTreeHelper.GetChild(parent, i); 

       if (child is System.Windows.Controls.Control) 
       { 
        var control = (System.Windows.Controls.Control)child; 

        // If control have error - we found first control, set focus to it and 
        // set flag to false. 
        if ((bool)control.GetValue(Validation.HasErrorProperty)) 
        { 
         _hasErrorsRecentlyChanged = false; 
         control.Focus(); 
         return; 
        } 
       } 

       _LoopThroughControls(child); 
      } 
     } 
    } 
4

Se puede usar un ValidationSummary en su vista para mostrar todos los errores de validación de su modelo planteaba. Cuando hace clic en un error en el ValidationSummary, se enfocará el control que causó el error de validación.

Se puede encontrar un ejemplo de ValidationSummary en el samples de Silverlight Toolkit.

Hasta ahora Google No utilizar el ValidationSummary en cualquier aplicación, por lo que no se puede dar ninguna información sobre el uso o "cómo utilizar", pero tal vez this le ayudará a

+0

que terminé haciendo precisamente eso. No es ideal, pero es lo suficientemente bueno por ahora. – Matthew

Cuestiones relacionadas