通过Demo学WPF—数据绑定(一)✨
前言
想学习WPF,但是看视频教程觉得太耗时间,直接看文档又觉得似懂非懂,因此想通过看Demo代码+文档的方式进行学习。
准备
微软官方其实提供了WPF的一些Demo,地址为:microsoft/WPF-Samples: Repository for WPF related samples (github.com)
将其克隆到本地,有很多的Demo代码:

新建一个空白解决方案:

添加现有项目:

选择Data Binding 中的 SimpleBinding:

项目文件如下所示:

查看SimpleBinding这个Demo的效果:

学习这个Demo
数据绑定的概念
首先需要知道数据绑定的基本概念,数据绑定是在应用 UI 与其显示的数据之间建立连接的过程。 如果绑定具有正确的设置,并且数据提供适当的通知,则在数据更改其值时,绑定到该数据的元素会自动反映更改。 数据绑定还意味着,如果元素中数据的外部表示形式发生更改,则基础数据可以自动进行更新以反映更改。 例如,如果用户编辑 TextBox 元素中的值,则基础数据值会自动更新以反映该更改。
现在再来看一下,数据绑定的模型图:

现在我们根据这张模型图,学习这个Demo。
这个模型图表示数据绑定至少需要三个东西:
- 绑定目标
- 绑定
- 绑定源
现在我们分别看看这个demo里面,这三个东西在哪?
绑定目标
我们发现这个demo的绑定目标是元素TextBox的Text属性与TextBlock的Text属性。
绑定

这是一个C#类,查找在该Demo中,哪里出现了Binding?
发现在MainWindow.xaml中出现了Binding,有两处地方,分别是:
<TextBox>
<TextBox.Text>
<Binding Source="{StaticResource MyDataSource}" Path="PersonName"
UpdateSourceTrigger="PropertyChanged"/>
</TextBox.Text>
</TextBox>
与
<TextBlock Text="{Binding Source={StaticResource MyDataSource}, Path=PersonName}"/>
这两处都是在 XAML 中声明绑定。
<TextBox>
<TextBox.Text>
<Binding Source="{StaticResource MyDataSource}" Path="PersonName"
UpdateSourceTrigger="PropertyChanged"/>
</TextBox.Text>
</TextBox>
这种使用的是对象元素语法。
<TextBlock Text="{Binding Source={StaticResource MyDataSource}, Path=PersonName}"/>
这种使用的是标记扩展。
从这里我们接触到了Binding类的三个属性,Source、Path与UpdateSourceTrigger。
那它们分别是什么意思呢?
先来看下Source:

我们发现这个demo里,Source="{StaticResource MyDataSource},StaticResource MyDataSource又是什么呢?
在Window.Resources标签下有一行代码:

<local:Person x:Key="MyDataSource" PersonName="Joe"/>
<Window.Resources>标签在XAML中用于定义可以在整个窗口中重用的资源。这些资源可以是各种类型,包括样式、数据源、数据模板、颜色、画刷等。
<local:Person x:Key="MyDataSource" PersonName="Joe"/>这行代码创建了一个Person对象,并将其命名为"MyDataSource",该对象的PersonName属性设置为"Joe",这样你就可以在窗口的其他地方通过这个键来引用这个对象。
因此Source={StaticResource MyDataSource}的意思就是将Binding对象的Source属性设置为键为"MyDataSource"的资源,在这里也就是一个Person对象。
再来看看Path:

表示绑定源属性的路径。
Path="PersonName"表示绑定源是刚刚那个Person对象的PersonName属性。
最后再看看UpdateSourceTrigger:

这个属性可能就会难理解一点。
它表示当绑定目标怎么样时,绑定源的值应该被更新。
它的类型为枚举类型,有以下几个值:
| 值 | 含义 |
|---|---|
| Default | 绑定目标属性的默认 UpdateSourceTrigger 值。 大多数依赖属性的默认值为 PropertyChanged,而 Text 属性的默认值为 LostFocus。 |
| Explicit | 仅在调用 UpdateSource() 方法时更新绑定源。 |
| LostFocus | 每当绑定目标元素失去焦点时,都会更新绑定源。 |
| PropertyChanged | 每当绑定目标属性发生更改时,都会更新绑定源。 |
<Label>Enter a Name:</Label>
<TextBox>
<TextBox.Text>
<Binding Source="{StaticResource MyDataSource}" Path="PersonName"
UpdateSourceTrigger="PropertyChanged"/>
</TextBox.Text>
</TextBox>
我们会发现在这个demo中,TextBox.Text设置了UpdateSourceTrigger属性。
这是因为大多数依赖项属性的默认值为 PropertyChanged,而 Text 属性的默认值为 LostFocus。在这个demo中,我们不希望失去焦点才更新源数据,而是一发生改变就更新绑定源,因此设置UpdateSourceTrigger属性为PropertyChanged。
总结一下,我们遇到的关于Binding类的三个属性Source、Path与UpdateSourceTrigger:
| 属性名 | 含义 |
|---|---|
| Source | 获取或设置要用作绑定源的对象。 |
| Path | 获取或设置绑定源属性的路径。 |
| UpdateSourceTrigger | 获取或设置一个值,它可确定绑定源更新的时机。 |
现在我们已经介绍了绑定目标、绑定就差绑定源了。
绑定源
在数据绑定中,绑定源对象是指用户从其获取数据的对象。
在这个demo中,绑定源是一个Person对象。
查看Person类的代码:
using System.ComponentModel;
namespace SimpleBinding
{
// This class implements INotifyPropertyChanged
// to support one-way and two-way bindings
// (such that the UI element updates when the source
// has been changed dynamically)
public class Person : INotifyPropertyChanged
{
private string _name;
public Person()
{
}
public Person(string value)
{
_name = value;
}
public string PersonName
{
get { return _name; }
set
{
_name = value;
// Call OnPropertyChanged whenever the property is updated
OnPropertyChanged("PersonName");
}
}
// Declare the event
public event PropertyChangedEventHandler PropertyChanged;
// Create the OnPropertyChanged method to raise the event
protected void OnPropertyChanged(string name)
{
var handler = PropertyChanged;
handler?.Invoke(this, new PropertyChangedEventArgs(name));
}
}
}
首先这个Person类实现了INotifyPropertyChanged接口,我们来看下INotifyPropertyChanged接口:
public interface INotifyPropertyChanged
{
//
// 摘要:
// Occurs when a property value changes.
event PropertyChangedEventHandler? PropertyChanged;
}
包含一个PropertyChanged事件,因此该Person类必须实现接口的成员PropertyChanged。
当属性值被设置时,会调用OnPropertyChanged方法,从而触发事件。
INotifyPropertyChanged接口定义了一个PropertyChanged事件,当一个属性的值发生变化时,你可以触发这个事件。WPF的数据绑定引擎会监听这个事件,当事件被触发时,它会更新绑定的UI元素的值。
如果你的数据源没有实现这个接口,那么当数据源的属性值发生变化时,WPF的数据绑定引擎将无法知道这个变化,因此它将无法更新UI元素的值。
这意味着,如果你的数据源的属性值在运行时可能会发生变化,并且你希望这些变化能够自动反映到UI上,那么你的数据源就需要实现INotifyPropertyChanged接口。
总结
通过这个小Demo,我们明白了WPF中的数据绑定的三要素,绑定对象、绑定、绑定源。在这个demo中,我们学会了如何在xaml中声明绑定,知道了Binding的三个属性Source、Path与UpdateSourceTrigger的含义,明白了数据源为什么要实现INotifyPropertyChanged接口,学会了WPF中数据绑定的基本用法,希望对你有所帮助。
通过Demo学WPF—数据绑定(一)✨的更多相关文章
- 从PRISM开始学WPF(七)MVVM(三)事件聚合器EventAggregator-更新至Prism7.1
原文:从PRISM开始学WPF(七)MVVM(三)事件聚合器EventAggregator-更新至Prism7.1 事件聚合器EventAggregator [7.1updated]除了app部分,没 ...
- 从PRISM开始学WPF(七)MVVM(三)事件聚合器EventAggregator?
原文:从PRISM开始学WPF(七)MVVM(三)事件聚合器EventAggregator? 从PRISM开始学WPF(一)WPF? 从PRISM开始学WPF(二)Prism? 从PRISM开始学WP ...
- 微软原文翻译:适用于.Net Core的WPF数据绑定概述
原文链接,大部分是机器翻译,仅做了小部分修改.英.中文对照,看不懂的看英文. Data binding overview in WPF 2019/09/19 Data binding in Windo ...
- WPF 数据绑定Binding
什么是数据绑定? Windows Presentation Foundation (WPF) 数据绑定为应用程序提供了一种简单而一致的方法来显示数据以及与数据交互. 通过数据绑定,您可以对两个不同对象 ...
- WPF数据绑定Binding(二)
WPF数据绑定Binding(二) 1.UI控件直接的数据绑定 UI对象间的绑定,也是最基本的形式,通常是将源对象Source的某个属性值绑定 (拷贝) 到目标对象Destination的某个属性上. ...
- WPF——数据绑定(一)什么是数据绑定
注意:本人初学WPF,文中可能有表达或者技术性问题,欢迎指正!谢谢! 一:什么是数据绑定? “Windows Presentation Foundation (WPF) 数据绑定为应用程序提供了一种简 ...
- 剖析WPF数据绑定机制
引言 WPF框架采取的是MVVM模式,也就是数据驱动UI,UI控件(Controls)被严格地限制在表示层内,不会参与业务逻辑的处理,只是通过数据绑定(Data Binding)简单忠实地表达与之绑定 ...
- 从PRISM开始学WPF,Prism7更新了什么
当时我在搬运Prism6.3的sample代码的时候,就是因为网上的资料太老旧,万万没想到这给自己挖了一个坑,因为我在做笔记的时候,prism已经在更新7.0了 现在已经是7.2了,(lll¬ω¬), ...
- WPF 10天修炼 第十天- WPF数据绑定
WPF数据绑定 数据绑定到元素属性是将源对象指定为一个WPF元素,并且源属性是一个依赖属性,依赖属性内置了变更通知.当改变源对象依赖属性值之后,绑定目标可以立即得到更新,开发人员不需要手动编写响应事件 ...
- 从PRISM开始学WPF(八)导航Navigation-更新至Prism7.1
原文:从PRISM开始学WPF(八)导航Navigation-更新至Prism7.1 0x6Navigation [7.1updated] Navigation 在wpf中并没有变化 Basic Na ...
随机推荐
- Jmeter对各种接口类型的测试
JMeter对各种类型接口的测试 默认做接口测试前,已经给出明确的接口文档(如,http://test.nnzhp.cn/wiki/index.php?doc-view-59):本地配好了JMeter ...
- 白嫖:GPT-4
众所周知,GPT-4需要充OpenAI 的 Plus才能使用,Plus则需要每月20美金. 很多同学很想体验GPT-4,但一方面不想花钱,一方面想花也没那么容易花出去(懂的都懂) 我看到有人分享可以免 ...
- 升讯威在线客服系统:与QQ、微信的区别和优势
本系列文章详细介绍使用 .net core 和 WPF 开发 升讯威在线客服与营销系统 的过程.本产品已经成熟稳定并投入商用. 请访问:https://kf.shengxunwei.com 文章目录列 ...
- Mysql--编译安装5.6版本
1 下载编译工具 yum -y install cmake gcc gcc-c++ ncurses-devel autoconf 2 创建用户 目录 useradd -s /sbin/nologin ...
- CJ88 DUMP The ASSERT condition was violated
一.CJ88运行某个项目时DUMP,其他项目正常 The ASSERT condition was violated. 源代码位置为交易货币为空导致DUMP 经过长时间的源码调试,也只定位在查询语句这 ...
- VS2019 快速实现 C# 连接 MySQL 数据库并实现基本操作代码
一.工具: Visual Studio 2019 MySQL 数据库 二.添加动态链接: Visual Studio 中选择项目-> 管理NuGet程序包(N) -> 然后在浏览里面搜索 ...
- 深入浅出 ZooKeeper
ZooKeeper 是一个分布式协调服务 ,由 Apache 进行维护. ZooKeeper 可以视为一个高可用的文件系统. ZooKeeper 可以用于发布/订阅.负载均衡.命令服务.分布式协调/通 ...
- 技术文档 | 在Jenkins及GitlabCI中集成OpenSCA,轻松实现CI/CD开源风险治理
插播: OpenSCA-cli 现支持通过 homebrew 以及 winget 安装: Mac/Linux brew install opensca-cli Windows winget inst ...
- js md5 和java md5后的值不一样
开发发现js 对字符串md5 和 java对字符串md5 计算的结果居然不一样,后来找了一个匹配的这里记录一下 注:加密的对象中不能有空格,有空格md5后的结果就不一致,都是眼泪.. js md5算法 ...
- Element-ui 之 form表单套数组、表单数组套数组的校验rules
https://blog.csdn.net/qq_61553794/article/details/135451461