Silverlight - Ver modelo

En este capítulo, veremos una técnica importante en el desarrollo de software de Silverlight, el uso de View Models.

  • los view model es una pieza clave, que introduce una técnica llamada presentación separada manteniendo la vista separada del modelo.

  • View Models ofrecen una forma de lograr una presentación separada, y veremos cómo explotan el enlace de datos de Silverlight para reducir la cantidad de código necesario en su interfaz de usuario.

Desafíos del desarrollo de la interfaz de usuario

View Modelsestán diseñados para resolver ciertos problemas que surgen con frecuencia al desarrollar software de interfaz de usuario. Quizás el más importante es que el código de la interfaz de usuario a menudo es difícil de probar de manera inextricable, especialmente con pruebas unitarias automatizadas. También existen problemas de calidad del código que pueden afectar la flexibilidad y el mantenimiento continuos de su código.

  • Si sigue el camino de menor resistencia que las herramientas de diseño de Visual Studio lo conducen, puede terminar colocando demasiado código en el código subyacente.

  • Es muy común ver que se agregan grandes cantidades de funcionalidad de la aplicación al código subyacente.

  • Pocos desarrolladores planearían realmente poner la lógica empresarial en una clase de interfaz de usuario, pero debido a que allí es donde Visual Studio coloca sus controladores de eventos, se convierte en un lugar demasiado conveniente para hacer las cosas.

  • Está ampliamente aceptado que el software es más fácil de desarrollar y mantener si las clases tienen responsabilidades bien definidas y razonablemente limitadas.

  • El trabajo del código detrás es interactuar directamente con los objetos que componen la interfaz de usuario donde sea necesario.

  • Tan pronto como comience a poner código que tome decisiones sobre cómo se comporta su aplicación, lo que tiende a generar problemas.

  • No solo la lógica de la aplicación puede fluir hacia el código que se supone que está relacionado con la interfaz de usuario, algunos desarrolladores comienzan a confiar en los controles y otros objetos de la interfaz de usuario para mantener un estado importante de la aplicación.

  • El modelo simplemente contiene los datos, la vista simplemente contiene la fecha formateada y el controlador (ViewModel) actúa como enlace entre los dos. El controlador puede tomar información de la vista y colocarla en el modelo y viceversa.

Presentación separada

Para evitar los problemas causados ​​por poner la lógica de la aplicación en el código detrás o XAML, es mejor usar una técnica conocida como separated presentation. Con XAML y código detrás con el mínimo requerido para trabajar con objetos de interfaz de usuario directamente, las clases de interfaz de usuario también contienen código para comportamientos de interacción complejos, lógica de aplicación y todo lo demás, como se muestra a continuación en el lado izquierdo.

Características importantes de la presentación separada:

  • Con una presentación separada, la clase de interfaz de usuario es mucho más simple. Tiene XAML, por supuesto, pero el código detrás hace tan poco como es práctico.

  • La lógica de la aplicación pertenece a una clase separada, que a menudo se denomina model.

  • Muchos desarrolladores intentan usar el enlace de datos para conectar elementos en el XAML directamente a propiedades en el modelo.

  • El problema es el model se ocupa completamente de lo que hace la aplicación y no de cómo interactúa el usuario con la aplicación.

  • La mayoría de las interfaces de usuario tienen algún estado que no pertenece al modelo de aplicación. Por ejemplo, si su interfaz de usuario utiliza arrastrar y soltar, algo debe realizar un seguimiento de cosas como dónde se encuentra el elemento que se está arrastrando en este momento, cómo debería cambiar su apariencia a medida que se mueve sobre posibles destinos de colocación y cómo esos destinos de colocación también pueden cambiar a medida que el elemento se arrastra sobre ellos.

  • Este tipo de estado puede volverse sorprendentemente complejo y necesita ser probado a fondo.

  • En la práctica, normalmente desea que haya otra clase entre la interfaz de usuario y el modelo. Esto tiene dos roles importantes.

    • Primero, adapta su modelo de aplicación para una vista de interfaz de usuario en particular.

    • En segundo lugar, es donde vive cualquier lógica de interacción no trivial, y con eso me refiero al código necesario para que su interfaz de usuario se comporte de la manera que usted desea.

Modelo / Vista / Modelo de vista

View Modeles un ejemplo del enfoque de presentación separada, pero aclaremos qué tipo de cosas tenemos en cada capa. Hay tres capas:

  • Model
  • View
  • ViewModel

Modelo

Esto es un classic modelo de objetos que comprende clases de C # ordinarias que no tienen relación directa con la interfaz de usuario.

Por lo general, esperaría que los códigos de su modelo pudieran compilarse sin referencias a ninguna biblioteca de interfaz de usuario. De hecho, probablemente podría tomar exactamente el mismo código fuente y compilarlo en una aplicación Silverlight, una aplicación de consola .NET normal o incluso un código web del lado del servidor.

Los tipos en el modelo deben representar los conceptos con los que trabaja su aplicación.

Ver

Una Vista es normalmente un UserControl, puede ser su MainPage, o puede ser simplemente una parte de su página.

En la mayoría de las aplicaciones de Silverlight, es una buena idea dividir su interfaz de usuario en partes pequeñas que definan un UserControl o View para cada parte.

Las aplicaciones de Silverlight no son únicas a este respecto. Algo que obviamente es específico de Silverlight es la Vista. Cuanto más fina sea la interfaz de usuario, mejores serán las cosas. No solo es menos probable que se tropiece con otros desarrolladores que trabajan en los mismos archivos, sino que mantener las cosas pequeñas y simples desalienta naturalmente los atajos que conducen a un código espagueti.

Por ejemplo, es muy común definir un View para representar un elemento individual en una lista.

ViewModel

Finalmente, para cada View, escribe un ViewModel. Entonces, esta es una de las características importantes de unViewModel clase.

Existe para servir a una vista particular. losViewModel está especializado para una forma particular de presentar las cosas, como un elemento de datos particular tal como aparece en las listas.

Por eso se llama ViewModel; adapta el modelo subyacente especialmente para una vista particular. Como el modelo, elViewModeltambién es una clase C # ordinaria. No necesita derivar de ningún tipo en particular.

Da la casualidad de que algunos desarrolladores encuentran conveniente poner algunas funciones comunes en una clase ViewModel base, pero el patrón no lo exige. En particular, tuViewModelno deriva de ningún tipo específico de Silverlight. Sin embargo, a diferencia del modelo, puede utilizar tipos de Silverlight en sus propiedades.

Por ejemplo, su ViewModel puede elegir hacer que ciertas partes de su interfaz de usuario sean visibles solo bajo ciertas condiciones, por lo que puede proporcionar una propiedad de tipo System.Windows.Visibility, que es el tipo de elementos de Silverlight que usan para su propiedad Visibility. Esto hace posible vincular la visibilidad de un elemento, como un panel, directamente al ViewModel.

Ejemplo

Veamos un ejemplo simple en el que usaremos Model-View-ViewModel (MVVM) Acercarse.

Step 1 - Cree un nuevo proyecto de aplicación Silverlight SilverlightMVVMDemo.

Step 2 - Agregue las tres carpetas (Modelo, ViewModel y Vistas) a su proyecto como se muestra a continuación.

Step 3 - Agregue una clase StudentModel en la carpeta Modelo y pegue el siguiente código en esa clase.

using System.ComponentModel; 
 
namespace SilverlightMVVMDemo.Model { 

   public class StudentModel {} 
	
   public class Student : INotifyPropertyChanged { 
      private string firstName; 
      private string lastName;  
		
      public string FirstName { 
         get { return firstName; } 
			
         set {
            if (firstName != value) { 
               firstName = value; 
               RaisePropertyChanged("FirstName"); 
               RaisePropertyChanged("FullName"); 
            } 
         } 
      }
		
      public string LastName { 
         get { return lastName; } 
			
         set { 
            if (lastName != value) { 
               lastName = value; 
               RaisePropertyChanged("LastName"); 
               RaisePropertyChanged("FullName"); 
            } 
         } 
      }  
		
      public string FullName { 
         get { 
            return firstName + " " + lastName; 
         } 
      } 
		
      public event PropertyChangedEventHandler PropertyChanged; 
		
      private void RaisePropertyChanged(string property) { 
         if (PropertyChanged != null) { 
            PropertyChanged(this, new PropertyChangedEventArgs(property)); 
         } 
      } 
   } 
}

Step 4 - Agregue otra clase StudentViewModel en la carpeta ViewModel y pegue el siguiente código.

using SilverlightMVVMDemo.Model; 
using System.Collections.ObjectModel;
  
namespace SilverlightMVVMDemo.ViewModel { 

   public class StudentViewModel { 
	
      public ObservableCollection<Student> Students {  
         get;  
         set;  
      }  
		
      public void LoadStudents() { 
         ObservableCollection<Student> students = new ObservableCollection<Student>(); 
				
         students.Add(new Student { FirstName = "Mark", LastName = "Allain" }); 
         students.Add(new Student { FirstName = "Allen", LastName = "Brown" }); 
         students.Add(new Student { FirstName = "Linda", LastName = "Hamerski" });
			
         Students = students; 
      } 
   } 
}

Step 5 - Agregar Silverlight User Control haciendo clic derecho en Views carpeta y seleccione Add New Item….

Step 6- Haga clic en Agregar. Ahora verá el archivo XAML. Agregue el siguiente código enStudentView.xaml archivo, que contiene diferentes elementos de la interfaz de usuario.

<UserControl x:Class = "SilverlightMVVMDemo.Views.StudentView" 
   xmlns = "http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
   xmlns:x = "http://schemas.microsoft.com/winfx/2006/xaml" 
   xmlns:d = "http://schemas.microsoft.com/expression/blend/2008" 
   xmlns:mc = "http://schemas.openxmlformats.org/markup-compatibility/2006" 
   mc:Ignorable = "d" 
   d:DesignHeight = "300" d:DesignWidth = "400">
   
   <Grid x:Name = "LayoutRoot" Background = "White">
	
      <StackPanel HorizontalAlignment = "Left">
		
         <ItemsControl ItemsSource = "{Binding Path=Students}">
			
            <ItemsControl.ItemTemplate>
				
               <DataTemplate> 
					
                  <StackPanel Orientation = "Horizontal"> 
                     <TextBox Text = "{Binding Path = FirstName, Mode = TwoWay}" 
                        Width = "100" Margin = "3 5 3 5"/> 
								
                     <TextBox Text = "{Binding Path = LastName, Mode = TwoWay}"  
                        Width = "100" Margin = "0 5 3 5"/> 
								
                     <TextBlock  Text = "{Binding Path = FullName, Mode=OneWay}" 
                        Margin = "0 5 3 5"/> 
								
                  </StackPanel>
						
               </DataTemplate> 
					
            </ItemsControl.ItemTemplate>
				
         </ItemsControl> 
			
      </StackPanel> 
		
   </Grid> 
	
</UserControl>

Step 7 - Ahora agregue el StudentView en tu MainPage.xaml archivo como se muestra a continuación.

<UserControl x:Class = "SilverlightMVVMDemo.MainPage" 
   xmlns = "http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
   xmlns:x = "http://schemas.microsoft.com/winfx/2006/xaml" 
   xmlns:d = "http://schemas.microsoft.com/expression/blend/2008" 
   xmlns:mc = "http://schemas.openxmlformats.org/markup-compatibility/2006" 
   xmlns:views = "clr-namespace:SilverlightMVVMDemo.Views" 
   mc:Ignorable = "d" 
   d:DesignHeight = "576.316" d:DesignWidth = "863.158"> 
   
   <Grid x:Name = "LayoutRoot" Background = "White"> 
      <views:StudentView x:Name = "StudentViewControl" Loaded = "StudentViewControl_Loaded"/> 
   </Grid> 
	
</UserControl>

Step 8 - Aquí está la implementación de Loaded evento en el MainPage.xaml.cs archivo, que actualizará el View desde el ViewModel.

using System.Windows; 
using System.Windows.Controls; 
 
namespace SilverlightMVVMDemo { 

   public partial class MainPage : UserControl { 
	
      public MainPage() { 
         InitializeComponent();
      }
   } 
	
   private void StudentViewControl_Loaded(object sender, RoutedEventArgs e) { 
      SilverlightMVVMDemo.ViewModel.StudentViewModel 
      studentViewModelObject = new SilverlightMVVMDemo.ViewModel.
      StudentViewModel(); 
      studentViewModelObject.LoadStudents();  
      StudentViewControl.DataContext = studentViewModelObject;  
   } 
}

Step 9 - Cuando se compile y ejecute el código anterior, verá el siguiente resultado en su página web.

UI vs ViewModel

Una de las partes más difíciles del enfoque MVVM es determinar dónde debería llegar la línea divisoria. No siempre es obvio qué cosas pertenecen a dónde.

  • En particular, algunos elementos de la interfaz de usuario proporcionan una funcionalidad que, según una vista estricta, debería pertenecer al modelo de vista.

  • En general, no todos los comportamientos implementados en el View son tan ViewModel amistoso.

  • Parte de la razón de esto es que no existe una forma estándar de empaquetar el comportamiento de ViewModel para su reutilización, especialmente si desea utilizar un entorno de diseño, como Visual Studio o Blend.

Ventajas de MVVM

MVVM ofrece las siguientes ventajas:

  • Separación de preocupaciones de presentación (vista, modelo de vista, modelo)

  • Código limpio, comprobable y manejable. Puede incluir lógica de nivel de presentación en pruebas unitarias.

  • No hay código detrás del código, por lo que la capa de presentación y la lógica están débilmente acopladas.

  • Mejor forma de enlace de datos.

Desventajas de MVVM

Para las IU simples, MVVM puede ser una exageración. La depuración sería un poco difícil cuando tenemos enlaces de datos complejos.