Balder 3D开发系列之--创建基本动画

本文详细介绍了如何在Balder框架中使用故事板(Storyboard)实现模型沿不同轴旋转的动画效果,包括添加组合框选择旋转方向、关键代码解析以及实际应用案例。

一、对于前一篇创建天空盒的一点补充

    

       在之前那篇文章中,我们在天空盒中创建了一块木板,但是,你会发现,这块木板还不够真实,因为在天空中是有太阳的,我们从不同的视角去观察它,应该出现明暗变化,为了达到这样的效果,我们只需要对Box做如下修改:

1     < Geomentry:Box  Dimension ="20,1,20"  InteractionEnabled ="True"  x:Name ="box"    >
2                   < Geomentry:Box.Material >
3                       < Material:Material  Ambient ="Black"   Specular ="White"  Shade ="Gouraud"  DiffuseMap ="/MaterialDemo;component/Assets/f.png"   />
4                   </ Geomentry:Box.Material >
5               </ Geomentry:Box >

仔细观察,就会发现,我们增加了Ambient(环境光),Specular(镜面反射),Shade(阴影)效果,就行了。具体关于它们的介绍,请参考3D设计光线相关资料,对此,由于笔者对此不熟悉,就不多做介绍了,以免误导他人。

 

二、本篇主题Balder中的动画

        


          Balder中的动画,其实,在之前的文章中已经使用过了,具体请看Sprite初次相遇,这时,你会骂道:“楼主,这。。这。。已经讲过了,也用过了,还将个屁啊。”没错,其实,今天讲的动画和那个动画一样又有点不一样。在上次中,我们看到主要代码是这样的:

 1  < Grid.Triggers >
 2    < EventTrigger  RoutedEvent ="Grid.Loaded" >
 3    < BeginStoryboard >
 4    < Storyboard  AutoReverse ="true"  RepeatBehavior ="Forever" >
 5    < DoubleAnimation  Storyboard.TargetName ="Camera"  Storyboard.TargetProperty ="(Camera.Position).(X)"  From ="-100"  To ="100"  Duration ="00:00:05" >
 6    < DoubleAnimation.EasingFunction >
 7    < ElasticEase />
 8    </ DoubleAnimation.EasingFunction >
 9    </ DoubleAnimation >
10    </ Storyboard >
11    </ BeginStoryboard >
12    </ EventTrigger >
13    </ Grid.Triggers >

这里是使用了一个事件触发器,来触发动画,但是,你要知道,在Silverlight中,RoutedEvent只是支持Loaded事件的,如果你要更大的灵活性,那怎么办?例如你要点击某个按钮来触发动画,什么时候让动画停止,开始另一个动画,这不是说使用触发器是不行的,只是操作起来相对不是那么直接了,你需要这样做:



  • 要对不属于控件的对象的属性进行动画处理,请将演示图板放在页面或应用程序的常规 Resources
    中。然后在放置"Triggers"的元素上分配一个事件处理程序。响应相关事件时,该事件处理程序应从资源字典中检索演示图板。然后,您对检索到的 Storyboard 调用 Begin



  • 要对属于控件的对象的属性进行动画处理(派生自 Control),请使用 VisualStateManager
    技术,并通过调用 GoToState
    基于控件的状态或输入信息运行适当的动画。

  • (以上摘自Silverlight官方文档)

 

         
,为此,还是选择对后台代码进行动画编程比较直接。而且,你会发现官方的例子,它的动画大多数都是在xaml中定义的,关于这方面,之前园子里Nowpaper已经介绍过一些了,请看这里http://www.cnblogs.com/nowpaper/archive/2010/11/16/1878242.html ,这里已经介绍了balder中的简单动画,而且讲得很好,其实,那篇文章中简单的动画总结起来就是通过计时器来定时的对模型和场景的观察角度和观察位置的变化,或者对模型直接的位置和角度变化。我们今天讲另一种动画实现方法:通过使用storyboard(故事板)来进行。

       storyboard相信大家都很熟悉,就是通过时间线控制动画,并为其子动画提供对象和属性目标信息。子动画有DoubleAnimation,ColorAnimation等等,这里我们是对模型或者摄像机的坐标进行变化,所以应该是DoubleAnimation,主要进行的属性变化当然是Position了,其中,Position又有三个分量:X,Y,Z分别代表各个方向轴坐标的坐标点。所以设置模型的目标属性是(Node.Position).(X),摄像机的目标属性是:"(Camera.Position).(X)" ,但是你会发现,这里每个动画都都具体到每个X,Y,Z分量,如果我们要同时进行X,Y,Z三个方向的动画就得定义三次。为此,在balder中针对于这种情况,封装了两个类:

1.CoordinateAnimation

2.StoryboardExtensions

其中,CoordinateAnimation类的结构比较简单:

 

 1  public   class  CoordinateAnimation
 2   {
 3    public   string  TargetName {  get set ; }
 4    public   string  TargetProperty {  get set ; }
 5    public  DependencyObject Target {  get set ; }
 6    public  Coordinate From {  get set ; }
 7    public  Coordinate To {  get set ; }
 8    public  IEasingFunction EasingFunction {  get set ; }
 9    public  TimeSpan ?  BeginTime {  get set ; }
10    public  Duration Duration {  get set ; }
11   }
12 

而相对复杂的是StoryboardExtensions,要注意的是它是一个静态类,因此,在使用的时候不能对它进行实例化,而是通过使用其静态方法:static void SetCoordinateAnimation(DependencyObject obj, CoordinateAnimation coordinateAnimation)

来进行初始化,方法中的参数obj是一个依赖对象,这里只要传入一个Storyboard实例就行了,而后面的参数就是一个CoordinateAnimation类的对象,这个对象在之前就设置好里面的各个属性,例如TargetName,TargetProperty,Target等属性。特别需要注意的是Target属性,如果没有指定的话,会出现TargetName 无法解析的异常。那么使用这个类,为什么能实现三个坐标方向的动画呢?秘密就在StoryboardExtensions类中,在它内部,对Storyboard添加了三个分量的自对象:

1.story board.C hildren.Add(xAnimation);
2.storyboard.Children.Add(yAnimation);
3.storyboard.Children.Add(zAnimation);
这一切都归功于依赖属性的强大之处。说了那么多,我们还是来实战一下吧,还是在上次木板天空盒的例子上更改:我是对木板实现各个方向的旋转动画。




三、实战动画之旋转




因为是旋转,因此,这里的TargetProperty不是Position而是Rotation。
第一步:
打开上次的工程,在xaml中我们添加一个ComboBox,来提供不同方向的旋转:
         <ComboBox Width="100" Height="40" SelectionChanged="ComboBox_SelectionChanged" Margin="30">
                <ComboBoxItem Content="沿着X轴转动" IsSelected="True"/>
                <ComboBoxItem Content="沿着Y轴转动"/>
                <ComboBoxItem Content="沿着Z轴转动"/>
            </ComboBox>

第二步:
在后台代码的SelectionChanged事件处理程序中添加如下关键代码:
 1   CoordinateAnimation  ca = new  CoordinateAnimation();
 2                  ca.From  = new  Balder.Math.Coordinate( 0 , 0 , 0 ); // 沿着X轴旋转360度
 3                  ca.To  =   new  Balder.Math.Coordinate( 365 , 0 , 0 );
 4                  ca.TargetProperty  =   " (Node.Rotation) " ;        // 目标属性
 5                  ca.TargetName  =   " box " ;
 6                  ca.Target  =  box;                              // 目标对象
 7                  ca.Duration  =  TimeSpan.FromMilliseconds( 1000 );
 8                  Storyboard sb  =   new  Storyboard();
 9                  sb.RepeatBehavior  =  RepeatBehavior.Forever;
10                  StoryboardExtensions.SetCoordinateAnimation(sb, ca);
11                  
12                  sb.Begin();
这里只给出了关键代码,因为其余几个方向的操作与之相似,就不多啰嗦了,另外要注意的是这个box是在xaml中的Box对象的实例,在xaml中的定义是:x:Name=“box”,然后在后台代码中引用,还有别忘记引用命名空间:Balder.Animation.Silverlight;最后看看效果:


转载于:https://my.oschina.net/u/1446855/blog/643516

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值