by kirupa |
1 March
2007
In the
previous page you learned how to add an event handler
using nothing but code. Now that you have an idea of how to
add event handlers, let's look at the two arguments they
take in greater detail.
Like I mentioned earlier, the event handler takes in two
arguments - a sender and an event. In many cases, you really
don't have to know much about them. For example, in the code
from earlier reproduced below, I am not even using either
sender or
e in my method's body:
- private
void
ButtonOkClicked(object
sender,
RoutedEventArgs
e)
- {
- this.Close();
- }
But, you will run into cases where you want to do more
than just have one control bound to an event handler. When
dealing with many interactive controls created using code,
you'll find that knowing more about the sender and event can
be helpful.
If you want know exactly which control triggered the event,
you will need to modify the sender object. The problem,
though, is that your controls are of types like Button, Text
Field, Checkbox, etc. The argument is of type object.
Unfortunately, you cannot simply type in
Button foo = sender.
What you need to do is typecast the object into the type
of the control that called it. The following code shows an
example of how I access the sender Button:
- private
void
ButtonOkClicked(object
sender,
RoutedEventArgs
e)
- {
- Button
clickedButton
= (Button)
sender;
- MessageBox.Show(clickedButton.Name);
- }
Notice that I create a new Button object called
clickedButton that casts my sender object as a Button also.
This allows me to access my button's properties just as if I
were manipulating my button directly by name.
When casting, you should make sure that you are actually
allowed to cast to that object. For example, I cannot cast
my sender object as Checkbox even though both it and a
Button can be based on an object.
Despite us not knowing what the
object type for sender really refers to, internally,
WPF has a good idea :P
If you do try to cast something to a type that it cannot be
cast to, you will receive an InvalidCastException:
[ I receive an InvalidCastException when tricking a checkbox
to behave like a button ]
If you are in a situation where you don't know what the
type of the control you clicked on is, you can use the
GetType property to find out:
- private
void
ButtonOkClicked(object
sender,
RoutedEventArgs
e)
- {
- MessageBox.Show(sender.GetType().Name);
- }
Now that you have a good idea of how to access the
sending object, let me touch back on a topic that I left
incomplete earlier. Earlier, I mentioned that the above
approach is just as good as if I were "manipulating my
button directly by name." The
question is, why am I not directly manipulating the button?
The reason is that, when you have many controls such as
an array of Buttons that map to the same event handler, you
cannot easily explicitly access each button individually.
For example, check out the following mini-application that
draws many styled buttons and allows you to interact with
them individually:
[ a small demo that shows why code-based event handling is
often needed ]
Click here to
run the WPF demo and view/download the source code for the above application.
In the above application, when you click on a button, the
button's name is displayed a as a message box. Because I am
creating each button dynamically using code, I have to cast
the sender object in my event handler so that I can know
which button has been rolled over.
In this section, I explained how to use the sender object to
determine what object is passed in. You are not limited to
using just the sender though. You can actually use your
event e itself to cast the source of the event into what you
want:
Button clickedButton = e.Source as
Button;
The reason I did not explain the above code in this section
because it logically makes more sense to have two arguments
standing for two different things - the object and the event
We are almost done with this article! On the next page
page I will wrap things up and discuss what the event
argument can help you to do.
Onwards to the
next page!
|