天天看点

WPF案例(-)模拟Windows7 Win+Tab切换

WPF案例(-)模拟Windows7 Win+Tab切换

    在建立本示例中的三维场景时,使用了Viewport3D,PerspectiveCamera,AmbientLight,Viewport2DVisual3D,RotateTransform3D,TranslateTransform3D,ScaleTransform3D等元素,下面分别简单说明一下这些元素在三维场景中分别充当了什么角色

1.Viewport3D :Viewport3D是一个2D可视化元素,它是在2D场景中封装3D元素的容器控件,具有两个重要的属性

public Camera Camera { get; set; }

public Visual3DCollection Children { get; }

   Camera 为3D场景指定观察者所处的位置

   Children 表示Viewport3D的所有3D子控件的集合类

2.PerspectiveCamera 表示透视投影摄像机,在本示例中使用它对3D场景进行透视投影

3.AmbientLight 灯光用来照亮3D场景

4.Viewport2DVisual3D 在3D场景中呈现可交互的2D控件,在本示例中就使用了6个Viewport2DVisual3D元素分别呈现了六幅Image

5.RotateTransform3D 对3D元素应用旋转,本示例中使用它对Viewport2DVisual3D进行Y轴45度旋转的模型变换

6.TranslateTransform3D 对3D元素应用平移,本示例中使用它对Viewport2DVisual3D分别进行X,Y,Z平移的模型变换

7.ScaleTransform3D 对3D元素应用拉伸缩放,本示例中使用它对Viewport2DVisual3D进行了X,Y的拉伸模型变换

以下为定义3D场景的XAML代码

WPF案例(-)模拟Windows7 Win+Tab切换
WPF案例(-)模拟Windows7 Win+Tab切换

3D场景 

  1  <Viewport3D  x:Name="Viewport3D" RenderOptions.EdgeMode="Aliased" ClipToBounds="False" 

                               IsHitTestVisible="False">

  2             <Viewport3D.Camera>

  3                 <PerspectiveCamera Position="0,0,8"  />

  4             </Viewport3D.Camera>

  5             <Viewport2DVisual3D x:Name="viewport2DVisual3D0" Geometry="{StaticResource geometry}"  

                                Material="{StaticResource material}" >

  6                 <Viewport2DVisual3D.Transform>

  7                     <Transform3DGroup>

  8                         <RotateTransform3D CenterX="0" CenterY="0" CenterZ="0">

  9                             <RotateTransform3D.Rotation>

 10                                 <AxisAngleRotation3D Axis="0,1,0" Angle="35"/>

 11                             </RotateTransform3D.Rotation>

 12                         </RotateTransform3D>

 13                         <TranslateTransform3D OffsetX="0" OffsetY="0" OffsetZ="0"/>

 14                         <ScaleTransform3D CenterX="0" CenterY="0" 

                                   CenterZ="0" ScaleX="1.5" ScaleY="1" />

 15                     </Transform3DGroup>

 16                 </Viewport2DVisual3D.Transform>

 17                 <Viewport2DVisual3D.Visual>

 18                     <Image Source="Images\051027nature01.jpg" Stretch="Fill"

                               HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />

 19                 </Viewport2DVisual3D.Visual>

 20             </Viewport2DVisual3D>

 21             <Viewport2DVisual3D x:Name="viewport2DVisual3D1" Geometry="{StaticResource geometry}" 

                              Material="{StaticResource material}">

 22                 <Viewport2DVisual3D.Transform>

 23                     <Transform3DGroup>

 24                         <RotateTransform3D CenterX="0" CenterY="0" CenterZ="0">

 25                             <RotateTransform3D.Rotation>

 26                                 <AxisAngleRotation3D Axis="0,1,0" Angle="35"/>

 27                             </RotateTransform3D.Rotation>

 28                         </RotateTransform3D>

 29                         <TranslateTransform3D OffsetX="-1" OffsetY="1" OffsetZ="-4"/>

 30                         <ScaleTransform3D CenterX="0" CenterY="0" CenterZ="0" 

                                   ScaleX="1.5" ScaleY="1" />

 31                     </Transform3DGroup>

 32                 </Viewport2DVisual3D.Transform>

 33                 <Viewport2DVisual3D.Visual>

 34                     <Image Source="Images\051027nature02.jpg" Stretch="Fill" 

                                      HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />

 35                 </Viewport2DVisual3D.Visual>

 36             </Viewport2DVisual3D>

 37             <Viewport2DVisual3D x:Name="viewport2DVisual3D2" Geometry="{StaticResource geometry}"

                                     Material="{StaticResource material}">

 38                 <Viewport2DVisual3D.Transform>

 39                     <Transform3DGroup>

 40                         <RotateTransform3D CenterX="0" CenterY="0" CenterZ="0">

 41                             <RotateTransform3D.Rotation>

 42                                 <AxisAngleRotation3D Axis="0,1,0" Angle="35"/>

 43                             </RotateTransform3D.Rotation>

 44                         </RotateTransform3D>

 45                         <TranslateTransform3D OffsetX="-2" OffsetY="1.5" OffsetZ="-8"/>

 46                         <ScaleTransform3D CenterX="0" CenterY="0" CenterZ="0"

                                    ScaleX="1.5" ScaleY="1" />

 47                     </Transform3DGroup>

 48                 </Viewport2DVisual3D.Transform>

 49                 <Viewport2DVisual3D.Visual>

 50                     <Image Source="Images\11550549.jpg" Stretch="Fill" 

                                    HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />

 51                 </Viewport2DVisual3D.Visual>

 52             </Viewport2DVisual3D>

 53             <Viewport2DVisual3D x:Name="viewport2DVisual3D3" Geometry="{StaticResource geometry}" 

                                Material="{StaticResource material}">

 54                 <Viewport2DVisual3D.Transform>

 55                     <Transform3DGroup>

 56                         <RotateTransform3D CenterX="0" CenterY="0" CenterZ="0">

 57                             <RotateTransform3D.Rotation>

 58                                 <AxisAngleRotation3D Axis="0,1,0" Angle="35"/>

 59                             </RotateTransform3D.Rotation>

 60                         </RotateTransform3D>

 61                         <TranslateTransform3D OffsetX="-3" OffsetY="1.5" OffsetZ="-12"/>

 62                         <ScaleTransform3D CenterX="0" CenterY="0" CenterZ="0" 

                                      ScaleX="1.5" ScaleY="1" />

 63                     </Transform3DGroup>

 64                 </Viewport2DVisual3D.Transform>

 65                 <Viewport2DVisual3D.Visual>

 66                     <Image Source="Images\11550556.jpg" Stretch="Fill" 

                             HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />

 67                 </Viewport2DVisual3D.Visual>

 68             </Viewport2DVisual3D>

 69             <Viewport2DVisual3D x:Name="viewport2DVisual3D4" Geometry="{StaticResource geometry}"

                                             Material="{StaticResource material}">

 70                 <Viewport2DVisual3D.Transform>

 71                     <Transform3DGroup>

 72                         <RotateTransform3D CenterX="0" CenterY="0" CenterZ="0">

 73                             <RotateTransform3D.Rotation>

 74                                 <AxisAngleRotation3D Axis="0,1,0" Angle="35"/>

 75                             </RotateTransform3D.Rotation>

 76                         </RotateTransform3D>

 77                         <TranslateTransform3D OffsetX="-4" OffsetY="1.5" OffsetZ="-16"/>

 78                         <ScaleTransform3D CenterX="0" CenterY="0" CenterZ="0"

                                        ScaleX="1.5" ScaleY="1" />

 79                     </Transform3DGroup>

 80                 </Viewport2DVisual3D.Transform>

 81                 <Viewport2DVisual3D.Visual>

 82                     <Image Source="Images\11550560.jpg" Stretch="Fill" 

                                   HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />

 83                 </Viewport2DVisual3D.Visual>

 84             </Viewport2DVisual3D>

 85             <Viewport2DVisual3D x:Name="viewport2DVisual3D5" Geometry="{StaticResource geometry}" 

                                      Material="{StaticResource material}">

 86                 <Viewport2DVisual3D.Transform>

 87                     <Transform3DGroup>

 88                         <RotateTransform3D CenterX="0" CenterY="0" CenterZ="0">

 89                             <RotateTransform3D.Rotation>

 90                                 <AxisAngleRotation3D Axis="0,1,0" Angle="35"/>

 91                             </RotateTransform3D.Rotation>

 92                         </RotateTransform3D>

 93                         <TranslateTransform3D OffsetX="-5" OffsetY="1.5" OffsetZ="-20"/>

 94                         <ScaleTransform3D CenterX="0" CenterY="0" CenterZ="0"

 95                     </Transform3DGroup>

 96                 </Viewport2DVisual3D.Transform>

 97                 <Viewport2DVisual3D.Visual>

 98                     <Image Source="Images\051123Webshots05.jpg" Stretch="Fill" 

                                 HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />

 99                 </Viewport2DVisual3D.Visual>

100             </Viewport2DVisual3D>

101             <ModelVisual3D>

102                 <ModelVisual3D.Content>

103                     <AmbientLight Color="White" />

104                 </ModelVisual3D.Content>

105             </ModelVisual3D>

106 </Viewport3D>

   通过以上的XAML语言定义了一个静态的3D场景,以下的代码实现将此3D场景支持动画效果,即模仿Windows7的Win+Tab切换特效

WPF案例(-)模拟Windows7 Win+Tab切换
WPF案例(-)模拟Windows7 Win+Tab切换

C#动画

  1         public void MoveCurrentToNext()

  2         {

  3             //向前移动,取Viewport3D的第一个Viewport2DVisual3为当前Viewport2DVisual3D

  4             var current = this.Viewport3D.Children[0];

  5             var child1 = this.Viewport3D.Children[1];

  6             var child2 = this.Viewport3D.Children[2];

  7             var child3 = this.Viewport3D.Children[3];

  8             var child4 = this.Viewport3D.Children[4];

  9             var child5 = this.Viewport3D.Children[5];

 10 

 11 

 12             this.Viewport3D.Children.RemoveAt(0);

 13             this.Viewport3D.Children.Insert(5, current);

 14 

 15             var translate = (current.Transform as Transform3DGroup).Children[1] 

                                                        as TranslateTransform3D;

 16 

 17             //对每个Viewport2DVisual3D元素应用平移动画

 18             AnimationVisualElement((current as Viewport2DVisual3D).Visual 

                                                   as FrameworkElement, .3);

 19             AnimationVisualElement(translate, true, -5.0, 1.5, -20.0);

 20 

 21             translate = (child1.Transform as Transform3DGroup).Children[1] 

                                                     as TranslateTransform3D;

 22             AnimationVisualElement(translate, true, .0, .0, .0);

 23 

 24             translate = (child2.Transform as Transform3DGroup).Children[1] 

                                                       as TranslateTransform3D;

 25             AnimationVisualElement(translate, true, -1.0, 1.0, -4.0);

 26 

 27             translate = (child3.Transform as Transform3DGroup).Children[1] 

                                                        as TranslateTransform3D;

 28             AnimationVisualElement(translate, true, -2.0, 1.5, -8.0);

 29 

 30             translate = (child4.Transform as Transform3DGroup).Children[1] 

 31             AnimationVisualElement(translate, true, -3.0, 1.5, -12.0);

 32 

 33             translate = (child5.Transform as Transform3DGroup).Children[1] 

 34             AnimationVisualElement(translate, true, -4.0, 1.5, -16.0);

 35 

 36         }

 37 

 38         public void MoveCurrentToPrevious()

 39         {

 40             //向后移动,取Viewport3D的最后一个Viewport2DVisual3D当前Viewport2DVisual3D

 41             var current = this.Viewport3D.Children[5];

 42             var child1 = this.Viewport3D.Children[0];

 43             var child2 = this.Viewport3D.Children[1];

 44             var child3 = this.Viewport3D.Children[2];

 45             var child4 = this.Viewport3D.Children[3];

 46             var child5 = this.Viewport3D.Children[4];

 47 

 48             this.Viewport3D.Children.RemoveAt(5);

 49             this.Viewport3D.Children.Insert(0, current);

 50 

 51             var translate = (current.Transform as Transform3DGroup).Children[1] 

                                                            as TranslateTransform3D;

 52 

 53             AnimationVisualElement(translate, false, 0.0, 0.0, 0.0);

 55 

 56             translate = (child1.Transform as Transform3DGroup).Children[1] 

                                                       as TranslateTransform3D;

 57             AnimationVisualElement(translate, false, -1.0, 1.0, -4.0);

 58 

 59             translate = (child2.Transform as Transform3DGroup).Children[1] 

 60             AnimationVisualElement(translate, false, -2.0, 1.5, -8.0);

 61 

 62             translate = (child3.Transform as Transform3DGroup).Children[1] 

                                                         as TranslateTransform3D;

 63             AnimationVisualElement(translate, false, -3.0, 1.5, -12.0);

 64 

 65             translate = (child4.Transform as Transform3DGroup).Children[1] 

 66             AnimationVisualElement(translate, false, -4.0, 1.5, -16.0);

 67 

 68             translate = (child5.Transform as Transform3DGroup).Children[1] 

 69             AnimationVisualElement(translate, false, -5.0, 1.5, -20.0);

 70         }

 71         private void AnimationVisualElement(FrameworkElement element, double duration)

 72         {

 73             if (element == null)

 74                 return;

 75             //对Visual元素的Visibility应用动画

 76             ObjectAnimationUsingKeyFrames objectAnimation = new ObjectAnimationUsingKeyFrames();

 77             objectAnimation.KeyFrames.Add(

                  new DiscreteObjectKeyFrame(Visibility.Collapsed, KeyTime.FromPercent(.0)));

 78             objectAnimation.KeyFrames.Add(

                  new DiscreteObjectKeyFrame(Visibility.Visible, KeyTime.FromPercent(1)));

 79             objectAnimation.Duration = TimeSpan.FromSeconds(duration);

 80             objectAnimation.FillBehavior = FillBehavior.Stop;

 81             element.BeginAnimation(FrameworkElement.VisibilityProperty, objectAnimation);

 82 

 83         }

 84         private void AnimationVisualElement(TranslateTransform3D translate, bool forward, 

                                                  double targetX, double targetY, double targetZ)

 85         {

 86             Duration duration = new Duration(TimeSpan.FromSeconds(.4));

 87             //对TranslateTransform3D的X偏移量应用动画

 88             DoubleAnimation animationX = new DoubleAnimation();

 89             animationX.To = targetX;

 90             animationX.Duration = duration;

 91             animationX.AccelerationRatio = forward ? 0 : 1;

 92             animationX.DecelerationRatio = forward ? 1 : 0;

 93             translate.BeginAnimation(TranslateTransform3D.OffsetXProperty, animationX);

 94             //对TranslateTransform3D的Y偏移量应用动画

 95             DoubleAnimation animationY = new DoubleAnimation();

 96             animationX.To = targetY;

 97             animationX.AccelerationRatio = forward ? 0.7 : 0.3;

 98             animationX.DecelerationRatio = forward ? 0.3 : 0.7;

 99             animationX.Duration = duration;

100             translate.BeginAnimation(TranslateTransform3D.OffsetYProperty, animationX);

101             //对TranslateTransform3D的Z偏移量应用动画

102             DoubleAnimation animationZ = new DoubleAnimation();

103             animationZ.To = targetZ;

104             animationZ.AccelerationRatio = forward ? 0.3 : 0.7;

105             animationZ.DecelerationRatio = forward ? 0.7 : 0.3;

106             animationZ.Duration = duration;

107             translate.BeginAnimation(TranslateTransform3D.OffsetZProperty, animationZ);

108         }

     在以上代码中主要实现了对ViewPort3D的6个子Viewport2DVisual3D分别应用TranslateTransform3D的平移动画,TranslateTransform3D具有三个跟位置有关的属性,分别表示X轴偏移量OffsetX,Y轴偏移量OffsetY,以及Z轴偏移量OffsetZ

    由于OffsetX,OffsetY,OffsetY在TranslateTransform3D中被定义为Double类型的依赖项属性,因此可以使用DoubleAnimation对属性的目标值定义动画效果,最后通过TranslateTransform3D的BeginAnimation方法分别对OffsetX,OffsetY,OffsetY属性应用动画

    最后定义快捷键事件,按下Ctrl+Down组合键,图片向前滑动,按下Ctrl+Up组合键,图片向后滑动

WPF案例(-)模拟Windows7 Win+Tab切换
WPF案例(-)模拟Windows7 Win+Tab切换

定义快捷键 

 1  private void Window_KeyDown(object sender, KeyEventArgs e)

 2         {

 3             if (e.KeyStates == Keyboard.GetKeyStates(Key.Down) && 

 4                         Keyboard.Modifiers == ModifierKeys.Control)

 5             {

 6                 //向前移动Visual元素

 7                 this.MoveCurrentToNext();

 8             }

 9             else if (e.KeyStates == Keyboard.GetKeyStates(Key.Up) && 

10                        Keyboard.Modifiers == ModifierKeys.Control)

11             {

12                 //向后移动Visual元素

13                 this.MoveCurrentToPrevious();

14             }

15             else if (e.KeyStates == Keyboard.GetKeyStates(Key.Escape))

16             {

17                 //注销

18                 Application.Current.Shutdown();

19             }

20         }

    注:在本示例中连续使用了6个Viewport2DVisual3D三维元素,并且在每个Viewport2DVisual3D元素的Visual上宿主一个二维的Image控件,对于本示例,为优化性能,应尽可能的减少Viewport2DVisual3D的数目,在这里一个好的方法是使用三维元素ModelVisual3D来代替Viewport2DVisual3D,将六幅图片分别定义成Material,再将Material应用到六个对应的GeometryModel3D三维模型中,最后使用Model3DGroup将六个GeometryModel3D三维模型打包作为ModelVisual3D的Content属性值,因此只需要一个ModelVisual3D就可实现相同的功能并能优化了性能