WPF Template

1.       为什么用模板
模板是用来定义(或重定义)对象的外观的好东西. WPF已经提供了Style来自定义外观, 那为什么还需要Template呢? 是因为Style只能让你一个一个地设置对象的属性, 但template用来改变对象的组织结构. Style就好象是更改一台电脑的配置, 你可以换个内存, 换个显卡, 但它还是一台电脑, 而Template则是把电脑整个换成一部汽车, 或者是其它一种你想要的东西. Template一般使用于两种情况下:
1)       需要修改一个控件的外观, 这个控件可能是1) WPF内建的控件, 比如你对默认的Button外观不爽了, 想把它换成一些别的什么, 比如一张图片或一个矩形. 2) 用户自建的控件, 它默认是什么都没有, 你得用模板使它可视化.
2)       需要为一种不可见的数据类型提供外观. 比如如果你把一个DateTime的对象作为Button的内容, 因为DateTime并不是一个可视的元素(UIElement), WPF会默认把其渲染成string; 为了提供更好的用户体验, 我们可以给它添加一个模板, 以控制WPF对DateTime对象的渲染
对应于这两种情况, WPF提供了两种模板类型, ControlTemplate和DataTemplate(以下简称CT和DT).
2.       开始使用模板的
例1. 使用CT
<Window xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Window1" Height="300" Width="300">
    <Button>
        <Button.Template>
            <ControlTemplate>
                <Grid>
                    <Rectangle Fill="LightBlue" Stroke="Black" StrokeThickness="5"
                               RadiusX="20" RadiusY="20"/>
                    <TextBlock HorizontalAlignment="Center" VerticalAlignment="Center">
                        I'm a CT
                    </TextBlock>
                </Grid>
            </ControlTemplate>
        </Button.Template>
    </Button></Window>

例2. 使用DT

<Window xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:sys="clr-namespace:System;assembly=mscorlib"
        Title="Window1" Height="300" Width="300">
    <Button>
        <Button.ContentTemplate>
            <DataTemplate>
                <StackPanel Orientation="Horizontal">
                    <Button Content="{Binding Year}" />
                    <Button Content="{Binding Month}" />
                    <Button Content="{Binding Day}" />
                </StackPanel>
            </DataTemplate>
        </Button.ContentTemplate>
        <sys:DateTime>3/1/2008</sys:DateTime>
    </Button>
</Window>
有一点需要注意, 例2中的通过ContentTemplate属性设置的DT不会影响外部Button的渲染, 而通过例1中CT则会影响Button的渲染, 如Button的边框, 高亮都不见了——就好像CT会影响外部的Container(在这里是一个Button)的渲染, 而DT则会影响Containner里的Content的渲染; 所以在有些地方, 如ItemsControl中, CT是通过ItemContainerStyle设置, 而DT是通过ItemTemplate设置的.
但是从例1中可以看出, 由于使用了CT, Button的内容被完全自定义了; 那如何在新的CT中使用Button原有的Content呢? 我们当然可以手动在CT中添加一个控件, 并将其Content绑定到TemplatedParent上, 如下:
<ControlTemplate TargetType="Button">
    <Grid>
        <Rectangle Fill="LightBlue" Stroke="Black" StrokeThickness="5" RadiusX="20" RadiusY="20"/>
        <ContentControl Content="{Binding Content, RelativeSource={RelativeSource TemplatedParent}}"
                        ContentTemplate="{Binding ContentTemplate, RelativeSource={RelativeSourceTemplatedParent}}"/>
    </Grid>
</ControlTemplate>
 但WPF提供了一种内建的方法——ContentPresenter:
<ControlTemplate TargetType="Button">
    <Grid>
        <Rectangle Fill="LightBlue" Stroke="Black" StrokeThickness="5" RadiusX="20" RadiusY="20"/>
        <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center" />
    </Grid>
</ControlTemplate>
除了通过ContentTemplate属性来修改CC中内容的模板外, 还可以使用CC.ContentTemplateSelector 来提供DataTemplate, 具体用法可查看MSDN, 在此不做复述.
3.       More about CT and DT
WPF中已有CT和DT两种模板, 还有无数 名为***Tempate的属性, 很容易产生混淆, 例如:
类型.属性
接受类型
Control.Template
ControlTemplate
ContentControl.ContentTemplate
DataTemplate
ItemsControl.ItemTemplate
DataTemplate
GridViewColumn.CellTemplate
DataTemplate
GridViewColumn.HeaderTemplate
DataTemplate
Control分两种, ContentControl和ItemsControl (以下简称CC和IC), 其概念上的区别在两者包含的子物件个数不一样 (CC一个, IC多个), 其代码上面的区别在于CC有一个叫Content的属性接受单个对象, IC有一个叫Items的属性接受对象集合. Control.Template和CC.ContentControl的作用无用多说, 可能带来疑问的是IC中的template. IC可以看作是很多个”小”CC的集合. 而这些”小”CC的Template和ContentTemplate属性就是可以通过IC的ItemContainerStyle, ItemTemplate和ItemTemplateSelector属性指定的.
之前的例子演示了CC中的Template, 接下来是关于IC中Template的例子.
4.       在IC中使用模板
1)       IC的模板
IC.Template的使用和CC很像; 以 ListView为例, 用以下的XAML生成ListView:
<ListView>
    <sys:DateTime>3/1/2008</sys:DateTime>
    <sys:DateTime>3/2/2008</sys:DateTime>
    <sys:DateTime>3/3/2008</sys:DateTime>
</ListView>
更改ListView的Template属性:
<ListView.Template>
    <ControlTemplate>
        <Border BorderBrush="Blue" BorderThickness="2">
            <StackPanel IsItemsHost="True"/>
        </Border>
    </ControlTemplate>
</ListView.Template>
需要特别注意其中的<StackPanel IsItemsHost="True"/>, 这个设置了IsItemsHost属性的StackPanel的作用跟CC中的ContentPresenter的作用是一样, 是用来加载使用该模板的Control原有的内容的. 不同的是CC只有一个子Item, 所以用一个ContentPresenter就可以了, 而IC有多个子Item, 所以用户需要使用一个Panel来放置items. 在这里用户可以通过使用不同的Panel来更改IC对子Item的布局, 比如使用一个UniformGrid:
<ControlTemplate>
    <Border BorderBrush="Blue" BorderThickness="2">
        <UniformGrid Columns="2" Rows="2" IsItemsHost="True"/>
    </Border>
</ControlTemplate>

2)       IC中Item的模板
在为IC中的子对象添加模板之前, 需要先明确与IC中的子对象有关的两种概念, 一种我们称为Item, 是我们直接在IC.Items中添加的对象; 另一种我们称为Item Container (对象容器), 是一种与IC类型相对应(e.g.与ListView对应的是ListViewItem), 用来存放Item的CC. Item Container的作用在于, 用户可能在IC.Items中添加的是一种数据类型 (无法可视化), 而IC会生成一个Container用来包装这些数据对象. 比如上例中, 我们在ListView的Items中设置了3个DataTime的对象, 则ListView会生成3个的ListViewItem, 并使ListViewItem.Content等于我们添加的DataTime对象.
使用Item Container的好处是显而易见的, 1, IC可以以一种统一的方式来处理它下面的子对象, 2, IC.Items可以接受任何类型的Colleciton, 而不一定非要一个Container的Collection.
所以, 想要控制ListView中子对象的渲染, 我们只需要更改其中Container, 也就是ListViewItem的Template和ContentTemplate就可以了. 对于前者, IC并没有直接提供属性来设置其下Container 的Template, 而是提供了ItemContainerStyle属性, 我们需要在Style中设置其Template属性, 比如:
<ListView.ItemContainerStyle>
        <Style TargetType="ListViewItem">
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="ListViewItem">
                    <Grid>
                        <Rectangle Fill="LightBlue" Stroke="Black" StrokeThickness="5" RadiusX="20" RadiusY="20"/>
                        <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center" />
                    </Grid>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>
</ListView.ItemContainerStyle>
对于Container的ContentTemplate属性, 有三种方法可以修改, 一是在ItemContainerStyle中设置其ContentTemplate属性, 这里不再复述; 二是通过IC.ItemTemplateSelector指定(跟CC一样); 三是使用IC直接提供的ItemTemplate属性, 如:
<ListView.ItemTemplate>
    <DataTemplate>
        <StackPanel Orientation="Horizontal">
            <Button Content="{Binding Year}" />
            <Button Content="{Binding Month}" />
            <Button Content="{Binding Day}" />
        </StackPanel>
    </DataTemplate>
</ListView.ItemTemplate>
需要注意的是, 通过IC.ItemTemplate属性设置的模板优先级比在ItemContainerStyle中设置的ContentTemplate高.
  • 2
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: WPF(Windows Presentation Foundation)是一种用于构建Windows应用程序的技术,而UI template是一种在WPF中用于创建可重复使用的用户界面样式和布局的机制。 WPF的UI template可以理解为一种定义了界面元素外观和样式的模板。通过使用UI template,我们可以很方便地将相同的界面元素样式应用于多个控件,从而实现界面的一致性和可重用性。 使用UI template的好处之一是简化了界面开发工作。开发人员只需要定义一次UI模板,然后可以在需要的地方直接应用这个模板,而不需要重新编写和调整样式。这在多个界面元素需要拥有相同外观的情况下特别有用。 另一个好处是提高了界面的灵活性。通过修改UI template,我们可以轻松地调整控件的样式、布局和属性,而不会破坏应用程序的整体结构。这样可以节省大量的时间和工作量,并且可以使界面更容易维护。 在WPF中,UI template是由XAML语言定义的。通过使用XAML,开发人员可以以声明式的方式定义界面元素的外观和样式,而不需要编写繁琐的代码。这使得UI template的创建、修改和管理变得更加方便和直观。 总的来说,WPF的UI template是一种用于创建可重复使用的用户界面样式和布局的机制,它可以简化界面开发工作,提高界面的灵活性,并通过XAML语言实现了对界面的声明式定义。 ### 回答2: WPF(Windows Presentation Foundation)是微软推出的一种用于构建富客户端应用程序的技术。在WPF中,UI模板(UI Template)是一种定义了控件外观和行为的重要组成部分。 UI模板被用于定义控件在界面上的外观,比如控件的背景、边框、字体样式、布局等。通过使用UI模板,我们可以根据应用程序的需求,自定义控件的外观,使之符合我们期望的样式和风格。这种灵活性使得WPF应用程序可以呈现出各种独特的界面设计。 UI模板的创建主要分为两个步骤:定义模板和应用模板。首先,我们需要根据需要定义一个模板,可以使用XAML(eXtensible Application Markup Language)来描述模板的结构和样式。模板中可以包含多个可视元素和控件,并可以使用各种布局控件进行排列。其次,我们需要将定义好的模板应用到相应的控件上。在WPF中,通过将控件的Template属性设置为我们定义的模板,就可以使控件采用我们自定义的样式。 使用UI模板可以为应用程序带来很多好处。首先,它使得应用程序的界面设计能够与众不同,使其与其他应用程序区别开来,提供独特的用户体验。其次,UI模板的灵活性使得我们可以方便地修改和调整控件的外观,而无需改变控件的内部逻辑。这种分离了界面与逻辑的设计思想有助于增强应用程序的可维护性和可扩展性。 总之,WPF的UI模板是一种非常强大的工具,可以帮助开发者定制出各种独特且具有个性化的界面,从而提升应用程序的用户体验。 ### 回答3: WPF (Windows Presentation Foundation)是一种用于创建丰富而功能强大的Windows桌面应用程序的框架。在WPF中,UI模板是一种用于定义UI元素外观和行为的技术。 UI模板是一种XAML标记语言的结构,它描述了如何渲染和布局一个UI元素,从而决定了它的外观和行为。UI模板可以用于自定义各种控件,例如按钮、文本框、列表和窗体等。通过创建和应用UI模板,开发者可以完全控制和定制应用程序的外观和交互方式。 WPF的UI模板由多个元素组成,其中包括容器元素、面板元素、控件元素和视觉元素等。容器元素用于包含和布局其他元素,面板元素用于定义元素的排列方式,控件元素用于添加交互和功能,视觉元素用于定义元素的外观。 开发者可以使用Visual Studio等工具创建和编辑UI模板。在模板中,可以通过修改元素的属性、样式和模板绑定来改变元素的外观和行为。还可以通过添加触发器和动画等功能来实现交互效果。 通过使用UI模板,开发者可以根据自己的需求和设计要求来定制应用程序的外观。他们可以创建独特和个性化的用户界面,从而提供更好的用户体验。此外,UI模板还可以被多个控件共享,以实现统一的外观和风格。 总之,WPF的UI模板是一种强大的工具,可以让开发者自由定制和控制应用程序的外观和行为。通过使用UI模板,可以创建独特和个性化的用户界面,为用户提供更好的体验。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值