我有一个关于更新可观察集合的问题。我正在使用Visual Studio 2010 c#。我是一个相对新手,可能犯了一个灾难性的错误,所以很抱歉开始。基本上,当我在Windows 7上运行它时,这段代码可以完美运行,但在Windows 8上,我在PropertyChanged上得到了一个NullReferenceException
。
我有一个保存任务可观察集合的类。
任务.cs
namespace TimeLocation
{
public static class TStatic
{
static TStatic()
{
TaskList = new ObservableCollection<Tasks>();
}
public static ObservableCollection<Tasks> TaskList { set; get; }
}
public class Tasks : INotifyPropertyChanged
{
public int taskID;
public string taskname;
public Tasks(string tname)
{
this.taskname = tname;
}
public string Taskname
{
get { return taskname; }
set
{
if (value != "")
{
taskname = value; OnPropertyChanged("Taskname");
}
}
}
public event PropertyChangedEventHandler PropertyChanged;
protected void OnPropertyChanged(string info)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(info));
}
}
}
我在 MainWindow 中有一个绑定到任务的网格,并且在更新时通过上面的PropertyChanged
更新正常。用户还可以通过使用鼠标拖动来编辑任务。我希望这也更新网格和可观察集合。当在Windows 7上运行时,这可以工作,但在Windows 8上失败。
在 mainwindow.xaml 的代码隐藏中
public partial class MainWindow : INotifyPropertyChanged
{
public MainWindow()
{
InitializeComponent();
DataContext = TStatic.TaskList;
}
private void dCanvas_PreviewMouseLeftButtonUp(object sender, System.Windows.Input.MouseButtonEventArgs e)
{
Tasks t = _selectedtask;
t.taskname = "Test";
PropertyChanged(t, new PropertyChangedEventArgs("Taskname"));
}
}
我确定任务名称已更新,因为当我将其保存到文件并添加监视时名称已更改。
_selectedtask
已填充了选择网格行的任务。
在 Windows 8 中,该行
PropertyChanged(t, new PropertyChangedEventArgs("Taskname"));
返回空错误。在 Windows 7 中,它不为空,并且可以正确更新网格。
首先,公共字段声明是一种非常糟糕的做法。应将它们设为私有,并在需要时通过公共属性授予对它们的访问权限。
其次,像 Window 这样的 UI 元素不应该实现 INotifyPropertyChanged 接口。您可以为视图模型类实现它(请参阅 MVVM 模式,这是 wpf 应用的推荐方法),或者至少为任务等数据类实现它。
在您的dCanvas_PreviewMouseLeftButtonUp代码中,更新可能不起作用,因为您更新了任务对象的字段,但调用了 MainWindow 的 PropertyChanged 方法。设置 TaskName 属性就足够了:
t.TaskName = "Test"