egret-docs-master/Engine3D/Egret3DCamera/animation/README.md

154 lines
4.5 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

在3D Max中可以通过时间轴制作摄像机动画你可以通过Egret3D所提供得插件将制作好的摄像机动画导出为`eca`格式文件,并通过在程序中对该文件的解析,生成摄像机动画。
为了方便查看效果我们首先在3D MAX中制作一个简单的摄像机动画。3D MAX中场景如下
![](575cd31ccd58b.png)
摄像机运动轨迹如下:
![](575cd3235cbe6.gif)
我们以摄像机视角,查看整个场景运行效果如图:
![](575cd32284507.gif)
通过Egret3D插件导出其动画文件名称为`Camera001.eca`,由于当前场景中摄像机名称为`Camera001`,所有导出文件保留其元素命名。
你需要借助`URLLoader`类来加载`Camera001.eca`文件,当文件加载完成后,得到的数据`evt.target.data`其数据类型为`egret3d.CameraAnimationController`。
在Egret3D中控制摄像机的动画类由`CameraAnimationController`实现,每一帧中的数据由`CameraAnimationFrame`实现。
当你的数据加载并解析完成后,你就可以使用这个`CameraAnimationController`。当在使用之前,你需要通过其中的`bindCamera`方法绑定要控制的摄像机。
具体编码步骤如下:
1、加载`eca`文件
```
var load:egret3d.URLLoader = new egret3d.URLLoader();
load.addEventListener(egret3d.LoaderEvent3D.LOADER_COMPLETE,this.com,this);
load.load("resource/Camera001.eca");
```
```
private ani:egret3d.CameraAnimationController;
private com(evt:egret3d.LoaderEvent3D)
{
this.ani = evt.target.data;
}
```
2、绑定摄像机
```
this.ani.bindCamera(this._view.camera3D);
```
3、注册刷新
```
this.canvas.addEventListener(egret3d.Event3D.ENTER_FRAME,this.update,this);
```
```
private update(evt:egret3d.Event3D)
{
this.ani.update(10,16);
}
```
每一次调用`CameraAnimationController`的`update`方法,才会更新一次摄像机动画。每一次更新,`update`方法需要两个参数。第一个参数为当前时间,第二个参数为每帧时间间隔。
4、播放动画
```
this.ani.play(true);
```
`play`方法中,参数如果为`true`,则摄像机动画循环播放。
5、暂停动画
```
this.ani.stop();
```
6、监听动画播放完毕事件
```
this.ani.addEventListener(egret3d. CameraAnimationController.EVENT_CAMERA_COMPLETE,this.AniComplete,this);
```
摄像机动画的事件直接封装到了`CameraAnimationController`中,并没有单独放置于独立的事件类中。
上述示例完整代码如下:
```
class CameraAni extends LoadingUI
{
private _view:egret3d.View3D;
protected canvas:egret3d.Egret3DCanvas;
public constructor()
{
super();
this.CloseLoadingView();
this.canvas = new egret3d.Egret3DCanvas();
this.canvas.x = 0;
this.canvas.y = 0;
this.canvas.width = window.innerWidth;
this.canvas.height = window.innerHeight;
this.canvas.start();
this._view = new egret3d.View3D(0,0,window.innerWidth,window.innerHeight);
this.canvas.addView3D(this._view);
this._view.backColor = 0x00ff00;
this.createCub();
this._view.camera3D.lookAt(new egret3d.Vector3D(300, 500, -1000), new egret3d.Vector3D(0, 0, 0));
var load:egret3d.URLLoader = new egret3d.URLLoader();
load.addEventListener(egret3d.LoaderEvent3D.LOADER_COMPLETE,this.com,this);
load.load("resource/Camera001.eca");
}
private cube:egret3d.Mesh;
private mat:egret3d.TextureMaterial;
private createCub()
{
var mat:egret3d.TextureMaterial = new egret3d.TextureMaterial();
var go:egret3d.CubeGeometry = new egret3d.CubeGeometry(10,10,10);
var cube:egret3d.Mesh = new egret3d.Mesh(go, mat);
this._view.addChild3D(cube);
}
private ani:egret3d.CameraAnimationController;
private com(evt:egret3d.LoaderEvent3D)
{
this.ani = evt.target.data;
this.ani.bindCamera(this._view.camera3D);
this.ani.play(true);
this.canvas.addEventListener(egret3d.Event3D.ENTER_FRAME,this.update,this);
}
private update(evt:egret3d.Event3D)
{
this.ani.update(10,16);
}
}
```
编译并运行,效果如图:
![](575cd31ce7598.gif)
## 摄像机帧数据
由于摄像机动画相对比较简单,不涉及变形等信息,只包含了时间和摄像机在三维空间中的运动轨迹于姿态。你可以通过`CameraAnimationController`类中的`cameraAnimationFrames`属性获取当前摄像机动画的全部帧数据。每个帧数据的内容可参考`CameraAnimationFrame`类的API内容。