微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

DependencyProperty

和传统属性的区别在哪里,为什么要搞出这样一个DependencyProperty呢?

  • 内存使用量。
    我们设计控件,不可避免的要设计很多控件的属性,高度,宽度等等,这样就会有大量(私有)字段的存在,一个继承树下来,低端的对象会无法避免的膨胀。而外部通过GetValue,SetValue暴露属性,内部维护这样一个EffectiveValueEntry的数组,顾名思义,只是维护了一个有效的、设置过值的列表,可以减少内存的使用量。
  • 传统属性的局限性。
    这个有很多,包括一个属性只能设置一个值,不能得到变化的通知,无法为现有的类添加新的属性等等。

在 MSDN 中,提到当你有下面四种情况时,应该考虑使用DependencyProperty:

 

一个Silverlight中创建 DependencyProperty 的例子

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using System.Windows.Media.Imaging;

namespace SilverlightApplication2
{
    public partial class SilverlightControl1 : UserControl
    { 

        /// /// Declare the dependency property as static,readonly field in your class.  /// 
        public static readonly DependencyProperty AquariumGraphicProperty 
            = DependencyProperty.Register(
          "AquariumGraphic",// Property name
          typeof(Uri),// Property type
          typeof(SilverlightControl1),// Type of the dependency property provider
          new PropertyMetadata(null,// 认的值
              new PropertyChangedCallback(OnUriChanged)               // Callback invoked on property value has changes
          )
        );

        /// /// Create the property and use the SetValue/GetValue methods of the DependencyObject class /// 
        public Uri AquariumGraphic
        {
            get { return (Uri)GetValue(AquariumGraphicProperty); }
            set { SetValue(AquariumGraphicProperty,value); }
        }
             
        public SilverlightControl1()
        {
            InitializeComponent();
        }        
     
        /// /// 值变化时,更新显示 /// 
        /// 
        /// 
        private static void OnUriChanged(DependencyObject d,DependencyPropertyChangedEventArgs e)
        {
            Shape sh = (Shape)d;
            ImageBrush ib = new ImageBrush();
            ib.ImageSource = new BitmapImage(e.NewValue as Uri);
            sh.Fill = ib;
        }

     
    }
}

我们首先来看看 AquariumGraphicProperty ,类型就是DependencyProperty,前面用了static readonly,一个单例模式,有DependencyProperty.Register,看起来像是往容器里注册,其实也差不多。

再来看AquariumGraphic,和传统的属性没什么区别,类型是 Uri 型,有get,set方法。只不过内部的实现分别调用了GetValue和SetValue,这两个方法是DependecyObject(简称DO,是WPF/Silverlight中所有可视Visual的基类)暴露出来的,传入的参数是AquariumGraphicProperty。

需要注意的是运行时,Xaml中是直接调用GetValue和SetValue的。所以,为了让使用XAML设置属性与使用代码设置属性一致,在属性包装器中除了GetValue和SetValue调用以外,不应该包含任何其他逻辑,这是非常重要的。如果需要添加自定义逻辑,应该在Register的回调函数添加

 

参考资料:

.Net3.0里的DependencyProperty(1):引入了DP的一些基本概念
http://www.cnblogs.com/yayx/archive/2007/05/26/761117.html

WPF里的DependencyProperty(2):DP的应用,主要想解释我们为什么要用它
http://www.cnblogs.com/yayx/archive/2008/04/20/1162963.html

WPF里的DependencyProperty(3):主要想演示下怎么用DP
http://www.cnblogs.com/yayx/archive/2008/04/22/1166064.html

WPF/Silverlight为什么要使用Canvas.SetLeft()这样的方法? :附属,从布局应用上解释了下为什么要有AttachedProperty
http://www.cnblogs.com/yayx/archive/2008/04/23/1167110.html

WPF里的DependencyProperty(4):介绍了DP的工作机制
http://www.cnblogs.com/yayx/archive/2008/04/24/1168738.html

WPF里的DependencyProperty(5) :介绍了PropertyMetadata和AttachedProperty
http://www.cnblogs.com/yayx/archive/2008/06/03/1213126.html

Windows Presentation Foundation 体系结构
http://msdn.microsoft.com/en-us/ms750441(zh-cn).aspx

如何学好WPF
http://www.cnblogs.com/zhouyongh/archive/2009/07/31/1536000.html

Tip: How to declare a dependency property in Silverlight?
http://www.silverlightshow.net/tips/Tip-How-to-declare-a-dependancy-property-in-Silverlight.aspx

WPF体系结构-- System.Windows.DependencyObject与智能的控件
http://bbniu.com/forum/thread-478-1-1.html

图解DotNet框架之九:WPF
http://www.cnblogs.com/xugao918/archive/2008/08/01/1258193.html

Silverlight自定义依赖项对象和依赖项属性
http://msdn.microsoft.com/zh-cn/library/cc903933(VS.95).aspx

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。

相关推荐