lunes, 21 de noviembre de 2011

El todopoderoso control listview (1)

El control ListView de ASP.NET (no confundirlo con el control ListView de WinForms) es un nuevo control ASP.NET que apareció en el Framework 3.5.

La documentacíón completa del control la tenéis en http://msdn.microsoft.com/es-es/library/system.web.ui.webcontrols.listview.aspx

Otro artículo muy bueno lo tenéis en http://msdn.microsoft.com/es-es/magazine/cc337898.aspx

Lo de "todopoderoso" lo digo porque puede sustituir a todos los controles enlazables (Repeater, gridview, formview, detailsview...), con lo que usando sólo este control puedes hacer cualqier control enlazado.  (pudiendo hacer incluso gridviews con inserciones!!!)

El secreto del ListView es el uso de las plantillas.

Si, por ejemplo, quisiéramos montar una grid, montaríamos algo parecido a esto:


En el Layout template definiríamos el formato de la parte externa a los datos (encabezado, pie...)

En el ItemTemplate definiríamos el formato que queremos de los datos




Un ejemplo básico

Vamos a ver un ejemplo:

Creamos una clase "Persona.cs"

public class Persona
{    
     public int Id { get; set; }    
     public string Nombre { get; set; }    
     public string Apellidos { get; set; }    
     public string Poblacion { get; set; }
}

Creamos una clase "RepPersona.cs", que hará de repositorio y de almacén de datos. Por supuesto, en un entorno real, los métodos irían contra una base de datos, pero por simplificar, lo hacemos con una lista.
public class RepPersona
{
    protected List<Persona> _personas = new List<Persona>();

    public RepPersona()
    {
        _personas.Add(new Persona() { Id = 1, Nombre = "Jose", Apellidos = "Garcia", Poblacion = "Valencia" });
        _personas.Add(new Persona() { Id = 2, Nombre = "Manuel", Apellidos = "Martinez", Poblacion = "Barcelona" });
        _personas.Add(new Persona() { Id = 3, Nombre = "Juan", Apellidos = "Gómez", Poblacion = "Madrid" });
    }

    public List<Persona> DamePersonas()
    {
        return _personas.ToList<Persona>();
    }
}


Ahora crearemos una página ASP.NET y crearemos el ObjectDataSource que lea los datos del repositorio y el ListView

<asp:ObjectDataSource runat="server" ID="odsDatos" DataObjectTypeName="Persona"
    SelectMethod="DamePersonas" TypeName="RepPersona"> </asp:ObjectDataSource>


<asp:ListView runat="server" ID="lvwDatos" DataSourceID="odsDatos">
    <LayoutTemplate>
        <table class="tabla1">
            <tr>
                <th>Id</th>
                <th>Nombre</th>
                <th>Apellidos</th>
                <th>Poblacion</th>
            </tr>

        <asp:PlaceHolder runat="server" ID="ItemPlaceholder"/>
        </table>     
    </LayoutTemplate>
    <ItemTemplate>
        <tr>
            <td><%#Eval("Id") %></td>
            <td><%#Eval("Nombre")%></td>
            <td><%#Eval("Apellidos")%></td>
            <td><%#Eval("Poblacion")%></td>
        </tr>
    

    </ItemTemplate>  
</asp:ListView>


Este código devolvería el siguiente resultado:

Aquí vemos una sección de LayoutTemplate, con un PlaceHolder, y un ItemTemplate.

En el LayoutTemplate, vemos la parte fija; es decir, el <table> y el encabezado.
El PlaceHolder es sustituido por el ItemPlaceHolder tantas veces como registros hayan.

Al ListView, en este caso, no hace falta que se le especifique el nombre del PlaceHolder si el PlaceHolder se llama "ItemPlaceHolder". Si el PlaceHolder se llamara de otra forma, habría que especificar el atributo "ItemPlaceholderID" con el nombre especificado.

Trabajar con plantillas es una forma muy flexible de representar datos.



Vamos a mostrar otro formato de plantilla

<asp:ListView runat="server" ID="LvwDatos2" DataSourceID="odsDatos">
    <LayoutTemplate>
        <h2>Personas</h2>
        <asp:PlaceHolder runat="server" ID="ItemPlaceholder"></asp:PlaceHolder>
    </LayoutTemplate>
    <ItemTemplate>
        <table>
            <tr>
                <td >(<%#Eval("Id") %>)</td>
            </tr>
            <tr>
                <td><%#Eval("Apellidos")%>, <%#Eval("Nombre")%></td>
            </tr>
            <tr>
                <td><%#Eval("Poblacion")%></td>
            </tr>
        </table>
    </ItemTemplate>    
    <ItemSeparatorTemplate>
----------
    </ItemSeparatorTemplate>
</asp:ListView>


Esto mostrará la siguiente salida

Aquí vemos que cada ItemTemplate tiene su propia tabla, y que hay un ItemSeparatorTemplate que permite añadir una plantilla entre cada itemTemplate

Agrupaciones

También podremos usar agrupaciones para poder mostrar items agrupados.

Mostremos un ejemplo de ListView con agrupaciones.

<asp:ListView runat="server" ID="LvwDatos3" DataSourceID="odsDatos" GroupItemCount="2">
    <LayoutTemplate>
        <h2>Personas</h2>
        <table>
            <asp:PlaceHolder runat="server" ID="GroupPlaceholder"></asp:PlaceHolder>
        </table>
    </LayoutTemplate>
    <GroupTemplate>
        <tr>
            <asp:PlaceHolder runat="server" ID="ItemPlaceholder"></asp:PlaceHolder>
        </tr>
    </GroupTemplate>
    <ItemTemplate>
        <td>
            <table>
                <tr>
                    <td>(<%#Eval("Id") %>)</td>
                </tr>
                <tr>
                    <td><%#Eval("Apellidos")%>, <%#Eval("Nombre")%></td>
                </tr> 
                <tr>
                    <td><%#Eval("Poblacion")%></td>
                </tr>                         
            </table>
        </td>
    </ItemTemplate>     
</asp:ListView>


Esta plantilla produciría la siguiente salida:


En este código podemos observar:

  • Con el atributo GroupItemCount indicamos el número de Items que aparecerán por grupo.
  • El LayoutTemplate tiene un PlaceHolder con el ID "GroupPlaceHolder". A este ID le pasa lo mismo que el ID "ItemPlaceHolder" Si se usa este ID, no es necesario especificarlo en el atributo "GroupPlaceHolderID" del listview.
  • Con el elemento "GroupTemplate" indicamos el código a usar por el grupo. En este caso, por cada grupo de 2 elementos, insertará una fila nueva de la tabla (<tr>)


De momento, esto es todo por ahora.
Me quedan otros posts donde introduciré las inserciones, las modificaciones y las paginaciones de este "todopoderoso" control.










No hay comentarios: