【问题标题】:'EditItem' is not allowed for this view` when editing a detail item编辑详细信息项时,此视图不允许“EditItem”
【发布时间】:2017-04-26 14:30:33
【问题描述】:

上下文

使用 Entity Framework 6 我有一个机身对象的 ObservableCollection,每个对象都有一个下属的 Identity 对象集合。通过 XAML 和视图模型,我一次查看这个集合一个机身(主),它的每个身份(细节)对象都在 DataGrid 中。为了一次只处理一个 Airframe 的显示/更新,我使用 CollectionView 以便我在集合中获得当前位置,并可以连接“转到下一个”和“转到上一个”按钮和命令。一个简化的代码摘录:

背后的代码

private ADBContext databaseContext;
private UnitOfWork unitOfWork;
private ViewModels.ViewModel ViewModel;
public MainWindow()
{
    InitializeComponent();

    databaseContext = new ADBContext();
    unitOfWork = new UnitOfWork(databaseContext);

    ViewModel = new ViewModels.ViewModel(unitOfWork);

    this.DataContext = ViewModel;
}

查看模型

    public class ViewModel : INotifyPropertyChanged
    {         
        public CollectionView AirframeCollectionView { get; set; }

        public IUnitOfWork UnitOfWork;

        public ViewModel(IUnitOfWork unitOfWork)
        {
            UnitOfWork = unitOfWork;

            AirframeCollectionView = CollectionViewSource.GetDefaultView(new ObservableCollection<Airframe>(UnitOfWork.Airframes.GetAirframesForRegistration(SearchRegistration)));

            RaisePropertyChanged("AirframeCollectionView");
        }

        public event PropertyChangedEventHandler PropertyChanged;

        public void RaisePropertyChanged(string propertyName)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
            }
        }
    }

XAML - 大师

<Grid.ColumnDefinitions>
    <ColumnDefinition Name="airframeLabels" MaxWidth="100"/>
    <ColumnDefinition Name="airframeDetails"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
    <RowDefinition Name="typeRow"/>
    <RowDefinition Name="constructionNoRow"/>
    <RowDefinition Name="remarksRow"/>
    <RowDefinition Name="rolledOutDateRow"/>
    <RowDefinition Name="firstFlightDateRow"/>
    <RowDefinition Name="statusRow"/>
</Grid.RowDefinitions>
<Label Grid.Column="0" Grid.Row="0">Type</Label>
<wpf:AutoCompleteTextBox Grid.Column="1" Grid.Row="0" 
                         Text="{Binding Path=AirframeCollectionView/TypeName}"
                         Provider="{Binding TypeNameStubSuggestions}"/>
<Label Grid.Column="0" Grid.Row="1">Construction no</Label>
<TextBox Grid.Column="1" Grid.Row="1" Margin="5" Name="constructionNo" 
         Text="{Binding AirframeCollectionView/ConstructionNumber}"/>
<Label Grid.Column="0" Grid.Row="2">Remarks</Label>
<TextBox Grid.Column="1" Grid.Row="2" Margin="5" Name="remarks"
         Text="{Binding AirframeCollectionView/Remarks}"/>
 <Label Grid.Column="0" Grid.Row="3">Rolled out</Label>
 <DatePickerTextBox Grid.Column="1" Margin="5" Grid.Row="3" Name="rolledOut" 
                    Text="{Binding AirframeCollectionView/RolloutDate, StringFormat=\{0:dd-MMM-yy\}}"/>
<Label Grid.Column="0" Grid.Row="4">First flight</Label>
<DatePickerTextBox Grid.Column="1" Margin="5" Grid.Row="4" Name="firstFlight" 
                   Text="{Binding AirframeCollectionView/FirstFlightDate, StringFormat=\{0:dd-MMM-yy\}}"/>
<Label Grid.Column="0" Grid.Row="5">Status</Label>
<ComboBox Grid.Column="1" Grid.Row="5" Margin="5" Name="status"
          ItemsSource="{Binding AirframeStatuses}"
          SelectedValue="{Binding AirframeCollectionView/StatusId, Mode=TwoWay}"
          SelectedValuePath="StatusId"
          DisplayMemberPath="StatusName"
          SelectedItem="{Binding AirframeCollectionView/StatusId}"/> 

XAML - 详细信息

<DataGrid Name="identitiesGrid"
          AutoGenerateColumns="False"
          ItemsSource="{Binding AirframeCollectionView/Identities, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
          IsReadOnly="False">
    <DataGrid.Columns>
        <DataGridTextColumn Header="Regn" Binding="{Binding Registration, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" IsReadOnly="False"/>
</DataGrid>

问题

这完美地显示了数据,我可以毫无问题地编辑主数据。当我单击详细 DataGrid 中的任何行时,第一次单击选择单元格,第二次单击导致异常“不允许在 PresentationFramework.dll 中使用 'EditItem' 发生类型为 'System.InvalidOperationException' 的未处理异常”这个视图`”。

问题

如何停止这个异常?

【问题讨论】:

    标签: c# wpf xaml mvvm datagrid


    【解决方案1】:

    如何停止这个异常?

    您需要确保“身份”属性的类型支持编辑。它应该实现 IList 接口。例如, HashSet 没有,但 List 和 ObservableCollection 可以。

    【讨论】:

    • 在数据库中,我有一个 Airframes 表,它与 Identities 表有外键关系。我使用存储库模式通过实体框架访问此结构,因此使用 UnitOfWork.Airframes.GetAirframesForRegistration 方法返回一个 IEnumerable ,其中 EF 为每个机身提供一个 Identities 属性。这被加载到 ObservableCollection 中,然后加载到 CollectionView AirframeCollectionView。我的假设是这种安排将具有支持编辑的身份属性。我弄错了吗?
    • 是的,Airframe 类的 Identities 导航属性必须(也)支持编辑,即它应该实现 IList 接口。自动生成的实体类将导航属性定义为 ICollection<T>不幸的是,这些集合在 WPF DataGrids 中不可编辑:stackoverflow.com/questions/6508479/…
    • 好的,明白了。因此,这意味着我需要将我的身份放入一个单独的结构中,也许是一个 ObservableCollection,用于显示/更新。当我发出 SaveChanges() 时,Entity Framework 是否仍然知道 Airframe 和它的 Identities 是链接的,还是我必须做一些事情来重新链接它们?
    • EF 并不真正关心该类是否将导航属性公开为 ICollection 或 IList。这确实是另一个问题,但您应该能够修改 .tt 模板文件以为您生成兼容类型的属性:stackoverflow.com/questions/20761622/….
    • 太好了,我现在可以使用它了。您的最后一个链接特别有用。这对于在 WPF 中编辑主/详细信息集合似乎有点笨拙,我猜这是一个非常普遍的要求。也许这是MS将来会考虑的事情。无论如何,衷心感谢您对此的意见。
    猜你喜欢
    • 1970-01-01
    • 2018-03-25
    • 2013-11-30
    • 2012-01-30
    • 2011-10-20
    • 1970-01-01
    • 2017-04-10
    • 1970-01-01
    相关资源
    最近更新 更多