2010-07-14 95 views
0

我正在嘗試做一些應該腦死的簡單的事情,但是,我無法讓它工作。我正在顯示列表框中的項目列表。我已將複選框添加到列表框,以便用戶可以選擇多個項目。但是,即使列表中綁定到ListBox的對象具有「IsSelected」屬性,它也沒有被綁定。我可以使用一些幫助,因爲這使我瘋狂。在WPF中綁定ListBox的IsSelectedProperty不起作用。需要幫助

<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> 

在視圖模型我有以下幾點:

public IEnumerable<SelectedClientVM> SelectedClients 
.... 
public class SelectedClientVM 
    { 
     public bool IsSelected { get; set; } 
     public Client Client { get; set; } 
     public override string ToString() 
     { 
      return Client.SearchText; 
     } 
    } 

回答

1

我認爲你想要什麼可以通過定義一個DataTemplate用於列表框中的每個項目來更好地實現。 A DataTemplate指定如何在列表框中呈現單個數據片段(在您的案例中爲Client)。

這是我的一個簡單的DataTemplate的XAML。

<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> 

以下是我引用它在列表框聲明:

<ListBox ItemsSource="{Binding SelectedClients}" 
     VirtualizingStackPanel.IsVirtualizing="True" 
     ItemTemplate="{StaticResource clientTemplate}" /> 

其次,格蘭特的回答,你要確保你的Client類實現INotifyPropertyChanged。另外,您需要使用支持更改通知的集合公開您的客戶端列表。我通常使用ObservableCollection<T>

+0

thanx兄弟來處理。那釘了它。這讓我瘋狂。我嘗試綁定到數據模板中的ListBoxItem,或者使用RelativeAncestor,但它們都不起作用。我從來沒有想過爲我使用的虛擬機類型使用數據模板,但現在我明白了......似乎很明顯。 – Keith 2010-07-14 19:04:33

+0

好,很高興爲你解決了它。對我而言,一旦我將我的大腦包裹在模型中,這絕對是一個燈泡爆發的時刻。 – 2010-07-14 20:13:30

0

這可能不是唯一的問題,但如果你想在視圖更新根據您的視圖模型,你必須實現INotifyPropertyChanged (或者做類似工作的東西)在你的IsSelected屬性上。

+0

問題是ViewModel沒有通過視圖中的更改得到更新。 當我想從視圖模型更新視圖時,它是一次性的事情,並通過手動觸發OnPropertychanged(「SelectedClients」) – Keith 2010-07-14 17:03:40