本篇再补充一块内容,就是自定义状态的介绍。

自定义状态用于封装用户控件在各种状态之间切换时的外观变化及其动画效果,方便调用。比如有个用户控件用于实现类似舞台幕布打开和关闭切换的效果,可以创建幕布关闭和幕布打开两个状态并编辑界面及动画,然后调用状态切换,就可以方便地实现幕布打开和关闭效果。下面看演示。

1. 首先创建一个用户控件命名为CurtainControl,打开该用户控件的xaml进行编辑。

2. 在状态面板中,点击添加状态组按钮,将新添加的状态组命名为CurtainControlStateGroup,点击添加状态按钮,添加两个状态,命名为CurtainOpened和CurtainClosed。

3. 点击选择状态面板中的“基本”状态项,将界面中的Grid分为四列,两边的两列为0,中间的两列为*,背景改为白色。在外层Grid内部放入两个Border,分别在中间两列,背景色改为某种径向渐变色(为了演示方便,实际项目可精心设计),加个边的颜色,最好抽取样式。完成后代码如下,

<UserControl
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:x:Class="BlendDemo.CurtainControl"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<UserControl.Resources>
<Style x:Key="CurtainStyle" TargetType="{x:Type Border}">
<Setter Property="Background">
<Setter.Value>
<RadialGradientBrush>
<GradientStop Color="Black" Offset="0"/>
<GradientStop Color="#FFFFC1C1" Offset="1"/>
<GradientStop Color="#FF382B2B" Offset="0.223"/>
<GradientStop Color="#FF755959" Offset="0.465"/>
</RadialGradientBrush>
</Setter.Value>
</Setter>
<Setter Property="BorderBrush" Value="#FF00B9FF"/>
<Setter Property="BorderThickness" Value="1"/>
</Style>
</UserControl.Resources>
<Grid Background="White">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="0"/>
<ColumnDefinition/>
<ColumnDefinition/>
<ColumnDefinition Width="0"/>
</Grid.ColumnDefinitions>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CurtainControlStateGroup">
<VisualState x:Name="CurtainOpened"/>
<VisualState x:Name="CurtainClosed"/>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<Border Grid.Column="1" Style="{DynamicResource CurtainStyle}"/>
<Border Grid.Column="2" Style="{DynamicResource CurtainStyle}"/>
</Grid>
</UserControl>

4. 点击状态面板中的CurtainControlStateGroup状态组的打开FluidLayout按钮(图标为上下两个波浪线),然后选择CurtainOpened状态项,进入动画录制状态。将第一个Border的Grid.Column由1改为0,将第二个Border的Grid.Column由2改为3。

5. 点击选择状态面板中的“基本”状态项,退出动画录制状态。将CurtainControlStateGroup状态组的默认过度时间改为1s。

此时用户控件已经完成,完整代码如下。

<UserControl
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:ei="http://schemas.microsoft.com/expression/2010/interactions"
x:Class ="BlendDemo.CurtainControl"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<UserControl.Resources>
<Style x:Key="CurtainStyle" TargetType="{x:Type Border}">
<Setter Property="Background">
<Setter.Value>
<RadialGradientBrush>
<GradientStop Color="Black" Offset="0"/>
<GradientStop Color="#FFFFC1C1" Offset="1"/>
<GradientStop Color="#FF382B2B" Offset="0.223"/>
<GradientStop Color="#FF755959" Offset="0.465"/>
</RadialGradientBrush>
</Setter.Value>
</Setter>
<Setter Property="BorderBrush" Value="#FF00B9FF"/>
<Setter Property="BorderThickness" Value="1"/>
</Style>
</UserControl.Resources>
<Grid Background="White">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="0"/>
<ColumnDefinition/>
<ColumnDefinition/>
<ColumnDefinition Width="0"/>
</Grid.ColumnDefinitions>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CurtainControlStateGroup" ei:ExtendedVisualStateManager.UseFluidLayout="True">
<VisualStateGroup.Transitions>
<VisualTransition GeneratedDuration="0:0:1"/>
</VisualStateGroup.Transitions>
<VisualState x:Name="CurtainOpened">
<Storyboard>
<Int32AnimationUsingKeyFrames Storyboard.TargetProperty="(Grid.Column)" Storyboard.TargetName="border">
<EasingInt32KeyFrame KeyTime="0" Value="0"/>
</Int32AnimationUsingKeyFrames>
<Int32AnimationUsingKeyFrames Storyboard.TargetProperty="(Grid.Column)" Storyboard.TargetName="border1">
<EasingInt32KeyFrame KeyTime="0" Value="3"/>
</Int32AnimationUsingKeyFrames>
</Storyboard>
</VisualState>
<VisualState x:Name="CurtainClosed"/>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<VisualStateManager.CustomVisualStateManager>
<ei:ExtendedVisualStateManager/>
</VisualStateManager.CustomVisualStateManager>
<Border x:Name="border" Grid.Column="1" Style="{DynamicResource CurtainStyle}"/>
<Border x:Name="border1" Grid.Column="2" Style="{DynamicResource CurtainStyle}"/>
</Grid>
</UserControl>

6. 创建一个空的窗口,并设置为程序启动窗口。在外层Grid中加入两行,第一行为Auto,在其中放两个Button(外面套一个横向的StackPanel),文字改为打开和关闭。第二行为*,放入CurtainControl控件,在资产面板的“项目”分类中找,如果找不到该控件,请先生成项目。

7. 在资产面板中,选择“行为”分类,拖动GoToStateAction到文档大纲面板中的第一个Button上。在属性面板中,点击公共组下面的TargetName属性的美工板元素选取器按钮(圆圈中间有一个黑点),在美工板中选择CurtainControl控件。点击StateName属性的下拉框,选择CurtainOpened状态。第二个Button也执行同样的操作,StateName属性选择CurtainClosed状态。

至此,演示示例已全部完成,Window1的代码如下。

<Window
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:BlendDemo"
xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity" xmlns:ei="http://schemas.microsoft.com/expression/2010/interactions"
x:Class="BlendDemo.Window1"
mc:Ignorable="d"
Title="Window1" Height="322" Width="375">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition/>
</Grid.RowDefinitions>
<local:CurtainControl x:Name="curtainControl" Grid.Row="1"/>
<StackPanel Orientation="Horizontal">
<Button Content="打开">
<i:Interaction.Triggers>
<i:EventTrigger EventName="Click">
<ei:GoToStateAction TargetName="curtainControl" StateName="CurtainOpened"/>
</i:EventTrigger>
</i:Interaction.Triggers>
</Button>
<Button Content="关闭">
<i:Interaction.Triggers>
<i:EventTrigger EventName="Click">
<ei:GoToStateAction TargetName="curtainControl" StateName="CurtainClosed"/>
</i:EventTrigger>
</i:Interaction.Triggers>
</Button>
</StackPanel>
</Grid>
</Window>

界面效果如下,

点击打开和关闭按钮试试效果吧。

Blend 2015 教程 (五) 自定义状态的更多相关文章

  1. Blend 2015 教程 (四)控件模板

    前一篇讲述了修改ListBox样式的方法,本篇将修改性别显示区域的样式. 1. 选择ListBox控件,编辑ItemTemplate的当前项,选择CheckBox控件,在美工板导航栏中点击CheckB ...

  2. Blend 2015 教程 (一) 基础

    微软公司在Visual Studio 2015产品套件中作出了许多革命性的变更,包括.NET开源,.NET服务器端部分跨平台,推出向个人和小团队免费的社区版,移动应用开发部分跨平台支持,商店应用支持C ...

  3. Blend 2015 教程 (二) 样式

    前一篇讲述了如何在新Blend中完成一个简单的带数据绑定的界面小例子,本篇将讲述一下,把View层和Style层分开,并搭建Style层框架的方法,并进行细节样式修改. 1. 在解决方案资源管理器面板 ...

  4. Blend 2015 教程 (三) 模板

    前一篇讲述了一些基本样式的修改方法,并搭建了Style层的基本框架,本篇将进一步修改ListBox的样式. 1. 首先选中ListBox控件,在美工板导航栏中点击ListBox,选择 编辑其他模板-编 ...

  5. Quartz教程五:SimpleTrigger

    原文链接 | 译文链接 | 翻译:nkcoder 本系列教程由quartz-2.2.x官方文档翻译.整理而来,希望给同样对quartz感兴趣的朋友一些参考和帮助,有任何不当或错误之处,欢迎指正:有兴趣 ...

  6. React Native实战系列教程之自定义原生UI组件和VideoView视频播放器开发

    React Native实战系列教程之自定义原生UI组件和VideoView视频播放器开发   2016/09/23 |  React Native技术文章 |  Sky丶清|  4 条评论 |  1 ...

  7. Elasticsearch入门教程(五):Elasticsearch查询(一)

    原文:Elasticsearch入门教程(五):Elasticsearch查询(一) 版权声明:本文为博主原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明. 本文链接:h ...

  8. C#微信公众号开发系列教程五(接收事件推送与消息排重)

    微信公众号开发系列教程一(调试环境部署) 微信公众号开发系列教程一(调试环境部署续:vs远程调试) C#微信公众号开发系列教程二(新手接入指南) C#微信公众号开发系列教程三(消息体签名及加解密) C ...

  9. Android Studio系列教程五--Gradle命令详解与导入第三方包

    Android Studio系列教程五--Gradle命令详解与导入第三方包 2015 年 01 月 05 日 DevTools 本文为个人原创,欢迎转载,但请务必在明显位置注明出处!http://s ...

随机推荐

  1. postman 获取时间戳的方法 和md5加密的方法

    获取时间戳方法: postman.setGlobalVariable("timestamp",Math.round(new Date().getTime()));   这整句是获取 ...

  2. 清除MAC 可清除空间

    一.首先:查到了官方解释 https://support.apple.com/zh-cn/HT202867官方说 在 macOS Sierra 中,当您打开优化 Mac 储存空间时,会显示“可清除”内 ...

  3. 利用iWARP/RDMA解决以太网高延迟

    导读:“iWARP能够带来超低延迟.”据介绍,RDMA,即远程直接内存访问提供了应用程序到应用程序的直接通信能力,这也就意味着,应用将跳过操作系统,实现远程内存应用程序的访问 关键词: iWARP 低 ...

  4. eclipse自动生成.apt_generated、factory path

  5. StrConv 内码转换

    StrConv(string,conversion,LCID) string,预转换的字符串了(也可以使用byte数组). Conversion: 是一个整数,只决定转换方式,VB里定义了一些常量,如 ...

  6. 【转】mac os、linux及unix之间的关系

    mac os.linux及unix之间的关系   unix 是由贝尔实验室开发的多用户.多任务操作系统 linux是一类Unix操作系统的统称,严格来说,linux系统只有内核叫“linux”,而li ...

  7. LevelDB 的缺憾

    [LevelDB 的缺憾] 1.Snapshots 只能通过 DB::GetSnapshot() 创建,意即只能创建当下的 Snapshot. 2.

  8. Display file information in the document window

    [Display file information in the document window] The status bar is located at the bottom of every d ...

  9. FP扣损耗逻辑代码

    芯片172没有扣减损耗, 取数:SAP_STPO的AUSCH   IN_BOM_DETAILS:耗损比例COMPONENT_YIELD_UOM   存储过程FP_MO2SAP:supplydmdpeg ...

  10. NBU 还原windows ORACLE数据库(EC)

    rman target / startup nomount; run{ allocate channel ch00 type 'SBT_TAPE'; send 'nb_ora_serv=nbumast ...