2010-09-29 24 views
6

我收到此错误信息:WPF DataGrid的分组不露面由于绑定错误

System.Windows.Data Error: 5 : Value produced by BindingExpression is not valid for target property.; Value='System.Windows.Data.ListCollectionView' BindingExpression:Path=MaterialList; DataItem='MaterialBrowserListViewModel' (HashCode=24964411); target element is 'CollectionViewSource' (HashCode=36518048); target property is 'Source' (type 'Object') 

下面是重要的XAML +视图模型代码。

我的绑定有什么问题?

视图模型:

public class MaterialBrowserListViewModel : ViewModelBase 
    { 
     private IDocumentRepository _docRepo; 
     private ICollectionView _materialList; 

     public MaterialBrowserListViewModel() 
     { 
      _docRepo= new DocumentRepository(); 


      MaterialList = CollectionViewSource.GetDefaultView(_docRepo.GetMaterialList()); 
      //_materialList.GroupDescriptions.Add(new PropertyGroupDescription("Schoolclasscode")); 
     } 

     public ICollectionView MaterialList 
     { 
      get { return _materialList; } 
      set 
      { 
       _materialList = value; 
       this.RaisePropertyChanged("MaterialList"); 
      } 
     } 
    } 

VIEW:

<UserControl.Resources> 
     <ResourceDictionary> 
      <ResourceDictionary.MergedDictionaries> 
       <!--<ResourceDictionary Source="Themes\DataGrid.Generic.xaml"/>--> 
      </ResourceDictionary.MergedDictionaries> 

      <CollectionViewSource Source="{Binding MaterialList}" x:Key="groupedView"> 
       <CollectionViewSource.GroupDescriptions> 
        <PropertyGroupDescription PropertyName="DocumentName"/> 
       </CollectionViewSource.GroupDescriptions> 
      </CollectionViewSource>    

      <!-- GroupHeaderStyle --> 
      <Style x:Key="GroupHeaderStyle" TargetType="{x:Type GroupItem}"> 
       <Setter Property="Template"> 
        <Setter.Value> 
         <ControlTemplate TargetType="{x:Type GroupItem}"> 
          <Expander IsExpanded="True" 
             Background="Blue" 
             Foreground="White"> 
           <Expander.Header> 
            <TextBlock Text="{Binding Name.Name}"/> 
           </Expander.Header> 
           <ItemsPresenter /> 
          </Expander> 
         </ControlTemplate> 
        </Setter.Value> 
       </Setter> 
      </Style> 
     </ResourceDictionary> 

    </UserControl.Resources> 
    <Grid HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Margin="10" Background="AliceBlue"> 
     <Grid.RowDefinitions> 
      <RowDefinition Height="35" /> 
      <RowDefinition Height="25"/> 
      <RowDefinition Height="*"/> 
     </Grid.RowDefinitions> 
     <StackPanel Margin="0,0,0,10" Grid.Row="0" Orientation="Horizontal"> 
      <Button Content="Open" /> 
      <Button Content="Delete" /> 
      <Button Content="Export" /> 
      <Button Content="Clear Filter" /> 
     </StackPanel> 
     <Grid Grid.Row="1"> 
      <Grid.ColumnDefinitions> 
       <ColumnDefinition Width="{Binding ElementName=col0, Path=ActualWidth}" /> 
       <ColumnDefinition Width="{Binding ElementName=col1, Path=ActualWidth}" /> 
       <ColumnDefinition Width="{Binding ElementName=col2, Path=ActualWidth}" /> 
       <ColumnDefinition Width="{Binding ElementName=col3, Path=ActualWidth}" /> 
       <ColumnDefinition Width="{Binding ElementName=col4, Path=ActualWidth}" /> 
       <ColumnDefinition Width="{Binding ElementName=col5, Path=ActualWidth}" /> 
      </Grid.ColumnDefinitions> 
      <DatePicker Grid.Column="0" /> 
      <TextBox Grid.Column="1" /> 
      <ComboBox Grid.Column="2" /> 
      <ComboBox Grid.Column="3" /> 
      <TextBox Grid.Column="4" /> 
     </Grid> 
     <DataGrid  
     CanUserAddRows="False" 
     CanUserDeleteRows="False"  
     AutoGenerateColumns="False" 
     ItemsSource="{Binding Source={StaticResource groupedView}}"   
     Grid.Column="0" 
     Grid.Row="2" 
     Grid.ColumnSpan="15" 
     x:Name="MaterialGrid"    
     IsSynchronizedWithCurrentItem="True" 
     AlternatingRowBackground="AliceBlue" 
     VirtualizingStackPanel.VirtualizationMode="Recycling" 
     VirtualizingStackPanel.IsVirtualizing="True" 
     HeadersVisibility="Column" 
     CanUserResizeColumns="True" 
     CanUserSortColumns="True" 
     IsReadOnly="True" 
      > 
      <DataGrid.GroupStyle> 
       <GroupStyle ContainerStyle="{StaticResource GroupHeaderStyle}"> 
        <GroupStyle.Panel> 
         <ItemsPanelTemplate> 
          <DataGridRowsPresenter/> 
         </ItemsPanelTemplate> 
        </GroupStyle.Panel> 
       </GroupStyle> 
      </DataGrid.GroupStyle> 
      <DataGrid.Columns> 
       <DataGridTextColumn Binding="{Binding Schoolday}" x:Name="col0" Header="Date" /> 
       <DataGridTextColumn Binding="{Binding Period}" x:Name="col1" Header="Period" /> 
       <DataGridTextColumn Binding="{Binding SchoolclassCode}" x:Name="col2" Header="Class code" /> 
       <DataGridTextColumn Binding="{Binding DocumentName}" x:Name="col3" Header="Document name" /> 
       <DataGridTextColumn Binding="{Binding Keywords}" x:Name="col4" Header="Keywords" /> 
       <DataGridTextColumn Binding="{Binding DocumentId}" x:Name="col5" Header="Doc Id" /> 
      </DataGrid.Columns> 
     </DataGrid> 
    </Grid> 
</UserControl> 

更新:为什么不工作的 “Schoolclasscode” 下面的绑定?

错误:System.Windows.Data Error: 40 : BindingExpression path error: 'SchoolclassCode' property not found on 'object' ''CollectionViewGroupInternal' (HashCode=15576908)'. BindingExpression:Path=SchoolclassCode; DataItem='CollectionViewGroupInternal' (HashCode=15576908); target element is 'TextBlock' (Name=''); target property is 'Text' (type 'String')

<!-- GroupHeaderStyle --> 
      <Style x:Key="GroupHeaderStyle" TargetType="{x:Type GroupItem}"> 
       <Setter Property="Template"> 
        <Setter.Value> 
         <ControlTemplate TargetType="{x:Type GroupItem}"> 
          <Expander IsExpanded="True" 
             Background="AliceBlue" 
             Foreground="White"> 
           <Expander.Header> 
            <TextBlock Text="{Binding SchoolclassCode}"/> 
           </Expander.Header> 
           <ItemsPresenter /> 
          </Expander> 
         </ControlTemplate> 
        </Setter.Value> 
       </Setter> 
      </Style> 

我现在已经改变了结合当前的DataContext看到什么在那里:

<DataGrid  
     CanUserAddRows="False" 
     CanUserDeleteRows="False"  
     AutoGenerateColumns="False" 
     ItemsSource="{Binding Source={StaticResource ResourceKey=groupedView}}"  
     Grid.Column="0" 
     Grid.Row="2" 
     Grid.ColumnSpan="15" 
     x:Name="MaterialGrid"    
     IsSynchronizedWithCurrentItem="True" 
     AlternatingRowBackground="AliceBlue" 
     VirtualizingStackPanel.VirtualizationMode="Recycling" 
     VirtualizingStackPanel.IsVirtualizing="True" 
     HeadersVisibility="Column" 
     CanUserResizeColumns="True" 
     CanUserSortColumns="True" 
     IsReadOnly="True" 
      > 
      <DataGrid.GroupStyle> 
       <GroupStyle> 
        <GroupStyle.ContainerStyle> 
         <Style TargetType="{x:Type GroupItem}"> 
          <Setter Property="Template"> 
           <Setter.Value> 
            <ControlTemplate TargetType="{x:Type GroupItem}"> 
             <Expander IsExpanded="True"> 
              <Expander.Header> 
               <TextBlock Foreground="Black" Text="{Binding }"/> 
              </Expander.Header> 
              <ItemsPresenter /> 
             </Expander> 
            </ControlTemplate> 
           </Setter.Value> 
          </Setter> 
         </Style> 
        </GroupStyle.ContainerStyle> 
       </GroupStyle> 
      </DataGrid.GroupStyle> 
      <DataGrid.Columns> 
       <DataGridTextColumn Binding="{Binding Schoolday}" x:Name="col0" Header="Date" /> 
       <DataGridTextColumn Binding="{Binding Period}" x:Name="col1" Header="Period" /> 
       <DataGridTextColumn Binding="{Binding SchoolclassCode}" x:Name="col2" Header="Class code" /> 
       <DataGridTextColumn Binding="{Binding DocumentName}" x:Name="col3" Header="Document name" /> 
       <DataGridTextColumn Binding="{Binding Keywords}" x:Name="col4" Width="*" Header="Keywords" /> 
       <!--<DataGridTextColumn Binding="{Binding DocumentId}" x:Name="col5" Header="Doc Id" />--> 
      </DataGrid.Columns> 
     </DataGrid> 

你在扩展文字请参阅类的名字吗?我如何从这一点访问我的ObservableCollection?

alt text

回答

2

一个CollectionViewSource需要收集和使用的ICollectionView包装它。但是,您直接绑定到无法换行的ICollectionView。使模型中的属性为一些原始集合类型IEnumerable)并绑定到它。

下面的代码到CollectionViewSource的IsSourceValid:

private static bool IsSourceValid(object o) 
{ 
    if (((o != null) && !(o is IEnumerable)) && (!(o is IListSource) && !(o is DataSourceProvider))) 
    { 
     return false; 
    } 
    return !(o is ICollectionView); 
} 

你可以看到它特别检查了ICollectionView,并在禁止它。即使ICollectionView IEnumerable,它仍然不被允许。

+0

this:_docRepo.GetMaterialList()返回一个ObservableCollection 。我应该把它变成一个IEnumerable?如果是,那么当我想要添加/删除材质时,我会松开INotifyCollectionChanged:/ – Elisabeth 2010-09-30 05:44:45

+0

不,ObservableCollection很好 - 它没有实现ICollectionView。 – 2010-09-30 11:14:43

+0

有趣......我之前使用过ObservableCollection,但它没有工作,现在它工作...脯氨酸我仍然在分组中改变了一些资源的东西。 – Elisabeth 2010-09-30 16:27:57

8

首先,我会对Elisa关于CollectionViewGroup.Name的决议发表评论 - 如果我有足够的积分可以这么做的话。我第一次尝试使用分组时遇到了这个错误。

Name属性的人口,从下方的源属性,通过使用的设置: _materialList.GroupDescriptions.Add(new PropertyGroupDescription("Schoolclasscode"));

(多于一个PropertyGroupDescription添加到一个视图导致要应用于每个附加组的样式和它们对应的Name相应的属性填充)

为了澄清Elisa的分辨率 - 只是改变如下的结合:

<Expander IsExpanded="True" Background="AliceBlue" Foreground="White"> 
    <Expander.Header> 
     <TextBlock Text="{Binding Name}"/> 
    </Expander.Header> 
    <ItemsPresenter /> 
</Expander> 

希望这种节省可以为别人节省时间。

+1

希望我可以多次投票! – CindyH 2013-10-18 19:07:38