WPF的依赖属性和附加属性

本文详细解析了WPF中的依赖属性,它提供了属性变化通知、限制和验证功能,简化了应用开发并节约内存。依赖属性通过哈希表存储,解决了WinForm中每个控件属性重复存储的问题。此外,依赖属性支持多种设置方式,如表达式、样式和数据绑定。文章通过实例展示了如何定义和使用依赖属性,强调了其在WPF核心特性中的关键作用。
摘要由CSDN通过智能技术生成

一:依赖属性的全面解析

  听到依赖属性,自然联想到C#中属性的概念。C#中属性是抽象模型的核心部分,而依赖属性是专门基于WPF创建的。在WPF库实现中,依赖属性使用普通的C#属性进行了包装,使得我们可以通过和以前一样的方式来使用依赖属性,但我们必须明确,在WPF中我们大多数都在使用依赖属性,而不是使用属性。依赖属性重要性在于,在WPF核心特性,如动画、数据绑定以及样式中都需要使用到依赖属性。既然WPF引入了依赖属性,也自然有其引入的道理。WPF中的依赖属性主要有以下三个优点:

  • 依赖属性加入了属性变化通知、限制、验证等功能。这样可以使我们更方便地实现应用,同时大大减少了代码量。许多之前需要写很多代码才能实现的功能,在WPF中可以轻松实现。
  • 节约内存:在WinForm中,每个UI控件的属性都赋予了初始值,这样每个相同的控件在内存中都会保存一份初始值。而WPF依赖属性很好地解决了这个问题,它内部实现使用哈希表存储机制,对多个相同控件的相同属性的值都只保存一份。关于依赖属性如何节约内存的更多内容参考:WPF的依赖属性是怎么节约内存的
  • 支持多种提供对象:可以通过多种方式来设置依赖属性的值。可以配合表达式、样式和绑定来对依赖属性设置值。

1.1 依赖属性的定义

  上面介绍了依赖属性所带来的好处,这时候,问题又来了,怎样自己定义一个依赖属性呢?C#属性的定义大家再熟悉不过了。下面通过把C#属性进行改写成依赖属性的方式来介绍依赖属性的定义。下面是一个属性的定义:

1 public class Person

2     {

3         public string Name { get; set; }

6     }

在把上面属性改写为依赖属性之前,下面总结下定义依赖属性的步骤:

  1. 让依赖属性的所在类型继承自DependencyObject类。
  2. 使用public static 声明一个DependencyProperty的变量,该变量就是真正的依赖属性。
  3. 在类型的静态构造函数中通过Register方法完成依赖属性的元数据注册。
  4. 提供一个依赖属性的包装属性,通过这个属性来完成对依赖属性的读写操作。

  根据上面的四个步骤,下面来把Name属性来改写成一个依赖属性,具体的实现代码如下所示:

// 1. 使类型继承DependencyObject类

    public class Person : DependencyObject

    {

        // 2. 声明一个静态只读的DependencyProperty 字段

        public static readonly DependencyProperty nameProperty;

       

        static Person()

        {

            // 3. 注册定义的依赖属性

            nameProperty = DependencyProperty.Register("Name", typeof(string), typeof(Person),

                new PropertyMetadata("Learning Hard",OnValueChanged));

        }

        // 4. 属性包装器,通过它来读取和设置我们刚才注册的依赖属性

        public string Name

        {

            get { return (string)GetValue(nameProperty); }

            set { SetValue(nameProperty, value); }

        }

        private static void OnValueChanged(DependencyObject dpobj, DependencyPropertyChangedEventArgs e)

        {

            // 当只发生改变时回调的方法

        }

    }

  从上面代码可以看出,依赖属性是通过调用DependencyObject的GetValue和SetValue来对依赖属性进行读写的。它使用哈希表来进行存储的,对应的Key就是属性的HashCode值,而值(Value)则是注册的DependencyPropery;而C#中的属性是类私有字段的封装,可以通过对该字段进行操作来对属性进行读写。总结为:属性是字段的包装,WPF中使用属性对依赖属性进行包装。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值