当前位置: 首页 > news >正文

WPF动画

补间动画:动画本质就是在一个时间段内对象尺寸、位移、旋转角度、缩放、颜色、透明度等属性值的连续变化。也包括图形变形的属性。时间、变化的对象、变化的值

工业应用场景:蚂蚁线、旋转、高度变化、指针偏移、小车

WPF动画与分类

特定对象处理动画过程。

3大类共43个动画类:

简单线性动画:18

关键帧动画:22

路径动画:3

简单线性动画

ByteAnimation

ColorAnimation

DecimalAnimation

DoubleAnimation

Int16Animation

Int32Animation

Int64Animation

Point3DAnimation

PointAnimation

PopupAnimation

QuaternionAnimation

RectAnimation

Rotation3DAnimation

SingleAnimation

SizeAnimation

ThicknessAnimation

Vector3DAnimation

VectorAnimation

关键帧动画

BooleanAnimationUsingKeyFrames

ByteAnimationUsingKeyFrames

CharAnimationUsingKeyFrames

ColorAnimationUsingKeyFrames

DecimalAnimationUsingKeyFrames

DoubleAnimationUsingKeyFrames

Int16AnimationUsingKeyFrames

Int32AnimationUsingKeyFrames

Int64AnimationUsingKeyFrames

MatrixAnimationUsingKeyFrames

ObjectAnimationUsingKeyFrames

Point3DAnimationUsingKeyFrames

PointAnimationUsingKeyFrames

QuaternionAnimationUsingKeyFrames

RectAnimationUsingKeyFrames

Rotation3DAnimationUsingKeyFrames

SingleAnimationUsingKeyFrames

SizeAnimationUsingKeyFrames

StringAnimationUsingKeyFrames

ThicknessAnimationUsingKeyFrames

Vector3DAnimationUsingKeyFrames

VectorAnimationUsingKeyFrames

路径动画

DoubleAnimationUsingPath

PointAnimationUsingPath

MatrixAnimationUsingPath

动画的选择

根据属性类型确定

例如:width是double类型的,就可以选择double的动画

变个大小、变个位置、变个颜色、变个显示

动画类基本使用

创建类对象,设置相关属性,动画的执行

C#使用动画:

C#代码:

using System.Windows;
using System.Windows.Media.Animation;namespace XH.AnimationLesson
{/// <summary>/// LinearAniamtionWindow.xaml 的交互逻辑/// </summary>public partial class LinearAniamtionWindow : Window{public LinearAniamtionWindow(){InitializeComponent();}private void Button_Click(object sender, RoutedEventArgs e){// 5秒钟 100变300 DoubleAnimation widthAnimation = new DoubleAnimation();widthAnimation.Duration = new TimeSpan(0,0,5);widthAnimation.From = 100;widthAnimation.To = 300;// 变化宽度this.border.BeginAnimation(WidthProperty, widthAnimation);DoubleAnimation heightAnimation = new DoubleAnimation();heightAnimation.Duration = new TimeSpan(0, 0, 5);heightAnimation.From = 50;heightAnimation.To = 350;// 变化高度this.border.BeginAnimation(HeightProperty, heightAnimation);}}
}

XAML控件定义:

  <Grid><Border x:Name="border" Background="Orange" Height="50" Width="100" HorizontalAlignment="Left" VerticalAlignment="Top" /><Button Content="开始" Name="btn" VerticalAlignment="Bottom" Click="Button_Click" /></Grid>
XAML中使用动画:

效果和C#是一样的

<Window x:Class="XH.AnimationLesson.LinearAniamtionWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="LinearAniamtionWindow" Height="450" Width="800"><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard><Storyboard><DoubleAnimation Duration="0:0:5" From="100" To="300" Storyboard.TargetName="border"Storyboard.TargetProperty="Width"/></Storyboard></BeginStoryboard><BeginStoryboard><Storyboard><DoubleAnimation Duration="0:0:5" From="50" To="350"Storyboard.TargetName="border"Storyboard.TargetProperty="Height"/></Storyboard></BeginStoryboard></EventTrigger></Window.Triggers><Grid><Border x:Name="border" Background="Orange" Height="50" Width="100" HorizontalAlignment="Left" VerticalAlignment="Top" /><Button Content="开始" Name="btn" VerticalAlignment="Bottom" /></Grid>
</Window>
动画的独立控制与整合:C#整合
// 5秒钟 100变300 
DoubleAnimation widthAnimation = new DoubleAnimation();
widthAnimation.Duration = new TimeSpan(0,0,5);
widthAnimation.From = 100;
widthAnimation.To = 300;DoubleAnimation heightAnimation = new DoubleAnimation();
heightAnimation.Duration = new TimeSpan(0, 0, 5);
heightAnimation.From = 50;
heightAnimation.To = 350;// 将两个动画同步触发 如果多个动画需要同时执行 可以将相应的对象放到一个 Storyboard
Storyboard sb = new Storyboard();
sb.Children.Add(widthAnimation);
sb.Children.Add(heightAnimation);// 这里指定相关的动画对象,与哪个页面对象相关
// 第一个参数:动画对象
// 第二个参数:附加对象
Storyboard.SetTarget(widthAnimation,border);
Storyboard.SetTargetProperty(widthAnimation,new PropertyPath("Width"));Storyboard.SetTarget(heightAnimation,border);
Storyboard.SetTargetProperty(heightAnimation, new PropertyPath("Height"));
sb.Begin();
动画类使用小结:
  • 必须针对依赖属性
  • 对象必须派生自DependencyObject,并且实现IAnimatable接口
  • 必须存在可用的兼容动画类(支持自定义)

位移动画处理

XAML代码:

<Window x:Class="XH.AnimationLesson.LinearAniamtionWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="LinearAniamtionWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><!--对象的位移变化对象--><ThicknessAnimation Duration="0:0:5" From="0 0 0 0" To="100 50 0 0"Storyboard.TargetName="border"Storyboard.TargetProperty="Margin"/><DoubleAnimation Duration="0:0:5" From="0" To="100" Storyboard.TargetProperty="X" Storyboard.TargetName="tt"/><DoubleAnimation Duration="0:0:5" From="10" To="100" Storyboard.TargetProperty="(Border.RenderTransform).(TranslateTransform.X)" Storyboard.TargetName="border"/></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Border x:Name="border" Background="Orange" Height="50" Width="100" Margin="0 0 0 0" Canvas.Left="0"HorizontalAlignment="Left" VerticalAlignment="Top" Opacity="1"><Border.RenderTransform><TranslateTransform X="10" Y="50" x:Name="tt"/></Border.RenderTransform></Border><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

只要是改变控件位置的都可以进行动画变化。

对于复杂的属性变化写法:(Border.RenderTransform).(TranslateTransform.X)

颜色与显示变更动画处理

<Window x:Class="XH.AnimationLesson.LinearAniamtionWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="LinearAniamtionWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><!--对象的颜色变化对象不可以直接变化资源对象 会报错:找不到对象名称--><ColorAnimation Duration="0:0:5" From="Orange" To="Green"Storyboard.TargetName="border"Storyboard.TargetProperty="Background.Color"/><ColorAnimation Duration="0:0:3" From="Orange" To="Green"Storyboard.TargetName="border"Storyboard.TargetProperty="(Border.Background).(SolidColorBrush.Color)"/><!--BeginTime:多久开始执行--><ColorAnimation Duration="0:0:3" From="Green" To="Red"BeginTime="0:0:3"Storyboard.TargetName="border"Storyboard.TargetProperty="(Border.Background).(SolidColorBrush.Color)"/></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Border x:Name="border" Background="Orange" Height="50" Width="100" Margin="0 0 0 0" Canvas.Left="0"HorizontalAlignment="Left" VerticalAlignment="Top" Opacity="1" /><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

属性:BeginTime 多久开始执行,使用的时候和关键帧差不多

注意:Background实际上改变颜色的属性是:(Border.Background).(SolidColorBrush.Color),不是Brush

关键帧处理:

四大帧对象类型:

  1. Linear+【类型名称】+KeyFrame 线性变化关键帧,(简单线性动画的处理基本一样)
  2. Discrete +【类型名称】+ KeyFrame 离散变化关键帧,不连续变化
  3. Spline +【类型名称】+ KeyFrame 样条关键帧-》样条函数(二次贝塞尔曲线-Path)
  4. Easing +【类型名称】+ KeyFrame 缓冲式关键帧,使用简单动画时介绍的缓动效果
线性关键帧动画基本使用
<Window x:Class="XH.AnimationLesson.KeyFrameAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="KeyFrameAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><!--1、如果动画对象的Duration时长大于子帧的时长,多出来的时间无变化--><!--2、如果动画对象的Duration时长小于子帧的时长,以对象的事件为准,超出的子帧时间不执行--><!--3、如果不指定动画对象的Duration时长,以关键帧时间全部执行--><!--注意:关键帧的时间没有先后顺序要求,严格按照时间轴进行执行--><ColorAnimationUsingKeyFrames Storyboard.TargetName="border"Storyboard.TargetProperty="Background.Color"><LinearColorKeyFrame Value="Orange" KeyTime="0:0:0" /><LinearColorKeyFrame Value="Green" KeyTime="0:0:2" /><LinearColorKeyFrame Value="Red" KeyTime="0:0:4" /></ColorAnimationUsingKeyFrames></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Border x:Name="border" Background="Orange" Height="50" Width="100" Visibility="Collapsed"HorizontalAlignment="Left"/><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

注意:

1、如果动画对象的Duration时长大于子帧的时长,多出来的时间无变化

2、如果动画对象的Duration时长小于子帧的时长,以对象的事件为准,超出的子帧时间不执行

3、如果不指定动画对象的Duration时长,以关键帧时间全部执行

注意:关键帧的时间没有先后顺序要求,严格按照时间轴进行执行

离散关键帧动画基本使用
<Window x:Class="XH.AnimationLesson.KeyFrameAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="KeyFrameAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><!--String 变化只有DiscreteStringKeyFrame离散关键帧变化--><StringAnimationUsingKeyFrames Duration="0:0:5"Storyboard.TargetName="tb"Storyboard.TargetProperty="Text"><DiscreteStringKeyFrame Value="你好" KeyTime="0:0:2" /></StringAnimationUsingKeyFrames></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><TextBlock Text="Hello" Name="tb"/><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

注意:String 变化只有DiscreteStringKeyFrame离散关键帧变化

样条关键帧动画基本使用
<Window x:Class="XH.AnimationLesson.KeyFrameAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="KeyFrameAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><ThicknessAnimationUsingKeyFrames Storyboard.TargetName="ellipse" Storyboard.TargetProperty="Margin" ><SplineThicknessKeyFrame Value="0 0 0 0" KeyTime="0:0:0" /><SplineThicknessKeyFrame KeyTime="00:00:04" Value="780 0 0 0" KeySpline="0 1 1 0"><!--可以简写--><!--<SplineThicknessKeyFrame.KeySpline><KeySpline ControlPoint1="0,1" ControlPoint2="1,0"/></SplineThicknessKeyFrame.KeySpline>--></SplineThicknessKeyFrame></ThicknessAnimationUsingKeyFrames></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Ellipse Width="20" Height="20" Fill="Red" VerticalAlignment="Top" HorizontalAlignment="Left"Margin="0 0 0 0" Name="ellipse"/><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

KeySpline可以在Blend中设置属性:

可以设置某一段时间变化快和慢

缓冲式关键帧
<Window x:Class="XH.AnimationLesson.KeyFrameAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="KeyFrameAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="ease_sb"><ThicknessAnimationUsingKeyFrames Storyboard.TargetName="border" Storyboard.TargetProperty="Margin"><LinearThicknessKeyFrame Value="0 0 0 0" KeyTime="0:0:0" /><LinearThicknessKeyFrame Value="100 0 0 0" KeyTime="0:0:2"/><LinearThicknessKeyFrame Value="100 0 0 0" KeyTime="0:0:3"/><EasingThicknessKeyFrame Value="300 0 0 0" KeyTime="0:0:5"><EasingThicknessKeyFrame.EasingFunction><!--EasingMode:在起始或者末尾哪个地方适用此缓冲--><!--BackEase:路径中进行动画处理之前略微收回动画的动作--><BackEase EasingMode="EaseInOut"/></EasingThicknessKeyFrame.EasingFunction></EasingThicknessKeyFrame></ThicknessAnimationUsingKeyFrames></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource ease_sb}" /></EventTrigger></Window.Triggers><Grid><Border x:Name="border" Background="Orange" Margin="0 0 0 0"Height="50" Width="100"HorizontalAlignment="Left" VerticalAlignment="Top"/><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

EasingMode:在起始或者末尾哪个地方适用此缓冲

BackEase:路径中进行动画处理之前略微收回动画的动作

ObjectAnimationUsingKeyFrames
<Window x:Class="XH.AnimationLesson.KeyFrameAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d" FontSize="20"Title="KeyFrameAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="obj_sb"><ObjectAnimationUsingKeyFrames Storyboard.TargetName="border" Storyboard.TargetProperty="Visibility"RepeatBehavior="Forever"><!--只能离散形式的动画效果--><DiscreteObjectKeyFrame KeyTime="0:0:0"><DiscreteObjectKeyFrame.Value><Visibility>Visible</Visibility></DiscreteObjectKeyFrame.Value></DiscreteObjectKeyFrame><DiscreteObjectKeyFrame KeyTime="0:0:0.1"><DiscreteObjectKeyFrame.Value><Visibility>Hidden</Visibility></DiscreteObjectKeyFrame.Value></DiscreteObjectKeyFrame><DiscreteObjectKeyFrame KeyTime="0:0:0.2"><DiscreteObjectKeyFrame.Value><Visibility>Visible</Visibility></DiscreteObjectKeyFrame.Value></DiscreteObjectKeyFrame></ObjectAnimationUsingKeyFrames></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource obj_sb}" /></EventTrigger></Window.Triggers><Grid><Border x:Name="border" Background="Orange" Margin="0 0 0 0"Height="50" Width="100" Visibility="Hidden"HorizontalAlignment="Left" VerticalAlignment="Top"/><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

注意:理论让任意类型参与动画,只能离散形式的动画效果 复杂类型用value包着即可

路劲动画

根据Path数据,限定动画路径

类型名称+ AnimationUsingPath

3个对象 Double、Point(X、Y)、Matrix(不需要记矩阵)

路径Path

DoubleAnimationUsingPath:

位移(TranslateTransform、CanvasLeftTop)、旋转(RoateTransform)

<Window x:Class="XH.AnimationLesson.PathAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d"Title="PathAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><!--Source:Path中的X值:X点位Storyboard.TargetProperty:需要变化的属性--><DoubleAnimationUsingPath Duration="0:0:4" Storyboard.TargetName="tt" Storyboard.TargetProperty="X"Source="X"><DoubleAnimationUsingPath.PathGeometry><PathGeometry Figures="M0 0 60,100 A100 50 0 0 1 400 150" /></DoubleAnimationUsingPath.PathGeometry></DoubleAnimationUsingPath><DoubleAnimationUsingPath Duration="0:0:4" Storyboard.TargetName="tt" Storyboard.TargetProperty="Y"Source="Y"><DoubleAnimationUsingPath.PathGeometry><PathGeometry Figures="M0 0 60,100 A100 50 0 0 1 400 150" /></DoubleAnimationUsingPath.PathGeometry></DoubleAnimationUsingPath><DoubleAnimationUsingPath Duration="0:0:4" Storyboard.TargetName="rt" Storyboard.TargetProperty="Angle"Source="Angle"><DoubleAnimationUsingPath.PathGeometry><PathGeometry Figures="M0 0 60,100 A100 50 0 0 1 400 150" /></DoubleAnimationUsingPath.PathGeometry></DoubleAnimationUsingPath></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Path Data="M0 0 60,100 A100 50 0 0 1 400 150" Stroke="Gray" StrokeThickness="2" /><Border x:Name="border" Background="Orange"Height="50" Width="100" Visibility="Collapsed"RenderTransformOrigin="0.5 0.5" Margin="-50 -25 0 0"HorizontalAlignment="Left" VerticalAlignment="Top"><Border.RenderTransform><TransformGroup><RotateTransform Angle="0" x:Name="rt" /><TranslateTransform X="0" Y="0" x:Name="tt"/></TransformGroup></Border.RenderTransform></Border><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>
PointAnimationUsingPath:位移
<Window x:Class="XH.AnimationLesson.PathAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d"Title="PathAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><PointAnimationUsingPath Duration="0:0:4" Storyboard.TargetName="eg" Storyboard.TargetProperty="Center"><PointAnimationUsingPath.PathGeometry><PathGeometry Figures="M0 0 60,100 A100 50 0 0 1 400 150" /></PointAnimationUsingPath.PathGeometry></PointAnimationUsingPath></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Path Data="M0 0 60,100 A100 50 0 0 1 400 150" Stroke="Gray" StrokeThickness="2" /><Path Fill="Orange" Visibility="Collapsed"><Path.Data><EllipseGeometry Center="0 0" RadiusX="40" RadiusY="40" x:Name="eg"/></Path.Data></Path><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

注意:必须是Point的依赖属性,否则不可以

MatrixAnimationUsingPath:合体,上面两个都包含
<Window x:Class="XH.AnimationLesson.PathAnimationWindow"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:XH.AnimationLesson"mc:Ignorable="d"Title="PathAnimationWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb"><MatrixAnimationUsingPath Duration="0:0:4" Storyboard.TargetName="mt" Storyboard.TargetProperty="Matrix"DoesRotateWithTangent="True"><!--DoesRotateWithTangent:是否沿着路径旋转--><MatrixAnimationUsingPath.PathGeometry><PathGeometry Figures="M0 0 60,100 A100 50 0 0 1 400 150" /></MatrixAnimationUsingPath.PathGeometry></MatrixAnimationUsingPath></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Path Data="M0 0 60,100 A100 50 0 0 1 400 150" Stroke="Gray" StrokeThickness="2" /><Border Background="Orange" Height="50" Width="100" Visibility="Visible"RenderTransformOrigin="0.5 0.5" Margin="-50 -25 0 0"HorizontalAlignment="Left" VerticalAlignment="Top"><Border.RenderTransform><MatrixTransform x:Name="mt" /></Border.RenderTransform></Border><Button Content="开始" Name="btn" Canvas.Left="200" VerticalAlignment="Bottom" /></Grid>
</Window>

DoesRotateWithTangent:是否沿着路径旋转

默认是位移变化。

动画辅助属性

SpeedRatio:播放速度

SpeedRatio:速率 默认为1,需要大于0,小于1变慢,大于1变快

 <ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border2" Storyboard.TargetProperty="Margin"From="0" To="400 0 0 0"SpeedRatio="2"/>
AccelerationRatio:加速速率

AccelerationRatio:百分比,百分之多少的路程加速运动 和DecelerationRatio之和必须小于1

<ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border3" Storyboard.TargetProperty="Margin"From="0" To="400 0 0 0"AccelerationRatio="0.3"DecelerationRatio="0.7"/>
DecelerationRatio:减速速率

DecelerationRatio:百分比,百分之多少的路程减速速运动 和AccelerationRatio之和必须小于1

<ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border3" Storyboard.TargetProperty="Margin"From="0" To="400 0 0 0"AccelerationRatio="0.3"DecelerationRatio="0.7"/>
AutoReverse:是否执行相反的动画

是否执行相反的动画 默认False,先执行一遍,再反着执行一遍

<ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border4" Storyboard.TargetProperty="Margin"From="0" To="400 0 0 0"AutoReverse="True"/>
FillBehavior:动画结束状态:HoldEnd、Stop

FillBehavior:获取保持的行为方式

HoldEnd:保持最后到最后

Stop:不保持,动画直接结束

 <ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border5" Storyboard.TargetProperty="Margin"From="0" To="400 0 0 0"FillBehavior="Stop"/>
RepeatBehavior:动画重复方式,包括三种值:Forever、次数、时间

RepeatBehavior:

Forever 永远执行 重复动画

numx 例如2x 重复2次 指定重复的次数 只能小写x

时:分:秒 例如:0:0:5 执行5秒结束 指定重复执行的时间

 <ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border6" Storyboard.TargetProperty="Margin"From="0" To="400 0 0 0"RepeatBehavior="0:0:5" AutoReverse="True"/>

前面这些属性在Animation对象中也可以设置


IsAddtive:将目标属性的当前值添加到动画的起始值

IsAdditive:分段加载 可以当前位置继续动画,无视From

 <ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border7" Storyboard.TargetProperty="Margin"From="0" To="200 0 0 0"IsAdditive="True"/>
<!--不指定From是从默认位置出发-->
<ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border8" Storyboard.TargetProperty="Margin"To="200 0 0 0"IsAdditive="True"/>
IsCumulative:如果动画不断重复,就累积动画值

IsCumulative:累计计算 在使用RepeatBehavior的时候累计动画

<ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border9" Storyboard.TargetProperty="Margin"From="0" To="200 0 0 0"IsCumulative="True"RepeatBehavior="2x"/>
<!--没有From也不会累计-->
<ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border10" Storyboard.TargetProperty="Margin"To="200 0 0 0"IsCumulative="True"/>
BeginTime:动画线启动等待时长
<ThicknessAnimation Duration="0:0:4" Storyboard.TargetName="border2" Storyboard.TargetProperty="Margin"From="0" To="400 0 0 0"BeginTime="0:0:2"/>
EasingFunction:动画缓动属性,EasingMode
BackEase、CircleEase、CubicEase、ElasticEase、ExponentialEase、PowerEase、QuadraticEase、QuarticEase、QuinticEase、SineEase
 <Window.Triggers><!--EasingFunction:缓动函数SineEase:正弦公式创建加速和/或减速的动画CubicEase:函数创建一个使用公式 f(t) = t3 进行加速和/或减速的动画--><EventTrigger RoutedEvent="Button.Click" SourceName="bt1"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:1" From="0" To="500,0,0,0" Storyboard.TargetName="bor1" Storyboard.TargetProperty="Margin"/></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt2"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor2" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><BounceEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt3"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor3" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><BackEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt4"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor4" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><CircleEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt5"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor5" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><CubicEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt6"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor6" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><ElasticEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt7"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor7" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><ExponentialEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt8"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor8" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><PowerEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt9"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor9" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><QuadraticEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt10"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor10" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><QuarticEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt11"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor11" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><QuinticEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="bt12"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:5" From="0" To="500,0,0,0" Storyboard.TargetName="bor12" Storyboard.TargetProperty="Margin"><ThicknessAnimation.EasingFunction><SineEase/></ThicknessAnimation.EasingFunction></ThicknessAnimation></Storyboard></BeginStoryboard></EventTrigger></Window.Triggers><Grid Height="auto"><Grid.ColumnDefinitions><ColumnDefinition/><ColumnDefinition Width="auto"/></Grid.ColumnDefinitions><Grid.RowDefinitions><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/></Grid.RowDefinitions><TextBlock Text="无" VerticalAlignment="Center" HorizontalAlignment="Center"/><TextBlock Text="BounceEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="1"/><TextBlock Text="BackEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="2"/><TextBlock Text="CircleEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="3"/><TextBlock Text="CubicEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="4"/><TextBlock Text="ElasticEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="5"/><TextBlock Text="ExponentialEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="6"/><TextBlock Text="PowerEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="7"/><TextBlock Text="QuadraticEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="8"/><TextBlock Text="QuarticEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="9"/><TextBlock Text="QuinticEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="10"/><TextBlock Text="SineEase" VerticalAlignment="Center" HorizontalAlignment="Center" Grid.Row="11"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Name="bor1"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="1" Name="bor2"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="2" Name="bor3"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="3" Name="bor4"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="4" Name="bor5"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="5" Name="bor6"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="6" Name="bor7"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="7" Name="bor8"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="8" Name="bor9"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="9" Name="bor10"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="10" Name="bor11"/><Border Width="30" Height="30" Background="Orange" VerticalAlignment="Center" HorizontalAlignment="Left" Grid.Row="11" Name="bor12"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Name="bt1"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="1" Name="bt2"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="2" Name="bt3"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="3" Name="bt4"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="4" Name="bt5"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="5" Name="bt6"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="6" Name="bt7"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="7" Name="bt8"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="8" Name="bt9"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="9" Name="bt10"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="10" Name="bt11"/><Button Width="40" Height="30" Content="开始" Grid.Column="1" VerticalAlignment="Center" Grid.Row="11" Name="bt12"/>
</Grid>
Timeline.DesiredFrameRate:设置帧率
 <Storyboard x:Key="sb" Timeline.DesiredFrameRate="120"></Storyboard>

Timeline.DesiredFrameRate:帧率刷新率 默认是60 最大120

生命周期事件

  1. Completed动画结束
  2. CurrentGlobalSpeedInvalidated:速度变化
  3. CurrentStateInvalidated:状态变化
  4. CurretnTimeInvalidated:时间线

执行顺序:

CurrentTimeInvalidated-->CurrentGlobalSpeedInvalidated-->CurrentStateInvalidated

-->...CurrentTimeInvalidated...-->CurrentGlobalSpeedInvalidated-->CurrentStateInvalidated

-->Completed

动画控制

动画的启动:事件、触发器、视觉管理器

事件控制

BeginStoryboard:开始中一个故事板

PauseStoryboard:暂停

ResumeStoryboard:恢复

StopStoryboard:停止

SeekStoryboard:跳转某一帧,某个时刻

SetStoryboardSpeedRatio:加速、减速

<Window x:Class="XH.AnimationLesson.AnimationControlWindow"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:XH.AnimationLesson"mc:Ignorable="d"Title="AnimationControlWindow" Height="450" Width="800"><!--动画控制--><Window.Resources><Storyboard x:Key="sb"><ThicknessAnimation Duration="0:0:5" From="0 0 0 0" To="600 0 0 0"Storyboard.TargetName="bor_1" Storyboard.TargetProperty="Margin" /></Storyboard></Window.Resources><Window.Triggers><!--开始--><EventTrigger RoutedEvent="Button.Click" SourceName="btn_1"><BeginStoryboard Storyboard="{StaticResource sb}" x:Name="bsb" /></EventTrigger><!--暂停--><EventTrigger RoutedEvent="Button.Click" SourceName="btn_2"><PauseStoryboard BeginStoryboardName="bsb" /></EventTrigger><!--恢复--><EventTrigger RoutedEvent="Button.Click" SourceName="btn_3"><ResumeStoryboard BeginStoryboardName="bsb" /></EventTrigger><!--停止--><EventTrigger RoutedEvent="Button.Click" SourceName="btn_4"><StopStoryboard BeginStoryboardName="bsb" /></EventTrigger><!--跳转某一帧--><EventTrigger RoutedEvent="Button.Click" SourceName="btn_5"><SeekStoryboard BeginStoryboardName="bsb" Offset="0:0:3" /></EventTrigger><!--加速--><EventTrigger RoutedEvent="Button.Click" SourceName="btn_6"><SetStoryboardSpeedRatio BeginStoryboardName="bsb" SpeedRatio="10" /></EventTrigger><!--减速--><EventTrigger RoutedEvent="Button.Click" SourceName="btn_7"><SetStoryboardSpeedRatio BeginStoryboardName="bsb" SpeedRatio="0.1" /></EventTrigger></Window.Triggers><Grid><Border Background="Orange" Width="50" Height="50" Name="bor_1" HorizontalAlignment="Left" /><UniformGrid Rows="1" VerticalAlignment="Bottom"><Button Content="开始" Name="btn_1"/><Button Content="暂停" Name="btn_2"/><Button Content="恢复" Name="btn_3"/><Button Content="停止" Name="btn_4"/><Button Content="跳转某一帧" Name="btn_5"/><Button Content="加速" Name="btn_6"/><Button Content="减速" Name="btn_7"/></UniformGrid></Grid>
</Window>

触发器控制

EnterActions:符合触发器条件进入触发器的时候

ExitActions:与触发器触发事件相反的时候

<Window x:Class="XH.AnimationLesson.AnimationTriggerWindow"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:XH.AnimationLesson"mc:Ignorable="d"Title="AnimationTriggerWindow" Height="450" Width="800"><!--触发器中调用动画--><Window.Resources><ControlTemplate TargetType="CheckBox" x:Key="cbTemp"><Border Background="{TemplateBinding Background}" Height="50" Width="50"Name="bor"><ContentPresenter VerticalAlignment="Center" HorizontalAlignment="Center" /></Border><ControlTemplate.Triggers><Trigger Property="IsChecked" Value="True"><Setter Property="Background" Value="Orange" TargetName="bor"/><!--触发器条件满足的时候--><!--没有写From:表示动画执行的起始值从当前对象状态小哎的相关属性值开始变化--><Trigger.EnterActions><BeginStoryboard><Storyboard><DoubleAnimation Duration="0:0:2" To="100"Storyboard.TargetName="bor" Storyboard.TargetProperty="Width"/><DoubleAnimation Duration="0:0:2" To="100"Storyboard.TargetName="bor" Storyboard.TargetProperty="Height"/></Storyboard></BeginStoryboard></Trigger.EnterActions><!--触发器条件不满足的时候--><!--没有写From:表示动画执行的起始值从当前对象状态小哎的相关属性值开始变化没有写To:表示动画执行的目标值以对象的初始状态下的相关属性值为结束--><Trigger.ExitActions><BeginStoryboard><Storyboard><DoubleAnimation Duration="0:0:2"Storyboard.TargetName="bor" Storyboard.TargetProperty="Width"/><DoubleAnimation Duration="0:0:2"Storyboard.TargetName="bor" Storyboard.TargetProperty="Height"/></Storyboard></BeginStoryboard></Trigger.ExitActions></Trigger></ControlTemplate.Triggers></ControlTemplate></Window.Resources><Grid><CheckBox Background="Gray"VerticalAlignment="Center" HorizontalAlignment="Center"IsChecked="False" Template="{StaticResource cbTemp}" x:Name="cb"/></Grid>
</Window>

没有写From:表示动画执行的起始值从当前对象状态小哎的相关属性值开始变化

没有写To:表示动画执行的目标值以对象的初始状态下的相关属性值为结束

视觉状态管理器

VisualState: 视图状态(Visual States)表示控件在一个特殊的逻辑状态下的样式、外观;

VisualStateGroup: 状态组由相互排斥的状态组成,状态组与状态组并不互斥;

VisualTransition: 视图转变 (Visual Transitions) 代表控件从一个视图状态向另一个状态转换时的过渡;

VisualStateManager: 由它负责在代码中来切换到不同的状态;

<VisualStateManager.VisualStateGroups><!--这里面可以存放多个Group--><VisualStateGroup><!--可以存放多个VisualState,状态互斥--><VisualState x:Name="state_1"><Storyboard><ThicknessAnimation Duration="0:0:2" From="0 0 0 0" To="600 0 0 0"Storyboard.TargetName="bor_1" Storyboard.TargetProperty="Margin" /></Storyboard></VisualState><VisualState x:Name="state_2"><Storyboard><ColorAnimation Duration="0:0:2" From="Orange" To="Green"Storyboard.TargetName="bor_1" Storyboard.TargetProperty="Background.Color" /></Storyboard></VisualState><!--空着是指回到原始状态--><VisualState x:Name="state_3"/></VisualStateGroup><VisualStateGroup></VisualStateGroup>
</VisualStateManager.VisualStateGroups>

GoToState:针对控件模板中的视觉状态进行切换

GoToElementState:针对某个对象中的视觉状态进行切换

private void Button_Click(object sender, RoutedEventArgs e)
{VisualStateManager.GoToElementState(this,"state_1",true);
}private void Button_Click_1(object sender, RoutedEventArgs e)
{VisualStateManager.GoToElementState(this, "state_2", true);
}private void Button_Click_2(object sender, RoutedEventArgs e)
{VisualStateManager.GoToElementState(this, "state_3", true);
}

案例实操

菜单隐藏:
<Window x:Class="XH.AnimationLesson.Demo.DrawerWindow"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:XH.AnimationLesson.Demo"mc:Ignorable="d"Title="DrawerWindow" Height="450" Width="800"><Window.Resources><!--<Storyboard x:Key="sb"><ThicknessAnimation Duration="0:0:0.5" To="0" Storyboard.TargetName="border" Storyboard.TargetProperty="Margin" /></Storyboard>--></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Button.Click" SourceName="btn_1"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:0.5" To="0" Storyboard.TargetName="border" Storyboard.TargetProperty="Margin" /></Storyboard></BeginStoryboard></EventTrigger><EventTrigger RoutedEvent="Button.Click" SourceName="btn_2"><BeginStoryboard><Storyboard><ThicknessAnimation Duration="0:0:0.5" To="-180 0 0 0" Storyboard.TargetName="border" Storyboard.TargetProperty="Margin" /></Storyboard></BeginStoryboard></EventTrigger></Window.Triggers><Grid><Button Width="30" Name="btn_1" Height="30" VerticalAlignment="Top" HorizontalAlignment="Left" /><Border Width="180" Background="#DDD" HorizontalAlignment="Left" Margin="-180 0 0 0" Name="border"><Button Width="30" Height="30" VerticalAlignment="Top" HorizontalAlignment="Right" Name="btn_2" /></Border></Grid>
</Window>
进度等待:
<Window x:Class="XH.AnimationLesson.Demo.LoadingWindow"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:XH.AnimationLesson.Demo"mc:Ignorable="d" Name="win"Title="LoadingWindow" Height="450" Width="800"><Window.Resources><Storyboard x:Key="sb" RepeatBehavior="Forever"><ThicknessAnimationUsingKeyFrames Storyboard.TargetName="ellipse_1" Storyboard.TargetProperty="Margin"><SplineThicknessKeyFrame Value="0 0 0 0" KeyTime="0:0:0" /><SplineThicknessKeyFrame KeyTime="00:00:02" Value="315 0 0 0" KeySpline="0.1,0.7,0.3,0.1" /></ThicknessAnimationUsingKeyFrames><ThicknessAnimationUsingKeyFrames Storyboard.TargetName="ellipse_2" Storyboard.TargetProperty="Margin" BeginTime="0:0:0.3"><SplineThicknessKeyFrame Value="0 0 0 0" KeyTime="0:0:0" /><SplineThicknessKeyFrame KeyTime="00:00:02" Value="315 0 0 0" KeySpline="0.1,0.7,0.3,0.1" /></ThicknessAnimationUsingKeyFrames><ThicknessAnimationUsingKeyFrames Storyboard.TargetName="ellipse_3" Storyboard.TargetProperty="Margin" BeginTime="0:0:0.6"><SplineThicknessKeyFrame Value="0 0 0 0" KeyTime="0:0:0" /><SplineThicknessKeyFrame KeyTime="00:00:02" Value="315 0 0 0" KeySpline="0.1,0.7,0.3,0.1" /></ThicknessAnimationUsingKeyFrames><ThicknessAnimationUsingKeyFrames Storyboard.TargetName="ellipse_4" Storyboard.TargetProperty="Margin" BeginTime="0:0:0.9"><SplineThicknessKeyFrame Value="0 0 0 0" KeyTime="0:0:0" /><SplineThicknessKeyFrame KeyTime="00:00:02" Value="315 0 0 0" KeySpline="0.1,0.7,0.3,0.1" /></ThicknessAnimationUsingKeyFrames></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Loaded" SourceName="win"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Grid VerticalAlignment="Center" Width="300" Background="AliceBlue" ClipToBounds="True"><Ellipse Width="15" Height="15" Fill="Red" VerticalAlignment="Center" HorizontalAlignment="Left"Margin="-15 0 0 0" Name="ellipse_1"/><Ellipse Width="15" Height="15" Fill="Red" VerticalAlignment="Center" HorizontalAlignment="Left"Margin="-15 0 0 0" Name="ellipse_2"/><Ellipse Width="15" Height="15" Fill="Red" VerticalAlignment="Center" HorizontalAlignment="Left"Margin="-15 0 0 0" Name="ellipse_3"/><Ellipse Width="15" Height="15" Fill="Red" VerticalAlignment="Center" HorizontalAlignment="Left"Margin="-15 0 0 0" Name="ellipse_4"/></Grid></Grid>
</Window>
机械臂控制
<Window x:Class="XH.AnimationLesson.Demo.RobotWindow"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:XH.AnimationLesson.Demo"mc:Ignorable="d" Name="win"Title="RobotWindow" Height="450" Width="800"><!--多轴机械臂动画--><Window.Resources><Storyboard x:Key="sb" AutoReverse="True" RepeatBehavior="Forever"><DoubleAnimation Duration="0:0:2" From="0" To="200" Storyboard.TargetName="tt" Storyboard.TargetProperty="X"/><DoubleAnimation Duration="0:0:2" From="-40" To="20" Storyboard.TargetName="rt" Storyboard.TargetProperty="Angle"/><DoubleAnimation Duration="0:0:2" From="40" To="80" Storyboard.TargetName="rt_1" Storyboard.TargetProperty="Angle"/><DoubleAnimation Duration="0:0:2" From="40" To="80" Storyboard.TargetName="rt_2" Storyboard.TargetProperty="Angle"/></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Loaded" SourceName="win"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Border Width="50" Height="50" Background="Orange" CornerRadius="10"><Border.RenderTransform><TranslateTransform X="0" x:Name="tt" /></Border.RenderTransform><!--想要在现有的空间内显示超出范围的部分 用Canvas--><Canvas><Border Height="20" Width="120" Background="Gray" VerticalAlignment="Bottom" Canvas.Left="13" Canvas.Top="-10" CornerRadius="10"><Border.RenderTransform><RotateTransform Angle="0" x:Name="rt" CenterX="10" CenterY="10" /></Border.RenderTransform><Canvas HorizontalAlignment="Right"><Border Height="13" Width="100" Background="Red" CornerRadius="10" Canvas.Left="-10" Canvas.Top="3.5"><Border.RenderTransform><RotateTransform Angle="0" x:Name="rt_1" CenterX="6.5" CenterY="6.5"/></Border.RenderTransform><Canvas HorizontalAlignment="Right"><Border Background="Green" Height="10" Width="20" CornerRadius="10" Canvas.Left="-6" Canvas.Top="1.5"><Border.RenderTransform><RotateTransform Angle="0" x:Name="rt_2" CenterX="5" CenterY="5" /></Border.RenderTransform></Border></Canvas></Border></Canvas></Border></Canvas></Border></Grid>
</Window>

效果如下:

蚂蚁线
<Window x:Class="XH.AnimationLesson.Demo.AntLineWindow"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:XH.AnimationLesson.Demo"mc:Ignorable="d" Name="win"Title="AntLineWindow" Height="450" Width="800"><!--蚂蚁线--><Window.Resources><Storyboard x:Key="sb" RepeatBehavior="Forever"><DoubleAnimation Duration="0:0:2" From="6" To="0" Storyboard.TargetName="path" Storyboard.TargetProperty="StrokeDashOffset"/></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Loaded" SourceName="win"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Path Data="M0 0 100 100A50 50 0 0 0 200 150" Stroke="Orange" StrokeThickness="5" StrokeDashArray="3 3" StrokeDashOffset="0" Name="path"/></Grid>
</Window>

效果图:

液面
<Window x:Class="XH.AnimationLesson.Demo.WaterWindow"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:XH.AnimationLesson.Demo"mc:Ignorable="d"Title="WaterWindow" Height="450" Width="800"><!--水液面--><Window.Resources><Storyboard x:Key="sb"><DoubleAnimation RepeatBehavior="Forever" Duration="0:0:1" From="0" To="-100" Storyboard.TargetName="tt" Storyboard.TargetProperty="X"/><DoubleAnimation RepeatBehavior="Forever" BeginTime="0:0:0.3" Duration="0:0:1.3" From="0" To="-100" Storyboard.TargetName="tt_2" Storyboard.TargetProperty="X"/><DoubleAnimation RepeatBehavior="Forever" BeginTime="0:0:0.6" Duration="0:0:1.6" From="-100" To="0" Storyboard.TargetName="tt_3" Storyboard.TargetProperty="X"/></Storyboard></Window.Resources><Window.Triggers><EventTrigger RoutedEvent="Loaded"><BeginStoryboard Storyboard="{StaticResource sb}" /></EventTrigger></Window.Triggers><Grid><Border Width="100" Height="100" Background="#ddd"><Border.Clip><EllipseGeometry Center="50 50" RadiusX="50" RadiusY="50" /></Border.Clip><Canvas><Path Data="M0 0A40 40 0 0 0 50 0A40 40 0 0 1 100 0A40 40 0 0 0 150 0 A40 40 0 0 1 200 0 L 200 100 0 100" Fill="Orange"><Path.RenderTransform><TranslateTransform X="-100" Y="40" x:Name="tt" /></Path.RenderTransform></Path><Path Data="M0 0A40 40 0 0 0 50 0A40 40 0 0 1 100 0A40 40 0 0 0 150 0 A40 40 0 0 1 200 0 L 200 100 0 100" Fill="#9f90"><Path.RenderTransform><TranslateTransform X="-100" Y="40" x:Name="tt_2" /></Path.RenderTransform></Path><Path Data="M0 0A40 40 0 0 0 50 0A40 40 0 0 1 100 0A40 40 0 0 0 150 0 A40 40 0 0 1 200 0 L 200 100 0 100" Fill="#9f80"><Path.RenderTransform><TranslateTransform X="0" Y="40" x:Name="tt_3" /></Path.RenderTransform></Path></Canvas></Border></Grid>
</Window>

相关文章:

WPF动画

补间动画&#xff1a;动画本质就是在一个时间段内对象尺寸、位移、旋转角度、缩放、颜色、透明度等属性值的连续变化。也包括图形变形的属性。时间、变化的对象、变化的值 工业应用场景&#xff1a;蚂蚁线、旋转、高度变化、指针偏移、小车 WPF动画与分类 特定对象处理动画过…...

大数据系列之:统计hive表的详细信息,生成csv统计表

大数据系列之:统计hive表的详细信息,生成csv统计表 一、获取源数据库、源数据库类型、hive数据库名称二、获取hive数据库名、hive表名、数仓层级、空间、维护者信息三、统计hive表信息四、统计源库信息五、合并hive表信息六、生成csv统计表七、完整代码一、获取源数据库、源数…...

flutter 画转盘

import package:flutter/material.dart; import dart:math;const double spacingAngle 45.0; // 每两个文字之间的角度 // 自定义绘制器&#xff0c;ArcTextPainter 用于在圆弧上绘制文字 class ArcTextPainter extends CustomPainter {final double rotationAngle; // 动画旋…...

图像识别,图片线条检测

import cv2 import numpy as np # 读取图片 img cv2.imread(1.png)# 灰度化 gray cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)# 边缘检测 edges cv2.Canny(gray, 100, 200) 当某个像素点的梯度强度低于 threshold1 时&#xff0c;该像素点被认为是非边缘&#xff1b;当梯度强度…...

python crawler web page

npm install or pip install 插件 import json import time from openpyxl import load_workbook from pip._vendor import requests from bs4 import BeautifulSoup import pandas as pd import re import xlsxwriter 設置request header header {user-agent: Mozilla/5.0…...

基于QT实现的TCP连接的网络通信(客户端)

上篇介绍了QT实现网络通信的服务器端&#xff0c;还没看服务器的朋友们先去上篇了解&#xff0c;这篇我来实现一下客户端的实现。 首先还是新建一个项目 选择mainwindow类 在通信前将.pro文件的第一行代码中追加network 窗口搭建 在mainwindow.ui中完成一下窗口的搭建 首先在…...

Vue2中watch与Vue3中watch对比

上一节说到了 computed计算属性对比 &#xff0c;虽然计算属性在大多数情况下更合适&#xff0c;但有时也需要一个自定义的侦听器。这就是为什么 Vue 通过 watch 选项提供了一个更通用的方法&#xff0c;来响应数据的变化。当需要在数据变化时执行异步或开销较大的操作时&#…...

Web 3 一些常见术语

目录 Provider 提供者Signer 签名者Transaction 交易Contract 合约Receipt 收据 首先&#xff0c;从高层次上对可用对象的类型及其负责的内容有一个基本的了解是很有用的。 Provider 提供者 一个 Provider 是与区块链的只读连接&#xff0c;允许查询区块链状态&#xff0c;例…...

揭开数据分析中的规范性分析:从入门到精通

目录 引言1. 规范性分析的基本概念2. 规范性分析的方法论2.1 线性规划&#xff1a;资源利用最大化2.2 决策树分析&#xff1a;直观的选择路径2.3 贝叶斯网络&#xff1a;应对不确定性的利器2.4 多目标优化&#xff1a;平衡多重目标的艺术 3. 规范性分析的实际应用3.1 商业决策中…...

Linux文件IO

目录 前言 一.文件操作 系统调用接口 1.打开文件 2.关闭文件 3.读取文件 4.写入文件 二.文件描述符 重定向 三.动静态库 前言 在Linux操作系统中&#xff0c;文件I/O是一个核心概念&#xff0c;涉及如何读写文件、与设备通信以及如何管理数据流。Linux下一切皆文件, …...

ccfcsp-202309(1、2、3)

202309-1 坐标变换&#xff08;其一&#xff09; #include <bits/stdc.h> using namespace std; int main() {ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);int n, m;cin >> n >> m;int x, y;int opx 0, opy 0;for(int i 0; i < n; i){cin &g…...

数据结构--数据结构概述

一、数据结构三要素 1. 数据的逻辑结构 数据的逻辑结构是指数据元素之间的关系和组织方式&#xff0c;通常分为线性结构和非线性结构。 线性结构&#xff1a;例如线性表&#xff0c;其中数据元素按照顺序排列&#xff0c;彼此之间存在一对一的关系。 非线性结构&#xff1a;…...

Spring中的BeanFactoryAware

BeanFactoryAware 是 Spring 框架中的一个接口&#xff0c;用于在 Spring 容器中获取 BeanFactory 实例。实现这个接口的类可以在其属性被设置后获取到 BeanFactory&#xff0c;从而可以访问 Spring 容器中的其他 bean。 BeanFactoryAware 接口概述 BeanFactoryAware 接口位于…...

Neo4j service is not installed

问题&#xff1a; Starting Neo4j. Neo4j service is not installed Unable to start. See user log for details. Run with --verbose for a more detailed error message.解决&#xff1a; neo4j windows-service install neo4j start ok了...

LeetCode 3132.找出与数组相加的整数 II:排序+3次尝试(nlog n)

【LetMeFly】3132.找出与数组相加的整数 II&#xff1a;排序3次尝试(nlog n) 力扣题目链接&#xff1a;https://leetcode.cn/problems/find-the-integer-added-to-array-ii/ 给你两个整数数组 nums1 和 nums2。 从 nums1 中移除两个元素&#xff0c;并且所有其他元素都与变量…...

微信小程序--26(全局配置-1)

一、全局配置文件 1.标志 app.json 2.配置项 pages 记录当前小程序所有页面的存放路径 window 全局配置小程序窗口配置 tabBar 设置小程序底部的tabBar效果 style 是否启用新版本的组将样式 3.window 导航栏区域 navigationBar …...

汽车4S店管理系统-计算机毕设Java|springboot实战项目

&#x1f34a;作者&#xff1a;计算机毕设残哥 &#x1f34a;简介&#xff1a;毕业后就一直专业从事计算机软件程序开发&#xff0c;至今也有8年工作经验。擅长Java、Python、微信小程序、安卓、大数据、PHP、.NET|C#、Golang等。 擅长&#xff1a;按照需求定制化开发项目、 源…...

bug的常见排查和分析思路以及相关的原因分类

作为开发人员&#xff0c;经常会收到来自用户和QA&#xff0c;领导反馈的各种问题。 为了快速问题&#xff0c;我们有时需要站在更高的角度&#xff0c;更全面的看待问题。才能更快锁定问题。 具体的bug还需要结合企业实际业务情况&#xff0c;相关的框架&#xff0c;依赖库&…...

Nature:7个提升科研产出的实用建议

我是娜姐 迪娜学姐 &#xff0c;一个SCI医学期刊编辑&#xff0c;探索用AI工具提效论文写作和发表。 一个值得思考的问题是&#xff1a;层出不穷的效率工具到底是提升还是降低了科研产出&#xff1f; 大学教授萨拉 (Sara) 描述了她典型的工作日场景&#xff1a;"…...

react-native从入门到实战系列教程-页面之间的跳转

路由的跳转,是app开发中需要处理的问题,一个页面不可能装下那么多的内容。在react-native中,我们使用的路由组件跟reactjs中还是有区别的,这里贴出官网的文档:https://reactnavigation.org/docs/navigating 实现效果 安装 按照官网的指导安装即可。代码实现 app.jsx中改造…...

HarmonyOS应用开发者高级认证(一)

1、依次点击A、B、C、D四个按钮&#xff0c;其中不会触发UI刷新的是&#xff1a; 答案&#xff1a; Button("C").onClick(() > {this.nameList[0].name "Jim"})分析&#xff1a;直接更新非一级数据不会触发UI刷新 2、如果要实现Row组件内的子元素均匀…...

【网络】套接字(socket)编程——UDP版

1.socket 1.1.什么是socket Socket 的中文翻译过来就是“套接字”。 套接字是什么&#xff0c;我们先来看看它的英文含义&#xff1a;插座。 Socket 就像一个电话插座&#xff0c;负责连通两端的电话&#xff0c;进行点对点通信&#xff0c;让电话可以进行通信&#xff0c;端…...

一篇文章让你彻底掌握 Shell

大家好&#xff0c;这里是 Lucifer三思而后行&#xff0c;专注于提升数据库运维效率。 文章目录 一篇文章让你彻底掌握 Shell简介什么是 shell什么是 shell 脚本Shell 环境指定脚本解释器 模式交互模式非交互模式 基本语法解释器注释echoprintfprintf 的转义符 变量变量命名原则…...

Java中的Collection集合:深入理解与应用

在Java中&#xff0c;Collection接口是Java集合框架&#xff08;Java Collections Framework&#xff09;的基石之一&#xff0c;它定义了一系列操作对象集合的方法&#xff0c;如添加、删除、遍历等。Collection接口是List、Set和Queue等具体集合类型的父接口&#xff0c;为Ja…...

Kubernetes-K8S

Kubernetes由于单词太长&#xff0c;省略掉中间8个字母简称为K8S。它介于应用服务和服务器之间。能够通过策略协调和管理多个服务&#xff0c;只需要一个YAML文件配置。定义应用的部署顺序等信息&#xff0c;自动部署应用到各个服务器&#xff0c;还可以自动扩容缩容。 架构原理…...

简化文本处理流程,通用文字识别助力提升信息采集效率

随着信息技术的发展、移动设备使用的普及和全球化的商业需求&#xff0c;非结构化数据转换为结构化数据的需求日益增长&#xff0c;数字化成为信息存储和管理的主流趋势。在此背景下&#xff0c;OCR技术应运而生&#xff0c;该技术可以将图像中文本信息转化为计算机等设备可以使…...

【网络】TCP协议通信的重要策略——滑动窗口,快重传,流量控制,拥塞控制,延时应答

目录 MSS值 滑动窗口 滑动窗口与重发机制 快重传机制 滑动窗口与流量控制 滑动窗口与拥塞控制 延时应答 个人主页&#xff1a;东洛的克莱斯韦克-CSDN博客 相关文章 【网络】传输层TCP协议的报头和传输机制-CSDN博客 【网络】详解TCP协议通信时客户/服务端的状态-CSDN博…...

极狐GitLab CI/CD 如何构建镜像并推送到 azure 镜像仓库?

极狐GitLab 是 GitLab 在中国的发行版&#xff0c;专门面向中国程序员和企业提供企业级一体化 DevOps 平台&#xff0c;用来帮助用户实现需求管理、源代码托管、CI/CD、安全合规&#xff0c;而且所有的操作都是在一个平台上进行&#xff0c;省事省心省钱。可以一键安装极狐GitL…...

Leetcode—1143. 最长公共子序列【中等】

2024每日刷题&#xff08;155&#xff09; Leetcode—1143. 最长公共子序列 实现代码 class Solution { public:int longestCommonSubsequence(string text1, string text2) {int m text1.length();int n text2.length();vector<vector<int>> dp(m 1, vector&…...

ZBrush笔刷介绍

根据使用的方法和效果&#xff0c;ZBrush的笔刷可以分类如下&#xff1a; 基本功能笔刷 这些笔刷用于常规的雕刻、移动和平滑操作。 纹理应用笔刷 一般需要自己额外购买的是这三种笔刷 Alpha Brushes&#xff1a;使用灰度图&#xff08;alpha&#xff09;来定义笔刷形状和纹…...

最火的服务器托管/名词解释seo

2.搭建双主双从 编号 角色 Ip地址 机器名 1 Master1 192.168.119.131 Hadoop2 2 Slave1 192.168.119.132 Hadoop3 3 Master2 192.168.119.133 Hadoop1 4 Slave2 192.168.119.134 Hadoop4 2.1修改配置文件 修改四台服务器的/etc/my.cnf文件 ①Master1 [mysqld] server-id1 #…...

苏州模板建站定制/近三天时政热点

在Vmware workstation 9中装了个Linux mint 15试试效果&#xff0c;居然不支持1600x900的分辨率&#xff0c;现在14寸的高分都是这分辨率了。上网搜了搜&#xff0c;把以下代码放到shell文件里能改变分辨率&#xff0c;设成1600x900.Mint15-Mate Xsession.d # cat /usr/local/b…...

莆田做网站建设/优化设计方法

jsp初学者必备知识一、bs模式&#xff0c;cs模式的概念&#xff1a;二、web应用程序是什么三、如何将开发的web项目部署到服务器总结前言 ##刚开始学习jsp应该有点困难吧&#xff0c;掌握这几个基础知识就会好了很多哦&#xff1a;bs模式&#xff0c;cs模式的概念&#xff0c…...

经济型网站建设/百度收录技巧

在 android 的API中有提供 SystemClock.setCurrentTimeMillis()函数来修改系统时间&#xff0c;可惜无论你怎么调用这个函数都是没用的&#xff0c;无论模拟器还是真机&#xff0c;在logcat中总会得到"Unable to open alarm driver: Permission denied ".这个函数需要…...

wordpress怎么汉化插件/河南做网站的公司

In this second part of the series on administration, you will learn how to lock down the site to keep the public from accessing the administration features.在介绍管理部分系列的第二部分&#xff0c;你将学习如何限制访问权限的相关内容。上一节加了三个admin链接&…...

做网站开发的电话销售话术/海城seo网站排名优化推广

测试用例是进行测试的最小单元粒度。在编写测试用例之前需要很多准备工作去分析需求&#xff0c;提取测试点&#xff0c;然后根据提取的测试点选择相应分析方法&#xff0c;来设计测试用例。但测试用例如果要自己在excl手动填写&#xff0c;制作用例模板时&#xff0c;需要注意…...