背水一战 Windows 10 (22) - 绑定: 通过 Binding 绑定对象, 通过 x:Bind 绑定对象, 通过 Binding 绑定集合, 通过 x:Bind 绑定集合, 通过 Binding 绑定字典表
背水一战 Windows 10 (22) - 绑定: 通过 Binding 绑定对象, 通过 x:Bind 绑定对象, 通过 Binding 绑定集合, 通过 x:Bind 绑定集合, 通过 Binding 绑定字典表
作者:webabcd
介绍
背水一战 Windows 10 之 绑定
- 通过 Binding 绑定对象
- 通过 x:Bind 绑定对象
- 通过 Binding 绑定集合
- 通过 x:Bind 绑定集合
- 通过 Binding 绑定字典表
示例
1、演示如何通过 Binding 绑定对象
Bind/BindingModel.xaml
<Page x:Class="Windows10.Bind.BindingModel" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:Windows10.Bind" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Name="root" Background="Transparent"> <StackPanel Margin="10 0 10 10"> <TextBlock Name="lblMsg" Margin="5" /> <TextBox Text="{Binding Name, Mode=TwoWay}" Margin="5" /> <TextBox Text="{Binding Age, Mode=TwoWay}" Margin="5" /> <ToggleSwitch IsOn="{Binding IsMale, Mode=TwoWay}" OffContent="女" OnContent="男" Header="性别" Margin="5" /> </StackPanel> </Grid> </Page>
Bind/BindingModel.xaml.cs
/* * 演示如何通过 Binding 绑定对象 * * * 如果需要数据源在属性值发生变化时对外通知,则需要实现 INotifyPropertyChanged 接口(为了简化实现,建议继承 Common/BindableBase.cs 这个类) * PropertyChanged - 对象的属性的值发生变化时触发的事件 */ using System; using System.ComponentModel; using Windows.System.Threading; using Windows.UI.Core; using Windows.UI.Xaml.Controls; using Windows10.Common; namespace Windows10.Bind { public sealed partial class BindingModel : Page { private Employee _employee; public BindingModel() { this.InitializeComponent(); this.Loaded += BindingModel_Loaded; } void BindingModel_Loaded(object sender, Windows.UI.Xaml.RoutedEventArgs e) { // 创建一个需要绑定的实体对象(注:Employee 实现了 INotifyPropertyChanged 接口) _employee = new Employee(); _employee.Name = "webabcd"; _employee.Age = 33; _employee.IsMale = true; // Employee 对象的属性的值发生变化时触发的事件(源自 INotifyPropertyChanged 接口) _employee.PropertyChanged += _employee_PropertyChanged; // 指定数据上下文(绑定的数据源) root.DataContext = _employee; // 每 5 秒更新一次数据 ThreadPoolTimer.CreatePeriodicTimer ( (timer) => { var ignored = Dispatcher.RunAsync ( CoreDispatcherPriority.Normal, () => { Random random = new Random(); _employee.Age = random.Next(10, 100); _employee.IsMale = random.Next() % 2 == 0 ? true : false; } ); }, TimeSpan.FromMilliseconds(5000) ); } // 每次属性的值发生变化时,显示变化后的结果 void _employee_PropertyChanged(object sender, PropertyChangedEventArgs e) { lblMsg.Text = "属性:“" + e.PropertyName + "”的值发生了变化"; lblMsg.Text += Environment.NewLine; lblMsg.Text += string.Format("当前的值为:Name-{0}, Age-{1}, IsMale-{2}", _employee.Name, _employee.Age, _employee.IsMale); } } }
2、演示如何通过 x:Bind 绑定对象
Bind/BindModel.xaml
<Page x:Class="Windows10.Bind.BindModel" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:Windows10.Bind" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Background="Transparent"> <StackPanel Margin="10 0 10 10"> <TextBlock Name="lblMsg" Margin="5" /> <TextBox Text="{x:Bind CurrentEmployee.Name, Mode=TwoWay}" Margin="5" /> <TextBox Text="{x:Bind CurrentEmployee.Age, Mode=TwoWay}" Margin="5" /> <ToggleSwitch IsOn="{x:Bind CurrentEmployee.IsMale, Mode=TwoWay}" OffContent="女" OnContent="男" Header="性别" Margin="5" /> </StackPanel> </Grid> </Page>
Bind/BindModel.xaml.cs
/* * 演示 x:Bind 绑定的相关知识点 * * * 如果需要数据源在属性值发生变化时对外通知,则需要实现 INotifyPropertyChanged 接口(为了简化实现,建议继承 Common/BindableBase.cs 这个类) * PropertyChanged - 对象的属性的值发生变化时触发的事件 */ using System; using System.Collections.ObjectModel; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows10.Common; namespace Windows10.Bind { // x:Bind 的数据上下文就是它所属的 Page 或 UserControl public sealed partial class BindDemo : Page { public BindDemo() { this.InitializeComponent(); } // 事件绑定到方法,无参数 private void EventBindNoArgs() { CurrentEmployee.Name = "wanglei" + new Random().Next(1000, 10000).ToString(); } // 事件绑定到方法,参数与对应的事件的参数相同 private void EventBindRegularArgs(object sender, RoutedEventArgs e) { CurrentEmployee.Name = "wanglei" + new Random().Next(1000, 10000).ToString(); } // 事件绑定到方法,参数与对应的事件的参数相同,但是其中的事件参数为 object 类型 private void EventBindBaseArgs(object sender, object e) { CurrentEmployee.Name = "wanglei" + new Random().Next(1000, 10000).ToString(); } public Employee CurrentEmployee { get; set; } = new Employee() { Name = "wanglei", Age = 36, IsMale = true }; public ObservableCollection<Employee> AllEmployees { get; set; } = TestData.GetEmployees(5); } }
3、示如何通过 Binding 绑定集合
Bind/BindingCollection.xaml
<Page x:Class="Windows10.Bind.BindingCollection" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:Windows10.Bind" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Background="Transparent"> <StackPanel Orientation="Vertical" VerticalAlignment="Top" Margin="10 0 10 10"> <Button Name="btnDelete" Content="删除第 1 条数据" Click="btnDelete_Click" Margin="5" /> <Button Name="btnUpdate" Content="更新前 2 条数据" Click="btnUpdate_Click" Margin="5" /> <ListView x:Name="listView" Margin="5"> <ListView.ItemTemplate> <DataTemplate> <Border Background="Blue" Width="200" CornerRadius="3" HorizontalAlignment="Left"> <TextBlock Text="{Binding Name}" /> </Border> </DataTemplate> </ListView.ItemTemplate> </ListView> </StackPanel> </Grid> </Page>
Bind/BindingCollection.xaml.cs
/* * 演示如何通过 Binding 绑定集合 * * * 如果需要集合数据源在数据添加,删除,更新时对外通知,则需要实现 INotifyCollectionChanged 接口 * CollectionChanged - 集合数据在发生添加,删除,更新时触发的事件 */ using System; using System.Collections.ObjectModel; using System.Collections.Specialized; using System.Linq; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows10.Common; namespace Windows10.Bind { public sealed partial class BindingCollection : Page { // ObservableCollection<T> 实现了 INotifyCollectionChanged 接口 private ObservableCollection<Employee> _employees; public BindingCollection() { this.InitializeComponent(); this.Loaded += BindingCollection_Loaded; } void BindingCollection_Loaded(object sender, RoutedEventArgs e) { _employees = new ObservableCollection<Employee>(TestData.GetEmployees()); // 集合数据在发生添加,删除,更新时触发的事件(源自 INotifyCollectionChanged 接口) _employees.CollectionChanged += _employees_CollectionChanged; // 指定 ListView 的数据源 listView.ItemsSource = _employees; } void _employees_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) { /* * e.Action - 引发此事件的操作类型(NotifyCollectionChangedAction 枚举) * Add, Remove, Replace, Move, Reset * e.OldItems - Remove, Replace, Move 操作时影响的数据列表 * e.OldStartingIndex - Remove, Replace, Move 操作发生处的索引 * e.NewItems - 更改中所涉及的新的数据列表 * e.NewStartingIndex - 更改中所涉及的新的数据列表的发生处的索引 */ } private void btnDelete_Click(object sender, RoutedEventArgs e) { // 此处的通知来自 INotifyCollectionChanged 接口 _employees.RemoveAt(0); } private void btnUpdate_Click(object sender, RoutedEventArgs e) { Random random = new Random(); // 此处的通知来自实现了 INotifyPropertyChanged 接口的 Employee _employees.First().Name = random.Next(1000, 10000).ToString(); // 此处的通知来自 INotifyCollectionChanged 接口 _employees[1] = new Employee() { Name = random.Next(1000, 10000).ToString() }; } } }
4、演示如何通过 x:Bind 绑定集合
Bind/BindCollection.xaml
<Page x:Class="Windows10.Bind.BindCollection" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:Windows10.Bind" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:common="using:Windows10.Common" mc:Ignorable="d"> <Grid Background="Transparent"> <StackPanel Orientation="Vertical" VerticalAlignment="Top" Margin="10 0 10 10"> <Button Name="btnDelete" Content="删除第 1 条数据" Click="btnDelete_Click" Margin="5" /> <Button Name="btnUpdate" Content="更新前 2 条数据" Click="btnUpdate_Click" Margin="5" /> <ListView x:Name="listView" ItemsSource="{x:Bind Employees}" Margin="5"> <ListView.ItemTemplate> <DataTemplate x:DataType="common:Employee"> <Border Background="Blue" Width="200" CornerRadius="3" HorizontalAlignment="Left"> <TextBlock Text="{x:Bind Name, Mode=OneWay}" /> </Border> </DataTemplate> </ListView.ItemTemplate> </ListView> </StackPanel> </Grid> </Page>
Bind/BindCollection.xaml.cs
/* * 演示如何通过 x:Bind 绑定集合 * * * 如果需要集合数据源在数据添加,删除,更新时对外通知,则需要实现 INotifyCollectionChanged 接口 * CollectionChanged - 集合数据在发生添加,删除,更新时触发的事件 */ using System; using System.Collections.ObjectModel; using System.Collections.Specialized; using System.Linq; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows10.Common; namespace Windows10.Bind { public sealed partial class BindCollection : Page { // 数据源 // ObservableCollection<T> 实现了 INotifyCollectionChanged 接口 public ObservableCollection<Employee> Employees { get; set; } = new ObservableCollection<Employee>(TestData.GetEmployees()); public BindCollection() { this.InitializeComponent(); this.Loaded += BindCollection_Loaded; } void BindCollection_Loaded(object sender, RoutedEventArgs e) { // 集合数据在发生添加,删除,更新时触发的事件(源自 INotifyCollectionChanged 接口) Employees.CollectionChanged += Employees_CollectionChanged; } void Employees_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) { /* * e.Action - 引发此事件的操作类型(NotifyCollectionChangedAction 枚举) * Add, Remove, Replace, Move, Reset * e.OldItems - Remove, Replace, Move 操作时影响的数据列表 * e.OldStartingIndex - Remove, Replace, Move 操作发生处的索引 * e.NewItems - 更改中所涉及的新的数据列表 * e.NewStartingIndex - 更改中所涉及的新的数据列表的发生处的索引 */ } private void btnDelete_Click(object sender, RoutedEventArgs e) { // 此处的通知来自 INotifyCollectionChanged 接口 Employees.RemoveAt(0); } private void btnUpdate_Click(object sender, RoutedEventArgs e) { Random random = new Random(); // 此处的通知来自实现了 INotifyPropertyChanged 接口的 Employee Employees.First().Name = random.Next(1000, 10000).ToString(); // 此处的通知来自 INotifyCollectionChanged 接口 Employees[1] = new Employee() { Name = random.Next(1000, 10000).ToString() }; } } }
5、演示如何通过 Binding 绑定字典表
Bind/BindingDictionary.xaml
<Page x:Class="Windows10.Bind.BindingDictionary" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:Windows10.Bind" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Background="Transparent"> <StackPanel Margin="10 0 10 10"> <TextBlock Name="lblMsg" Margin="5" /> <ComboBox x:Name="combo" SelectionChanged="combo_SelectionChanged" Margin="5"> <ComboBox.ItemTemplate> <DataTemplate> <StackPanel Orientation="Horizontal"> <TextBlock Text="{Binding Key}"/> <TextBlock Text=" - "/> <TextBlock Text="{Binding Value}"/> </StackPanel> </DataTemplate> </ComboBox.ItemTemplate> </ComboBox> </StackPanel> </Grid> </Page>
Bind/BindingDictionary.xaml.cs
/* * 演示如何通过 Binding 绑定字典表 */ using System.Collections.Generic; using Windows.UI.Xaml.Controls; namespace Windows10.Bind { public sealed partial class BindingDictionary : Page { private Dictionary<string, string> _data; public BindingDictionary() { this.InitializeComponent(); _data = new Dictionary<string, string>(); _data.Add("key1", "value1"); _data.Add("key2", "value2"); _data.Add("key3", "value3"); combo.ItemsSource = _data; } private void combo_SelectionChanged(object sender, SelectionChangedEventArgs e) { KeyValuePair<string, string> selectedItem = (KeyValuePair<string, string>)combo.SelectedItem; lblMsg.Text = $"selectedItem: {selectedItem.Key}, {selectedItem.Value}"; } } }
OK
[源码下载]