处理 OnPropertyChanged [英] Handling OnPropertyChanged

查看:15
本文介绍了处理 OnPropertyChanged的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我并不精通基于事件的编程.基本上,我仍然在纠结.我正在尝试设置一些东西,但即使有教程,我也无法理解它.我想做的(用文字)如下:

I'm not well versed in event-based programming. Basically, I'm still stumbling around with it. I'm trying to get something set up, but even with the tutorials, I can't wrap my head around it. What I would like to do (in words) is the following:

  1. 我有一个属性发生变化的数据对象.我在属性的设置器中注意到了这一点,并想引发属性已更改的事件.

  1. I have a dataobject where a property changes. I notice this in the setter of the property, and want to raise an event that the property has changed.

在其他地方(完全在不同的类中),我想知道这个对象的属性已经改变,并采取一些措施.

Elsewhere (in a different class entirely), I want to know that the property on this object has changed, and take some action.

现在我确信这是一个足够常见的场景,但我的 google-fu 让我失望了.我只是不明白 http://msdn.microsoft.com/en-us/library/ms743695.aspx.

Now I'm sure this is a common enough scenario, but my google-fu is letting me down. I'm simply not understanding http://msdn.microsoft.com/en-us/library/ms743695.aspx.

我有这个:

public class ChattyClass {
  private int someMember;

  public event PropertyChangedEventHandler PropertyChanged;

  public int SomeMember {
    get {
      return this.someMember;
    }
    set {
      if (this.someMember != value){
        someMember = value;
        // Raise event/fire handlers. But how?
      }
   }
}

public class NosyClass{
  private List<ChattyClass> myChatters;

  public void addChatter(ChattyClass chatter){
    myChatters.add(chatter);
    // Start listening to property changed events
  }

  private void listner(){
    // I want this to be called when the PropertyChangedEvent is called
    Console.WriteLine("Hey! Hey! Listen! A property of a chatter in my list has changed!");
  }
}

我该怎么做才能把它连接起来?

What do I do to wire this up?

关于让我回到链接的评论:

Concerning the comment pointing me back to the link:

在我看到的例子中:

protected void OnPropertyChanged(string name)
{
    PropertyChangedEventHandler handler = PropertyChanged;
    if (handler != null)
    {
        handler(this, new PropertyChangedEventArgs(name));
    }
}

我不明白的:

  • 为什么这不只是调用 PropertyChanged(this, new PropertyCHangedEventArgs(name))
  • PropertyChanged 在哪里被分配?
  • 作业是什么样的?

推荐答案

你必须触发事件.在 MSDN 上的示例中,他们制作了一个受保护的方法 OnPropertyChanged 来更轻松地处理这个问题(并避免重复代码).

You have to fire the event. In the example on MSDN, they made a protected method OnPropertyChanged to handle this easier (and to avoid duplicate code).

// Create the OnPropertyChanged method to raise the event 
protected void OnPropertyChanged(string name)
{
    PropertyChangedEventHandler handler = PropertyChanged;
    if (handler != null)
    {
        handler(this, new PropertyChangedEventArgs(name));
    }
}

此方法的作用是查看是否分配了事件处理程序(如果未分配而您只是调用它,您将得到 NullReferenceException).如果分配了一个,则调用此事件处理程序.提供的事件处理程序必须具有 PropertyChangedEventHandler 委托的签名.这个签名是:

What this method does, is look whether there is an event handler assigned or not (if it is not assigned and you just call it, you'll get a NullReferenceException). If there is one assigned, call this event handler. The event handler provided, has to have the signature of the PropertyChangedEventHandler delegate. This signature is:

void MyMethod(object sender, PropertyChangedEventArgs e)

其中第一个参数必须是 object 类型并表示触发事件的对象,第二个参数包含此事件的参数.在这种情况下,您自己的类会触发事件并因此将 this 作为参数 sender.第二个参数包含已更改的属性的名称.

Where the first parameter has to be of the type object and represents the object that fires the event, and the second parameter contains the arguments of this event. In this case, your own class fires the event and thus give this as parameter sender. The second parameter contains the name of the property that has changed.

现在为了能够在事件触发时做出反应,您必须为类分配一个事件处理程序.在这种情况下,您必须在 addChatter 方法中指定它.除此之外,您必须首先定义您的处理程序.在您的 NosyClass 中,您必须添加一个方法来执行此操作,例如:

Now to be able to react upon the firing of the event, you have to assign an event handler to the class. In this case, you'll have to assign this in your addChatter method. Apart from that, you'll have to first define your handler. In your NosyClass you'll have to add a method to do this, for example:

private void chatter_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
    Console.WriteLine("A property has changed: " + e.PropertyName);
}

如你所见,这个方法对应于我之前解释的签名.在第二个参数中,您将能够找到更改了哪个参数的信息.最后要做的是添加事件处理程序.现在在你的 addChatter 方法中,你必须分配这个:

As you can see, this method corresponds to the signature I explained before. In the second parameter, you'll be able to find the information of which parameter has been changed. Last thing to do, is add the event handler. Now in your addChatter method, you'll have to assign this:

public void AddChatter(ChattyClass chatter)
{
    myChatters.Add(chatter);
    // Assign the event handler
    chatter.PropertyChanged += new PropertyChangedEventHandler(chatter_PropertyChanged);
}

我建议您阅读一些有关 .NET/C# 中的事件:http://msdn.microsoft.com/en-us/library/awbftdfh.我认为在阅读/了解此内容后,您会更加清楚.

I would suggest you to read something about events in .NET / C#: http://msdn.microsoft.com/en-us/library/awbftdfh . I think after reading/learning this, things will be more clear to you.

如果您想快速测试它,可以在 here on pastebin 找到一个控制台应用程序(只需复制/粘贴到一个新的控制台应用程序中).

You can find a console application here on pastebin if you would like to test it quickly (just copy/paste into a new console application).

使用较新版本的 C#,您可以内联对事件处理程序的调用:

With newer versions of C#, you can inline the call to the event handler:

// inside your setter
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(MyProperty)));

您还可以使用 Fody PropertyChanged 之类的东西来自动生成必要的代码(访问他们的链接GitHub 页面,带有示例).

You could also use something like Fody PropertyChanged to automatically generated the necessary code (visit the link to their GitHub page, with samples).

这篇关于处理 OnPropertyChanged的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆