1. 前言

在UWP中DataTemplate是一个十分重要的功能,并且几乎无处不在,例如DataGrid中的DataGridTemplateColumn:

<controls:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal"
VerticalAlignment="Center">
<TextBlock Text="{x:Bind FirstName}" />
<TextBlock Text="{x:Bind LastName}" />
</StackPanel>
</DataTemplate>
</controls:DataGridTemplateColumn.CellTemplate>

而且DateTemplate(或ControlTemplate)极有可能需要由代码动态生成。

UWP大致上有两种使用代码生成DateTemplate的方式。

2. 使用资源字典

这其实并不是由代码动态生成DataTemplate,只是比较方便的从资源字典读取DataTemplate的邪道,一般来说不好意思暴露给项目外的用户。

创建一个UserControl,然后把父类从“UserControl”改为“ResourceDictionary”,然后在Xaml中编写DataTemplate,为这个DataTemplate的x:Name赋值,并且将x:FieldModifier改为“internal”(这样DataTemplate才可以作为一个字段被项目中的其它类访问),代码如下:

public sealed partial class XamlResource : ResourceDictionary
{
public XamlResource()
{
this.InitializeComponent();
}
}
<ResourceDictionary x:Class="App5.XamlResource"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:App5"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d">
<DataTemplate x:Name="ItemTemplate"
x:FieldModifier="internal" >
<TextBlock Text="{Binding Name}" />
</DataTemplate>
</ResourceDictionary>

使用起来也很方便:

XamlResource resource = new XamlResource();
ListControl.ItemTemplate = resource.ItemTemplate;

这种做法的好处是编辑Datatemplate时有智能感知和属性面板,不容易出错;调用起来也很简单。虽然不够动态,但我常常使用这种方式创建DataTemplate。

3. 使用XamlReader

XamlReader用于解析XAML并创建相应的对象树。文档里给出的例子是构建一个Ellipse:

string xaml ="<Ellipse Name=\"EllipseAdded\" Width=\"300.5\" Height=\"200\" Fill =\"Red\" xmlns=\"http://schemas.microsoft.com/winfx/2006/xaml/presentation\"/>";
object ellipse = XamlReader.Load(xaml);

当然了,要在代码里构建一个Ellipse何必这样大费周章。对于XamlReader,我平时用得最多的就是用来创建DataTemplate和ControlTemplate这些不方便用代码构建的元素。记得在XAML的根元素添加xmlns=""http://schemas.microsoft.com/winfx/2006/xaml/presentation""xmlns:x=""http://schemas.microsoft.com/winfx/2006/xaml""

var template = (DataTemplate)XamlReader.Load(@"
<DataTemplate xmlns=""http://schemas.microsoft.com/winfx/2006/xaml/presentation""
xmlns:x=""http://schemas.microsoft.com/winfx/2006/xaml"">
<TextBlock Text=""{Binding " + DisplayMemberPath + @"}"" VerticalAlignment=""Center""/>
</DataTemplate>");
ListControl.ItemTemplate = template;

这种方式满足了“动态”这个需求,缺点也很明显:动态的就容易出错,而且这种方式很难构建复杂的DataTemplate。

4. 结语

这两种方式我都很常用,复杂的就用资源字典方式,简单但需要动态的就用XamlReader。有些人会为XamlReader做得更多,例如通过反射将一个TextBlock转换为XAML,再使用XamlReader读取成DataTemplate。我觉得这样也不错,但我还没遇到过这种应用场景就不尝试了。

5. 参考

DataTemplate

XamlReader

x:FieldModifier

最新文章

  1. .net(C#)中this关键字
  2. js中java式的类成员
  3. 在VMware上安装CentOS-6.5 minimal - 安装VMware Tools
  4. const修饰指针
  5. Ansible二三事
  6. 自定义构造方法和description方法
  7. BZOJ 1677: [Usaco2005 Jan]Sumsets 求和
  8. Windows Phone开发(29):隔离存储C
  9. Linux Shell : Test命令参数解析
  10. STM32+NRF24L01无线(转)
  11. 微信小程序--合法域名校验出错
  12. 利用jmeter进行数据库测试
  13. c++简单线程池实现
  14. matlab GUI保存axes(坐标轴)上的图像
  15. mobile_轮播图_style_left 版本
  16. 为Firefox浏览器安装Firebug插件
  17. 日常工作中 Oracle12c参数的处理:
  18. KVM上如何让虚拟机支持虚拟化(kvm虚拟化的嵌套)
  19. hdu3746 Cyclic Nacklace KMP
  20. MongoDB索引相关文章-摘自网络

热门文章

  1. codeforces 2B The least round way(DP+数学)
  2. 关于正餐智能POS6.0.1.1改版后,订单模块无法进行部分退款的FAQ
  3. django加密解密api
  4. SQL Server死锁的解决过程
  5. Maven——settings.xml配置
  6. Java 7 for Absolute Beginners/Java 7基础教程--代码纠错
  7. 附2 rabbitmq用户管理、角色管理与权限管理
  8. 给 datepicker 设定日期格式
  9. ES5-ES6-ES7_iterator和for of
  10. 【CQOI2012】局部极小值