Logic flaw in CancelEventHandler?

  • Thread starter Thread starter Tom Briese
  • Start date Start date
T

Tom Briese

When using an event with a delegate type of CancelEventHandler, shouldn't the delegate be checking to see if the Cancel property on the event object has been set to true and stop execution upon the first 'cancel' it encounters? It seems you will only get the cancel information for the last event hanlder to process, and all previous are effectively ignored.

Am I missing something?

Here is a quick example to show what I mean:

public class MyForm : Form {
public event CancelEventHandler MyCancelEvent;

private void CancelHandlerOne(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 1: Event.Cancel passed in is " + e.Cancel.ToString());
}


private void CancelHandlerTwo(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 2: Event.Cancel passed in is " + e.Cancel.ToString());
System.Diagnostics.Debug.WriteLine("Handler 2: Setting Event.Cancel to " + bool.TrueString);
}

private void CancelHandlerThree(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 3: Event.Cancel passed in is " + e.Cancel.ToString());
}

private void MyForm_Load(object sender, System.EventArgs e) {
MyCancelEvent += new CancelEventHandler(CancelHandlerOne);
MyCancelEvent += new CancelEventHandler(CancelHandlerTwo);
MyCancelEvent += new CancelEventHandler(CancelHandlerThree);
}

private void button1_Click(object sender, System.EventArgs e) {
CancelEventArgs evt = new CancelEventArgs(false);
if (MyCancelEvent != null)
MyCancelEvent(this, evt);
System.Diagnostics.Debug.WriteLine("Event.Cancel after event call is " + evt.Cancel.ToString());
}

Pressing the button produces the following output:

Handler 1: Event.Cancel passed in is False
Handler 2: Event.Cancel passed in is False
Handler 2: Setting Event.Cancel to True
Handler 3: Event.Cancel passed in is False
Event.Cancel after event call is False
 
Where's the e.Cancel = true;?

-mike
MVP

When using an event with a delegate type of CancelEventHandler, shouldn't the delegate be checking to see if the Cancel property on the event object has been set to true and stop execution upon the first 'cancel' it encounters? It seems you will only get the cancel information for the last event hanlder to process, and all previous are effectively ignored.

Am I missing something?

Here is a quick example to show what I mean:

public class MyForm : Form {
public event CancelEventHandler MyCancelEvent;

private void CancelHandlerOne(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 1: Event.Cancel passed in is " + e.Cancel.ToString());
}


private void CancelHandlerTwo(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 2: Event.Cancel passed in is " + e.Cancel.ToString());
System.Diagnostics.Debug.WriteLine("Handler 2: Setting Event.Cancel to " + bool.TrueString);
}

private void CancelHandlerThree(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 3: Event.Cancel passed in is " + e.Cancel.ToString());
}

private void MyForm_Load(object sender, System.EventArgs e) {
MyCancelEvent += new CancelEventHandler(CancelHandlerOne);
MyCancelEvent += new CancelEventHandler(CancelHandlerTwo);
MyCancelEvent += new CancelEventHandler(CancelHandlerThree);
}

private void button1_Click(object sender, System.EventArgs e) {
CancelEventArgs evt = new CancelEventArgs(false);
if (MyCancelEvent != null)
MyCancelEvent(this, evt);
System.Diagnostics.Debug.WriteLine("Event.Cancel after event call is " + evt.Cancel.ToString());
}

Pressing the button produces the following output:

Handler 1: Event.Cancel passed in is False
Handler 2: Event.Cancel passed in is False
Handler 2: Setting Event.Cancel to True
Handler 3: Event.Cancel passed in is False
Event.Cancel after event call is False
 
Sorry, yes I failed to include the setting of the value. The event handlers should look like:

private void CancelHandlerTwo(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 2: Event.Cancel passed in is " + e.Cancel.ToString());
System.Diagnostics.Debug.WriteLine("Handler 2: Setting Event.Cancel to " + bool.TrueString);
e.Cancel = true;
}

private void CancelHandlerThree(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 3: Event.Cancel passed in is " + e.Cancel.ToString());
System.Diagnostics.Debug.WriteLine("Handler 3: Setting Event.Cancel to " + bool.FalseString);
e.Cancel = false;
}

And the output would then be:

Handler 1: Event.Cancel passed in is False
Handler 2: Event.Cancel passed in is False
Handler 2: Setting Event.Cancel to True
Handler 3: Event.Cancel passed in is True
Handler 3: Setting Event.Cancel to False
Event.Cancel after event call is False

I guess each handler could take responsibility for inspecting the inital value of the Cancel property on the event when passed in, but this isn't really called out in the documentation.

Where's the e.Cancel = true;?

-mike
MVP

When using an event with a delegate type of CancelEventHandler, shouldn't the delegate be checking to see if the Cancel property on the event object has been set to true and stop execution upon the first 'cancel' it encounters? It seems you will only get the cancel information for the last event hanlder to process, and all previous are effectively ignored.

Am I missing something?

Here is a quick example to show what I mean:

public class MyForm : Form {
public event CancelEventHandler MyCancelEvent;

private void CancelHandlerOne(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 1: Event.Cancel passed in is " + e.Cancel.ToString());
}


private void CancelHandlerTwo(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 2: Event.Cancel passed in is " + e.Cancel.ToString());
System.Diagnostics.Debug.WriteLine("Handler 2: Setting Event.Cancel to " + bool.TrueString);
}

private void CancelHandlerThree(object sender, CancelEventArgs e) {
System.Diagnostics.Debug.WriteLine("Handler 3: Event.Cancel passed in is " + e.Cancel.ToString());
}

private void MyForm_Load(object sender, System.EventArgs e) {
MyCancelEvent += new CancelEventHandler(CancelHandlerOne);
MyCancelEvent += new CancelEventHandler(CancelHandlerTwo);
MyCancelEvent += new CancelEventHandler(CancelHandlerThree);
}

private void button1_Click(object sender, System.EventArgs e) {
CancelEventArgs evt = new CancelEventArgs(false);
if (MyCancelEvent != null)
MyCancelEvent(this, evt);
System.Diagnostics.Debug.WriteLine("Event.Cancel after event call is " + evt.Cancel.ToString());
}

Pressing the button produces the following output:

Handler 1: Event.Cancel passed in is False
Handler 2: Event.Cancel passed in is False
Handler 2: Setting Event.Cancel to True
Handler 3: Event.Cancel passed in is False
Event.Cancel after event call is False
 
Back
Top