本實(shí)例最終執(zhí)行效果:
左邊是一個(gè)ListBox,用來(lái)顯示用戶的主要信息;右邊是4個(gè)TextBox,用來(lái)顯示左邊ListBox中被選中用戶的詳細(xì)信息。
本實(shí)例中,存在一個(gè)XML格式的數(shù)據(jù)源,XML文件格式如下:
<?xml version="1.0"?>
<Company>
<Employee>
<ID>372401</ID>
<Name>徐棟</Name>
<Age>26</Age>
<Sex>男</Sex>
</Employee>
……
</Company>
接下來(lái),使用WPF的XAML語(yǔ)言來(lái)創(chuàng)建界面,訪問(wèn)該數(shù)據(jù)源。
對(duì)數(shù)據(jù)源的調(diào)用我放在<Window.Resources>中。通過(guò)<XmlDataProvider>標(biāo)記,實(shí)現(xiàn)對(duì)XML數(shù)據(jù)源的調(diào)用,x:Key是資源的引用的ID,Source是XML資源文件路徑,XPath指出XML文件內(nèi)部數(shù)據(jù)存放的路徑。
在<Window.Resources>還有另外兩個(gè)標(biāo)記,分別是DataTemplate和Style。
DataTemplate是ListBox的ListBoxItem中顯示的數(shù)據(jù)內(nèi)容,在DataTemplate中放置一個(gè)TextBlock用來(lái),將TextBlock的Text屬性與XML數(shù)據(jù)源中的Name標(biāo)記綁定,也就說(shuō)用來(lái)顯示XML文件中的Name。
Style是WPF的樣式。在這里,我們指定了本W(wǎng)indow中,所有的TextBlock都采用Style中定義的樣式。
整個(gè)Source中代碼如下:
<Window.Resources>
<XmlDataProvider x:Key="employeeSource" Source="Employees.xml" XPath="/Company/*"/>
<DataTemplate x:Key="showName">
<TextBlock Text="{Binding XPath=Name}" />
</DataTemplate>
<Style TargetType="{x:Type TextBlock}" >
<Setter Property="FontStyle" Value="Italic" />
<Setter Property="FontFamily" Value="Trebuchet MS" />
<Setter Property="FontSize" Value="12" />
</Style>
</Window.Resources>
資源文件已經(jīng)定義號(hào),然后在Windows中放置Grid布局控件來(lái)規(guī)劃窗口。在Grid上分別放置用來(lái)顯示名稱的ListBox和用來(lái)顯示相信用戶信息的TextBlock。在ListBox和TextBlock中顯示的數(shù)據(jù),來(lái)自上面定義的資源,這里通過(guò)綁定功能實(shí)現(xiàn)。
首先綁定ListBox。
首先將ListBox的ItemSource屬性與資源中的XmlDataProvider綁定,說(shuō)明ListBox中Item的數(shù)據(jù)源。
ItemsSource="{Binding Source={StaticResource employeeSource}}"
然后將ListBox的ItemTemplate屬性與資源中的DataTemplate 綁定,說(shuō)明ListBox中Item的數(shù)據(jù)顯示內(nèi)容。
ItemTemplate="{StaticResource showName}"
最后,非常重要的一點(diǎn),我們需要將ListBox與數(shù)據(jù)源設(shè)置為同步,這樣數(shù)據(jù)源中的游標(biāo)才會(huì)隨著選中ListBox中不同Item而移用。
IsSynchronizedWithCurrentItem="True"
這個(gè)ListBox的代碼如下:
<ListBox Grid.Column="0" Grid.Row="0" Margin="5,5,5,5" ItemsSource="{Binding Source={StaticResource employeeSource}}" ItemTemplate="{StaticResource showName}" IsSynchronizedWithCurrentItem="True"/>
通過(guò)以上設(shè)置,ListBox與數(shù)據(jù)源綁定結(jié)束,已經(jīng)在ListBox中列出XML中的Name數(shù)據(jù),接下來(lái)需要使用TextBlock顯示用戶詳細(xì)信息。
實(shí)現(xiàn)這個(gè)功能,我們需要定義四個(gè)TextBlock分別顯示XML中的ID、Name、Age 和Sex 四項(xiàng)數(shù)據(jù),然后將這個(gè)四個(gè)TextBlock的Text分別綁定XML中四項(xiàng)數(shù)據(jù)。這四個(gè)TextBlock實(shí)現(xiàn)方式基本相同,以顯示ID的TextBlock為例,說(shuō)明TextBlock的綁定方式。
TextBlock的數(shù)據(jù)源綁定ListBox不同,是采用DataContext來(lái)綁定。TextBlock的Text屬性與ID綁定。實(shí)現(xiàn)代碼如下:
<TextBlock>
ID: <TextBlock Margin="10,0,0,0" DataContext="{Binding Source={StaticResource employeeSource}}" Text="{Binding XPath=ID}"/>
</TextBlock>
至此,一個(gè)最簡(jiǎn)單的WPF與XML綁定的程序就已經(jīng)完成,可以實(shí)現(xiàn)文章開(kāi)頭處描寫的功能。
同時(shí),WPF還能夠與SQL數(shù)據(jù)源綁定,自定義的對(duì)象綁定,可見(jiàn)WPF的數(shù)據(jù)綁定功能非常強(qiáng)大;在這個(gè)XML綁定的程序,沒(méi)有一行C#的代碼,通過(guò)對(duì)XAML這種聲明式語(yǔ)言的修改,就能實(shí)現(xiàn)以前實(shí)現(xiàn)非常復(fù)雜的數(shù)據(jù)綁定功能,也體現(xiàn)了WPF簡(jiǎn)單之處。(徐棟)
本文附帶Demo的全部代碼如下:
XML文件(Employees.xml):
<?xml version="1.0"?>
<Company>
<Employee>
<ID>372401</ID>
<Name>徐棟</Name>
<Age>26</Age>
<Sex>男</Sex>
</Employee>
<Employee>
<ID>151806</ID>
<Name>呂布</Name>
<Age>36</Age>
<Sex>男</Sex>
</Employee>
<Employee>
<ID>108208</ID>
<Name>貂蟬</Name>
<Age>19</Age>
<Sex>女</Sex>
</Employee>
<Employee>
<ID>051806</ID>
<Name>關(guān)羽</Name>
<Age>36</Age>
<Sex>男</Sex>
</Employee>
</Company>
XAML文件(Windows1.XAML):
<Window x:Class="WPFDataBindingXML.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="WPFDataBindingXML" Height="300" Width="300"
>
<Window.Resources>
<XmlDataProvider x:Key="employeeSource" Source="Employees.xml" XPath="/Company/*"/>
<DataTemplate x:Key="showName">
<TextBlock Text="{Binding XPath=Name}" />
</DataTemplate>
<Style TargetType="{x:Type TextBlock}" >
<Setter Property="FontStyle" Value="Italic" />
<Setter Property="FontFamily" Value="Trebuchet MS" />
<Setter Property="FontSize" Value="12" />
</Style>
</Window.Resources>
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition/>
</Grid.RowDefinitions>
<ListBox Grid.Column="0" Grid.Row="0" Margin="5,5,5,5" ItemsSource="{Binding Source={StaticResource employeeSource}}" ItemTemplate="{StaticResource showName}" IsSynchronizedWithCurrentItem="True"/> <StackPanel Margin="5,5,5,5" Grid.Column="1" Grid.Row="0">
<TextBlock>
ID: <TextBlock Margin="10,0,0,0" DataContext="{Binding Source={StaticResource employeeSource}}" Text="{Binding XPath=ID}"/>
</TextBlock>
<TextBlock>
Name: <TextBlock Margin="10,0,0,0" DataContext="{Binding Source={StaticResource employeeSource}}" Text="{Binding XPath=Name}"/>
</TextBlock>
<TextBlock>
Age: <TextBlock Margin="10,0,0,0" DataContext="{Binding Source={StaticResource employeeSource}}" Text="{Binding XPath=Age}"/>
</TextBlock>
<TextBlock>
Sex: <TextBlock Margin="10,0,0,0" DataContext="{Binding Source={StaticResource employeeSource}}" Text="{Binding XPath=Sex}"/>
</TextBlock>
</StackPanel>
</Grid>
</Window>