2011-03-23 18 views
6

tengo 2 colecciones quiero para unirse a una separada GridViewColumn en un ListView:¿Cómo vincular un ListView a múltiples colecciones almacenadas en un único ViewModel en WPF?

public class EffectView : INotifyPropertyChanged 
{ 

    ObservableCollection<Effect> effects; 
    public ObservableCollection<Effect> Effects 
    { 
     get { return this.effects; } 
     set 
     { 
      this.effects = value; 
      this.RaisePropertyChanged ("Effects"); 
     } 
    } 

    ObservableCollection<EffectDescription> descriptions; 
    public ObservableCollection<EffectDescription> Descriptions 
    { 
     get { return this.descriptions; } 
     set 
     { 
      this.descriptions = value; 
      this.RaisePropertyChanged ("Descriptions"); 
     } 
    } 
} 

que pueda hacer esto:

<ListView ItemsSource="{Binding EffectView.Effects}"> 
    <ListView.View> 
     <GridView> 
      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Name}" 
          Header="Name" /> 

      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Opacity}" 
          Header="Opacity" /> 

      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding ?}" 
          Header="Description" /> 
     </GridView> 
    </ListView.View> 
</ListView> 

Pero entonces todo está en el ámbito de EffectView.Effects, pero quiero que el valor por defecto alcance para ser EffectView para que pueda asignar fácilmente varias colecciones al ListView.

Algo así como:

<ListView ItemsSource="{Binding EffectView}"> 
    <ListView.View> 
     <GridView> 
      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Effects Path=Name}" 
          Header="Name" /> 

      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Effects Path=Opacity}" 
          Header="Opacity" /> 

      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Descriptions Path=Usage}" 
          Header="Description" /> 
     </GridView> 
    </ListView.View> 
</ListView> 

Cualquier manera de lograr esto?

Respuesta

8

El ItemsSource de un ListView es la colección cuyos elementos aparecerán en la lista. Así que pensar por un momento acerca de lo que está pidiendo el ListView hacer:

  • Como una colección de origen, utilice algo que no es una colección, pero ellos
  • contiene, para cada fila de la lista, la pantalla un elemento de una colección y un artículo de la otra colección

Preste atención a ese segundo punto: cada fila debe mostrar algún elemento de la colección Events y algún elemento de la colección Descriptions.

¿Qué artículo debe recoger de cada uno? ¿Cuál es la relación entre los artículos en las dos colecciones?

Se parece que lo que realmente necesita es una colección de objetos que contiene tanto un evento y una descripción. A continuación, puede enlazar a esa colección para mostrar elementos de ambas entidades. Más o menos, algo como esto:

public class EffectView : INotifyPropertyChanged 
{ 

    ObservableCollection<EffectsAndDescriptions> effects; 
    public ObservableCollection<EffectAndDescriptions> Effects 
    { 
     get { return this.effects; } 
     set 
     { 
      this.effects = value; 
      this.RaisePropertyChanged ("EffectsAndDescriptions"); 
     } 
    } 

} 

internal class EffectsAndDescriptions 
{ 
    public Effect Effect { get; set; } 
    public Description Description { get; set; } 
} 

Ahora usted puede unirse a la colección EffectsAndDescriptions (nota de este asume el DataContext de padre del ListView es EffectView)

<ListView ItemsSource="{Binding EffectsAndDescriptions}"> 
    <ListView.View> 
     <GridView> 
      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Effect.Name}" 
          Header="Name" /> 

      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Effect.Opacity}" 
          Header="Opacity" /> 

      <GridViewColumn Width="Auto" 
          DisplayMemberBinding="{Binding Description.Usage}" 
          Header="Description" /> 
     </GridView> 
    </ListView.View> 
</ListView> 
1

Eso no es realmente posible. ItemsSource espera que se apruebe algo que, como mínimo, implemente IEnumerable. Incluso si implementó IEnumerable en su EffectView, tendría que ajustar Effect y EffectDescription en un único objeto para devolver.

Puede vincular su ListView a su colección de Efectos, luego usar un IValueConverter personalizado para tomar el Efecto y devolver una descripción. Pero no estoy seguro de que esto se ajuste a tu situación.

Su mejor opción sería incluir un objeto contenedor (es decir, EffectWithDescription) que incluya tanto su Effect como su EffectDescription. A continuación, exponga una colección de objetos EffectWithDescription. Sin embargo, necesitarás asegurarte de que esta nueva colección se mantenga sincronizada con las otras colecciones.

Cuestiones relacionadas