如何在 C# 中实现取消事件
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2366684/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to implement a cancel event in C#
提问by Sako73
I know that in C#, there are several built in events that pass a parameter ("Cancel") which if set to truewill stop further execution in the object that raised the event.
我知道在 C# 中,有几个内置事件传递一个参数(“取消”),如果设置为true将停止在引发事件的对象中进一步执行。
How would you implement an event where the raising object was able to keep track of a property in the EventArgs?
您将如何实现引发对象能够跟踪 EventArgs 中的属性的事件?
Here is a WinForms example of what I am trying to do:
http://msdn.microsoft.com/en-us/library/system.componentmodel.canceleventargs.cancel.aspx
这是我正在尝试做的一个 WinForms 示例:
http://msdn.microsoft.com/en-us/library/system.componentmodel.canceleventargs.cancel.aspx
Thank you.
谢谢你。
采纳答案by Jon Seigel
It's really easy.
这真的很容易。
private event _myEvent;
// ...
// Create the event args
CancelEventArgs args = new CancelEventArgs();
// Fire the event
_myEvent.DynamicInvoke(new object[] { this, args });
// Check the result when the event handler returns
if (args.Cancel)
{
// ...
}
回答by Jonathan Allen
Easy:
简单:
- Create an instance of CancelEventArgs (or your custom type).
- Raise the event, passing that instance.
- Check the Canceld property on [1].
- 创建 CancelEventArgs(或您的自定义类型)的实例。
- 引发事件,传递该实例。
- 检查 [1] 上的已取消属性。
Do you need code samples?
您需要代码示例吗?
回答by Maurizio Reginelli
You have to wait the call that raise the event and then check the flag in your EventArgs (in particular CancelEventArgs).
您必须等待引发事件的调用,然后检查 EventArgs(特别是 CancelEventArgs)中的标志。
回答by Tal Segal
What I needed was a way to stop the subscribers from receiving the event after a subscriber canceled it. In my situation I don't want the event to further propagate to the other subscribers after some subscriber canceled it. I have implemented this using custom event handling:
我需要的是一种在订阅者取消事件后阻止订阅者接收事件的方法。在我的情况下,我不希望该事件在某些订阅者取消后进一步传播给其他订阅者。我已经使用自定义事件处理实现了这一点:
public class Program
{
private static List<EventHandler<CancelEventArgs>> SubscribersList = new List<EventHandler<CancelEventArgs>>();
public static event EventHandler<CancelEventArgs> TheEvent
{
add {
if (!SubscribersList.Contains(value))
{
SubscribersList.Add(value);
}
}
remove
{
if (SubscribersList.Contains(value))
{
SubscribersList.Remove(value);
}
}
}
public static void RaiseTheEvent(object sender, CancelEventArgs cancelArgs)
{
foreach (EventHandler<CancelEventArgs> sub in SubscribersList)
{
sub(sender, cancelArgs);
// Stop the Execution after a subscriber cancels the event
if (cancelArgs.Cancel)
{
break;
}
}
}
static void Main(string[] args)
{
new Subscriber1();
new Subscriber2();
Console.WriteLine("Program: Raising the event");
CancelEventArgs cancelArgs = new CancelEventArgs();
RaiseTheEvent(null, cancelArgs);
if (cancelArgs.Cancel)
{
Console.WriteLine("Program: The Event was Canceled");
}
else
{
Console.WriteLine("Program: The Event was NOT Canceled");
}
Console.ReadLine();
}
}
public class Subscriber1
{
public Subscriber1()
{
Program.TheEvent += new EventHandler<CancelEventArgs>(program_TheEvent);
}
void program_TheEvent(object sender, CancelEventArgs e)
{
Console.WriteLine("Subscriber1: in program_TheEvent");
Console.WriteLine("Subscriber1: Canceling the event");
e.Cancel = true;
}
}
public class Subscriber2
{
public Subscriber2()
{
Program.TheEvent += new EventHandler<CancelEventArgs>(program_TheEvent);
}
void program_TheEvent(object sender, CancelEventArgs e)
{
Console.WriteLine("Subscriber2: in program_TheEvent");
}
}
回答by Dave Tillman
Here is the way that I avoid calling further subscribers once one of them asserts cancel:
这是我避免在其中一个订阅者断言取消后调用更多订阅者的方式:
var tmp = AutoBalanceTriggered;
if (tmp != null)
{
var args = new CancelEventArgs();
foreach (EventHandler<CancelEventArgs> t in tmp.GetInvocationList())
{
t(this, args);
if (args.Cancel) // a client cancelled the operation
{
break;
}
}
}