Ir a la sección de Como en .NET Cómo en .NET
 

Array de controles en Visual Basic 2005

En realidad es una colección generic de controles

 

Publicado el 09/Abr/2007
Actualizado el 09/Abr/2007
Autor: Guillermo 'guille' Som

En este artículo te explico cómo crear un array (en realidad una colección generic) de controles con Visual Basic 2005 (o Visual Basic 8.0 o superior), para usarlo en tus formularios. Pulsa aquí para ver cómo crear el array de controles con Visual C# 2005 (o C# 2.0 o superior).

 

 

Introducción:

Esta es la versión para Visual Basic 2005 del código que publiqué el 14 de Noviembre de 2002 para crear un array de controles en .NET (con ejemplos para Visual Basic y Visual C#).

En esta ocasión la clase que hace las veces de array (ArrayControles(Of T)) está definida como una colección generic de tipo List(Of T), de forma que T sea el tipo de control que va a mantener la colección.

Al ser una colección de tipo List(Of T), se podrá usar como un array, así que no habrá problemas, pero para facilitar las cosas, la clase/colección también define una sobrecarga de la propiedad predeterminada (indizador en C#) para que se pueda acceder al control por medio del nombre.

 

¿Cómo usar la clase ArrayControles(Of T)?

Esta clase necesita unos requisitos previos para poder usarla con los controles de un formulario.
Y es que todos los controles del formulario que vayan a estar agrupados en la misma colección, deben llamarse de la misma forma y solo cambiar en el número que habrá que indicar después de un guión bajo.
Por ejemplo, si quieres crear un array de controles TextBox, de forma que puedas acceder a ellos mediante la clase ArrayControles como si fueran un array, es decir, indicando un índice numérico, tendrás que añadir esos controles al formulario y darles nombres que tengan el formato: nombre_indice.
nombre será el nombre que quieras, el guión bajo es el que separa el índice del nombre y por último, un valor numérico que debería coincidir con el índice a usar, es decir, si vas a crear varios controles, procura que los valores de los índices sean consecutivos, y empezando por cero.

Por ejemplo, puedes tener 3 controles de tipo TextBox con estos nombres:
datos_00, datos_01 y datos_02.
(El nombre que le des no es importante, solo que todos empiecen con el mismo nombre.)
Tampoco es importante que uses ceros extras, ya que eso solo será para que tu lo tengas más claro si tienes más de 10 controles, ya que la clase solo tiene en cuenta el valor numérico, por tanto _00 será 0, _01 será 1 y así sucesivamente.
Ese nombre (datos en este ejemplo) será el que tendrás que indicar al crear la instancia de la clase, y al definir la variable de la clase tendrás que decir que tipo de control va a contener:

Private m_TextBox1 As ArrayControles(Of TextBox)

...

m_TextBox1 = New ArrayControles(Of TextBox)("datos", Me)

Como ves, en el constructor también puedes indicar el contenedor donde están esos controles, y aquí es donde entra la "importancia" del nombre, ya que en esa colección solo se guardarán los controles que tengan el nombre que has indicado, y que, por supuesto, deben ser del tipo que la colección va a contener, por tanto, no debes darle ese mismo nombre a otros controles de otro tipo o los controles que no quieras que estén en esa misma colección.

Si quieres tener varias colecciones de varios tipos de controles, puedes hacerlo, pero teniendo en cuenta lo que te acabo de comentar: que el nombre de esos controles sean diferentes y que usen el formato "nombre" "guión bajo" "índice numérico".

 

Un ejemplo de cómo usar la colección

En el formulario de prueba de esta clase, he creado tres colecciones para tres tipos de controles, las cuales están definidas de esta forma:

Private m_Label1 As ArrayControles(Of Label)
Private m_TextBox1 As ArrayControles(Of TextBox)
Private m_RadioButton1 As ArrayControles(Of RadioButton)

En el evento Load del formulario es donde se crean las instancias y se asignan los controles:

' Asignar los controles y reorganizar los índices
' No importa si el nombre no coincide exactamente,
' ya que no se diferencian las mayúsculas de las minúsculas.

m_Label1 = New ArrayControles(Of Label)("Label1", Me)
m_TextBox1 = New ArrayControles(Of TextBox)("textBox1", Me)
m_RadioButton1 = New ArrayControles(Of RadioButton)("RadioButton1", Me)

Como ves en el comentario del código anterior, el nombre no tiene porqué coincidir exactamente (no diferencia mayúsculas de minúsculas), ya que en realidad, en el constructor de la clase, el nombre indicado se guarda en minúsculas y en las comprobaciones que se hacen no se hace distinción en el "case" del nombre.

Lo que si es importante es que en el formulario haya controles de tipo Label que tengan el nombre al estilo del indicado en el constructor, en este ejemplo, esos controles deberían llamarse Label1_n, donde _n será un valor numérico que empieza por cero y sea ascendente de uno en uno.

Si el orden no es correlativo y no empiezan por cero, no podrás usar de forma "correcta" el acceso a los datos por el índice numérico, pero si por el nombre.

Por ejemplo, si has definido las etiquetas en el formulario con los nombres Label1_0, Label1_20, Label1_3, al usar m_Label1(1) te devolverá (posiblemente) el control Label1_20, pero si usas: m_Label1("Label1_3") te devolverá el índice en el que esté el control llamado Label1_3, que "posiblemente" será el índice 2.

Así que... para no complicarte la vida, usa los valores de forma correlativa y empezando por cero.

 

Asignar eventos para los controles de una misma colección

La "gracia" de usar esta colección es que puedes crear un solo método de evento para manejar todos los controles de un mismo array (o colección).

Por ejemplo, si quieres que cuando las cajas de texto reciban el foco se seleccione todo el texto que hay, puedes hacer esto:

Private Sub TextBox1_Enter( _
                ByVal sender As Object, ByVal e As EventArgs)

    m_TextBox1(sender).SelectAll()

End Sub

Ese caso caso, el control que produce el evento debe ser del tipo de la colección. No importa que no esté en el array, al menos tal y como tengo actualmente el código, ya que si cambias el código de la propiedad predeterminada (indizador en C#) que recibe un parámetro de tipo Object usando lo que ahora mismo está comentado, entonces se devolverá un valor nulo si ese control no está en la colección.

Nota:
En C# hay que tener cuidado con la sobrecarga del indizador que recibe un parámetro de tipo Object, ya que siempre tendrá preferencia sobre el tipo entero, por tanto hay que hacer una comprobación extra para saber si el tipo de datos del parámetro es de tipo entero, de forma que se llame al indizador de la clase base (que es el que usa el parámetro de tipo entero).
Cuando se usa la sobrecarga del tipo String no hay problemas.

En Visual Basic no existe ese efecto no deseado.

Pero si lo que quieres es que, por ejemplo, cuando el TextBox reciba el foco se tenga en cuenta otro control de otro array que tenga el mismo índice, por ejemplo una etiqueta, puedes usar el método Index para averiguar el índice numérico del control, de forma que ese valor lo puedas usar en el otro array (por eso te comentaba que es muy importante que los índices que uses sean correlativos y empiecen por cero, para que no haya problemas, digamos, colaterales).

' Fíjate que en el Label, los valores son _0, _1 y _2
' y en el TextBox son _00, _01 y _02,
' aunque parece que "no coinciden", 
' lo que importa es que el valor numérico sea el adecuado.

Dim index As Integer = m_TextBox1.Index(sender)
m_TextBox1(index).SelectAll()
' resaltar la etiqueta
m_Label1(index).BackColor = Color.FromKnownColor(KnownColor.ControlDark)

Al usar el método Index que recibe un tipo Object, el valor del índice que se devuelve es el que se indique en el nombre del control, por tanto, si el TextBox que ha producido el evento en el que está ese código se llama TextBox1_22, el valor de index será 22. Ves nuevamente porqué es importante que los controles estén correlativos y empiecen por cero... (sí, ya se que te has enterado, pero para que quede claro).

 

Y para terminar con la explicación, decirte cómo hacer que todos los controles de una colección usen el mismo método de evento.

Por ejemplo, que todos los controles del array m_TextBox1 usen el evento TextBox1_Enter cuando reciban el foco:

For Each txt As TextBox In m_TextBox1
    AddHandler txt.Enter, AddressOf TextBox1_Enter
Next

Lo mismo tendrías que hacer para el resto de evento, por ejemplo, para que se asigne el evento cuando pulsas una tecla en el control de tipo TextBox:

For Each txt As TextBox In m_TextBox1
    AddHandler txt.KeyPress, AddressOf TextBox1_KeyPress
Next

Como puedes suponer, puedes poner todo el código en el mismo bucle, (en el formulario de ejemplo he creado un método que asigna todos los eventos de los tres arrays de controles).

Además, tanto en el método TextBox1_Enter como TextBox1_KeyPress deben estar definidos con los parámetros adecuados a esos eventos.
La forma más fácil de crearlos es eligiendo los eventos que queremos interceptar de cualquiera de los controles que tienes en el formulario, creando el método correspondiente y quitándole el "Handles" que añade el Visual Basic.

En el código del formulario, el método asignarEventos se encarga de asignar los eventos.

 

Y esto es todo... más abajo te dejo el código fuente completo tanto para Visual Basic como para C# así como el código de la clase y el formulario de prueba (aunque sin la definición de los controles) pero para Visual Basic 2005, si quieres ver el código de C# tendrás que ir al artículo para ese lenguaje.

 

El aspecto del formulario en modo de diseño es el de la siguiente figura:

El formulario en modo de diseño
El formulario en modo de diseño

 

 

Espero que te sea de utilidad.

Nos vemos.
Guillermo

Abajo del todo tienes el ZIP con el código fuente tanto para Visual Basic como para C#.

 


Código para Visual Basic.NET (VB.NET)El código para Visual Basic .NET (2005 o superior)

 

El código de la clase ArrayControles

'------------------------------------------------------------------------------
' ArrayControles                                                    (09/Abr/07)
'
' Clase-colección para simular un array de controles de Visual Basic 6.0
' Se utilizan clases generic para contener los controles.
'
' Esta clase está basada en ControlArray (09/Ago/2002),
' publicada en mi sitio el 14/Nov/2002:
' http://www.elguille.info/NET/dotnet/arrayControles.htm
'
' ©Guillermo 'guille' Som, 2002, 2007
'------------------------------------------------------------------------------
Option Strict On

Imports Microsoft.VisualBasic
Imports System
Imports System.Collections.Generic

Imports System.Windows.Forms
Imports System.Drawing


Namespace elGuille.info.Utilidades


''' <summary>
''' Clase para contener controles del tipo indicado,
''' que debe derivarse de Control.
''' </summary>
''' <typeparam name="T">
''' El tipo de control que contendrá la colección.
''' </typeparam>
''' <remarks>
''' Se deriva de List(Of T)
''' Autor: Guillermo 'guille' Som
''' Fecha: 09/Abr/2007
''' </remarks>
Public Class ArrayControles(Of T As Control)
    Inherits System.Collections.Generic.List(Of T)

    Private m_Nombre As String

    ''' <summary>
    ''' En el constructor se debe indicar el nombre del control.
    ''' </summary>
    ''' <param name="elNombre">
    ''' El nombre base de los controles del array,
    ''' esos controles deben tener el nombre: elNombre_numero.
    ''' No se admite una cadena vacía.
    ''' </param>
    ''' <remarks></remarks>
    Public Sub New(ByVal elNombre As String)
        MyBase.New()
        If String.IsNullOrEmpty(elNombre) Then
            Throw New ArgumentException( _
                        "El nombre del control no puede ser una cadena vacía")
        End If
        ' Asignarlo a la propiedad
        ' para que se convierta en minúsculas
        ' o cualquier otra comprobación.
        Me.Nombre = elNombre
    End Sub

    ''' <summary>
    ''' Constructor para inicializar directamente la colección de controles
    ''' </summary>
    ''' <param name="ctrls">
    ''' Colección de controles en la que están los que debemos usar.
    ''' </param>
    ''' <param name="elNombre">
    ''' El nombre base de los controles a tener en cuenta.
    ''' </param>
    ''' <remarks></remarks>
    Public Sub New( _
                ByVal elNombre As String, _
                ByVal ctrls As Control.ControlCollection)
        Me.New(elNombre)

        Me.Clear()
        asignarLosControles(ctrls)
        Me.Reorganizar()
    End Sub

    ''' <summary>
    ''' Constructor para inicializar directamente la colección de controles
    ''' </summary>
    ''' <param name="contenedor">
    ''' El contenedor que tiene los controles a comprobar.
    ''' </param>
    ''' <param name="elNombre">
    ''' El nombre base de los controles a tener en cuenta.
    ''' </param>
    ''' <remarks></remarks>
    Public Sub New( _
                ByVal elNombre As String, _
                ByVal contenedor As ContainerControl)
        Me.New(elNombre, contenedor.Controls)
    End Sub

    ''' <summary>
    ''' Asignar los controles de la colección indicada.
    ''' </summary>
    ''' <param name="ctrls">
    ''' Colección de controles en la que están los que debemos usar.
    ''' El nombre usado será el indicado al crear la colección.
    ''' </param>
    ''' <remarks>
    ''' La colección de controles puede ser Me.Controls
    ''' ya que aquí solo se tendrán en cuenta los controles
    ''' que tengan el nombre usado en esta clase,
    ''' y se recorren todas las colecciones de controles que haya.
    ''' </remarks>
    Public Sub AsignarControles(ByVal ctrls As Control.ControlCollection)
        Me.Clear()
        asignarLosControles(ctrls)
        Me.Reorganizar()
    End Sub

    ''' <summary>
    ''' Asignar los controles del contenedor indicado.
    ''' </summary>
    ''' <param name="contenedor">
    ''' El contenedor de los controles en los que se buscarán
    ''' los del tipo indicado en esta colección.
    ''' </param>
    ''' <remarks></remarks>
    Public Sub AsignarControles(ByVal contenedor As ContainerControl)
        Me.Clear()
        asignarLosControles(contenedor.Controls)
        Me.Reorganizar()
    End Sub

    Private Sub asignarLosControles(ByVal ctrls As Control.ControlCollection)
        ' El tipo debe ser Control, para tener en cuenta todos los controles
        ' que haya en la colección indicada.
        For Each ctr As Control In ctrls
            ' Hacer una llamada recursiva por si este control "contiene" otros
            If ctr.Controls.Count > 0 Then
                asignarLosControles(ctr.Controls)
            End If

            If ctr.Name.ToLower().IndexOf(m_Nombre) > -1 Then
                Me.Add(TryCast(ctr, T))
            End If
        Next
    End Sub

    ' Sobrecargas de la propiedad predeterminada (Item)

    ''' <summary>
    ''' Propiedad predeterminada para devolver
    ''' el control con el nombre indicado.
    ''' </summary>
    ''' <param name="name">
    ''' El nombre del control a buscar.
    ''' </param>
    ''' <value></value>
    ''' <returns>
    ''' El control que tiene el nombre indicado.
    ''' </returns>
    ''' <remarks></remarks>
    Default Public Overloads ReadOnly Property Item(ByVal name As String) As T
        Get
            Dim index As Integer = Me.Index(name)
            ' Si existe, devolverlo, sino, devolver un valor nulo
            If index = -1 Then
                Return Nothing
            End If

            Return Me(index)
        End Get
    End Property

    ''' <summary>
    ''' Sobrecarga de la propiedad predeterminada
    ''' para permitir el acceso con un valor de tipo Object.
    ''' Aunque el tipo debe ser del que contiene la colección,
    ''' si no es así, se devuelve un valor nulo.
    ''' </summary>
    ''' <param name="obj">
    ''' El control a comprobar
    ''' </param>
    ''' <value></value>
    ''' <returns>
    ''' Si el parámetro es del tipo adecuado, 
    ''' se devuelve con el tipo de la colección,
    ''' si no lo es, se devuelve un valor nulo.
    ''' </returns>
    ''' <remarks></remarks>
    Default Public Overloads ReadOnly Property Item(ByVal obj As Object) As T
        Get
            Dim ctrl As T = TryCast(obj, T)

            Return ctrl

            ' Quita estos comentarios y comenta el Return anterior
            ' si quieres que se compruebe exactamente el control.

            '' Buscar ese control en la colección,
            '' para asegurarnos de que en realidad está.

            'If ctrl Is Nothing Then
            '    Return Nothing
            'End If

            'For Each c As T In Me
            '    If c Is ctrl Then
            '        Return c
            '    End If
            'Next

            'Return Nothing
        End Get
    End Property

    ''' <summary>
    ''' Devuelve el índice del control de esta colección
    ''' que tenga el mismo índice que el del parámetro.
    ''' Ese parámetro puede ser cualquier control,
    ''' y lo que se tendrá en cuenta será el nombre usado,
    ''' el cual debe tener la forma nombre_indice,
    ''' de forma que se devolverá el control que tenga ese mismo índice.
    ''' </summary>
    ''' <param name="obj">
    ''' El control a comprobar si existe un índice como el indicado.
    ''' Al ser de tipo Object no es necesario que sea del mismo tipo
    ''' que los que contiene esta colección.
    ''' </param>
    ''' <returns>
    ''' El índice correspondiente.
    ''' Aunque no se comprueba si existe en la colección.
    ''' En el caso de que el parámetro no tenga el formato adecuado,
    ''' se devuelve -1.
    ''' </returns>
    ''' <remarks>
    ''' Esta sobrecarga se puede usar para buscar el control correspondiente
    ''' con el del índice de otro control, por ejemplo:
    ''' i = m_TextBox1.Index(sender)
    ''' Por supuesto, el parámetro debe ser de tipo Control.
    ''' Este método podría estar compartido, pero debido a que su uso
    ''' sería ArrayControles(Of TIPO).Index(sender)
    ''' he preferido dejarlo como de instancia.
    ''' </remarks>
    Public Function Index(ByVal obj As Object) As Integer
        Dim ctrl As Control = TryCast(obj, Control)
        If ctrl Is Nothing Then
            Return -1
        End If

        Dim i As Integer = -1
        i = ctrl.Name.LastIndexOf("_")
        If i > -1 Then
            i = CInt(ctrl.Name.Substring(i + 1))
        End If

        Return i
    End Function

    ''' <summary>
    ''' Devuelve el índice del control con el nombre indicado.
    ''' </summary>
    ''' <param name="name">
    ''' Nombre del control a buscar en la colección.
    ''' </param>
    ''' <returns>
    ''' Un valor de tipo entero con el índice del control.
    ''' </returns>
    ''' <remarks></remarks>
    Public Function Index(ByVal name As String) As Integer
        Dim hallado As Integer = -1

        For i As Integer = 0 To Me.Count - 1
            Dim ctrl As T = Me(i)
            If String.Compare(ctrl.Name, name, True) = 0 Then
                hallado = i
                Exit For
            End If
        Next
        Return hallado
    End Function

    ''' <summary>
    ''' Devuelve el índice del control indicado.
    ''' </summary>
    ''' <param name="ctrl">
    ''' El control del que queremos averiguar el índice.
    ''' </param>
    ''' <returns>
    ''' Un valor de tipo entero con el índice del control.
    ''' </returns>
    ''' <remarks></remarks>
    Public Function Index(ByVal ctrl As T) As Integer
        Dim i As Integer = ctrl.Name.LastIndexOf("_")

        ' Si el nombre no tiene el signo _
        If i = -1 Then
            i = Me.IndexOf(ctrl)
        Else
            i = CInt(ctrl.Name.Substring(i + 1))
        End If

        Return i
    End Function
    '
    ''' <summary>
    ''' La propiedad Nombre, externamente será de solo lectura.
    ''' </summary>
    ''' <value>El nombre de la colección de controles</value>
    ''' <returns>
    ''' El nombre de la colección de controles.
    ''' </returns>
    ''' <remarks>
    ''' </remarks>
    Public Property Nombre() As String
        Get
            Return m_Nombre
        End Get
        Private Set(ByVal value As String)
            m_Nombre = value.ToLower()
        End Set
    End Property
    '
    ''' <summary>
    ''' Reorganizar el contenido de la colección,
    ''' ordenando por el índice indicado después del guión bajo
    ''' </summary>
    ''' <remarks></remarks>
    Public Sub Reorganizar()
        Dim ca As New List(Of T)

        For i As Integer = 0 To Me.Count - 1
            For Each ctr As T In Me
                If i = Me.Index(ctr) Then
                    ca.Add(ctr)
                    Exit For
                End If
            Next
        Next
        '
        Me.Clear()
        For Each ctr As T In ca
            Me.Add(ctr)
        Next
    End Sub
End Class

End Namespace
 

El código del formulario:

'------------------------------------------------------------------------------
' Prueba para usar la clase ArrayControles                          (09/Abr/07)
'
' Utilizando una clase generic para los controles.
' 
' Basado en el ejemplo publicado en mi sitio:
' http://www.elguille.info/NET/dotnet/arrayControles.htm
'
' ©Guillermo 'guille' Som, 2002, 2007
'------------------------------------------------------------------------------
Option Strict On

Imports Microsoft.VisualBasic
Imports System

Imports System.Windows.Forms
Imports System.Drawing

Imports arrayControlesGeneric_vb.elGuille.info.Utilidades

Public Class Form1

    ' Colecciones (como arrays) para contener los controles

    ' De esta forma tendremos que instanciar las colecciones
    Private m_Label1 As ArrayControles(Of Label)
    Private m_TextBox1 As ArrayControles(Of TextBox)
    Private m_RadioButton1 As ArrayControles(Of RadioButton)
    '
    ' Asignar los eventos a los controles
    Private Sub asignarEventos()

        ' Aquí estarán los procedimientos a asignar a cada array de controles

        For Each opt As RadioButton In m_RadioButton1
            AddHandler opt.KeyPress, AddressOf RadioButton1_KeyPress
            ' Para el evento general de recibir foco
            AddHandler opt.Enter, AddressOf control_Enter
        Next

        For Each txt As TextBox In m_TextBox1
            AddHandler txt.Enter, AddressOf TextBox1_Enter
            AddHandler txt.KeyPress, AddressOf TextBox1_KeyPress
            AddHandler txt.Leave, AddressOf TextBox1_Leave
            ' Para el evento general de recibir foco
            AddHandler txt.Enter, AddressOf control_Enter
        Next

        For Each lbl As Label In m_Label1
            ' Para el evento general de recibir foco
            AddHandler lbl.Enter, AddressOf control_Enter
        Next
        '
    End Sub

    Private Sub Form1_Load( _
                    ByVal sender As Object, ByVal e As EventArgs) _
                    Handles MyBase.Load

        ' Asignar los controles y reorganizar los índices
        ' No importa si el nombre no coincide exactamente,
        ' ya que no se diferencian las mayúsculas de las minúsculas.

        m_Label1 = New ArrayControles(Of Label)("Label1", Me)
        m_TextBox1 = New ArrayControles(Of TextBox)("textBox1", Me)
        m_RadioButton1 = New ArrayControles(Of RadioButton)("RadioButton1", Me)

        ' Asignar sólo los eventos
        asignarEventos()

        ' Asignar unos textos a las cajas de texto
        For i As Integer = 0 To m_TextBox1.Count - 1
            m_TextBox1(i).Text = "Caja de textos " & i
        Next

    End Sub

    Private Sub control_Enter(ByVal sender As Object, ByVal e As EventArgs)
        Dim ctrl As Control = TryCast(sender, Control)

        Me.labelInfo.Text = "El control con el foco es: " & ctrl.Name
    End Sub

    Private Sub TextBox1_Enter( _
                    ByVal sender As Object, ByVal e As EventArgs)

        ' Fíjate que en el Label, los valores son _0, _1 y _2
        ' y en el TextBox son _00, _01 y _02,
        ' aunque parece que "no coinciden", 
        ' lo que importa es que el valor numérico sea el adecuado.

        Dim index As Integer = m_TextBox1.Index(sender)
        m_TextBox1(index).SelectAll()
        ' resaltar la etiqueta
        m_Label1(index).BackColor = Color.FromKnownColor(KnownColor.ControlDark)
    End Sub

    Private Sub TextBox1_Leave( _
                    ByVal sender As Object, ByVal e As EventArgs)

        ' En este caso, esto es más cómodo:
        ' ya que solo queremos el índice.
        Dim index As Integer = m_TextBox1.Index(sender)

        ' poner la etiqueta con el color normal
        m_Label1(index).BackColor = Color.FromKnownColor(KnownColor.Control)
    End Sub

    Private Sub TextBox1_KeyPress( _
                    ByVal sender As Object, ByVal e As KeyPressEventArgs)

        If e.KeyChar = ChrW(Keys.Return) Then
            Dim index As Integer

            ' Esto es más fácil de usar:
            index = m_TextBox1.Index(sender)

            If index = m_TextBox1.Count - 1 Then
                m_RadioButton1(0).Focus()
            Else
                m_TextBox1(index + 1).Focus()
            End If

            ' Evitar el pitido
            e.Handled = True
        End If
    End Sub
    '
    Private Sub RadioButton1_KeyPress( _
                    ByVal sender As Object, ByVal e As KeyPressEventArgs)

        If e.KeyChar = ChrW(Keys.Return) Then
            Dim index As Integer

            ' Esto es más fácil de usar:
            index = m_RadioButton1.Index(sender)

            If index = 0 Then
                m_RadioButton1(index + 1).Focus()
            Else
                m_TextBox1(0).Focus()
            End If
        End If
    End Sub
    '
    Private Sub btnSalir_Click( _
                    ByVal sender As Object, ByVal e As EventArgs) _
                    Handles btnSalir.Click
        Me.Close()
    End Sub
End Class

 


Espacios de nombres usados en el código de este artículo:

System.Windows.Forms
System.Drawing
System.Collections.Generic

elGuille.info.Utilidades
 


Código de ejemplo (comprimido):

 

Código de ejemplo para Visual Basic y C# 2005: array_controles_generic_2005.zip - 32.0 KB

(MD5 checksum: D279DA4548A708CC141CF67BF9822F32)

 


Ir al índice principal de el Guille

Valid XHTML 1.0 Transitional