我想在DataGrid中显示List的Items。所以我做了一些可能有用的事情。
首先,我将DataGrid的ItemsSource
设置为位于类中的List,并将我的自定义列的DataGridTextColumns
绑定到列表的项目。
班级:
public class Auftrag : INotifyPropertyCanged
{
private int _id; // ID is an example to show that there is more then `Services`
private List<Services> _services = new List<Services>();
[...] // There are more Fields
[...] // There are more Properties
public int ID { get; set; } // ID is just an Example. My Properties aren't {get; set;} My properties has all the same structure like `Services` Property
public List<Services> Services
{
get => _services;
set
{
if(_services == value) return;
_services = value;
OnPropertyChanged("Services");
}
}
}
Services
类包含您可以在XAML
绑定View
的{{1}}中看到的项目。
ViewModel
在ViewModel中,我创建了一个Property,用于保存我的DataBase的结果:
DataGridTextColumn
我正在阅读DataBase并将结果添加到Properties:
private Auftrag _sAuftrag = new Auftrag();
public Auftrag SAuftrag
{
get => _sAuftrag;
set
{
if (_sAuftrag == value) return;
_sAuftrag = value;
OnPropertyChanged("SAuftrag");
}
}
视图
public async Task<bool> LoadSingleAuftrag(int aID)
{
return await Task.Run(() =>
{
// Check SQL Connection, Run Query etc.
[...]
using(var reader = cmd.ExecuteReader())
{
while(reader.Read())
{
SAuftrag.AuftragsId = reader["AuftragsID"] as int? ?? default(int);
SAuftrag.KundenId = reader["KundenID"] as int? ?? default(int);
SAuftrag.Status = reader["Status"] as string;
SAuftrag.CreatedDate = reader["ErstelltAm"] as DateTime? ?? default(DateTime);
SAuftrag.FinishedDate = reader["FertigGestelltAm"] as DateTime? ?? default(DateTime);
SAuftrag.Services.Add(new Services
{
Servicename = reader["Servicename"] as string,
Servicebeschreibung = reader["Servicebeschreibung"] as string,
Einzelpreis = reader["Preis"] as double? ?? default(double),
Anzahl = reader["Anzahl"] as int? ?? default(int),
Preis = Convert.ToDouble(reader["Preis"]) * Convert.ToInt32(reader["Anzahl"])
});
}
// Is working fine, so the Items are sucessfully stored into the `Services` list.
Debug.WriteLine("Anzahl: " + SAuftrag.Services[0].Anzahl);
Debug.WriteLine("Einzelpreis: " + SAuftrag.Services[0].Einzelpreis);
Debug.WriteLine("Gesamtpreis: " + SAuftrag.Services[0].Preis);
}
}
}
对我来说,它看起来是正确的,应该可行。但由于某些原因,我得到<Window.DataContext>
<viewModels:AuftragViewModel />
</Window.DataContext>
[...]
<DataGrid ItemsSource="{Binding SAuftrag.Services}" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn x:Name="Servicename" Header="Servicename" Binding="{Binding Path=Servicename}" />
<DataGridTextColumn x:Name="Beschreibung" Header="Beschreibung" Binding="{Binding Path=Servicebeschreibung}" />
<DataGridTextColumn x:Name="Anzahl" Header="Anzahl" Binding="{Binding Path=Anzahl}" />
</DataGrid.Columns>
</DataGrid>
错误。
如果我对DataGrid进行了评论,则应用程序可以正常工作,并且绑定是可见的(例如InvalidOperationException
绑定)。所以没有ID
。
简短版本的错误讯息:
Instance Error
An ItemsControl is not consistent with its element source. For more information, see the inner exception.
类的属性是否会导致错误?:
服务类
Services
View.CodeBehind
在后面的代码中,我调用了一个加载数据的方法:
[..]
private double _preis;
private double _einzelpreis;
[..]
public double Preis
{
get => _preis;
set
{
if (_preis == value) return; // Possible loss of precision while rounding values warning
_preis = value;
OnPropertyChanged("Preis");
}
}
public double Einzelpreis
{
get => _einzelpreis;
set
{
if (_einzelpreis == value) return; // Possible loss of precision while rounding values warning
_einzelpreis = value;
OnPropertyChanged("Einzelpreis");
}
}
答案 0 :(得分:0)
@ASh在评论中写道,试用ObservableCollection
代替List
。
我不知道原因,但在将List
更改为ObservableCollection
并通过Dispatcher
添加项目后,它正在运行。
因此,如果将来有人出现此类错误,请不要再使用List
。我想这是使用ObservableCollection
的最佳方式。
感谢@ASh。