关于.net:WPF界面应用开发技巧绑定到列集合

6次阅读

共计 5935 个字符,预计需要花费 15 分钟才能阅读完成。

点击获取工具 >>

DevExpress WPF 领有 120+ 个控件和库,将帮忙您交付满足甚至超出企业需要的高性能业务应用程序。通过 DevExpress WPF 能创立有着弱小互动性能的 XAML 根底应用程序,这些应用程序专一于当代客户的需要和构建将来新一代反对触摸的解决方案。

应用模型视图 ViewModel(MVVM)架构模式设计 WPF 应用程序时,可能须要形容模型或 ViewModel 中的列。网格能够绑定到蕴含列设置的对象汇合,该对象设置在 Model 或 ViewModel 中进行了形容,从而最大限度地缩小了“暗藏代码”的需要。

实现视图模型

假如一个雇员视图模型,它包含以下类:

  • Employee – 蕴含员工信息(例如名字和姓氏,职务等)的数据对象。
  • ViewModel – 员工视图模型。
  • EmployeeData – 提供要在网格控件中显示的员工信息。
  • Column – 形容网格列,此类提供的属性对应于所有类型的网格列的通用设置。
  • ComboBoxColumn – 对应于 ComboBoxEdit in-place 编辑器的网格列,此类提供 Source 属性,其中蕴含组合框我的项目的列表(在此示例中,这些城市)。
  • SettingsType – 枚举用于编辑单元格值的 in-place 编辑器的可能类型。

C#

`using System;
using System.Collections;
using System.Collections.Generic;
using System.Collections.ObjectModel;

namespace Model {
public class ViewModel {
public List<string> Cities {get; private set;}
// Returns a list of employees so that they can be bound to the grid control.
public List<Employee> Source {get; private set;}
// The collection of grid columns.
public ObservableCollection<Column> Columns {get; private set;}
public ViewModel() {
Source = EmployeeData.DataSource;
List<string> _cities = new List<string>();
foreach (Employee employee in Source) {
if (!_cities.Contains(employee.City))
_cities.Add(employee.City);
}
Cities = _cities;
Columns = new ObservableCollection<Column>() {
new Column() { FieldName = “FirstName”, Settings = SettingsType.Default},
new Column() { FieldName = “LastName”, Settings = SettingsType.Default},
new Column() { FieldName = “JobTitle”, Settings = SettingsType.Default},
new Column() { FieldName = “BirthDate”, Settings = SettingsType.Default},
new ComboColumn() { FieldName = “City”, Settings = SettingsType.Combo, Source = Cities}
};
}
}
// The data item.
public class Employee {
public string FirstName {get; set;}
public string LastName {get; set;}
public string JobTitle {get; set;}
public string City {get; set;}
public DateTime BirthDate {get; set;}
}
public class EmployeeData : List<Employee> {
public static List<Employee> DataSource {
get {
List<Employee> list = new List<Employee>();
list.Add(new Employee() {
FirstName = “Nathan”,
LastName = “White”,
City = “NY”,
JobTitle = “Sales Manager”,
BirthDate = new DateTime(1970, 1, 10) });
return list;
}
}
}
public class Column {
// Specifies the name of a data source field to which the column is bound.
public string FieldName {get; set;}
// Specifies the type of an in-place editor used to edit column values.
public SettingsType Settings {get; set;}
}
// Corresponds to a column with the combo box in-place editor.
public class ComboColumn : Column {
// The source of combo box items.
public IList Source {get; set;}
}
public enum SettingsType {Default, Combo}
}`

留神 :如果将 Columns 汇合调配给网格控件后可能会更改,则它应实现 INotifyCollectionChanged,以便网格中可主动反映 View Model 内所做的更改。

列模板和选择器

网格控件基于列模板生成列,创立多个模板,每种列类型一个模板。应用单个模板,您能够在有限数量的网格控件中创立有限数量的列。在此示例中,有两个列模板:_DefaultColumnTemplate_和_ComboColumnTemplate_。

为防止绑定到列属性时的性能问题,请应用 dxci:DependencyObjectExtensions.DataContext 附加属性,请参见上面的示例。

XAML

`<!—->
xmlns:dxci=”http://schemas.devexpress.com/winfx/2008/xaml/core/internal”
<!—->
<DataTemplate x:Key=”DefaultColumnTemplate”>
<ContentControl>
<dxg:GridColumn FieldName=”{Binding Path=(dxci:DependencyObjectExtensions.DataContext).FieldName, RelativeSource={RelativeSource Self}}”
Header=”{Binding Path=(dxci:DependencyObjectExtensions.DataContext).Header, RelativeSource={RelativeSource Self}}”
Width=”{Binding Path=(dxci:DependencyObjectExtensions.DataContext).Width, RelativeSource={RelativeSource Self}}” />
</ContentControl>
</DataTemplate>`

要依据列的类型抉择所需的模板,请应用模板选择器。在此示例中,模板选择器由 ColumnTemplateSelector 类示意。

XAML

`<Window x:Class=”WpfApplication10.MainWindow”
xmlns=”http://schemas.microsoft.com/winfx/2006/xaml/presentation”
xmlns:x=”http://schemas.microsoft.com/winfx/2006/xaml”
Title=”MainWindow” Height=”350″ Width=”525″
xmlns:dxg=”http://schemas.devexpress.com/winfx/2008/xaml/grid”
xmlns:dxe=”http://schemas.devexpress.com/winfx/2008/xaml/editors”
xmlns:dx=”http://schemas.devexpress.com/winfx/2008/xaml/core”
xmlns:dxci=”http://schemas.devexpress.com/winfx/2008/xaml/core/internal”
xmlns:model=”clr-namespace:Model”
xmlns:view=”clr-namespace:View”>
<Window.DataContext>
<model:ViewModel/>
</Window.DataContext>
<Window.Resources>
<view:ColumnTemplateSelector x:Key=”ColumnTemplateSelector”/>
<DataTemplate x:Key=”DefaultColumnTemplate”>
<ContentControl>
<dxg:GridColumn FieldName=”{Binding Path=(dxci:DependencyObjectExtensions.DataContext).FieldName, RelativeSource={RelativeSource Self}}”/>
</ContentControl>
</DataTemplate>
<DataTemplate x:Key=”ComboColumnTemplate”>
<ContentControl>
<dxg:GridColumn FieldName=”{Binding Path=(dxci:DependencyObjectExtensions.DataContext).FieldName, RelativeSource={RelativeSource Self}}”>
<dxg:GridColumn.EditSettings>
<dxe:ComboBoxEditSettings ItemsSource=”{Binding Source}”/>
</dxg:GridColumn.EditSettings>
</dxg:GridColumn>
</ContentControl>
</DataTemplate>
</Window.Resources>
<Grid>
</Grid>
</Window>`

C#

`using System.Windows;
using System.Windows.Controls;
using Model;

namespace View {
public class ColumnTemplateSelector : DataTemplateSelector {
public override DataTemplate SelectTemplate(object item, DependencyObject container) {
Column column = (Column)item;
return (DataTemplate)((Control)container).FindResource(column.Settings + “ColumnTemplate”);
}
}
}`

留神 :如果能够应用单个模板形容所有网格列,则无需创立列模板选择器,而是将此模板调配给网格的 DataControlBase.ColumnGeneratorTemplate 属性。

留神 :您能够创立一种款式来指定应用不同模板生成的所有列共有的设置,您能够在款式内指定对 ViewModel 属性的绑定(请参见上面的 FieldName):

XAML

`<Window.Resources>
<Style x:Key=”ColumnStyle” TargetType=”dxg:GridColumn”>
<Setter Property=”FilterPopupMode” Value=”CheckedList”/>
<Setter Property=”FieldName” Value=”{Binding Path=(dxci:DependencyObjectExtensions.DataContext).FieldName, RelativeSource={RelativeSource Self}}”/>
</Style>
</Window.Resources>`

该款式应调配给 DataControlBase.ColumnGeneratorStyle 属性。

自定义 WPF DXGrid

最初,指定网格的 DataControlBase.ItemsSource,DataControlBase.ColumnsSource 和 DataControlBase.ColumnGeneratorTemplateSelector。DataControlBase.ItemsSource 属性指定网格的数据源,DataControlBase.ColumnsSource 属性指定网格从中生成列的源,DataControlBase.ColumnGeneratorTemplateSelector 属性指定列模板选择器,该选择器依据其类型为每个列返回一个模板。

XAML

`<Grid>
<dxg:GridControl Name=”grid”
ItemsSource=”{Binding Source}”
ColumnsSource=”{Binding Columns}”
ColumnGeneratorTemplateSelector=”{StaticResource ColumnTemplateSelector}”>
<dxg:GridControl.View>
<dxg:TableView Name=”tableView1″
AutoWidth=”True”
NavigationStyle=”Cell” />
</dxg:GridControl.View>
</dxg:GridControl>
</Grid>`

下图显示了后果。

正文完
 0