Mostrar información de resumen en el pie de página de GridView (VB)

por Scott Mitchell

Descargar PDF

La información de resumen se muestra a menudo en la parte inferior del informe en una fila de resumen. El control GridView puede incluir una fila de pie de página en cuyas celdas se pueden insertar datos agregados mediante programación. En este tutorial veremos cómo mostrar datos agregados en esta fila de pie de página.

Introducción

Además de ver los precios de cada uno de los productos, unidades en existencias, unidades de pedido y reordenar niveles, un usuario también podría estar interesado en la información agregada, como el precio medio, el número total de unidades en existencias, etc. Esta información de resumen se muestra a menudo en la parte inferior del informe en una fila de resumen. El control GridView puede incluir una fila de pie de página en cuyas celdas se pueden insertar datos agregados mediante programación.

Esta tarea presenta tres desafíos:

  1. Configuración de GridView para mostrar su fila de pie de página
  2. Determinar los datos de resumen; es decir, ¿cómo calculamos el precio medio o el total de las unidades en existencias?
  3. Inserción de los datos de resumen en las celdas adecuadas de la fila de pie de página

En este tutorial veremos cómo superar estos desafíos. En concreto, crearemos una página que enumera las categorías de una lista desplegable con los productos de la categoría seleccionada que se muestran en GridView. GridView incluirá una fila de pie de página que muestra el precio medio y el número total de unidades en stock y en el pedido de productos de esa categoría.

Summary Information is Displayed in the GridView's Footer Row

Ilustración 1: la información de resumen se muestra en la fila pie de página de GridView (haga clic para ver la imagen a tamaño completo)

Este tutorial, con su categoría a la interfaz de maestro y detalle de productos, se basa en los conceptos descritos en el tutorial anterior Filtrado de maestros y detalles con una DropDownList. Si aún no ha trabajado en el tutorial anterior, hágalo antes de continuar con este.

Paso 1: agregar las categorías DropDownList y Products GridView

Antes de hablar con nosotros mismos con la adición de información de resumen al pie de página de GridView, primero vamos a crear el informe maestro/detalle. Una vez completado este primer paso, veremos cómo incluir datos de resumen.

Para empezar, abra la página SummaryDataInFooter.aspx en la carpeta CustomFormatting. Agregue un control DropDownList y establezca su ID en Categories. A continuación, haga clic en el vínculo Elegir origen de datos de la etiqueta inteligente DropDownList y opte por agregar un nuevo ObjectDataSource denominado CategoriesDataSource que invoca el método GetCategories() de la clase CategoriesBLL.

Add a New ObjectDataSource Named CategoriesDataSource

Ilustración 2: adición de un nuevo elemento ObjectDataSource denominado CategoriesDataSource (haga clic para ver la imagen a tamaño completo)

Have the ObjectDataSource Invoke the CategoriesBLL Class's GetCategories() Method

Ilustración 3: hacer que ObjectDataSource invoque el método GetCategories() de la clase CategoriesBLL (Haga clic para ver la imagen a tamaño completo)

Después de configurar ObjectDataSource, el asistente nos devuelve al asistente para configuración del origen de datos de DropDownList desde el que es necesario especificar qué valor de campo de datos se debe mostrar y cuál debe corresponder al valor del ListItem de DropDownList. Haga que se muestre el campo CategoryName y use el CategoryID como valor.

Use the CategoryName and CategoryID Fields as the Text and Value for the ListItems, Respectively

Ilustración 4: use los campos CategoryName y CategoryID como Text y Value para los ListItem, respectivamente (Haga clic para ver la imagen a tamaño completo)

En este punto tenemos un DropDownList (Categories) que enumera las categorías del sistema. Ahora es necesario agregar una clase GridView que muestre los productos que pertenecen a la categoría seleccionada. Sin embargo, antes de hacerlo, dedique un momento a activar la casilla Habilitar AutoPostBack en la etiqueta inteligente DropDownList. Como se describe en el tutorial Filtrado de maestros y detalles con un DropDownList, estableciendo la propiedad AutoPostBack de DropDownList en True la página se publicará cada vez que se cambie el valor DropDownList. Esto hará que GridView se actualice, mostrando esos productos para la categoría recién seleccionada. Si la propiedad AutoPostBack está establecida en False (valor predeterminado), cambiar la categoría no provocará una devolución de entrada y, por tanto, no actualizará los productos enumerados.

Check the Enable AutoPostBack Checkbox in the DropDownList's Smart Tag

Ilustración 5: active la casilla Habilitar AutoPostBack en la etiqueta inteligente de DropDownList (Haga clic para ver la imagen a tamaño completo)

Agregue un control GridView a la página para mostrar los productos de la categoría seleccionada. Establezca el ID de GridView en ProductsInCategory y enlácelo a un nuevo ObjectDataSource denominado ProductsInCategoryDataSource.

Add a New ObjectDataSource Named ProductsInCategoryDataSource

Ilustración 6: agregar un nuevo ObjectDataSource denominado ProductsInCategoryDataSource (Haga clic para ver la imagen a tamaño completo)

Configure ObjectDataSource para que invoque el método GetProductsByCategoryID(categoryID) de la clase ProductsBLL.

Have the ObjectDataSource Invoke the GetProductsByCategoryID(categoryID) Method

Ilustración 7: hacer que ObjectDataSource invoque el método GetProductsByCategoryID(categoryID) (Haga clic para ver la imagen a tamaño completo)

Dado que el método GetProductsByCategoryID(categoryID) toma un parámetro de entrada, en el paso final del asistente podemos especificar el origen del valor del parámetro. Para mostrar esos productos de la categoría seleccionada, tenga el parámetro extraído del DropDownList Categories.

Screenshot showing the Configure Data Source window with the categoryID parameter value selected.

Ilustración 8: obtener el valor de parámetro categoryID de las categorías seleccionadas DropDownList (Haga clic para ver la imagen a tamaño completo)

Después de completar el asistente, GridView tendrá un BoundField para cada una de las propiedades del producto. Vamos a limpiar estos BoundFields para que solo se muestren los BoundFields ProductName, UnitPrice, UnitsInStock y UnitsOnOrder. No dude en agregar cualquier configuración de nivel de campo al resto de BoundFields (por ejemplo, dar formato al UnitPrice como moneda). Después de realizar estos cambios, el marcado declarativo de GridView debe ser similar al siguiente:

<asp:GridView ID="ProductsInCategory" runat="server" AutoGenerateColumns="False"
    DataKeyNames="ProductID" DataSourceID="ProductsInCategoryDataSource"
    EnableViewState="False">
    <Columns>
        <asp:BoundField DataField="ProductName" HeaderText="Product"
          SortExpression="ProductName" />
        <asp:BoundField DataField="UnitPrice" DataFormatString="{0:c}"
          HeaderText="Price"
            HtmlEncode="False" SortExpression="UnitPrice">
            <ItemStyle HorizontalAlign="Right" />
        </asp:BoundField>
        <asp:BoundField DataField="UnitsInStock"
          HeaderText="Units In Stock" SortExpression="UnitsInStock">
            <ItemStyle HorizontalAlign="Right" />
        </asp:BoundField>
        <asp:BoundField DataField="UnitsOnOrder"
          HeaderText="Units On Order" SortExpression="UnitsOnOrder">
            <ItemStyle HorizontalAlign="Right" />
        </asp:BoundField>
    </Columns>
</asp:GridView>

En este punto tenemos un informe maestro/detalle totalmente funcional que muestra el nombre, el precio unitario, las unidades en existencias y las unidades para los productos que pertenecen a la categoría seleccionada.

Screenshot showing the GridView report for those products that belong to the Beverages category.

Ilustración 9: obtener el valor de parámetro categoryID de las categorías seleccionadas DropDownList (Haga clic para ver la imagen a tamaño completo)

El control GridView puede mostrar una fila de encabezado y pie de página. Estas filas se muestran en función de los valores de las propiedades ShowHeader y ShowFooter, respectivamente, con el valor predeterminado ShowHeader para True y ShowFooter para False. Para incluir un pie de página en GridView simplemente establezca su propiedad ShowFooter en True.

Set the GridView's ShowFooter Property to True

Ilustración 10: establezca la propiedad ShowFooter de GridView en True (Haga clic para ver la imagen a tamaño completo)

La fila de pie de página tiene una celda para cada uno de los campos definidos en GridView; sin embargo, estas celdas están vacías de forma predeterminada. Dedique un momento a ver nuestro progreso en un explorador. Con la propiedad ShowFooter ahora establecida en True, GridView incluye una fila de pie de página vacía.

The GridView Now Includes a Footer Row

Ilustración 11: GridView ahora incluye una fila de pie de página (Haga clic para ver la imagen a tamaño completo)

La fila de pie de página de la ilustración 11 no destaca, ya que tiene un fondo blanco. Vamos a crear una clase CSS de FooterStyle en Styles.css que especifique un fondo rojo oscuro y, a continuación, configure el archivo GridView.skin Skin en el tema DataWebControls para asignar esta clase CSS a la propiedad CssClass de GridView FooterStyle. Si necesita refrescar sus conocimientos sobre Skins y Temas, consulte el tutorial Visualización de datos con ObjectDataSource.

Empiece agregando la siguiente clase CSS a Styles.css:

.FooterStyle
{
    background-color: #a33;
    color: White;
    text-align: right;
}

La clase CSS FooterStyle es similar en estilo a la clase HeaderStyle, aunque el color de fondo del HeaderStyle es más sutil y su texto se muestra en una fuente negrita. Además, el texto del pie de página está alineado a la derecha, mientras que el texto del encabezado está centrado.

A continuación, para asociar esta clase CSS a cada pie de página de GridView, abra el archivo GridView.skin en el tema DataWebControls y establezca la propiedad CssClass de FooterStyle. Después de esta adición, el marcado del archivo debe ser similar al siguiente:

<asp:GridView runat="server" CssClass="DataWebControlStyle">
   <AlternatingRowStyle CssClass="AlternatingRowStyle" />
   <RowStyle CssClass="RowStyle" />
   <HeaderStyle CssClass="HeaderStyle" />
   <FooterStyle CssClass="FooterStyle" />
   <SelectedRowStyle CssClass="SelectedRowStyle" />
</asp:GridView>

Como se muestra en la captura de pantalla siguiente, este cambio hace que el pie de página destaque más claramente.

Screenshot showing the summary data in the GridView's footer row formatted with a new background color.

Ilustración 12: la fila pie de página de GridView ahora tiene un color de fondo rojizo (Haga clic para ver la imagen a tamaño completo)

Paso 3: calcular los datos de resumen

Con el pie de página de GridView mostrado, el siguiente desafío que nos enfrenta es cómo calcular los datos de resumen. Hay dos maneras de calcular esta información de agregado:

  1. Mediante una consulta SQL podríamos emitir una consulta adicional a la base de datos para calcular los datos de resumen de una categoría determinada. SQL incluye una serie de funciones de agregado junto con una cláusula GROUP BY para especificar los datos sobre los que se deben resumir los datos. La siguiente consulta SQL devolvería la información necesaria:

    SELECT CategoryID, AVG(UnitPrice), SUM(UnitsInStock),
    SUM(UnitsOnOrder)
    FROM Products
    WHERE CategoryID = categoryID
    GROUP BY CategoryID
    

    Por supuesto, no querrá emitir esta consulta directamente desde la página SummaryDataInFooter.aspx, sino crear un método en el ProductsTableAdapter y el ProductsBLL.

  2. Calcule esta información a medida que se agrega a GridView como se describe en el tutorial Formato personalizado basado en datos, el controlador de eventos RowDataBound de GridView se activa una vez para cada fila que se agrega a GridView después de su entrada de datos. Al crear un controlador de eventos para este evento, podemos mantener un total en ejecución de los valores que queremos agregar. Una vez enlazada la última fila de datos a GridView, tenemos los totales y la información necesaria para calcular el promedio.

Normalmente emplee el segundo enfoque, ya que guarda un viaje a la base de datos y el esfuerzo necesario para implementar la funcionalidad de resumen en la capa de acceso a datos y en la capa de lógica de negocios, pero cualquier enfoque sería suficiente. Para este tutorial, vamos a usar la segunda opción y realizar un seguimiento del total en ejecución mediante el controlador de eventos RowDataBound.

Cree un controlador de eventos RowDataBound para GridView seleccionando GridView en el Diseñador, haciendo clic en el icono de rayo en la ventana Propiedades y haciendo doble clic en el evento RowDataBound. Como alternativa, puede seleccionar GridView y su evento RowDataBound en las listas desplegables de la parte superior del archivo de clase de código subyacente de ASP.NET. Esto creará un nuevo controlador de eventos denominado ProductsInCategory_RowDataBound en la clase de código subyacente de la página SummaryDataInFooter.aspx.

Protected Sub ProductsInCategory_RowDataBound _
    (sender As Object, e As GridViewRowEventArgs) _
        Handles ProductsInCategory.RowDataBound
End Sub

Para mantener un total en ejecución, es necesario definir variables fuera del ámbito del controlador de eventos. Cree las cuatro variables de nivel de página siguientes:

  • _totalUnitPrice, de tipo Decimal
  • _totalNonNullUnitPriceCount, de tipo Integer
  • _totalUnitsInStock, de tipo Integer
  • _totalUnitsOnOrder, de tipo Integer

A continuación, escriba el código para incrementar estas tres variables para cada fila de datos encontrada en el controlador de eventos RowDataBound.

Dim _totalUnitPrice As Decimal = 0
Dim _totalNonNullUnitPriceCount As Integer = 0
Dim _totalUnitsInStock As Integer = 0
Dim _totalUnitsOnOrder As Integer = 0
Protected Sub ProductsInCategory_RowDataBound _
    (sender As Object, e As GridViewRowEventArgs) _
        Handles ProductsInCategory.RowDataBound
    If e.Row.RowType = DataControlRowType.DataRow Then
        Dim product As Northwind.ProductsRow = _
            CType(CType(e.Row.DataItem, DataRowView).Row, Northwind.ProductsRow)
        If Not product.IsUnitPriceNull() Then
            _totalUnitPrice += product.UnitPrice
            _totalNonNullUnitPriceCount += 1
        End If
        If Not product.IsUnitsInStockNull() Then
            _totalUnitsInStock += product.UnitsInStock
        End If
        If Not product.IsUnitsOnOrderNull() Then
            _totalUnitsOnOrder += product.UnitsOnOrder
        End If
    ElseIf e.Row.RowType = DataControlRowType.Footer Then
        Dim avgUnitPrice As Decimal = _
            _totalUnitPrice / CType(_totalNonNullUnitPriceCount, Decimal)
        e.Row.Cells(1).Text = "Avg.: " & avgUnitPrice.ToString("c")
        e.Row.Cells(2).Text = "Total: " & _totalUnitsInStock.ToString()
        e.Row.Cells(3).Text = "Total: " & _totalUnitsOnOrder.ToString()
    End If
End Sub

El controlador de eventos RowDataBound comienza asegurándonos de que estamos tratando con un DataRow. Una vez que se haya establecido, la instancia Northwind.ProductsRow que se acaba de enlazar al objeto GridViewRow de e.Row se almacena en la variable product. A continuación, las variables totales en ejecución se incrementan mediante los valores correspondientes del producto actual (suponiendo que no contienen un valor NULL de base de datos). Realizamos un seguimiento de las UnitPrice totales en ejecución y del número de registros sin NULLUnitPrice porque el precio medio es el cociente de estos dos números.

Con los datos de resumen totales, el último paso es mostrarlo en la fila pie de página de GridView. Esta tarea también se puede realizar mediante programación a través del controlador de eventos RowDataBound. Recuerde que el controlador de eventos RowDataBound se activa para cada fila enlazada a GridView, incluida la fila de pie de página. Por lo tanto, podemos aumentar nuestro controlador de eventos para mostrar los datos en la fila de pie de página mediante el código siguiente:

Protected Sub ProductsInCategory_RowDataBound _
    (sender As Object, e As GridViewRowEventArgs) _
        Handles ProductsInCategory.RowDataBound
    If e.Row.RowType = DataControlRowType.DataRow Then
      ... Increment the running totals ...
    ElseIf e.Row.RowType = DataControlRowType.Footer
      ... Display the summary data in the footer ...
    End If
End Sub

Puesto que la fila de pie de página se agrega a GridView una vez agregadas todas las filas de datos, podemos estar seguros de que en el momento en que estamos listos para mostrar los datos de resumen en el pie de página los cálculos totales en ejecución se habrán completado. El último paso, a continuación, es establecer estos valores en las celdas del pie de página.

Para mostrar texto en una celda de pie de página determinada, use e.Row.Cells(index).Text = value, donde la indexación de Cells comienza en 0. El código siguiente calcula el precio medio (el precio total dividido por el número de productos) y lo muestra junto con el número total de unidades en stock y unidades en orden en las celdas de pie de página adecuadas de GridView.

Protected Sub ProductsInCategory_RowDataBound _
    (sender As Object, e As GridViewRowEventArgs) _
        Handles ProductsInCategory.RowDataBound
    If e.Row.RowType = DataControlRowType.DataRow Then
      ... <i>Increment the running totals</i> ...
    ElseIf e.Row.RowType = DataControlRowType.Footer
      Dim avgUnitPrice As Decimal = _
        _totalUnitPrice / CType(_totalNonNullUnitPriceCount, Decimal)
      e.Row.Cells(1).Text = "Avg.: " & avgUnitPrice.ToString("c")
      e.Row.Cells(2).Text = "Total: " & _totalUnitsInStock.ToString()
      e.Row.Cells(3).Text = "Total: " & _totalUnitsOnOrder.ToString()
    End If
End Sub

En la ilustración 13 se muestra el informe después de agregar este código. Tenga en cuenta cómo el ToString("c") hace que la información de resumen de precios promedio tenga formato como una moneda.

Screenshot showing the summary data in the GridView's footer row formatted as a currency.

Ilustración 13: la fila pie de página de GridView ahora tiene un color de fondo rojizo (Haga clic para ver la imagen a tamaño completo)

Resumen

Mostrar datos de resumen es un requisito común del informe y el control GridView facilita la inclusión de dicha información en su fila de pie de página. La fila de pie de página se muestra cuando la propiedad ShowFooter de GridView se establece en True y puede tener el texto en sus celdas establecido mediante programación a través del controlador de eventos RowDataBound. Para calcular los datos de resumen, puede volver a consultar la base de datos o mediante código de la clase de código subyacente de la página ASP.NET para calcular mediante programación los datos de resumen.

En este tutorial se concluye el examen del formato personalizado con los controles GridView, DetailsView y FormView. Nuestro siguiente tutorial inicia nuestra exploración de la inserción, actualización y eliminación de datos mediante estos mismos controles.

¡Feliz programación!

Acerca del autor

Scott Mitchell, autor de siete libros de ASP/ASP.NET y fundador de 4GuysFromRolla.com, ha estado trabajando con tecnologías web de Microsoft desde 1998. Scott trabaja como consultor independiente, entrenador y escritor. Su último libro es Sams Teach Yourself ASP.NET 2.0 in 24 Hours. Puede ponerse en contacto con él a través de mitchell@4GuysFromRolla.com. o de su blog, que se puede encontrar en http://ScottOnWriting.NET.