如何使用委托和事件

本文关键字:事件 何使用 | 更新日期: 2023-09-27 18:07:02

我正在尝试学习c#和编程,我遇到了一个问题。我试图寻找答案,但失败了,所以我很抱歉,如果我重复了另一个主题。

我有1个窗口窗体(Form1),外部类(Class1),窗体上的按钮和标签。这个类是一个简单的文件碎纸机,从点击按钮开始。Label1。应该从外部类更新文本,显示当前正在分解的文件。

我已经发现,我需要使用委托和事件来正确地实现这一点,但我不知道如何正确使用它们。代码:

//Form1 
  private async void button2_Click(object sender, EventArgs e)
  {
  var task = new Task(() =>
  {
  check = true;
  bool success = FileUtilities.Shred(textBox1.Text);
  });
  task.Start();
  public void ChangeName(string text)
  {
  label3.Text = text; 
  }
  //Class1
  public static bool ShredFile(string filePath, bool shouldDelete = true)
  { 
  bool success = true; 
  try
  { 
  FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Write);
  //Label1.text = filePath; - should be like that.

我已经尝试使用public void ChangeName访问属性,但它没有工作。我不明白我应该在哪里创建一个委托,一个事件,以及在哪里订阅这个事件。

UPDATE:我已经找到了问题所在。我的程序中有几个线程,我不能通过我的类访问label on form。我必须使用回调,之后订阅和事件工作得很好。谢谢你Thorsten Dittmar,为我们指明了正确的道路。

如何使用委托和事件

实际上有几种方法可以达到您想要的效果。我将采用以下方式,因为它最容易实现,并且不涉及任何回调;-)

这背后的基本思想是:将UI更新留给维护UI的类。其他一切都是工具,甚至不需要知道是否有UI。

如果你的UI代码中有一个触发文件分解的点,执行三个步骤:

  1. 更新你的UI,例如显示被分解的文件的文件名(UI类)
  2. 撕碎文件(工具类)
  3. 显示粉碎操作的成功或失败(UI类)
看到了

?无事件:-)

但是你的问题是如何实际创建和使用事件,所以....

通常一个事件在发送端由两部分组成:

  • event
  • 触发事件的方法

你像这样声明它们,例如:

public class EventSender
{
    public event EventHandler<EventArgsType> MyEvent;
    protected void OnMyEvent(...)
    {
        if (MyEvent != null)
            MyEvent(this, new EventArgsType(...));
    }
}

EventArgsTypeEventArgs的一个子类,你可以用它来传递信息从发送方到接收方。一个例子:

public class EventSender
{
    public class EventArgsType : EventArgs
    {
        public EventArgsType(string fileName) : base()
        {
            FileName = fileName;
        }
        public string FileName
        {
            get;
            private set;
        }
    }
    public event EventHandler<EventArgsType> MyEvent;
    protected void OnMyEvent(string filename)
    {
        if (MyEvent != null)
            MyEvent(this, new EventArgsType(filename));
    }
}

当事件应该被引发时,从EventSender 类中调用OnMyEvent方法就足够了。

现在接收者需要将自己附加到事件上,然后在事件被触发时调用一个方法。示例

public class Receiver
{
    private EventSender _sender;
    public Receiver()
    {
        _sender = new EventSender();
        _sender.MyEvent += HandleMyEvent;
    }
    private void HandleMyEvent(object sender, EventSender.EventArgsType e)
    {
        // Do something with e.FileName
    }
}

那么在你的情况下我该怎么做呢?我将创建一个非静态FileShredder,它实现一个或多个类似于示例的事件,并具有一个非静态方法来分解文件。

在您的UI中开始任何任务之前,我将创建该类的实例,附加所需的事件处理程序,然后我将使用该实例来分解文件。在UI类的事件处理程序中,更改标签等内容。