您的位置:首页 > 其它

Flash 3D引擎(Sandy3D)应用指南 6 —— 导入外部3D模型 Part2

2009-06-27 09:28 344 查看
指南目标

在这个Part2的指南中,我们将学到怎么直接导入一个3DS MAX提供的文本格式的ASE文件.这里要考虑反复转换3DS和ASE的文件格式。你将会看到需要编写和理解更多的代码,但我相信我们不会有太大的问题。

怎么做

在下面的文档中你会找到一个叫“asset”的目录存放了从3DS max导出的文件。

example007.zip

代码:

package {
import flash.display.Sprite;
import flash.events.*;
import sandy.core.Scene3D;
import sandy.core.data.*;
import sandy.core.scenegraph.*;
import sandy.materials.*;
import sandy.materials.attributes.*;
import sandy.primitive.*;
import sandy.parser.*;

public class Example007 extends Sprite {
private var scene:Scene3D;
private var camera:Camera3D;
private var pot:Shape3D;

public function Example007() {
var parser:IParser = Parser.create("asset/teieraASE.ASE",Parser.ASE );

parser.addEventListener( ParserEvent.FAIL, onError );
parser.addEventListener( ParserEvent.INIT, createScene );
parser.parse();
}

private function onError( pEvt:ParserEvent ):void {
trace("there is an error in loading your stuff");
}

private function createScene(p_eEvent:ParserEvent ):void {
camera = new Camera3D( 300, 300 );
camera.y = 30;
camera.z = -200;

var g:Group = Group( p_eEvent.group);

pot = g.children[0] as Shape3D;
pot.x = 0;

var materialAttr:MaterialAttributes = new MaterialAttributes(new LightAttributes( true, 0.2 ) );
var material:Material = new ColorMaterial( 0xE0F87E, 0.9, materialAttr);
material.lightingEnable = true;
var app:Appearance = new Appearance( material);

pot.appearance = app;

scene = new Scene3D( "scene", this, camera, g );

addEventListener( Event.ENTER_FRAME, enterFrameHandler );
}

private function enterFrameHandler( event : Event ) : void {
pot.pan +=3;
scene.render();
}
}
}

分析代码

与之前的指南的第一个不同是我们需要import一个我们之前没有import的包:

...

import sandy.parser.*;

然后我们定义一个新的变量与之前的(pot 变量)的名称相同但属于不同的类型:Shape3D.这是因为需要与模型交互,我们就需要一个Shape3D的对象。

private var pot:Shape3D;

现在来到最重要的部份了你将会看到与之前的工作有多少不同,先看看代码,然后我们现解释这些代码:

var parser:IParser = Parser.create("asset/teieraASE.ASE",Parser.ASE );
parser.addEventListener( ParserEvent.FAIL, onError );
parser.addEventListener( ParserEvent.INIT, createScene );
parser.parse();

就像你看到的,在我们的类的构造函数里并没有放置Camera3D对象和Scene3D。这是因为我们没有我们的模型对象,而且我们也不知道我们能不能导入它、解析这个模型要多长时间,或我们不知道这个模型文件有没有被破坏。所以一个好的方式是这样:

1、我们先初始化一个Parser类说明我们将要进行解析。

2、我们加入两个监听器:一个用来监听导入过程中是否有错误发生,另一个监听导入过程是否完成。

3、然后调用方法开始进行解析过程。

我们现在解释一下createScene(p_eEvent:ParserEvent) 方法,这与之前的例子很不同,实际上这是一个事件的回调函数。

关键点在于:

var g:Group = Group( p_eEvent.group);

就是这“简单”的一行代码我们能看到当分发器包含一个节点元素时这个事件会被激发,这个就是我们需要传进Scene3D的构造函数的Group对象。所以就是这么简单,我们手里有一个分组包含了人们要导入的模型。

Group类有方法可以返回一个Node元素的数组,我们只需要测试这些节点是否存在或它们是不是Shape3D对象。因为这是一个简单的代码同时我们知道只有一个节点在这个Group对象里,我们把这个节点传换为Shape3D类型赋给我们的"pot"对象。

pot = g.getChildFromId(1) as Shape3D;

然后我们只需要应用一个皮肤到我们的对像我们就完成了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: