當我在DataGridViewModel類中調用FillGPLocationAndPrint時,出現此異常。以下是內部例外。會發生什麼是一個硬編碼的字典傳遞到FillGPLocationAndPrint,它從那裏獲取數據並將其放入綁定到DataGrid的ItemsSource屬性的GridData ObservableCollection中。這引發了一個名爲CollectionChanged的事件,該事件調用GridDataChanged方法,該方法負責增加DataGrid高度屬性和MainWindow高度屬性。基本上,隨着行數的增加和減少,網格和窗口高度會動態變化。DataGrid:ItemsControl與其項目不一致源
編輯:
進一步看起來有點到這個問題之後,這個問題實際上是由
mainVm.WindowHeight += ROW_HEIGHT;
和
mainVm.WindowHeight -= ROW_HEIGHT;
報表所致。出於某種原因,它不喜歡改變窗口的高度。 mainVm是一個表示主窗口的ViewModel的對象,而WindowHeight是一個與主窗口中的Height屬性綁定的double。
這裏的InnerException:
開發者信息(使用文本可視化閱讀本): 這個異常被拋出,因爲發電機控制「System.Windows.Controls.DataGrid Items.Count:3」名稱'grdData'已收到與Items集合的當前狀態不一致的CollectionChanged事件序列。檢測到以下差異: 累計計數2與實際計數3不同。[累計計數爲(最後一次復位時的計數+上次復位後的#次數 - #移除)] 在索引1:發生器的項目'{NewItemPlaceholder}'與實際項目「MechQualTestDataEntry.MechTestData」不同。
一個或多個以下的來源可能都提出了錯誤的事件: System.Windows.Controls.ItemContainerGenerator System.Windows.Controls.ItemCollection System.Windows.Data.ListCollectionView System.Collections.ObjectModel.ObservableCollection `1 [[MechQualTestDataEntry.MechTestData,MechQualTestDataEntry,版本= 2.0.5.25,文化=中性公鑰=空]] (標有星號源被認爲是更可能是問題的原因。)
最常見的原因是(a)在不提高相應事件的情況下更改集合或其計數,以及(b)用公司籌集事件orrect索引或項目參數。
異常的堆棧跟蹤描述瞭如何檢測不一致性,而不是它們是如何發生的。爲了獲得更及時的異常,請將生成器上的附加屬性「PresentationTraceSources.TraceLevel」設置爲「高」,然後重新運行該方案。一種方法是運行與以下類似的命令: System.Diagnostics.PresentationTraceSources.SetTraceLevel(myItemsControl.ItemContainerGenerator,System.Diagnostics.PresentationTraceLevel.High) 從即時窗口。這會導致檢測邏輯在每個CollectionChanged事件之後運行,因此會降低應用程序的速度。
這裏是DataGridViewModel類(縮小):
private const int GRID_HEIGHT_MAX = 390;
private const int GRID_HEIGHT_MIN = 60;
private const int ROW_HEIGHT = 22;
private int prevRowCount;
private double gridHeight;
private MainWindowViewModel mainVm;
private ObservableCollection<MechTestData> gridData;
public DataGridViewModel(MainWindowViewModel mainVm)
{
this.mainVm = mainVm;
GridHeight = GRID_HEIGHT_MIN;
gridData = new ObservableCollection<MechTestData>();
gridData.CollectionChanged += GridDataChanged;
}
public double GridHeight
{
get
{
return gridHeight;
}
set
{
gridHeight = value;
OnPropertyChanged("GridHeight");
}
}
public ObservableCollection<MechTestData> GridData
{
get
{
return gridData;
}
set
{
gridData = value;
OnPropertyChanged("GridData");
}
}
private void GridDataChanged(object sender, NotifyCollectionChangedEventArgs e)
{
// If the grid height is less than or equal to
// the maximum grid height
if (gridHeight <= GRID_HEIGHT_MAX + 1)
{
// If we added rows, increase the grid height
if (gridData.Count > prevRowCount)
{
GridHeight += ROW_HEIGHT;
mainVm.WindowHeight += ROW_HEIGHT;
}
}
// if the grid height is less than or equal to
// the minimum grid height
if (gridHeight > GRID_HEIGHT_MIN)
{
// If we deleted rows, decrease the grid height
if (gridData.Count < prevRowCount)
{
GridHeight -= ROW_HEIGHT;
mainVm.WindowHeight -= ROW_HEIGHT;
}
}
// Cache the row count
prevRowCount = gridData.Count;
}
public void FillGPLocationAndPrint(Dictionary<string, string> gpLocationToDiePrintMap)
{
foreach (KeyValuePair<string, string> map in gpLocationToDiePrintMap)
{
GridData.Add(new MechTestData(map.Key, map.Value));
}
}
ViewModelBase類:
public abstract class ViewModelBase : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
protected void OnPropertyChanged(string propertyName)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(propertyName));
}
}
}
XAML(減去所有其他組件):
<Window
x:Class="MechQualTestDataEntry.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:p="clr-namespace:MechQualTestDataEntry.Properties"
xmlns:wpftk="http://schemas.microsoft.com/wpf/2008/toolkit"
xmlns:local="clr-namespace:MechQualTestDataEntry"
Icon="/MechQualTestDataEntry;component/Resources/MechQualIcon.ico"
Title="MainWindow"
Background="MidnightBlue"
ResizeMode="CanMinimize"
Height="{Binding WindowHeight}"
MinHeight="{Binding WindowHeight}"
MaxHeight="{Binding WindowHeight}"
MinWidth="700"
MaxWidth="1000"
Width="820">
<Window.Resources>
<local:DateTimeConverter x:Key="DateTimeFormatter"/>
</Window.Resources>
<!-- Data Grid -->
<DataGrid
DockPanel.Dock="Bottom"
x:Name="grdData"
CellStyle="{StaticResource cellStyle}"
FontFamily="Verdana"
Height="{Binding GridHeight}"
Foreground="MidnightBlue"
AutoGenerateColumns="False"
RowHeight="22"
CanUserAddRows="True"
CanUserDeleteRows="True"
CanUserReorderColumns="False"
CanUserResizeColumns="False"
CanUserResizeRows="False"
CanUserSortColumns="True"
ItemsSource="{Binding GridData}"
SelectionUnit="CellOrRowHeader"
SelectionMode="Extended">
<DataGrid.Resources>
<Style TargetType="{x:Type DataGridCell}">
<EventSetter
Event="PreviewMouseLeftButtonDown"
Handler="DataGridCell_PreviewMouseLeftButtonDown"/>
</Style>
<Style TargetType="{x:Type DataGridRowHeader}">
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="False">
<Setter Property="Background" Value="DeepSkyBlue" />
<Setter Property="BorderBrush" Value="MidnightBlue" />
<Setter Property="BorderThickness" Value="1" />
<Setter Property="Width" Value="15" />
<Setter Property="HorizontalContentAlignment" Value="Right" />
<Setter Property="VerticalContentAlignment" Value="Center" />
</Trigger>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="Background" Value="MidnightBlue" />
<Setter Property="BorderBrush" Value="DeepSkyBlue" />
<Setter Property="BorderThickness" Value="1" />
<Setter Property="Width" Value="15" />
<Setter Property="HorizontalContentAlignment" Value="Right" />
<Setter Property="VerticalContentAlignment" Value="Center" />
</Trigger>
</Style.Triggers>
</Style>
</DataGrid.Resources>
<DataGrid.Columns>
<!-- TO Number -->
<DataGridTextColumn
Width="40"
Binding="{Binding TONumber}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="TO #"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- GelPak Location -->
<DataGridTextColumn
Width="60"
Binding="{Binding GelPakLocation}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="GelPak Location"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- Die Print -->
<DataGridTextColumn
Width="60"
Binding="{Binding DiePrint}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
Text="Die Print"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- Wire Pull Test -->
<DataGridTextColumn
Width="70"
Binding="{Binding WirePullTestValue}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="Wire Pull Test"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- Failure Mode -->
<DataGridTextColumn
Width="84"
Binding="{Binding FailureMode}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
Text="Failure Mode"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- Ball Shear -->
<DataGridTextColumn
Width="70"
Binding="{Binding BallShearTestValue}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="Ball Shear Test"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- Die Shear -->
<DataGridTextColumn
Width="70"
Binding="{Binding DieShearTestValue}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="Die Shear Test"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- InP Remaining -->
<DataGridTextColumn
Width="70"
Binding="{Binding InPRemaining}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="InP Remaining"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- Test Result -->
<DataGridTextColumn
Width="70"
Binding="{Binding TestResult}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="Pass/Fail"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
<!-- Notes -->
<DataGridTextColumn
Width="*"
Binding="{Binding Notes}">
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock
Style="{StaticResource tbkStyleGridHeader}"
TextWrapping="Wrap"
Text="Notes"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>
</DataGrid.Columns>
</DataGrid>
在任何幫助解決這個問題將非常感激。
問候,
凱爾
可能的快速解決方案從頭開始:將有問題的代碼放在Dispatcher.BeginInvoke()中。 –
剛剛嘗試過,它會拋出完全相同的異常。我把:GridData.Add(新的MechTestData(map.Key,map.Value));在調度程序調用方法內部。 – kformeck
我想補充一點,我的原始解決方案在我的開發機器上完美工作,但是當我部署它時,幾乎在每臺生產機器上都會遇到這種異常。所有生產機器都運行與我的開發機器相同的操作系統:安裝了.NET 4.0的Windows 7 Professional x64 – kformeck