Agregando funcionalidad al
control DataGrid con VB .NET Fecha: 11/Ago/2004 (11/Agosto/2004) |
En este ejemplo de código vamos a ver como agregar funcionalidad al Control DataGrid con VB .NET
Entre las funcionalidades que agregaremos están el poder agregar columnas calculadas dinámicamente al DataGrid, poder darle formato a las columnas, poder evitar o permitir agregar mas registros en el DataGrid (el registro que aparece al final del DataGrid con un asterisco *), Poder validar las teclas presionadas por el usuario a fin de permitir solo números o bien convertir las letras minúsculas a MAYÚSCULAS y finalmente el poder sumar una columna completa de manera rápida y colocar su resultado dinámicamente en un control Label
'**************************************************************************** '* Código realizado por Eduardo Puchades Fuentes © (Mexicano) ;-) * '****************************************************************************Public Class Form1 Inherits System.Windows.Forms.Form #Region " Código generado por el Diseñador de Windows Forms " ' Este código decidí quitarlo para ahorrar espacio si desea el código completo puede descargar el fichero .zip que se encuentra al final de esta página #End Region Private Sub CheckBox5_CheckedChanged(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles CheckBox5.CheckedChanged ' Aquí cambiamos el valor de AllowNew para ' evitar o permitir agregar registros ' a nuestro DataGrid Dim Valor As Boolean If sender.Checked = True Then Valor = False Else Valor = True End If 'Instanciamos y creamos nuestro manejador Dim cm As CurrencyManager cm = CType(BindingContext(DataSet1, Me.DataSet1.Tables(0).TableName), CurrencyManager) 'Instanciamos y creamos un DataView asociado a nuestro manejador CurrencyManager Dim Dv As DataView = CType(cm.List, DataView) 'Asignamos el valor que deseamos para evitar o permitir nuevos registros Dv.AllowNew = Valor End Sub Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load 'Cargamos nuestro DataSet leyendo nuestro archivo XML que contiene los datos Me.DataSet1.ReadXml("..\Datos.xml") 'Asignamos el DataSource y el DataMember de nuestro DataGrid Me.DataGrid1.DataSource = Me.DataSet1 Me.DataGrid1.DataMember = Me.DataSet1.Tables(0).TableName End Sub Private Sub CheckBox2_CheckedChanged(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles CheckBox2.CheckedChanged 'Aquí vamos a agregar una columna en tiempo de ejecución 'llamada Cantidad para que el usuario pueda cambiar la cantidad If sender.Checked = True Then 'Cambiamos el estado del cursor poniendo un reloj de arena Me.Cursor = System.Windows.Forms.Cursors.WaitCursor 'Declaramos una variable de DataColumn y creamos la columna Dim MiColum As DataColumn = New DataColumn MiColum.DataType = System.Type.GetType("System.Int32") MiColum.AllowDBNull = False MiColum.DefaultValue = 1 MiColum.Caption = "Cantidad" MiColum.ColumnName = "Cantidad" 'Agregamos la columna a la colección de columnas del DataSet1 Me.DataSet1.Tables(0).Columns.Add(MiColum) 'Regresamos el estado del cursor a normal Me.Cursor = System.Windows.Forms.Cursors.Default End If End Sub Private Sub CheckBox3_CheckedChanged(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles CheckBox3.CheckedChanged 'Aquí vamos a agregar una columna calculada dinámicamente 'y llamada SubTotal para multiplicar la columna Precio x cantidad If sender.Checked = True Then 'Verificamos que ya esté agregada la columna de Cantidad If Me.DataSet1.Tables(0).Columns.Count = 3 And Me.CheckBox2.Checked = False Then Me.CheckBox2.Checked = True 'Cambiamos el estado del cursor poniendo un reloj de arena Me.Cursor = System.Windows.Forms.Cursors.WaitCursor 'Declaramos una variable de DataColumn y creamos la columna Dim MiColum As DataColumn = New DataColumn MiColum.DataType = System.Type.GetType("System.Decimal") MiColum.AllowDBNull = False MiColum.DefaultValue = 1 MiColum.Caption = "Sub Total" MiColum.ColumnName = "SubTotal" 'Aplicamos el tipo de operación que deseamos MiColum.Expression = "Precio * Cantidad" 'Agregamos la columna a la colección de columnas del DataSet1 Me.DataSet1.Tables(0).Columns.Add(MiColum) 'Regresamos el estado del cursor a normal Me.Cursor = System.Windows.Forms.Cursors.Default End If End Sub Private Sub CheckBox4_CheckedChanged(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles CheckBox4.CheckedChanged 'Aquí vamos a agregar una columna calculada dinámicamente 'y llamada Impuesto para multiplicar la columna SubTotal x .1 If sender.Checked = True Then 'Verificamos que ya esté agregada la columna de Sub Total If Me.DataSet1.Tables(0).Columns.Count <= 4 And Me.CheckBox3.Checked = False Then Me.CheckBox3.Checked = True 'Cambiamos el estado del cursor poniendo un reloj de arena Me.Cursor = System.Windows.Forms.Cursors.WaitCursor 'Declaramos una variable de DataColumn y creamos la columna Dim MiColum As DataColumn = New DataColumn MiColum.DataType = System.Type.GetType("System.Decimal") MiColum.AllowDBNull = False MiColum.DefaultValue = 1 MiColum.Caption = "Impuesto" MiColum.ColumnName = "Impuesto" 'Aplicamos el tipo de operación que deseamos MiColum.Expression = "SubTotal * .1" 'Agregamos la columna a la colección de columnas del DataSet1 Me.DataSet1.Tables(0).Columns.Add(MiColum) 'Regresamos el estado del cursor a normal Me.Cursor = System.Windows.Forms.Cursors.Default End If End Sub Private Sub CheckBox6_CheckedChanged(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles CheckBox6.CheckedChanged 'Aquí vamos a agregar una columna calculada dinámicamente 'y llamada Total para sumar la columna SubTotal + Impuesto If sender.Checked = True Then 'Verificamos que ya esté agregada la columna de Impuesto If Me.DataSet1.Tables(0).Columns.Count <= 5 And Me.CheckBox4.Checked = False Then Me.CheckBox4.Checked = True 'Cambiamos el estado del cursor poniendo un reloj de arena Me.Cursor = System.Windows.Forms.Cursors.WaitCursor 'Declaramos una variable de DataColumn y creamos la columna Dim MiColum As DataColumn = New DataColumn MiColum.DataType = System.Type.GetType("System.Decimal") MiColum.AllowDBNull = False MiColum.DefaultValue = 1 MiColum.Caption = "Total" MiColum.ColumnName = "Total" 'Aplicamos el tipo de operación que deseamos MiColum.Expression = "SubTotal + Impuesto" 'Agregamos la columna a la colección de columnas del DataSet1 Me.DataSet1.Tables(0).Columns.Add(MiColum) 'Regresamos el estado del cursor a normal Me.Cursor = System.Windows.Forms.Cursors.Default End If End Sub Private Sub DataGrid1_CurrentCellChanged(ByVal sender As Object, ByVal e As System.EventArgs) Handles DataGrid1.CurrentCellChanged 'Aquí vamos a sumar toda la columna llamada Total 'Comprobamos que nuestro DataGrid tenga nuestra columna llamada Total If Me.CheckBox7.Checked = True And Me.DataSet1.Tables(0).Columns.Count = 7 Then 'Declaramos una variable objeto Dim objSum As Object ' Y Ocupamos la Función Compute del DataTable para sumar y asignar el valor a la variable ' Note que estamos ocupando el Nombre de la columna agregada como Total en Sum(Total) ' y después de la coma estamos agregando un filtro para que sume únicamente los registros donde el ' Valor de la columna Total es mayor que 0, así evitamos que al utilizar números negativos ' Estos ocasionen un resultado inesperado, puede ocupar ese filtro para sumar únicamente ' Los registros de un producto determinado o un producto con descuento por ejemplo. objSum = Me.DataSet1.Tables(0).Compute("Sum(Total)", "Total > 0") ' Convertimos el resultado a un string y le damos formato de Moneda Me.Label1.Text = Format(CStr(objSum), "Currency") End If End Sub Private Sub CreaFormato() 'Aquí vamos a aplicar un formato a nuestro DataGrid 'y vamos a validar las teclas presionadas en las columnas Precio y Cantidad 'Borramos la tabla de estilos en el DataGrid si es que existe Me.DataGrid1.TableStyles.Clear() 'Instanciamos y creamos una nueva tabla de estilos Dim TableStyle1 As New DataGridTableStyle 'Le indicamos el nombre de la tabla de nuestro DataSet TableStyle1.MappingName = Me.DataSet1.Tables(0).TableName 'Creamos un formato de celdas Alternando el color blanco del fondo 'con un color gris claro TableStyle1.AlternatingBackColor = Color.LightGray 'Instanciamos y creamos nuestro primer formato de columna Dim TextCol1 As New DataGridTextBoxColumn 'Le indicamos el nombre de la columna TextCol1.MappingName = "IDProducto" 'Le indicamos el nombre que deseamos aparezca en el encabezado de la columna TextCol1.HeaderText = "IDProducto" 'Le indicamos el ancho de la columna TextCol1.Width = 70 'Agregamos nuestro formato de columna a la colección de nuestra Tabla de estilos TableStyle1.GridColumnStyles.Add(TextCol1) 'Instanciamos y creamos nuestro segundo formato de columna Dim TextCol2 As New DataGridTextBoxColumn 'Le indicamos el nombre de la columna TextCol2.MappingName = "Nombre" 'Le indicamos el nombre que deseamos aparezca en el encabezado de la columna TextCol2.HeaderText = "Nombre" 'Le indicamos el ancho de la columna TextCol2.Width = 120 'Agregamos nuestro formato de columna a la colección de nuestra Tabla de estilos TableStyle1.GridColumnStyles.Add(TextCol2) 'MUCHO OJO AQUÍ 'Aquí vamos a instanciar y crear nuestro tercer formato de columna 'Pero puede usted notar que estoy ocupando una clase llamada 'DataGridTextBoxColumnSoloNumeros esta clase es una clase que previamente he 'Creado y esta clase es un componente heredado de DataGridTextBoxColumn 'A esta clase heredada le he agregado la Funcionalidad de permitirnos 'Validar las teclas que presionan los usuarios, evitando de esta manera 'que inserten letras donde solo deben ir números 'En esta clase también he agregado un ejemplo para poder convertir 'las teclas presionadas por el usuario de minúsculas a MAYÚSCULAS 'Instanciamos y creamos nuestro Tercer Formato de columna 'ocupando la clase antes mencionada Dim TextCol3 As New DataGridTextBoxColumnSoloNumeros 'Le indicamos que la alineación la queremos del lado derecho TextCol3.Alignment = HorizontalAlignment.Right 'Le indicamos el nombre de la columna TextCol3.MappingName = "Precio" 'Le indicamos el nombre que deseamos aparezca en el encabezado de la columna TextCol3.HeaderText = "Precio" 'Le indicamos el ancho de la columna TextCol3.Width = 60 'Aquí con la letra "c" le estamos indicando que queremos un formato currency (Moneda) TextCol3.Format = "c" 'Agregamos nuestro formato de columna a la colección de nuestra Tabla de estilos TableStyle1.GridColumnStyles.Add(TextCol3) 'Instanciamos y creamos nuestro Cuarto Formato de columna 'ocupando la clase antes mencionada Dim TextCol4 As New DataGridTextBoxColumnSoloNumeros 'Le indicamos que la alineación la queremos del lado derecho TextCol4.Alignment = HorizontalAlignment.Right 'Le indicamos el nombre de la columna TextCol4.MappingName = "Cantidad" 'Le indicamos el nombre que deseamos aparezca en el encabezado de la columna TextCol4.HeaderText = "Cantidad" 'Le indicamos el ancho de la columna TextCol4.Width = 60 'Aquí con la letra "g" le estamos indicando que queremos un formato de número general TextCol4.Format = "g" 'Agregamos nuestro formato de columna a la colección de nuestra Tabla de estilos TableStyle1.GridColumnStyles.Add(TextCol4) 'Instanciamos y creamos nuestro segundo formato de columna Dim TextCol5 As New DataGridTextBoxColumn 'Le indicamos que la alineación la queremos del lado derecho TextCol5.Alignment = HorizontalAlignment.Right 'Le indicamos el nombre de la columna TextCol5.MappingName = "SubTotal" 'Le indicamos el nombre que deseamos aparezca en el encabezado de la columna TextCol5.HeaderText = "Sub total" 'Le indicamos el ancho de la columna TextCol5.Width = 60 'Aquí con la letra "c" le estamos indicando que queremos un formato currency (Moneda) TextCol5.Format = "c" 'Agregamos nuestro formato de columna a la colección de nuestra Tabla de estilos TableStyle1.GridColumnStyles.Add(TextCol5) 'Instanciamos y creamos nuestro segundo formato de columna Dim TextCol6 As New DataGridTextBoxColumn 'Le indicamos que la alineación la queremos del lado derecho TextCol6.Alignment = HorizontalAlignment.Right 'Le indicamos el nombre de la columna TextCol6.MappingName = "Impuesto" 'Le indicamos el nombre que deseamos aparezca en el encabezado de la columna TextCol6.HeaderText = "Impuesto" 'Le indicamos el ancho de la columna TextCol6.Width = 60 'Aquí con la letra "c" le estamos indicando que queremos un formato currency (Moneda) TextCol6.Format = "c" 'Agregamos nuestro formato de columna a la colección de nuestra Tabla de estilos TableStyle1.GridColumnStyles.Add(TextCol6) 'Instanciamos y creamos nuestro segundo formato de columna Dim TextCol7 As New DataGridTextBoxColumn 'Le indicamos que la alineación la queremos del lado derecho TextCol7.Alignment = HorizontalAlignment.Right 'Le indicamos el nombre de la columna TextCol7.MappingName = "Total" 'Le indicamos el nombre que deseamos aparezca en el encabezado de la columna TextCol7.HeaderText = "Total" 'Le indicamos el ancho de la columna TextCol7.Width = 60 'Aquí con la letra "c" le estamos indicando que queremos un formato currency (Moneda) TextCol7.Format = "c" 'Agregamos nuestro formato de columna a la colección de nuestra Tabla de estilos TableStyle1.GridColumnStyles.Add(TextCol7) Me.DataGrid1.TableStyles.Add(TableStyle1) End Sub Private Sub CheckBox1_CheckedChanged(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles CheckBox1.CheckedChanged If sender.Checked = True Then CreaFormato() Else Me.DataGrid1.TableStyles.Clear() End If End Sub End ClassAquí termina el código del Form1
NOTA: este código no incluye la sección de código generado por el diseñador de Windows Forms
si quiere el código completo puede descargar el fichero .zip al final de esta página
Esta es la clase heredada de DataGridTextBoxColumn para validar las teclas presionadas en el DataGrid.
Option Strict Off Option Explicit On Imports Microsoft.VisualBasic Imports System Imports System.ComponentModel Imports System.Windows.Forms Public Class DataGridTextBoxColumnSoloNumeros Inherits DataGridTextBoxColumn Public Sub New() MyBase.New() AddHandler Me.TextBox.KeyPress, New System.Windows.Forms.KeyPressEventHandler(AddressOf HandleKeyPress) End Sub Private Sub HandleKeyPress(ByVal sender As Object, ByVal e As KeyPressEventArgs) 'Aquí puede cambiar el código para que el usuario unicamente presione letras 'o para cambiar las letras minúsculas por MAYÚSCULAS con el ejemplo siguiente 'If e.KeyChar.IsLower(e.KeyChar) Then ' e.KeyChar.ToUpper(e.KeyChar) 'End If 'Ignora la tecla presionada si no es dígito o tecla de control If e.KeyChar.IsDigit(e.KeyChar) Then e.Handled = False ElseIf e.KeyChar.IsControl(e.KeyChar) Then e.Handled = False Else e.Handled = True End If 'Ignora la tecla presionada si el valor es mas grande de cuatro dígitos If ((Me.TextBox.Text.Length >= 4) AndAlso Not (e.KeyChar.IsControl(e.KeyChar)) AndAlso Me.TextBox.SelectionLength = 0) Then e.Handled = True End If End Sub End Class
Fichero con el código de ejemplo: yosall_datagrid.zip - Tamaño KB