Binding the IsSelectedProperty of a ListBox in WPF is not working. Need Help
I am trying to do something that should be brain-dead simple, however, I cannot get it to work. I am displaying a list of items in开发者_JAVA百科 a listbox. I have added check boxes to the list box so that the user can select multiple items. However, even though the object in the list being bound to the ListBox has an "IsSelected" property, it is not being bound. I could use some help as this is driving me nuts.
<Style x:Key="CheckBoxListStyle" TargetType="{x:Type ListBox}">
<Setter Property="SelectionMode" Value="Multiple"></Setter>
<Setter Property="ItemContainerStyle">
<Setter.Value>
<Style TargetType="{x:Type ListBoxItem}">
<Setter Property="Margin" Value="2"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ListBoxItem}">
<CheckBox Focusable="False"
IsChecked="{Binding Path=IsSelected, RelativeSource={RelativeSource TemplatedParent}, Mode=TwoWay}">
<ContentPresenter></ContentPresenter>
</CheckBox>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Setter.Value>
</Setter>
<ListBox
Style="{StaticResource CheckBoxListStyle}"
IsEnabled="{Binding Path=SpecificClients.Value, Mode=OneWay}"
ItemsSource="{Binding Path=SelectedClients}"
VirtualizingStackPanel.IsVirtualizing="True"
VirtualizingStackPanel.VirtualizationMode="Recycling"
ScrollViewer.VerticalScrollBarVisibility="Auto"
MaxHeight="95">
</ListBox>
In the View Model I have the following:
public IEnumerable<SelectedClientVM> SelectedClients
....
public class SelectedClientVM
{
public bool IsSelected { get; set; }
public Client Client { get; set; }
public override string ToString()
{
return Client.SearchText;
}
}
I think what you want can be better achieved by defining a DataTemplate
to be used for each item in the ListBox. A DataTemplate
specifies how you want an individual piece of data (a Client
in your case) rendered in the ListBox.
Here's my XAML for a simple DataTemplate.
<DataTemplate x:Key="clientTemplate" DataType="{x:Type local:Client}">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition />
</Grid.ColumnDefinitions>
<CheckBox IsChecked="{Binding IsSelected}" />
<TextBlock Grid.Column="1" Text="{Binding Name}" Margin="5,0,0,0" />
</Grid>
</DataTemplate>
Here's how I referenced it in the ListBox declaration:
<ListBox ItemsSource="{Binding SelectedClients}"
VirtualizingStackPanel.IsVirtualizing="True"
ItemTemplate="{StaticResource clientTemplate}" />
Secondly, to Grant's answer, you'll want to be sure that your Client
class implements INotifyPropertyChanged
. Plus, you'll want to expose your list of Clients using a collection that supports change notifications. I usually use ObservableCollection<T>
.
This may not be the only issue, but if you want the view to update based on your ViewModel you'll have to implement INotifyPropertyChanged (or something that does a similar job) on your IsSelected property.
精彩评论