Msgstr "Коллекция предметов должна быть пустой перед использованием ItemsSource." - PullRequest
157 голосов
/ 26 марта 2009

Я пытаюсь получить изображения для отображения в WPF ListView, стилизованном под WrapPanel, как описано в этой старой статье команды ATC Avalon: Как создать пользовательское представление .

WPF ListView WrapPanel Images

Когда я пытаюсь заполнить ListView набором запросов объектов LINO-to-Entities ADO.NET Entity Framework, я получаю следующее исключение:

Exception

Коллекция предметов должна быть пустой до используя ItemsSource.

Мой код & hellip;

Visual Basic

Private Sub Window1_Loaded(...) Handles MyBase.Loaded
    ListViewImages.ItemsSource = From g In db.Graphic _
                                 Order By g.DateAdded Ascending _
                                 Select g
End Sub

XAML

<ListView Name="ListViewImages"
          SelectionMode="Single"
          ItemsSource="{Binding}">
    <local:ImageView />
</ListView>

Я поставил точку останова на этой строке. ListViewImages.ItemsSource - это Nothing непосредственно перед назначением LINQ.

Ответы [ 15 ]

168 голосов
/ 07 августа 2009

У меня была такая же ошибка некоторое время в немного другом сценарии. У меня было

<wpftoolkit:DataGrid
    AutoGenerateColumns="False"
    ItemsSource="{Binding Path=Accounts}" >
    <wpftoolkit:DataGridTextColumn 
        Header="Account Name" 
        Binding="{Binding Path=AccountName}" />
</wpftoolkit:DataGrid>

, который я установил, чтобы быть

<wpftoolkit:DataGrid
    AutoGenerateColumns="False"
    ItemsSource="{Binding Path=Accounts}" >
    <wpftoolkit:DataGrid.Columns>
        <wpftoolkit:DataGridTextColumn 
            Header="Account Name" 
            Binding="{Binding Path=AccountName}" />
    </wpftoolkit:DataGrid.Columns>
</wpftoolkit:DataGrid>
115 голосов
/ 26 марта 2009

Причина, по которой выбрасывается это конкретное исключение, заключается в том, что содержимое элемента применяется к коллекции элементов ListView. Таким образом, XAML инициализирует ListView с одним локальным: ImageView в своей коллекции Items. Но при использовании ItemsControl вы должны использовать либо свойство Items, либо свойство ItemsSource, вы не можете использовать оба одновременно. Следовательно, когда обрабатывается атрибут ItemsSource, генерируется исключение.

Вы можете узнать, к какому свойству будет применяться содержимое элемента, найдя ContentPropertyAttribute в классе. В этом случае определено выше в иерархии классов, в ItemsControl:

[ContentPropertyAttribute("Items")]

Предполагалось, что View для ListView будет установлен локально: ImageView, так что исправление должно явно указывать свойство, которое нужно установить.

Исправьте XAML, и исключение исчезнет:

<ListView Name="ListViewImages"
          SelectionMode="Single"
          ItemsSource="{Binding}">
    <ListView.View>
        <local:ImageView />
    </ListView.View>
</ListView>

Отсутствует тег <ListView.View>.

63 голосов
/ 21 мая 2011

Я только что столкнулся с ОЧЕНЬ коварным примером этой проблемы. Мой оригинальный фрагмент был гораздо более сложным, что затрудняло увидеть ошибку.

   <ItemsControl           
      Foreground="Black"  Background="White" Grid.IsSharedSizingScope="True"
      x:Name="MyGrid" ItemsSource="{Binding}">
      >
      <ItemsControl.ItemsPanel>
           <!-- All is fine here -->
      </ItemsControl.ItemsPanel>
      <ItemsControl.ItemTemplate>
           <!-- All is fine here -->
      </ItemsControl.ItemTemplate>
      <!-- Have you caught the error yet? -->
    </ItemsControl>

Ошибка? Дополнительная > после начального открытия тега <ItemsControl>! < применяется к встроенной коллекции Предметов. Когда позже был задан DataContext, мгновенный крах. Поэтому при отладке этой проблемы обращайте внимание не только на ошибки, которые окружают ваши дочерние элементы данных ItemsControl.

39 голосов
/ 20 января 2010

Я тоже по другому сценарию.

<ComboBox Cursor="Hand" DataContext="{Binding}"  
              FontSize="16" Height="27" ItemsSource="{Binding}" 
              Name="cbxDamnCombo" SelectedIndex="0" SelectedValuePath="MemberId">

        <DataTemplate>
            <TextBlock DataContext="{Binding}">
                <TextBlock.Text>
                  <MultiBinding StringFormat="{}{0} / {1}">
                    <Binding Path="MemberName"/>
                    <Binding Path="Phone"/>
                  </MultiBinding>
                </TextBlock.Text>
            </TextBlock>
        </DataTemplate>

</ComboBox>

Теперь, когда вы закончите с отсутствующим тегом Control.ItemTemplate , все станет нормально:

<ComboBox Cursor="Hand" DataContext="{Binding}"  
              FontSize="16" Height="27" ItemsSource="{Binding}" 
              Name="cbxDamnCombo" SelectedIndex="0" SelectedValuePath="MemberId">
    <ComboBox.ItemTemplate>
        <DataTemplate>
            <TextBlock DataContext="{Binding}">
                <TextBlock.Text>
                  <MultiBinding StringFormat="{}{0} / {1}">
                    <Binding Path="MemberName"/>
                    <Binding Path="Phone"/>
                  </MultiBinding>
                </TextBlock.Text>
            </TextBlock>
        </DataTemplate>
    <ComboBox.ItemTemplate>
</ComboBox>
24 голосов
/ 29 декабря 2010

У меня была такая же ошибка в другом сценарии

<ItemsControl ItemsSource="{Binding TableList}">
    <ItemsPanelTemplate>
        <WrapPanel Orientation="Horizontal"/>
    </ItemsPanelTemplate>
</ItemsControl>

Решением было добавить тег ItemsControl.ItemsPanel перед ItemsPanelTemplate

<ItemsControl ItemsSource="{Binding TableList}">
    <ItemsControl.ItemsPanel>
        <ItemsPanelTemplate>
            <WrapPanel Orientation="Horizontal"/>
        </ItemsPanelTemplate>
    </ItemsControl.ItemsPanel>
</ItemsControl>
12 голосов
/ 08 ноября 2013

Исключение

Коллекция элементов должна быть пустой перед использованием ItemsSource.

Это исключение возникает, когда вы добавляете элементы в ItemsSource из разных источников . Так Убедитесь, что вы случайно не пропустили тег, не поместили тег, не добавили дополнительные теги или не написали тег.

<!--Right-->

<ItemsControl ItemsSource="{Binding MyItems}">
     <ItemsControl.ItemsPanel.../>
     <ItemsControl.MyAttachedProperty.../>
     <FrameworkElement.ActualWidth.../>
</ItemsControl>


<!--WRONG-->

<ItemsControl ItemsSource="{Binding MyItems}">
     <Grid.../>
     <Button.../>
     <DataTemplate.../>
     <Heigth.../>
</ItemsControl>

Пока ItemsControl.ItemsSource уже настроен через Binding, другие элементы (Сетка, Кнопка, ...) не могут быть добавлены к источнику. Однако, хотя ItemsSource не используется , следующий код разрешен :

<!--Right-->
<ItemsControl>
     <Button.../>
     <TextBlock.../>
     <sys:String.../>
</ItemsControl>

обратите внимание на отсутствующую ItemsSource="{Binding MyItems}" часть.

11 голосов
/ 12 мая 2015

Чтобы сформулировать ответ иначе; убедитесь, что нет отсутствующих родительских узлов или неправильных узлов .

Это не удалось:

Нет родительского (или неправильного родителя) для ItemsPanelTemplate дочернего узла

<ItemsControl ItemsSource="{Binding TimeSpanChoices}">
    <ItemsPanelTemplate>
        <UniformGrid Rows="1" />
    </ItemsPanelTemplate>
    ...
</ItemsControl>

Это сработало:

<ItemsControl ItemsSource="{Binding TimeSpanChoices}">
    <ItemsControl.ItemsPanel> <!-- I am the missing parent! -->
        <ItemsPanelTemplate>
            <UniformGrid Rows="1" />
        </ItemsPanelTemplate>
    </ItemsControl.ItemsPanel>
    ...    
</ItemsControl>
5 голосов
/ 11 октября 2012

Сохранить шаблон столбца внутри DataGrid.Columns. Это помогло мне решить эту проблему.

Ref: DataGridTemplateColumn: коллекция элементов должна быть пустой перед использованием ItemsSource.

4 голосов
/ 14 сентября 2012

Моя была со стилем данных. Если вы пропустите теги <DataGrid.RowStyle> вокруг стиля, вы получите эту проблему. Странно то, что какое-то время это работало. Вот плохой код.

 <DataGrid Name="DicsountScheduleItemsDataGrid"
                  Grid.Column="0"
                  Grid.Row="2"
                  AutoGenerateColumns="false"
                  ItemsSource="{Binding DiscountScheduleItems, Mode=OneWay}">
            <Style TargetType="DataGridRow">
                <Setter Property="IsSelected"
                        Value="{Binding IsSelected, Mode=TwoWay}" />
            </Style>

и хорошо

 <DataGrid Name="DicsountScheduleItemsDataGrid"
                  Grid.Column="0"
                  Grid.Row="2"
                  AutoGenerateColumns="false"
                  ItemsSource="{Binding DiscountScheduleItems, Mode=OneWay}">
            <DataGrid.RowStyle>
            <Style TargetType="DataGridRow">
                <Setter Property="IsSelected"
                        Value="{Binding IsSelected, Mode=TwoWay}" />
            </Style>
            </DataGrid.RowStyle>
4 голосов
/ 16 декабря 2011

В моем случае он не использовал DataTemplate для ItemsControl.

Старый:

<ItemsControl Width="243" ItemsSource="{Binding List, Mode=TwoWay}">
    <StackPanel Orientation="Horizontal">
        <TextBox Width="25" Margin="0,0,5,0" Text="{Binding Path=Property1}"/>
        <Label Content="{Binding Path=Property2}"/>
    </StackPanel>
</ItemsControl>

Новое:

<ItemsControl Width="243" ItemsSource="{Binding List, Mode=TwoWay}">
    <ItemsControl.ItemTemplate>
        <DataTemplate>
            <StackPanel Orientation="Horizontal">
                <TextBox Width="25" Margin="0,0,5,0" Text="{Binding Path=Property1}"/>
                <Label Content="{Binding Path=Property2}"/>
            </StackPanel>
        </DataTemplate>
    </ItemsControl.ItemTemplate>
</ItemsControl>
...