by
kirupa | 19 November 2007
In the
previous page,
you created another dependency property called
RectangleColor that allows you to easily change the
background color of the rounded rectangle in your
user control. Just like before, you copied and
pasted some code I provided, but unlike before,
there are some differences, so let's take a look at
the code and see what is interesting:
- public
Brush
RectangleColor
- {
- get
- {
- return
(Brush)
GetValue(RectangleColorProperty);
- }
- set
- {
- SetValue(RectangleColorProperty,
value);
- }
- }
In the above section of code, we create the CLR
wrapper for our new dependency property called
RectangleColor. Just like before with InfoText, you
have a get/set implementation that ties you into the
WPF property system via GetValue and SetValue.
Finally, notice that the return value of our
dependency property is of
type Brush.
- public
static
readonly
DependencyProperty
RectangleColorProperty
=
-
DependencyProperty.Register(
-
"RectangleColor",
-
typeof(Brush),
-
typeof(InfoRectangle),
-
new
FrameworkPropertyMetadata(null,
-
FrameworkPropertyMetadataOptions.AffectsRender,
-
new
PropertyChangedCallback(ChangeColor)));
Here is our public, static, and read-only
DependencyProperty declaration where we register our
RectangleColor in WPF's property system. Much of
this should be review. The first argument to our
Register method is the name of our dependency
property, RectangleColor. The second argument is the
return type of our property, and in our case, it is
a Brush. The final, third argument that should be
familiar to you is the type of this dependency
property's owner. Our owner is still the
InfoRectangle class, so that is what we specified..
- public
static
readonly
DependencyProperty
RectangleColorProperty
=
-
DependencyProperty.Register(
-
"RectangleColor",
-
typeof(Brush),
-
typeof(InfoRectangle),
-
new
FrameworkPropertyMetadata(null,
-
FrameworkPropertyMetadataOptions.AffectsRender,
-
new
PropertyChangedCallback(ChangeColor)));
The last argument you pass in to our register
method is our FrameworkPropertyMetadata object.
That hasn't since what you did before with InfoText.
What is different now is the number of arguments you
pass into our new FrameworkPropertyMetadata
constructor, for there are overloaded methods and
then there are
overloaded methods. The
FrameworkPropertyMetadata constructor falls in the
latter category with a whopping eleven variants:
Anyway, we are passing in three arguments into
our FrameworkPropertyMetadata constructor. The first
argument sets the default value of our dependency
property. I am simply keeping it at null. The second
argument sets some extra metadata for our property
that defines how it will impact other properties and
controls in your applications. Let's explore that
further.
Dependency properties do not always just refer to
simple data that is loosely attached to the WPF
property system. In many cases, your dependency
property affects layout, data binding, how things
are rendered, etc. It is helpful to call out what
your dependency property, and that is what we do in
the above code. Because we are modifying a Brush
that visually affects how an object looks, I am
specifying the AffectsRender item from the
FrameworkPropertyMetadataOptions enumerator.
The third and final argument is where I specify
our familiar property callback method. Whenever a
change is made to RectangleColor such as changing
the color via XAML or using Set via code, then this
method, called ChangeColor in our case, gets called.
Let's take a look at ChangeColor.
- private
static
void
ChangeColor(DependencyObject
source,
DependencyPropertyChangedEventArgs
e)
- {
- (source
as
InfoRectangle).BackgroundRectangle.Fill
=
e.NewValue
as
Brush;
- }
Because this is static method, we have no way of
using the this
keyword to reference your current object. That part
is review. We cast
our source as the InfoRectangle type and directly
set our BackgroundRectangle's Fill property using
our event argument's NewValue property. Because our
dependency property is of type Brush, I cast the new
value as Brush also.
Notice that, unlike with InfoText, I am not
creating a separate method to handle assigning our
Fill property the new value. There is no right or
wrong way to do that, so I just wanted to show that
it is possible to apply your property changes
directly via your callback method without having to
use a separate helper method also.
We are nearing the end of this tutorial with the
last page coming up! I will discuss why dependency
properties are useful and demonstrate their
usefulness by animating our RectangleColor property.
Onwards to the
next page!
|