Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/wpf/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在WPF中绑定ListBox的IsSelectedProperty不起作用。需要帮助吗_C#_Wpf - Fatal编程技术网

C# 在WPF中绑定ListBox的IsSelectedProperty不起作用。需要帮助吗

C# 在WPF中绑定ListBox的IsSelectedProperty不起作用。需要帮助吗,c#,wpf,C#,Wpf,我正在尝试做一些简单的事情,但是,我无法让它工作。我正在列表框中显示项目列表。我在列表框中添加了复选框,以便用户可以选择多个项目。但是,即使列表中绑定到ListBox的对象具有“IsSelected”属性,它也不会被绑定。我需要一些帮助,因为这快把我逼疯了 <Style x:Key="CheckBoxListStyle" TargetType="{x:Type ListBox}"> <Setter Property="SelectionMode" Value="Mult

我正在尝试做一些简单的事情,但是,我无法让它工作。我正在列表框中显示项目列表。我在列表框中添加了复选框,以便用户可以选择多个项目。但是,即使列表中绑定到ListBox的对象具有“IsSelected”属性,它也不会被绑定。我需要一些帮助,因为这快把我逼疯了

<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;
        }
    }
public IEnumerable Selected客户端
....
公共类SelectedClientVM
{
公共布尔值被选为{get;set;}
公共客户端{get;set;}
公共重写字符串ToString()
{
返回Client.SearchText;
}
}

这可能不是唯一的问题,但如果您希望视图根据您的ViewModel进行更新,则必须在IsSelected属性上实现(或执行类似工作的内容)。

我认为,通过为列表框中的每个项目定义一个
数据模板可以更好地实现您的愿望。
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声明中引用它的方式:

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


其次,为了格兰特的回答,您需要确保您的
客户机
类实现了
INotifyPropertyChanged
。另外,您还需要使用支持更改通知的集合公开客户端列表。我通常使用
observateCollection

问题是视图模型不会因视图中的更改而更新。当我想从视图模型更新视图时,这是一次性的,通过手动启动PropertyChanged(“SelectedClient”)thanx dude来处理。那就对了。它快把我逼疯了。我尝试绑定到数据模板中的ListBoxItem,或者使用RelativeAncestor,但都不起作用。我从未想过为我正在使用的VM类型使用数据模板,尽管现在我看到了。。。。看起来很明显。很好,很高兴为你解决了这个问题。对我来说,这绝对是一个灯泡熄灭的时刻,一旦我把我的大脑围绕在模型上。