首页 > 解决方案 > 列表视图中的 ItemsControl

问题描述

我有一些定义的 XAML,看起来像

<ListView ItemsSource="{Binding ConfigItems,Mode=OneWay}" Margin="5">
    <ListView.ItemContainerStyle> 
        <Style TargetType="ListViewItem"> 
            <Setter Property="HorizontalContentAlignment" Value="Stretch"></Setter> 
        </Style> 
    </ListView.ItemContainerStyle>
    <ItemsControl
        ItemsSource="{Binding}"
        ItemTemplateSelector="{StaticResource ConfigItemDataSelector}"/>
</ListView>

现在我意识到这不是应该的,但这就是问题的根源。因为我得到一个异常,表明ItemsSource在使用它之前应该是空的。从12 年前提出的一个问题中,我看到同时使用ItemsItemsSource属性时会引发此异常。所以我开始使用其中一个。但是当我像上面那样定义它或完全省略时,我得到了这个错误ItemsSource。当我尝试使用时,Items我在编译时收到一个错误,表明列表必须有一个 setter。如果有一些混淆, ConfigItemDataSelector 看起来基本上会返回一个 DataTemplate ,具体取决于正在使用的视图模型。但我认为查看选择器会分散问题的注意力。

public sealed class ConfigItemDataSelector : DataTemplateSelector
{
    public DataTemplate MeasurementDataTemplate { get; set; }
. . .
    public override DataTemplate SelectTemplate(object item, DependencyObject container)
    {
        if (item is MeasurementConfigItemViewModel)
        {
            return MeasurementDataTemplate;
        }
        else if (item is LEDFeedbackConfigItemViewModel)
        {
            return LEDFeedbackDataTemplate;
        }
. . . 
        return null;
    }
}

那么应该如何ListView使用ItemsControl呢?

标签: c#wpf.net-coremvvm

解决方案


您不能将 ItemsControl 放入 ListView.Items

尝试这个

    <ListView ItemsSource="{Binding ConfigItems,Mode=OneWay}" Margin="5">
        <ListView.ItemContainerStyle>
            <Style TargetType="ListViewItem">
                <Setter Property="HorizontalContentAlignment" Value="Stretch"></Setter>
            </Style>
        </ListView.ItemContainerStyle>
        <ListView.ItemTemplate>
            <DataTemplate>
                <ItemsControl ItemsSource="{Binding}"
                              ItemTemplateSelector="{StaticResource ConfigItemDataSelector}"/>
            </DataTemplate>
        </ListView.ItemTemplate>
    </ListView>

您可以在referencesource.microsoft.com中查看源代码

ItemsControl 具有 DefaultPropertyAttribute("Items"),因此如果您没有声明您在 xaml 中使用的属性,它将设置为 ListView.Items 相等

<ListView ItemsSource="{Binding ConfigItems,Mode=OneWay}" Margin="5">
    <ListView.ItemContainerStyle> 
        <Style TargetType="ListViewItem"> 
            <Setter Property="HorizontalContentAlignment" Value="Stretch"></Setter> 
        </Style> 
    </ListView.ItemContainerStyle>
    <ListView.Items>
      <ItemsControl
        ItemsSource="{Binding}"
        ItemTemplateSelector="{StaticResource ConfigItemDataSelector}"/>
    </ListView.Items>  
</ListView>

并抛出异常说“ItemsSource 在使用之前应该为空”


推荐阅读