Windows Phone7 中实现主从视图
在实际开发中,经常会使用到主从的显示,当选中一个父项,则子项的集合自动进行修改,我们可以使用传统的SelectedIndexChanged修改去实现,但是通常情况下借助于collectionViewSource类更方便的来实现。
准备工作:
1.新建实体类
职工类:
public class Employee { public int Number { get; set; } public string Name { get; set; } public string Sex { get; set; } public int BirthYear { get; set; } }
部门类:
public class Department { public string DeptName { get; set; } public ObservableCollection<Employee> Employees { get; set; } }
自定义集合类(关键):
public class DepartmentList:ObservableCollection<Department> { public DepartmentList() { ObservableCollection<Employee> employees1 = new ObservableCollection<Employee>() { new Employee{ Number=2012, Name="MagicBoy", Sex="男", BirthYear=2000}, new Employee{ Number=1001, Name="ListenFly", Sex="男", BirthYear=1990}, new Employee{ Number=2555,Name="Tank", Sex="男", BirthYear=1980} }; ObservableCollection<Employee> employees2 = new ObservableCollection<Employee>() { new Employee{ Number=2012, Name="Harry", Sex="男", BirthYear=2000}, new Employee{ Number=1001, Name="Fly", Sex="男", BirthYear=1990}, new Employee{ Number=2555,Name="MayDay", Sex="男", BirthYear=1980} }; this.Add (new Department{ DeptName="录音部", Employees=employees1}); this.Add(new Department { DeptName = "唱片部", Employees = employees2 }); } }
一共创建了三个类,一个职工类,一个部门类,部门类和职工类是一对多的关系,所以在部门类中有一个职工的集合;最后一个类是自定义集合,顾名思义,实现了ObservableCollection<Deparment>,然后在类中添加了两个Department对象(同时初始化职工类的数据,这样便有了一对多的数据).
然后看XAML怎么使用:
首先在phone中引用对当前命名空间的引用,前缀为local,然后声明资源;资源包括一个DepartmentList的对象,一个CollectionViewSource的对象(source属性表明该数据源,在这里赋值为DepartmentList,这样便可以进行主动的实现,后边会讲到),同时为了让ListBox显示更好的效果(多列),在此创建了一个模板,用于显示职工信息。
<phone:PhoneApplicationPage.Resources> <local:DepartmentList x:Key="depList"></local:DepartmentList> <CollectionViewSource x:Key="departmentView" Source="{StaticResource depList}"></CollectionViewSource> <DataTemplate x:Key="dtEmployees"> <StackPanel Height="50" HorizontalAlignment="Center" Width="480" VerticalAlignment="Top" Orientation="Horizontal"> <TextBlock Height="50" HorizontalAlignment="Left" Text="{Binding Number}" VerticalAlignment="Top" Width="120"></TextBlock> <TextBlock Height="50" HorizontalAlignment="Left" Text="{Binding Name}" VerticalAlignment="Top" Width="120"></TextBlock> <TextBlock Height="50" HorizontalAlignment="Left" Text="{Binding Sex}" VerticalAlignment="Top" Width="120"></TextBlock> <TextBlock Height="50" HorizontalAlignment="Left" Text="{Binding BirthYear}" VerticalAlignment="Top" Width="120"></TextBlock> </StackPanel> </DataTemplate> </phone:PhoneApplicationPage.Resources>
看下显示部分的代码:
<Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0"> <Grid.RowDefinitions> <RowDefinition></RowDefinition> <RowDefinition></RowDefinition> </Grid.RowDefinitions> <ListBox x:Name="listDepartment" Grid.Row="0" DisplayMemberPath="DeptName"
ItemsSource="{Binding Source={StaticResource departmentView}}"></ListBox> <ListBox x:Name="listEmployees" Grid.Row="1" VerticalAlignment="Top" Height="400" ItemTemplate="{StaticResource dtEmployees}"
ItemsSource="{Binding Path=CurrentItem.Employees,Source={StaticResource departmentView}}"> </ListBox> </Grid>
代码很简单,两个ListBox构成,这个不是重点,重点的属性的设置,可以看到设置listDepartment(部门列表)的DisplayMemberPath为部门名称,同时设置ItemSource为
很奇怪的表达式ItemsSource="{Binding Source={StaticResource departmentView}}" ,慢慢来分析,Binding不用解释就是绑定,Source为指向一个数据源,这里
数据源就是在资源中创建的collectionViewSource,由于我们指定了listDepartment的DisplayMemberPath为DepName,所以只会显示部门信息。
然后来看第二个ListBox,listEmployees先是指定了ItemTemplate,后头去看我们的这个模板,可以看到在模板中使用一个StackPanel横向放了四个TextBlock,同时
设置Text绑定为一个个属性。我们指定listEmployeest的项模板为资源中创建的,重点不是这个,重点同样为ItemsSource的设置,
ItemsSource="{Binding Path=CurrentItem.Employees,Source={StaticResource departmentView}}",这个看起来比刚才的还要复杂,没关系,道理是一样的。
首先我们会发现这个表达式中后半部分和listDeparment是一样的,那就是Source={StaticResource departmentView},说明这两个ListBox的数据源是一致的,重点
是前边的Path=CurrentItem.Employees,很神奇,这个CurrentItem就是代表当前绑定源departmentView的当前选中项,这个CollectionViewSource会自动识别(其实
可以省略的),所以CurrentItem.Employees就是当前department对应的Employees.到此Windows Phone中实现简单的主从显示就完成了,附效果图和源码.