原文 http://www.cnblogs.com/mgen/archive/2011/06/19/2084553.html
示例程序:
如上程序截图,一目了然典型的主从模式绑定应用,如果里面的数据不是用XML来存储而是已经初始化好的C#对象(比如国家是Country类的对 象,名字是Name属性,Provinces属性保存一个Province集合,代表国家的省/州,Province类包含Name属性代表名 称,Cities属性代表一些列City类对象……)那么主从模式绑定可以很简单的这样写:
1. 设置最外层DataContext为一系列的“国家”(“国家”集合)
2. 国家ListBox直接绑定
3. 省/州ListBox的ItemsSource为: {Binding Path=Provinces} (或者/Provinces)
4. 城市ListBox的ItemsSource为: {Binding Path=Province/Cities}
(注意所有ListBox的IsSynchronizedWithCurrentItem都设置成True)
但是如果放在Xml数据上,由于绑定上要用到XPath属性而不是Path属性,因此上述传统方案不适用,解决方案就是通过直接绑定所属
ListBox的SelectedItem值,然后再在这个值上进行XPath查询。注意第二层绑定直接用XPath,没有绑定最外层ListBox的
SelectedItem。ListBox代码如下:
<HeaderedContentControl>
<ListBox ItemsSource="{Binding}"
DisplayMemberPath="@name"
IsSynchronizedWithCurrentItem="True"/>
</HeaderedContentControl>
<HeaderedContentControl Header="省/州"
Grid.Column="1">
<ListBox Name="lbxProvince"
ItemsSource="{Binding XPath=province}"
DisplayMemberPath="@name"
IsSynchronizedWithCurrentItem="True"/>
</HeaderedContentControl>
<HeaderedContentControl Header="城市"
Grid.Column="2">
<ListBox DataContext="{Binding ElementName=lbxProvince, Path=SelectedItem}"
ItemsSource="{Binding XPath=city}"
IsSynchronizedWithCurrentItem="True"/>
</HeaderedContentControl>
完整的XAML代码
<Window.Resources>
<XmlDataProvider x:Key="xml" XPath="/countries/country">
<!-- 示例数据 -->
<x:XData>
<countries xmlns="">
<country name="中国">
<province name="陕西">
<city>西安</city>
<city>宝鸡</city>
</province>
<province name="山西">
<city>太原</city>
<city>大同</city>
</province>
<province name="内蒙古自治区">
<city>呼和浩特</city>
<city>包头</city>
<city>集宁</city>
</province>
<province name="河北">
<city>石家庄</city>
<city>保定</city>
</province>
</country>
<country name="美国">
<province name="加利福尼亚">
<city>洛杉矶</city>
<city>圣迭戈</city>
</province>
<province name="福罗里达">
<city>杰克逊维尔</city>
<city>迈阿密</city>
</province>
</country>
</countries>
</x:XData>
</XmlDataProvider>
<Style TargetType="HeaderedContentControl">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="HeaderedContentControl">
<DockPanel>
<Border DockPanel.Dock="Top"
Margin="3"
CornerRadius="3"
Background="DarkRed">
<TextBlock Text="{TemplateBinding Header}"
HorizontalAlignment="Center"
Foreground="White"></TextBlock>
</Border>
<ContentPresenter ContentSource="Content"
ContentTemplate="{TemplateBinding ContentTemplate}"></ContentPresenter>
</DockPanel>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style TargetType="ListBoxItem">
<Setter Property="SnapsToDevicePixels" Value="true"/>
<Setter Property="OverridesDefaultStyle" Value="true"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="ListBoxItem">
<Border Name="Border"
Padding="2"
SnapsToDevicePixels="true">
<ContentPresenter />
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsSelected" Value="true">
<Setter TargetName="Border" Property="Background" Value="YellowGreen"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
<Grid DataContext="{Binding Source={StaticResource xml}}">
<Grid.ColumnDefinitions>
<ColumnDefinition></ColumnDefinition>
<ColumnDefinition></ColumnDefinition>
<ColumnDefinition></ColumnDefinition>
</Grid.ColumnDefinitions>
<HeaderedContentControl Header="国家">
<ListBox ItemsSource="{Binding}"
DisplayMemberPath="@name"
IsSynchronizedWithCurrentItem="True"></ListBox>
</HeaderedContentControl>
<HeaderedContentControl Header="省/州"
Grid.Column="1">
<ListBox Name="lbxProvince"
ItemsSource="{Binding XPath=province}"
DisplayMemberPath="@name"
IsSynchronizedWithCurrentItem="True"></ListBox>
</HeaderedContentControl>
<HeaderedContentControl Header="城市"
Grid.Column="2">
<ListBox DataContext="{Binding ElementName=lbxProvince, Path=SelectedItem}"
ItemsSource="{Binding XPath=city}"
IsSynchronizedWithCurrentItem="True"></ListBox>
</HeaderedContentControl>
</Grid>