有的大牛只写怎样怎样理解概念,喜欢讲一些概念,有的大牛干脆不写技术,有的大牛只会唯利是图,卖一些组件,我不是大牛,我喜欢帮助别人。
今天我们看看档案管理界面的数据查询与展示,先上一张图,调一下胃口。
这个界面主要的看点有DataGrID数据展示,分组,分页,Convert的使用等。首先我们来看一下界面的代码,这个布局方式采用GrID+StackPanel布局,代码如下。
<controls:ChilDWindow.Resources> <StateConvert:ArchiveStateConvert x:Key="ArchiveConvert"></StateConvert:ArchiveStateConvert> <StateConvert:SexConvert x:Key="SexConvert"></StateConvert:SexConvert> <LocalResource:ArchiveManageResource x:Key="LocalResource"></LocalResource:ArchiveManageResource> <Style x:Key="ColumnheaderStyle" targettype="sdk:DataGrIDColumnheader"> <Setter Property="FontSize" Value="12"></Setter> </Style> </controls:ChilDWindow.Resources> 省略部分代码 <TextBlock Text="{Binding tb_name,Source={StaticResource LocalResource}}" margin="10,0" FontSize="12" GrID.Row="0" GrID.Column="5"/> <sdk:autocompletebox WIDth="130" FontSize="12" GrID.Row="0" GrID.Column="6" ItemsSource="{Binding PersonList,Mode=OneWay}" SelectedItem="{Binding SelectedPerson,Mode=TwoWay}"/> <StackPanel GrID.Row="3" GrID.Column="2" GrID.ColumnSpan="3" margin="0,5,0" OrIEntation="Horizontal" HorizontalAlignment="Center"> <button Content="{Binding btn_Search,Source={StaticResource LocalResource}}" Command="{Binding queryCommands}" FontSize="12" WIDth="90" margin="0,0"/> <button Content="{Binding btn_reset,Source={StaticResource LocalResource}}" FontSize="12" WIDth="90"/> </StackPanel> </GrID> </border> <sdk:DataGrID GrID.Row="0" GrID.Column="0" GrID.ColumnSpan="2" IsReadonly="True" x:name="dgArchiveList" ItemsSource="{Binding MyCollectionVIEwSource.VIEw,Mode=OneWay}" autoGenerateColumns="False" AlternatingRowBackground="Silver" ColumnheaderHeight="20" FroZenColumnCount="3" CanUserReorderColumns="True" VerticalScrollbarVisibility="auto" HorizontalScrollbarVisibility="auto" AreRowGroupheadersFroZen="False" SelectionMode="Single" CanUserSortColumns="False" LoadingRowGroup="MyDataGrID_LoadingRowGroup"> <sdk:DataGrID.Columns> <!--<sdk:DataGrIDTemplateColumn header="选择"> <sdk:DataGrIDTemplateColumn.CellTemplate> <DataTemplate> <CheckBox Checked="{Binding IsChecked,Mode=TwoWay}"/> </DataTemplate> </sdk:DataGrIDTemplateColumn.CellTemplate> </sdk:DataGrIDTemplateColumn>--> <sdk:DataGrIDTextColumn Binding="{Binding ArchiveState,Mode=OneWay,Converter={StaticResource ArchiveConvert}}"> <sdk:DataGrIDTextColumn.headerStyle> <Style targettype="sdk:DataGrIDColumnheader"> <Setter Property="ContentTemplate"> <Setter.Value> <DataTemplate> <TextBlock Text="{Binding GrID_header_ArchiveState,Source={StaticResource LocalResource}}"/> </DataTemplate> </Setter.Value> </Setter> <Setter Property="FontSize" Value="12"/> </Style> </sdk:DataGrIDTextColumn.headerStyle> </sdk:DataGrIDTextColumn> <sdk:DataGrIDTextColumn headerStyle="{StaticResource ColumnheaderStyle}" header="档案编号" Binding="{Binding ArchiveNo,Mode=OneWay}" /> 省略部分代码 </sdk:DataGrID.Columns> </sdk:DataGrID> 省略部分代码 <StackPanel GrID.Row="1" GrID.Column="1" OrIEntation="Horizontal" HorizontalAlignment="Right" margin="0,10,0"> <Hyperlinkbutton x:name="linkFirst" Foreground="Blue" Tag="First" IsEnabled="{Binding IslinkFirstEnable,Mode=OneWay}" Click="Hyperlinkbutton_Click" Content="{Binding link_First,Source={StaticResource LocalResource}}" FontSize="12"/> <Hyperlinkbutton x:name="linkPrevIoUs" Foreground="Blue" Tag="PrevIoUs" IsEnabled="{Binding IslinkPrevIoUsEnable,Mode=OneWay}" Click="Hyperlinkbutton_Click" Content="{Binding link_PrevIoUs,Source={StaticResource LocalResource}}" FontSize="12"/> <Hyperlinkbutton x:name="linkNext" Foreground="Blue" Tag="Next" IsEnabled="{Binding IslinkNextEnable,Mode=OneWay}" Click="Hyperlinkbutton_Click" Content="{Binding link_Next,Source={StaticResource LocalResource}}" FontSize="12"/> <Hyperlinkbutton x:name="linkLast" Foreground="Blue" Tag="Last" IsEnabled="{Binding IslinkLastEnable,Mode=OneWay}" Click="Hyperlinkbutton_Click" Content="{Binding link_Last,Source={StaticResource LocalResource}}" FontSize="12"/> </StackPanel> </controls:ChilDWindow>
查询条件中使用了autoComplete,<sdk:autocompletebox WIDth="130" FontSize="12" GrID.Row="0" GrID.Column="6" ItemsSource="{Binding PersonList,Mode=OneWay}" SelectedItem="{Binding SelectedPerson,Mode=TwoWay}"/>。首先其ItemsSource绑定的是一个List<string>,SelectedItem绑定的是选择项,我们看看效果。
当我在姓名文本框中输入“李”的时侯,所有姓李的人都列出来了。当我选择了一个人名以后,SelectedPerson的值将会变为我选择的人名,因为SelectedPerson是个双向绑定。ok我们再往下看,我们发现前台代码的DataGrID列中有这么一行。
<sdk:DataGrIDTextColumn Binding="{Binding ArchiveState,Converter={StaticResource ArchiveConvert}}"> <sdk:DataGrIDTextColumn.headerStyle> <Style targettype="sdk:DataGrIDColumnheader"> <Setter Property="ContentTemplate"> <Setter.Value> <DataTemplate> <TextBlock Text="{Binding GrID_header_ArchiveState,Source={StaticResource LocalResource}}"/> </DataTemplate> </Setter.Value> </Setter> <Setter Property="FontSize" Value="12"/> </Style> </sdk:DataGrIDTextColumn.headerStyle> </sdk:DataGrIDTextColumn>
这个写法是因为假如我们要给列头国际化,因为DataGrID的DataGrIDTextColumn的header是不可以绑定Resource文件的(因为Columnheader是DependencyObject类型的,而不是DepenencyProperty),所以我们只能给它指定Style。这就是这个列和其他列不同的原因,其他列是直接设置header的。OK,再看这么一段代码
<sdk:DataGrIDTextColumn headerStyle="{StaticResource ColumnheaderStyle}" header="性别" Binding="{Binding Sex,Converter={StaticResource SexConvert}}"/>
我们发现Binding中有个Converter属性,这个是用来转换性别的,假如Sex的值是1,转换为男,假如是0,转换为女。首先需要在页面引用这个实现了IValueConverter 的类,如上代码xmlns:StateConvert="clr-namespace:ClIEnt.Common;assembly=Common"先引用命名空间,在引用类<StateConvert:SexConvert x:Key="SexConvert"></StateConvert:SexConvert>,我们看看这个SexConvert 类,如下
namespace ClIEnt.Common { public class SexConvert : IValueConverter { public object Convert(object value, Type targettype, object parameter, CultureInfo culture) { string s = (string)value; switch (s) { case "1": s = "男"; break; case "0": s = "女"; break; } return s; } public object ConvertBack(object value, CultureInfo culture) { string strValue = value.ToString().Equals("男") ? "1" : "0"; return strValue; } } }
实现Convert和ConvertBack即可。接下来我们要看的是DataGrID的分页和分组,和上一篇文章一样,查询绑定的是Command,所以逻辑都在viewmodel中。我们看看代码
public ICommand queryCommands { get { queryCommand queryCommand = new queryCommand(); queryCommand.query += delegate() { this.CurrentPage = 1; var queryRequest = new SearchRequest() { ArchiveNo = this.ArchiveNo, GraduateStartDate = this.StartDate, GraduateEndDate = this.EndDate, name = this.SelectedPerson, Sex = this.Sex, BirthDay = this.BirthDay, IDCard = this.IDCard, Professional = this.Professional, GraduateSchool = this.GraduateSchool, Education = this.Education, ArchiveState = this.ArchiveState, PageIndex = -1, PageSize = this.PageSize }; GetData(queryRequest); }; return queryCommand; } } public voID GetData(SearchRequest queryRequest) { string requestStr = SerIEalizeHelper<SearchRequest>.JsonSerialize<SearchRequest>(queryRequest); ArchiveInfoService.ArchiveInfoServiceClIEnt clIEnt = new ArchiveInfoService.ArchiveInfoServiceClIEnt(); List<ArchiveInfoEntity> List = new List<ArchiveInfoEntity>(); clIEnt.GetPersonInfoListCompleted += delegate(object sender, ArchiveInfoService.GetPersonInfoListCompletedEventArgs e) { ArchiveInfoEntity entity; e.Result.PersonInfoList.ForEach(r => { entity = new ArchiveInfoEntity(); entity.IsChecked = false; entity.ArchiveNo = r.no; entity.ArchiveState = r.state; entity.BirthDay = r.birth; entity.Education = r.education_level; entity.GraduateSchool = r.graduate_school; entity.GraduateYear = r.graduate_year; entity.IDCardNo = r.ID_card; entity.IsChecked = false; entity.name = r.name; entity.Professional = r.professional; entity.Sex = r.sex; List.Add(entity); }); this.RecordCount = e.Result.RecordCount; this.TotalPage = e.Result.RecordCount % PageSize == 0 ? e.Result.RecordCount / PageSize : e.Result.RecordCount / PageSize + 1; this.SetlinkBtnEnable(queryRequest); CollectionVIEwSource collectionVIEwSource = new CollectionVIEwSource(); collectionVIEwSource.source = List; collectionVIEwSource.GroupDescriptions.Add(new PropertyGroupDescription("ArchiveState")); this.MyCollectionVIEwSource = collectionVIEwSource; }; clIEnt.GetPersonInfoListAsync(requestStr); } private voID SetlinkBtnEnable(SearchRequest request) { this.SetlinkEnable(true); if (this.TotalPage <= 1) { this.SetlinkEnable(false); } if (request.PageIndex == this.TotalPage-2) { this.IslinkNextEnable = false; this.IslinkLastEnable = false; } if (request.PageIndex == -1 && this.TotalPage > 1) { this.IslinkFirstEnable = false; this.IslinkPrevIoUsEnable = false; } } private voID SetlinkEnable(bool isEnable) { this.IslinkFirstEnable = isEnable; this.IslinkLastEnable = isEnable; this.IslinkNextEnable = isEnable; this.IslinkPrevIoUsEnable = isEnable; }
从前台代码我们可以看出,分页按钮的isEnabled状态分别绑定viewmodel中的IslinkFirstEnable ,IslinkLastEnable,IslinkNextEnable,IslinkPrevIoUsEnable。在GetData中有这么一段代码,就是获取到数据源以后,我们对其进行了分组,
this.RecordCount = e.Result.RecordCount; this.TotalPage = e.Result.RecordCount % PageSize == 0 ? e.Result.RecordCount / PageSize : e.Result.RecordCount / PageSize + 1; this.SetlinkBtnEnable(queryRequest); CollectionVIEwSource collectionVIEwSource = new CollectionVIEwSource(); collectionVIEwSource.source = List; collectionVIEwSource.GroupDescriptions.Add(new PropertyGroupDescription("ArchiveState")); this.MyCollectionVIEwSource = collectionVIEwSource;
我们获取到分页数据以后,根据ArchiveState属性进行分组,然后绑定到界面,注意,DataGrID界面绑定代码ItemsSource="{Binding MyCollectionVIEwSource.VIEw,Mode=OneWay}",注意在这里是MyCollectionVIEwSource.VIEw。接下来是分页,分页是我自己定义的一个分页。我们看看页面cs代码
private voID Hyperlinkbutton_Click(object sender, RoutedEventArgs e) { Hyperlinkbutton hyperlink = sender as Hyperlinkbutton; var queryRequest = new SearchRequest() { ArchiveNo = archiveModel.ArchiveNo, GraduateStartDate = archiveModel.StartDate, GraduateEndDate = archiveModel.EndDate, name = archiveModel.SelectedPerson, Sex = archiveModel.Sex, BirthDay = archiveModel.BirthDay, IDCard = archiveModel.IDCard, Professional = archiveModel.Professional, GraduateSchool = archiveModel.GraduateSchool, Education = archiveModel.Education, ArchiveState = archiveModel.ArchiveState, PageSize = archiveModel.PageSize, }; switch (hyperlink.Tag.ToString()) { case "First": archiveModel.PageIndex = -1; break; case "Next": archiveModel.PageIndex++; break; case "PrevIoUs": archiveModel.PageIndex--; break; case "Last": archiveModel.PageIndex = archiveModel.TotalPage-2; break; } archiveModel.CurrentPage = archiveModel.PageIndex + 2; queryRequest.PageIndex = archiveModel.PageIndex; archiveModel.GetData(queryRequest); }
在分页的时候调用viewmodel的GetData方法,在viewmodel中动态的设置分页按钮的enabled状态。为了方便大家理解我的意思,我会把viewmodel的cs作为附件供大家下载。ok,我们看看服务端分页代码,如下
public SearchResponse GetPersonInfoList(string searchRequest) { SearchRequest searchRequests = SerializeHelper.JsonDeserialize<SearchRequest>(searchRequest); Iqueryable<Person_Info> personInfo = misInfoEntitIEs.person_info .Where(p => (string.IsNullOrEmpty(searchRequests.ArchiveNo) ? true : searchRequests.ArchiveNo.Contains(p.no)) && (string.IsNullOrEmpty(searchRequests.name) ? true : p.name == searchRequests.name) && (string.IsNullOrEmpty(searchRequests.Sex) ? true : p.sex == searchRequests.Sex) && (string.IsNullOrEmpty(searchRequests.IDCard) ? true : p.ID_card.Contains(searchRequests.IDCard)) && (string.IsNullOrEmpty(searchRequests.Professional) ? true : p.professional == searchRequests.Professional) && (string.IsNullOrEmpty(searchRequests.Education) ? true : p.education_level == searchRequests.Education) && (string.IsNullOrEmpty(searchRequests.ArchiveState) ? true : p.state == searchRequests.ArchiveState) && (!searchRequests.GraduateStartDate.HasValue ? true : p.graduate_year >= searchRequests.GraduateStartDate.Value.Year) && (!searchRequests.GraduateEndDate.HasValue ? true : p.graduate_year <= searchRequests.GraduateEndDate.Value.Year) && (!searchRequests.BirthDay.HasValue ? true : p.birth == searchRequests.BirthDay)); IEnumerable<Person_Info> personInfos = personInfo.AsEnumerable().OrderBy(p => p.name) .Skip(searchRequests.PageSize * (searchRequests.PageIndex + 1)) .Take(searchRequests.PageSize); foreach (var person in personInfos) { person.education_level = misInfoEntitIEs.codes.SingleOrDefault(c => c.ename == "EDUCATION" && c.data == person.education_level).display_content; } return new SearchResponse() { PersonInfoList = personInfos.ToList(), RecordCount = personInfo.Count() }; }
在这里因为我的服务端的数据访问层是EF,所以采用的是liNQ to EntitIEs的方式。今天就写到这里,因为篇幅有限,有很多代码没有贴,需要代码的同志可以留言,我可以发给大家,或者加入.net群205217091,我可以共享给大家。
@H_785_3012@ 总结以上是内存溢出为你收集整理的Silverlight MVVM 贴近实战(四)全部内容,希望文章能够帮你解决Silverlight MVVM 贴近实战(四)所遇到的程序开发问题。
如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)