TOC

This article has been localized into Spanish by the community.

El control ListView:

Filtrado de ListView

Ya se han llevado a cabo diferentes acciones con la ListView, como agrupar y ordenar, pero otra habilidad muy útil es el filtrado. Obviamente, se puede simplemente limitar los elementos añadidos a la ListView desde un principio, pero a menudo se necesitará filtrar la ListView dinámicamente, en tiempo de ejecución, normalmente basándose en un string introducido por el usuario para realizar el filtrado. Afortunadamente, los mecanismos view de la ListView también convierten esto en algo fácil de hacer, como se vio que hacían con la ordenación y la agrupación.

El filtrado es realmente bastante fácil de hacer, por ello pasemos directamente a un ejemplo, y posteriormente lo discutiremos:

<Window x:Class="WpfTutorialSamples.ListView_control.FilteringSample"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="FilteringSample" Height="200" Width="300">
    <DockPanel Margin="10">
        <TextBox DockPanel.Dock="Top" Margin="0,0,0,10" Name="txtFilter" TextChanged="txtFilter_TextChanged" />
        <ListView Name="lvUsers">
            <ListView.View>
                <GridView>
                    <GridViewColumn Header="Name" Width="120" DisplayMemberBinding="{Binding Name}" />
                    <GridViewColumn Header="Age" Width="50" DisplayMemberBinding="{Binding Age}" />
                </GridView>
            </ListView.View>
        </ListView>
    </DockPanel>
</Window>
using System;
using System.Collections.Generic;
using System.Windows;
using System.Windows.Data;

namespace WpfTutorialSamples.ListView_control
{
	public partial class FilteringSample : Window
	{
		public FilteringSample()
		{
			InitializeComponent();
			List<User> items = new List<User>();
			items.Add(new User() { Name = "John Doe", Age = 42 });
			items.Add(new User() { Name = "Jane Doe", Age = 39 });
			items.Add(new User() { Name = "Sammy Doe", Age = 13 });
			items.Add(new User() { Name = "Donna Doe", Age = 13 });
			lvUsers.ItemsSource = items;

			CollectionView view = (CollectionView)CollectionViewSource.GetDefaultView(lvUsers.ItemsSource);
			view.Filter = UserFilter;
		}

		private bool UserFilter(object item)
		{
			if(String.IsNullOrEmpty(txtFilter.Text))
				return true;
			else
				return ((item as User).Name.IndexOf(txtFilter.Text, StringComparison.OrdinalIgnoreCase) >= 0);
		}

		private void txtFilter_TextChanged(object sender, System.Windows.Controls.TextChangedEventArgs e)
		{
			CollectionViewSource.GetDefaultView(lvUsers.ItemsSource).Refresh();
		}
	}

	public enum SexType { Male, Female };

	public class User
	{
		public string Name { get; set; }

		public int Age { get; set; }

		public string Mail { get; set; }

		public SexType Sex { get; set; }
	}
}

La parte XAML es bastante sencilla: Se tiene un TextBox, donde el usuario puede introducir un string de búsqueda, y luego una ListView para mostrar el resultado.

En el Code-behind se comienza añadiendo algunos objetos User (Usuario) a la ListView, como ya se hizo en ejemplos anteriores. La parte interesante se encuentra en las dos últimas líneas del constructor, donde se obtiene una referencia a la instancia CollectionView de la ListView y luego se le asigna un delegado a la propiedad Filter. Este delegado apunta a la función denominada UserFilter, que se ha implementado justo después. Esta función toma cada elemento como el primer (y único) parámetro y luego devuelve un valor booleano que indica si el elemento dado debe ser visible o no en la lista.

En el método UserFilter(), se examina el control TextBox (txtFilter) para ver si contiene algún texto - si lo contiene, se usa para comprobar si el nombre del usuario (que es la propiedad por la que se ha decidido filtrar) contiene el string introducido, y después devuelve verdadero o falso dependiendo de ello. Si el TextBox está vacío, se devuelve verdadero, porque en ese caso se desea que todos los elementos sean visibles.

El evento txtFilter_TextChanged también es importante. Cada vez que el texto cambia, se obtiene una referencia al objeto View de la ListView y luego se llama a su método Refresh(). Esto asegura que el delegado Filter es llamado cada vez que el usuario cambia el valor del string de búsqueda/filtrado del TextBox.

Resumen

Esta ha sido una implementación bastante sencilla, pero desde el momento en el que se tiene acceso a cada elemento, en este caso de la clase User, se puede llevar a cabo cualquier tipo de filtrado que se desee, ya que se tiene acceso a todos los datos sobre cada uno de los elementos en la lista. Por ejemplo, el ejemplo anterior podría fácilmente modificarse para filtrar por la edad, examinando la propiedad Age en lugar la propiedad Name, o se podría cambiar para examinar más de una propiedad, por ejemplo para filtrar los usuarios con una edad (Age) por debajo de X Y(AND) un nombre que no contenga "Y".


This article has been fully translated into the following languages: Is your preferred language not on the list? Click here to help us translate this article into your language!