Usando el Patrón de Diseño Observer Manual de Laboratorio (Hands-On Lab)

Por Joel Francia H.

Descarga Descargar Ejemplo de este artículo.

Contenido

 1. Introducción - Utilizando el patrón Observer con Microsoft Visual Studio 2005
 2. Definición
 3. Ejercicio 1 – Creación de una aplicación simple utilizando los conceptos básicos del patrón Observer
 4. Creando la aplicación
 5. Creando la interfaz

1. Introducción - Utilizando el patrón Observer con Microsoft Visual Studio 2005

Este laboratorio incluye los siguientes ejercicios y objetivos:

  • Al finalizar este laboratorio estarás en capacidad de:

    • Aplicar los conceptos utilizados para la aplicación del patrón de diseño Observer e identificar sus beneficios y funcionalidades.

 

2. Definición

Define una depedencia del tipo uno a muchos entre objetos, de tal forma que cuando un objeto cambia su estado, todos los objetos dependientes son notificados y actualizados automáticamente (Ver Figura 1):

Bb972192.art296-img01-570x509(es-es,MSDN.10).gif
Figura 1. Volver al texto.

 

3. Ejercicio 1 – Creación de una aplicación simple utilizando los conceptos básicos del patrón Observer

En este ejercicio se crearán 3 formularios, 2 de los cuales actuarán como observadores y responderán a cambios realizados al tercero (sujeto).

 

4. Creando la aplicación

  1. Ejecuta Microsoft Visual Studio 2005 y luego elige crear un nuevo proyecto. Para ello, ve al menú File | New | Project. Luego escoge el tipo de proyecto Visual C# y la plantilla Windows Application. Nómbralo PatronObserver, y acepta (Ver a Figura 2):

    Bb972192.art296-img02-570x393(es-es,MSDN.10).gif
    Figura 2. Volver al texto.

  2. Añade una nueva clase al proyecto. Para hacerlo, ve al Solution Explorer, ubicado en la parte derecha de la pantalla, y haz clic derecho sobre el nombre del proyecto; luego, en el menú, elige Add | Add New Item. Posteriormente, elige añadir una clase y nómbrala Interfaces.cs o Interfaces.vb, según el lenguaje (Ver Figura 3):

    Bb972192.art296-img03-570x349(es-es,MSDN.10).gif
    Figura 3. Volver al texto.

 

5. Creando la interfaz

  1. En la clase creada, especificaremos los dos tipos de interfaces a utilizar para la creación del patrón Observer:

  2. Luego, añadiremos dos formularios más al proyecto. Ve a la ventana Add New Item antes mencionada y elige la plantilla Windows Form. Nombra los dos formularios ListaObservador y ColorObservador (Ver Figura 4):

    Bb972192.art296-img04-570x350(es-es,MSDN.10).gif
    Figura 4. Volver al texto.

  3. Ve al código del Form1 (doble clic sobre el respectivo formulario) y sitúate en la declaración de la clase Form1. Para que este formulario actúe como un Sujeto que posteriormente dé información a sus Observadores, es necesario que implementes la interfaz Sujeto antes creada. Algo parecido se aplica a los otros dos forms (observadores). Para ello, modifica las siguiente líneas de código:

  4. Ve al diseño del form principal (Form1). Este contendrá un comboBox (cbxColor) que permitirá elegir al usuario un conjunto de colores que luego serán reflejados en los otros formularios. Inserta el control y ve a su Propiedad Items, luego añade la siguiente lista de colores (Ver la Figura 5):

    Bb972192.art296-img05-570x259(es-es,MSDN.10).gif
    Figura 5. Volver al texto.

  5. Dentro del código del formulario principal, introduce lo siguiente:

  6. Vayamos ahora al diseño del formulario ListObserver. Este contendrá un listBox (listaColores) el cual almacenará el nombre de los colores según se elijan en el formulario principal (Ver Figura 6):

    Bb972192.art296-img06-193x271(es-es,MSDN.10).gif
    Figura 6. Volver al texto.

  7. Programamos el siguiente código dentro del ListaObservador:

  8. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  9. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  10. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  11. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  12. Visual C# .net

    public interface Sujeto
    

{       void registrarInteres(Observador obs); }   public interface Observador {       void enviarNotificacion(string mensaje); }

**Visual Basic .net**

<pre IsFakePre="true" xmlns="http://www.w3.org/1999/xhtml">Public Interface Sujeto 

    Sub registrarInteres(ByVal obs As Observador) End Interface   Public Interface Observador     Sub enviarNotificacion(ByVal mensaje As String) End Interface

  1. Luego, añadiremos dos formularios más al proyecto. Ve a la ventana Add New Item antes mencionada y elige la plantilla Windows Form. Nombra los dos formularios ListaObservador y ColorObservador (Ver Figura 4):

    Bb972192.art296-img04-570x350(es-es,MSDN.10).gif
    Figura 4. Volver al texto.

  2. Ve al código del Form1 (doble clic sobre el respectivo formulario) y sitúate en la declaración de la clase Form1. Para que este formulario actúe como un Sujeto que posteriormente dé información a sus Observadores, es necesario que implementes la interfaz Sujeto antes creada. Algo parecido se aplica a los otros dos forms (observadores). Para ello, modifica las siguiente líneas de código:

  3. Ve al diseño del form principal (Form1). Este contendrá un comboBox (cbxColor) que permitirá elegir al usuario un conjunto de colores que luego serán reflejados en los otros formularios. Inserta el control y ve a su Propiedad Items, luego añade la siguiente lista de colores (Ver la Figura 5):

    Bb972192.art296-img05-570x259(es-es,MSDN.10).gif
    Figura 5. Volver al texto.

  4. Dentro del código del formulario principal, introduce lo siguiente:

  5. Vayamos ahora al diseño del formulario ListObserver. Este contendrá un listBox (listaColores) el cual almacenará el nombre de los colores según se elijan en el formulario principal (Ver Figura 6):

    Bb972192.art296-img06-193x271(es-es,MSDN.10).gif
    Figura 6. Volver al texto.

  6. Programamos el siguiente código dentro del ListaObservador:

  7. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  8. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  9. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  10. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  11. Ve al código del Form1 (doble clic sobre el respectivo formulario) y sitúate en la declaración de la clase Form1. Para que este formulario actúe como un Sujeto que posteriormente dé información a sus Observadores, es necesario que implementes la interfaz Sujeto antes creada. Algo parecido se aplica a los otros dos forms (observadores). Para ello, modifica las siguiente líneas de código:

  12. Ve al diseño del form principal (Form1). Este contendrá un comboBox (cbxColor) que permitirá elegir al usuario un conjunto de colores que luego serán reflejados en los otros formularios. Inserta el control y ve a su Propiedad Items, luego añade la siguiente lista de colores (Ver la Figura 5):

    Bb972192.art296-img05-570x259(es-es,MSDN.10).gif
    Figura 5. Volver al texto.

  13. Dentro del código del formulario principal, introduce lo siguiente:

  14. Vayamos ahora al diseño del formulario ListObserver. Este contendrá un listBox (listaColores) el cual almacenará el nombre de los colores según se elijan en el formulario principal (Ver Figura 6):

    Bb972192.art296-img06-193x271(es-es,MSDN.10).gif
    Figura 6. Volver al texto.

  15. Programamos el siguiente código dentro del ListaObservador:

  16. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  17. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  18. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  19. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  20. Visual C# .net

    public partial class Form1 : Form, Sujeto 
    

public partial class ListaObservador : Form, Observador public partial class ColorObservador : Form, Observador

**Visual Basic .net**

<pre IsFakePre="true" xmlns="http://www.w3.org/1999/xhtml">Public Class Form1 

    Implements Sujeto   Public Class ListaObservador     Implements Observador   Public Class ColorObservador     Implements Observador

  1. Ve al diseño del form principal (Form1). Este contendrá un comboBox (cbxColor) que permitirá elegir al usuario un conjunto de colores que luego serán reflejados en los otros formularios. Inserta el control y ve a su Propiedad Items, luego añade la siguiente lista de colores (Ver la Figura 5):

    Bb972192.art296-img05-570x259(es-es,MSDN.10).gif
    Figura 5. Volver al texto.

  2. Dentro del código del formulario principal, introduce lo siguiente:

  3. Vayamos ahora al diseño del formulario ListObserver. Este contendrá un listBox (listaColores) el cual almacenará el nombre de los colores según se elijan en el formulario principal (Ver Figura 6):

    Bb972192.art296-img06-193x271(es-es,MSDN.10).gif
    Figura 6. Volver al texto.

  4. Programamos el siguiente código dentro del ListaObservador:

  5. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  6. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  7. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  8. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  9. Dentro del código del formulario principal, introduce lo siguiente:

  10. Vayamos ahora al diseño del formulario ListObserver. Este contendrá un listBox (listaColores) el cual almacenará el nombre de los colores según se elijan en el formulario principal (Ver Figura 6):

    Bb972192.art296-img06-193x271(es-es,MSDN.10).gif
    Figura 6. Volver al texto.

  11. Programamos el siguiente código dentro del ListaObservador:

  12. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  13. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  14. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  15. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  16. Visual C# .net

    // coleccion de observadores 
    

public List<Observador> observadores = new     List<Observador>();   public Form1()     {     //hacemos que se muestren los formularios observadores     InitializeComponent();     ListObserver observadorLista = new ListObserver(this);     observadorLista.Show();     ColorObserver observadorColor = new ColorObserver(this);     observadorColor.Show();     }       // implementación de la interfaz     public void registrarInteres(Observador obs)     {         // Agrega un objeto Observador a la colección         observadores.Add(obs);     }       // Método que recorre la colección Observadores     //llamando a los enviarNotificacion() de cada observer         private void elegirColor(object sender, EventArgs e)     {         for (int i = 0; i < observadores.Count; i++)         {             Observador obs = (Observador)observadores[i];             obs.enviarNotificacion(cbxColor.Text);         }     }

**Visual Basic .net**

<pre IsFakePre="true" xmlns="http://www.w3.org/1999/xhtml">      'coleccion de observadores

Public observadores As List<Observador>   'hacemos que se muestren los formularios observadores Public Sub New()         Me.observadores = New List<Observador>         Me.components = Nothing         Me.InitializeComponent()         Dim observadorLista As New ListObserver(Me)         observadorLista.Show()         Dim observadorColor As New ColorObserver(Me)         observadorColor.Show() End Sub   'Implementacion de la interface, añade un observador a la 'colección Public Sub registrarInteres(ByVal obs As Observador) Implements Sujeto.registrarInteres         Me.observadores.Add(obs) End Sub         'Método que recorre la colección Observadores                       'llamando a los enviarNotificacion() de cada observer Private Sub elegirColor(ByVal sender As Object, ByVal e As EventArgs)         Dim num As Integer         For num = 0 To Me.observadores.Count - 1             Dim obs As Observador = CType(Me.observadores.Item(num), Observador)             obs.enviarNotificacion(cbxColor.Text)         Next num End Sub

  1. Vayamos ahora al diseño del formulario ListObserver. Este contendrá un listBox (listaColores) el cual almacenará el nombre de los colores según se elijan en el formulario principal (Ver Figura 6):

    Bb972192.art296-img06-193x271(es-es,MSDN.10).gif
    Figura 6. Volver al texto.

  2. Programamos el siguiente código dentro del ListaObservador:

  3. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  4. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  5. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  6. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  7. Programamos el siguiente código dentro del ListaObservador:

  8. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  9. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  10. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  11. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  12. Visual C# .net

    // Se inscribe al formulario para que sea observador del sujeto //al cual hemos pasado como argumento
    

public void registrar(Sujeto sujeto) {       sujeto.registrarInteres(this); }   //Añade al listBox el color enviado por el sujeto y satisface a la interfaz Observervador public void enviarNotificacion(string mensaje) {       listaColores.Items.Add(mensaje); }   public ListaObservervador(Sujeto subj) {       InitializeComponent();       registrar(subj); }

**Visual Basic .net**

<pre IsFakePre="true" xmlns="http://www.w3.org/1999/xhtml">Public Sub New(ByVal subj As Sujeto)

    InitializeComponent()     registrar(subj) End Sub   'Se inscribe al formulario para que sea observador del sujeto al 'cual hemos pasado como argumento Public Sub registrar(ByVal sujeto As Sujeto)     sujeto.registrarInteres(Me) End Sub   'Añade al listBox el color enviado por el sujeto y satisface a 'la interfaz Observervador Public Sub enviarNotificacion(ByVal mensaje As String) Implements Observador.enviarNotificacion     Me.listaColores.Items.Add(mensaje) End Sub

  1. Por último, modificaremos el código del formulario ColorObservador, el cual modificará su color de fondo cada vez que se elija un valor dentro del comboBox del form principal:

  2. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  3. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  4. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  5. Visual C# .net

    //Agregamos atributos a la clase
    

private Container componentes = null; private System.Collections.Generic.Dictionary<string,Color>       colorFondo; private string colNombre;   public ColorObserver(Sujeto subj) {       InitializeComponent();       registrar(subj); }   //Se subscribe al sujeto e inicializa el Dictionary de colores private void registrar(Sujeto sujeto) {       sujeto.registrarInteres (this);       //crea el Dictionary conteniendo los colores       colorFondo = new Dictionary<string,Color>       colorFondo.Add("rojo", Color.Red );       colorFondo.Add ("azul", Color.Blue );       colorFondo.Add ("verde", Color.Green );       colorFondo.Add("amarillo", Color.Yellow);       colorFondo.Add("blanco", Color.White);       colNombre = ""; }   //Modifica el color de fondo del formulario al recibir la //notificación del sujeto y satisface la interfaz Observervador public void enviarNotificacion(string mensaje) {       colNombre = mensaje;       mensaje = mensaje.ToLower ();       //Convierte el string de color a un objeto Color       Color col = (Color)colorFondo[mensaje];             this.BackColor=col;             //Cambia el título del form       this.Text=mensaje; }

**Visual Basic .net**

<pre IsFakePre="true" xmlns="http://www.w3.org/1999/xhtml">Private colorFondo As New Dictionary(Of String, Color)

    Private colNombre As String         Public Sub New(ByVal sujeto As Sujeto)         Me.InitializeComponent()         Me.registrar(sujeto)     End Sub       Private Sub init(ByVal sujeto As Sujeto)         sujeto.registrarInteres(Me)         Me.colorFondo = New Dictionary(Of String, Color)         Me.colorFondo.Add("rojo", Color.Red)         Me.colorFondo.Add("azul", Color.Blue)         Me.colorFondo.Add("verde", Color.Green)         Me.colorFondo.Add("amarillo", Color.Yellow)         Me.colorFondo.Add("blanco", Color.White)         Me.colNombre = ""     End Sub       Public Sub enviarNotificacion(ByVal mensaje As String) Implements Observador.enviarNotificacion         Me.colNombre = mensaje         mensaje = mensaje.ToLower         Dim color1 As Color = CType(Me.colorFondo.Item(mensaje), Color)         Me.BackColor = color1         Me.Text = mensaje End Sub

  1. Crearemos la clase ColorDelegate que permitirá llamar al método del formulario principal mediante un delegado:

  2. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  3. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  4. Visual C# .net

    using System;
    

using System.Collections.Generic; using System.Text;   namespace PatronObserver {     public class ColorDelegate     {           public delegate void ColorDelegado();         public event ColorDelegado eleccionColor;              public object elegirCambioColor         {             set             {                eleccionColor();             }         }     } }

**Visual Basic .net**

<pre IsFakePre="true" xmlns="http://www.w3.org/1999/xhtml">Public Class ColorDelegate 

    Public Delegate Sub ColorDelegado()     Public Event eleccionColor()       Public Property elegirCambioColor() As Object                 Set(ByVal value As Object)             RaiseEvent eleccionColor()         End Set         Get             Return Nothing         End Get       End Property End Class

  1. Programa el evento SelectedValueChanged del comboBox cbColores en el formulario principal de la siguiente manera:

  2. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

  3. Visual C# .net

    private void cbxColor_SelectedValueChanged(object sender, EventArgs e) 
    

{             //ejecutamos el método creado anteriormente mediante el delegado para notificar a todos los observadores del cambio //sucedido en el comboBox                         ColorDelegate oEleccionColor = new ColorDelegate();             ColorDelegate.ColorDelegado oColorDelegado = new             ColorDelegate.ColorDelegado(elegirColor);             oEleccionColor.eleccionColor += oColorDelegado;             oEleccionColor.elegirCambioColor = sender;         oEleccionColor.eleccionColor -= oColorDelegado; }

**Visual Basic .net**

<pre IsFakePre="true" xmlns="http://www.w3.org/1999/xhtml">Private Sub ComboBox1_SelectedValueChanged(ByVal sender As       System.Object, ByVal e As

System.EventArgs) Handles ComboBox1.SelectedValueChanged       //falta corregir el cambio en vb End Sub

  1. Finalmente, ejecuta el programa. Notarás que los formularios ListaObservador y ColorObservador cambiarán de acuerdo a lo ocurrido en el comboBox del formulario principal.(Ver Figura 7):

    Bb972192.art296-img07-570x212(es-es,MSDN.10).gif
    Figura 7 . Volver al texto.

En la elaboración del material me apoyaron dos personas que tengo que mencionar: Jorge Enrique Polo Martinez, (un alumno de la Universidad Ricardo Palma) y Aldo Gutierrez Tanabe (un alumno de la Universidad San Ignacio de Loyola) ambos de Perú. Aldo ha llevado un curso de patrones que dicto en la Universidad y también ha colaborado en la elaboración de otros cursos de patrones que he dictado para empresas.

Joel Francia H. es Docente Universitario. Trabaja como Instructor, Consultor y Desarrollador de aplicaciones .net. Cuenta con las certificaciones MCAD, MCSD, MCT, y es además MVP en C# .net y expone regularmente en eventos técnicos y conferencias a nivel nacional. Su trabajo se centra actualmente en el desarrollo de aplicaciones distribuidas, implementaciones de Servicios Web, .net Remoting, XML y la implementación y el uso de patrones UML para el desarrollo de aplicaciones .net usando Building Blocks, UML y RUP.