Formularios con ComboBox para ordenar y extraer datos de una hoja

En último formulario hicimos uso de los botones: Cuadro de Control, usado para ingresar y recibir datos de tipo texto, botones de comando, usados para realizar una serie de acciones sobre una hoja o modificar el estado y propiedades de un botón de control de formulario y, un botón de Cuadro combinado, llamado también, ComboBox, para colocar los elementos en una lista.

En esta sesión vamos a usar los beneficios que nos puede proporcionar el famoso ComboBox o cuadro combinado.

Nuestro ejemplo consiste en extraer los datos correspondientes a un empleado de la lista contenida en el archivo Personal.xlsx. Descargue este archivo haciendo clic aquí

Ahora cárguelo a memoria y vea el contenido de la primera hoja llamada Personal.

Esta hoja contiene los datos de los empleados de una cierta empresa. Tiene 8 campos y 119 registros. Como se puede deducir, esta tabla contiene dos campos o claves principales por las cuales se puede realizar una búsqueda y luego extraer la información almacenada correspondiente a un empleado. Estos campos son: Código y Nombres (1ra y 2da columnas).

Nuestro objetivo es extraer todos los datos de un empleado en particular. Para ello debemos tener como dato su Código o sus Nombres. Para una búsqueda adecuada, la tabla debe estar ordenada por el campo clave que nos permita realizar la búsqueda.

Supongamos que el código es 1977. Nos orientamos hacia la columna A, preguntamos si el contenido de A2, Range(“A2”) = 1977. Si no es igual, pasamos a la siguiente fila (en la misma columna); es decir, podemos usar ActiveCell.Ofset(1,0).Select. El cursor se desplaza una fila hacia abajo (1), en la misma columna (0) y volvemos apreguntar.

Así sucesivamente. Si son iguales (ya lo encontró) procedemos a extraer el código a un cuadro de texto, los nombres a otro, el departamento a otro, etc.

Pero, como esta tabla contiene dos campos claves (Código y Nombres), usaremos un ComboBox para disponer de la lista de los nombres de estos dos campos. Si hacemos clic en Codigo, un segundo ComboBox deberá contener todos los códigos de todos los empleados de la tabla.

Para esto, mediante una sentencia For … Next, extraemos todos los códigos (1ra columna) de la tabla y la colocamos en un segundo ComboBox.

Luego, al hacer clic en un elemento de esta lista (hacer clic en un determinado código), estaremos cambiando el estado de este objeto ComboBox, por lo que el código realizará la búsqueda comentada en el párrafo anterior.

Bien, empecemos.

Estando abierto el archivo Personal, vaya al Editor ([Alt]+F11), inserte un UserForm, que su nombre sea FrmBuscar, su caption: Formulario para búsqueda de datos. Inserte, en la parte superior izquierda, una [Etiqueta], como se muestra en la imagen que adjuntamos al final de esta sección. Estando seleccionada esta etiqueta, cambie su [Name] por Lbl01. En su [Caption] digite: PRIMERO HAGA CLIC AQUÍ.

Como deseamos colocar una instrucción para el manejo de este formulario, vamos a colocar un mensaje en esta etiqueta. Para ello, estando seleccionado, en la ventana de propiedades, cambie su altura [Height] a 50. Clic en su [BackColor] y despliegue la lista para seleccionar de el color que desee. Igualmente cambie su amplitud, propiedad [Width] a 300.

Inerte los demás botones de control según se muestra en la imagen adjunta. Los nombres:

Primer cuadro combinado: , CboCampo.
Segundo cuadro combinado: , CboBuscar
para los 8 cuadros de texto: TxtCodigo, TxtNombres, TxtDepto, TxtSeccion, TxtPuesto, TxtSueldoAnual, TxtFechaIng y TxtFechanac.
El primer botón de comando (lado izquierdo), , CmdNuevo, , Nueva búsqueda y el último: , CmdFin, su , Salir.
También hemos desplegado una etiqueta por encima del combobox Campo, su , “Campo” y el del segundo, “Buscar”.

Empecemos la progrmación de estos objetos:

Doble clic en . Su código debe ser:
Private Sub CmdFin_Click()
End
End Sub

 

Ahora haga doble clic en este objeto (Lbl01) e ingrese el siguiente código:

Private Sub Lbl01_Click()
Lbl01.Caption = "Este formulario le permite extraer datos del archivo Personal." + Chr(13) + Chr(13) + _
"Para ello debe seleccionar primero la clave de búsqueda de la lista Campo, " + Chr(13) + _
"luego de la cual, debe seleccionar el elemento a buscar desde la lista Buscar."
CboCampo.AddItem "Codigo"
CboCampo.AddItem "Nombres"

End Sub
 

El “espacio en blanco y el guión bajo” son necesarios para indicar que la siguiente línea es parte de la primera. Y chr(13) permite decirle que cambie a la siguiente línea.

Observe que también estamos cargado el primer cuadro combinado Campo con dos elementos: Codigo, Nombres. Pudimos haber usado un botón de comando para que, cuando se haga clic en él, el combo box Campo se cargue con estos valores; solo estamos usando una diversidad de opciones. Veamos el código correspondiente al botón .

Haga doble clic en este botón. De inmediato se inserta:


Private Sub CboCampo_Change()

End Sub

¿Qué es lo que queremos?

Al ejecutarse el formulario, deberá hacerse clic en la etiqueta grande para que el botón Campo se cargue con sus dos valores. Si al desplegar su lista, hacemos clic en el elemento “Codigo”, la tabla de la hoja Personal se debe ordenar por el campo Codigo (1ra columna).

Por el contrario, si hacemos clic en “Nombres”, la tabla se debe ordenar por el campo Nombres (2da columna). En la variable xLook, guardaremos el elemento seleccionado. Ahora debemos ordenar por el campo seleccionado. El procedimiento de ordenación la hemos obtendio grabando una macro desde el Excel.

Esta es la macro:

==========================================
Sub MacroPrueba()
'
' MacroPrueba Macro
'

'
Range("B13").Select
ActiveWorkbook.Worksheets("Personal").ListObjects("Tabla1").Sort.SortFields. _
Clear
ActiveWorkbook.Worksheets("Personal").ListObjects("Tabla1").Sort.SortFields. _
Add Key:=Range("Tabla1[Codigo]"), SortOn:=xlSortOnValues, Order:= _
xlAscending, DataOption:=xlSortNormal
With ActiveWorkbook.Worksheets("Personal").ListObjects("Tabla1").Sort
.Header = xlYes
.MatchCase = False
.Orientation = xlTopToBottom
.SortMethod = xlPinYin
.Apply
End With
End Sub

Puesto que esta macro deseamos usarla con una tabla cualquiera (que tenga nombre de rango y tenga formato de tabla) y con un campo cualquiera por el cual se deberá ordenar, los argumentos “Personal”, “Tabla1” y "Tabla1[Codigo]" los vamos a reemplazar por variables (sin comilla doble).

Para ello están las instrucciones:

xTabla = "Tabla1"
xHoja = "Personal"

del código del ComboBox Campo.
 

En cuanto a la primera instrucción:


xLook = CboCampo.List(CboCampo.ListIndex)

CboCampo.ListIndex tiene por valor 0 ó 1. Es cero cuando se hace clic en Codigo y es 1 cuando se hace clic en Nombres, elementos del ComboBox Campo.

En este caso dicho valor se usa para extraer el contenido del combo box (Codigo o Nombres) y guardarlo en xLook. xTabla contiene el rango de datos y xHoja guarda el nombre de la hoja (Personal).

De esta manera la macro que ordena quedará modificada así:


Sub Ordenar(xDato)

'
Range("B6").Select
ActiveWorkbook.Worksheets(xHoja).ListObjects(xTabla).Sort.SortFields. _
Clear
ActiveWorkbook.Worksheets(xHoja).ListObjects(xTabla).Sort.SortFields. _
Add Key:=Range(xDato), SortOn:=xlSortOnValues, Order:= _
xlAscending, DataOption:=xlSortNormal
With ActiveWorkbook.Worksheets(xHoja).ListObjects(xTabla).Sort
.Header = xlYes
.MatchCase = False
.Orientation = xlTopToBottom
.SortMethod = xlPinYin
.Apply
End With
End Sub

Luego de invocarse al procedimiento Ordenar desde el código del botón Campo, debemos colocar todos los datos contenidos en dicho campo en el ComboBox Buscar. Es decir, si hemos seleccionado el elemento Codigo, mediante un While … Wend se debe extraer todos los códigos de los empleados y colocarlos al botón Buscar. Pasará de una fila a otra, mediante la sentencia:

ActiveCell.Offset(1, 0).Select

De manera que el código completo del ComboBox Campo es:

Private Sub CboCampo_Change()
xLook = CboCampo.List(CboCampo.ListIndex)
xTabla = "Tabla1"
xHoja = "Personal"
Call Ordenar(xLook)
Sheets(xHoja).Select
If xLook = "Codigo" Then
Range("A2").Select
Else
Range("B2").Select
End If
nFila = Selection.End(xlDown).Row
For i = 2 To nFila
CboBuscar.AddItem ActiveCell
ActiveCell.Offset(1, 0).Select
Next
Range("A1").Select

End Sub
 

Una vez cargado el ComboBox Buscar, debemos seleccionar un elemento de la lista y volver a la hoja del Excel para buscar el empleado cuyo campo clave se seleccionó en el primer combobox.

Por ejemplo, si se hizo clic en el elemento “Codigo” del combobox Campo, el segundo combobox, Buscar, contendrá el Código de todos los empleados.

Al desplegar la lista de este segundo combobox y hace clic en uno de sus elementos (supongamos que se hace clic en 1290), mediante el uso del While … Wend debemos buscar el empleado cuyo código es 1290. Una vez encontrado, de dicha fila y de sus 8 columnas, extraeremos loos datos celda por celda para colocarlos en los 8 cuadros de texto disponibles en el formulario.

El código del procedimiento del combobox Buscar es:

Private Sub CboBuscar_Change()

On Error Resume Next
xField = CboBuscar.List(CboBuscar.ListIndex)

Sheets(xHoja).Select
Range("A1").Select
If xLook = "Codigo" Then
Range("A2").Select
xField = Val(xField)
Else
Range("B2").Select
End If
While ActiveCell <> ""
If xField = ActiveCell Then
TxtCodigo.Text = Cells(ActiveCell.Row, 1)
TxtNombres.Text = Cells(ActiveCell.Row, 2)
TxtDepto.Text = Cells(ActiveCell.Row, 4)
TxtSeccion.Text = Cells(ActiveCell.Row, 5)
TxtPuesto.Text = Cells(ActiveCell.Row, 3)
TxtSueldoAnual.Text = Cells(ActiveCell.Row, 6
) TxtFechaIng.Text = Cells(ActiveCell.Row, 7)
TxtFechaNac.Text = Cells(ActiveCell.Row, 8)
End If
ActiveCell.Offset(1, 0).Select
Wend

End Sub
 

Ahora sólo nos falta programar el botón . Este botón nos permitirá ralizar la búsqueda por el otro campo clave.

Para ello, tanto los cuadros de texto como el combo box Buscar, deben ser “limpliados”. Según esto, el código del botón Nuevo será:


Private Sub CmdNuevo_Click()
TxtCodigo.Text = ""
TxtNombres.Text = ""
TxtDepto.Text = ""
TxtSeccion.Text = ""
TxtPuesto.Text = ""
TxtSueldoAnual.Text = ""
TxtFechaIng.Text = ""
TxtFechaNac.Text = ""
CboBuscar.Clear

End Sub

Este formulario, como puede ver, no está abriendo o activando libro alguno. Insertemos un módulo para activar el libro y mostrar el formulario. El contenido del procedimiento contenido en este módulo debe ser:

Sub ExtraerInfo()

Workbooks("Personal").Activate
Sheets("Personal").Select
FrmBuscar.Show
End Sub
 

Sólo nos falta insertar un botón en la hoja Personal y asignarle la macro anterior.

La siguiente imagen muestra el formulario descrito:

Guarde el libro como Personal.xlsm, habilitado para macros. Si desea verlo, haga clic aquí

En la próxima sesión usaremos un formulario con cuadro de lista. Para ir a la siguiente sesión haga clic aquí