Create Custom Dependency Property In WPF

Introduction

 
Before understanding this article I would recommend you read about Dependency Property
 

How to create custom dependency property?

 
To create new dependency property we need to follow the below procedure,
  • Declare and register dependency property
  • For registered property set value using SetValue method and get value using GetValue method
  • Write a method to handle change done on dependency property
Example
 
We will add dependency property called “SetBackGroundRed” to CustomButton by inheriting Button class.To create custom dependency property we will follow the steps which we defined previously
 

Declare and register dependency property

 
While registering dependency property we need below parameters
  • Name of the property: In our case it is SetBackGroundRed
  • Type of property: In our case we will set as Bool
  • Type of owner property: In our case owner property will be CustomProperty
  • PropertyMetadata with Name of the method which handles change done on dependency property: in our case method which change done on dependency property is ChangeBackGround 
  1. public static readonly DependencyProperty dependencyProperty =  
  2.             DependencyProperty.Register("SetBackGroundRed"typeof(bool), typeof(CustomButton),  
  3.                 new PropertyMetadata(false,new PropertyChangedCallback(ChangeBackGround)));  
For registered property set value using SetValue method and get value using GetValue method
 
SetValue and GetValue are methods defined by DependencyObject Class
  1. public bool SetBackGroundRed  
  2. {  
  3.     get=> (bool)GetValue(dependencyProperty);  
  4.     set=> SetValue(dependencyProperty, value);  
  5. }  

Write a method to handle change done on dependency property

 
In the below code we can see that we provided a method to handle changes in dependency property using DependencyObject d and DependencyPropertyChangedEventArgs e like below. In the below example when property value is set as True we will set background as Red else CustomButton will have default value. 
 
DependencyObject defines the CustomButton instance
 
DependencyPropertyChangedEventArgs dfines the value which is set to SetBackGroundRed
  1. private static void ChangeBackGround(DependencyObject d, DependencyPropertyChangedEventArgs e)  
  2. {  
  3.      if((bool)e.NewValue)  
  4.         (d as CustomButton).Background = Brushes.Red;  
  5. }  
All code in single file looks like below
  1. using System.Windows;  
  2. using System.Windows.Controls;  
  3. using System.Windows.Media;  
  4.   
  5. namespace DependencyPropertiesSample  
  6. {  
  7.     public class CustomButton : Button  
  8.     {  
  9.         public static readonly DependencyProperty dependencyProperty =  
  10.             DependencyProperty.Register("SetBackGroundRed"typeof(bool), typeof(CustomButton),  
  11.                 new PropertyMetadata(false,new PropertyChangedCallback(ChangeBackGround)));         
  12.   
  13.         public bool SetBackGroundRed  
  14.         {  
  15.             get=> (bool)GetValue(dependencyProperty);  
  16.             set=> SetValue(dependencyProperty, value);  
  17.         }  
  18.   
  19.         private static void ChangeBackGround(DependencyObject d, DependencyPropertyChangedEventArgs e)  
  20.         {  
  21.             if((bool)e.NewValue)  
  22.                 (d as CustomButton).Background = Brushes.Red;  
  23.         }  
  24.     }  
  25. }  
In XAML side add below code
  1. <Window x:Class="DependencyPropertiesSample.MainWindow"  
  2.         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"  
  3.         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"  
  4.         xmlns:d="http://schemas.microsoft.com/expression/blend/2008"  
  5.         xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"  
  6.         xmlns:local="clr-namespace:DependencyPropertiesSample"  
  7.         mc:Ignorable="d" SizeToContent="WidthAndHeight" WindowStyle="None"  
  8.         AllowsTransparency="True" MouseDown="Window_MouseDown" BorderBrush="Silver" BorderThickness="2"  
  9.         Title="PersonView" Height="120" Width="400">  
  10.     <Grid>  
  11.         <Grid.RowDefinitions>  
  12.             <RowDefinition Height="30"/>  
  13.             <RowDefinition Height="80"/>  
  14.         </Grid.RowDefinitions>  
  15.         <Grid Grid.Row="0" Width="400" Background="Orange">  
  16.             <Label Content="Custom Dependency Property with example" FontSize="14" Foreground="White" FontWeight="SemiBold"/>  
  17.             <Button Height="24" Width="24" Name="btnClose" HorizontalAlignment="Right" FontWeight="Bold" Cursor="Hand"  
  18.                     VerticalAlignment="Center" Content="X" Click="BtnClose_Click" Focusable="False" Background="{x:Null}" Foreground="White" />  
  19.             <x:Code>  
  20.                 private void BtnClose_Click(object sender, RoutedEventArgs e)  
  21.                 {  
  22.                     Close();  
  23.                 }  
  24.                  private void Window_MouseDown(object sender, System.Windows.Input.MouseButtonEventArgs e)  
  25.                 {  
  26.                     try  
  27.                     {  
  28.                         this.DragMove();  
  29.                     }  
  30.                     catch   
  31.                     {  
  32.                     }  
  33.                 }  
  34.             </x:Code>  
  35.         </Grid>         
  36.         <Grid Grid.Row="1" Background="White">  
  37.             <GroupBox Header="Custom Dependency Property" Height="60">  
  38.                 <local:CustomButton SetBackGroundRed="True" Width="200" Height="30" Content="Custom Button" Foreground="White" />  
  39.             </GroupBox>              
  40.         </Grid>  
  41.     </Grid>  
  42. </Window>  
In XAML we can see that we are handling CustomButton Background by Boolean variable SetBackGroundRed; i.e., if value is set to True background will become Red, else Background will have default Background color.
  1. <local:CustomButton SetBackGroundRed="True" Width="200" Height="30" Content="Custom Button" Foreground="White" />  
Below is the execution window when SetBackGroundRed=False 
 
 
Below is the execution window when SetBackGroundRed=True 
 
 

Summary

 
In this article we saw the how to create custom dependency property and how to handle the value change in dependency property.