关于游戏引擎PushButton的教程和演示(一)
我对Flash并没有比大家更多的认识(我的朋友都知道,我不过只是做些ASP.NET动态网站和进行些浏览器编程,如ExtJs,jQuery),一个偶然的想法,我打开了FlexBuilder,辗转多个网页,感谢chrome,让我找到了PushButton,以下教程的大部分内容都来自于Matthew Casperson的博客,如果你也像我一样,对PushButton或者游戏开发忽然很感兴趣,请跟着Matthew Casperson一起开始游戏之旅。
如果你需要了解PushButton,你只需要在Google上搜索flex pushbutton就能获得一个关于 PushButton的概括性介绍,比较关键的介绍是,这是一个模块化的以组件为核心的游戏引擎(在以后的开发中,您将有深刻的体会),对于网络中的些许介绍,我想声明一点的是,当前的版本为r470,我并没有发现一些博客中所提到的ProjectManager.air(这困扰了我很久),不过很快你将发现这并不影响什么。
http://pushbuttonengine.com/,官方论坛,在这里你能找到你想要的大部分,包括下载链接以及http://pushbuttonengine.com/forum/index.php,PushButton的官方论坛,社区里人们很友善,这里包括技术交流也有组件买卖。
Get Started
开始PushButton,首先你需要下载当前的最新版本(http://pushbuttonengine.googlecode.com/files/PushButtonEngine-r470.zip),这是当前的稳定版本,能够解决足够的问题。下载完毕后,您要保证的是您的开发工具完备,我对Flash并不熟悉,我只是一个半路出家的和尚,所以我选择Flex(基于 Eclipse,让我觉得舒服)。
解压后我们找到PushButton的类库所在,在Bin文件夹中我找到了PBEngine.swc(这花了我一阵时间来研究swc在flash中的职责),也就是我们需要引用的类库文件。我在上面提到过,并没有发现有些帖子博客中提到的Manager.air,在这里我们直接在Flex中新建一个Flex项目,在建立时在lib文件夹中引入PBEngine.swc,到这里我们的准备工作就基本结束了。
为了证明我们的操作成功与否,我们需要做一些测试证明一下。我们在 <mx:Application
xmlns:mx="http://www.adobe.com/2006/mxml"
layout="absolute"
applicationComplete="appComplete()"
width="480"
height="384" backgroundGradientAlphas="[1.0, 1.0]" backgroundGradientColors="[#A53EE1, #C8C8C8]">标签中设置了应用程序结束时调用的 appComplete方法,在这个方法中我们需要调用
protected function appComplete():void
{
Global.startup(this);
用Matthew Casperson
的话就是,当我们要用PushButton做什么事情之前,首先一定要调用Global.startup(this);这是一切的基础
。
然后让我们做一个简单的动画(一个屏幕上的圆,来完成我们第一期的练习)。
首先,在PushButton中,所有的东西都称之为”Entity“ 翻译成实体也好,所以,要显示一个圆,
我们需要两个实体,首先我们需要一个类似于舞台类似于场景的东西我们称之为 ”Scene“(这在以后的例子中仍然会用到),然后需要一个圆,放到这个"Scene"中去。
在PushButton中,组件构成了实体,实体就像一个空的盒子一样,每放入一个组件,盒子将拥有一个新的功能和特点。PushButton并没有采用传统的继承的设计模式,并没有在创建一个实体的时候创建一个类,而是实现了一个接口Entity的一个对象,并包含了实现其他功能接口的组件,由实体包裹着组件(模块化的思想渐渐付出水面,但是精彩的还在后面,这种模块化让你想到了什么?XML?)。
我们创造了一个工厂类来产生我们需要的实体,以供在应用程序入口Main.mxml中调用
2 <mx:Application
3 xmlns:mx="http://www.adobe.com/2006/mxml"
4 layout="absolute"
5 applicationComplete="appComplete()"
6 width="480"
7 height="384">
8
9 <mx:Script>
10 <![CDATA[
11
12 import com.pblabs.engine.core.*;
13
14 protected function appComplete():void
15 {
16 Global.startup(this);
17
18 EntityFactory.createScene("scene");
19 EntityFactory.createPlayer("player", "scene");
20 }
21
22 ]]>
23 </mx:Script>
24
25 </mx:Application>
26
在 EntityFactory中,我们先创建Scene。
2 {
3 import mx.core.*;
4
5 import com.pblabs.engine.core.*;
6 import com.pblabs.engine.entity.*;
7 import com.pblabs.rendering2D.*;
8 import com.pblabs.rendering2D.ui.*;
9
10 import flash.geom.Point;
11
12 public class EntityFactory
13 {
14 static protected const SCENE_SPATIAL_COMPONENT:String = "Spatial";
15 static protected const SCENE_RENDERER_COMPONENT:String = "Renderer";
16
17 static public function createScene(name:String):IEntity
18 {
19 var Scene:IEntity = allocateEntity();
20 Scene.initialize(name);
21
22 var Spatial:BasicSpatialManager2D = new BasicSpatialManager2D();
23 Scene.addComponent( Spatial, SCENE_SPATIAL_COMPONENT );
24
25 var Renderer:Scene2DComponent = new Scene2DComponent();
26 Renderer.spatialDatabase = Spatial;
27
28 var View:SceneView = new SceneView();
29 View.width = Application.application.width;
30 View.height = Application.application.height;
31 Renderer.sceneView = View;
32
33 Renderer.position = new Point(0,0);
34 Renderer.renderMask = new ObjectType("Renderable");
35
36 Scene.addComponent( Renderer, SCENE_RENDERER_COMPONENT );
37
38 return Scene;
39 }
在类的数据成员我们发现了两类组件的标记常量,一个叫"Spatial",一个叫"Renderer",由于我并没有从事过动画创作和任何游戏开发,我只能在开发中逐渐理解他们的含义,最简单的理解就是Spatial组件负责空间上的事务,如位置(position),大小(size)等等,而 Renderer组件则负责处理渲染事务,关于什么叫渲染我并没有专业开发人员更理解,不过它决定了物体的形状,外貌等等。
在创建Scene时,需要特殊注意的是,实体Scene的组件Render同样需要一个View来将Scene渲染上去,这个时候我们需要创建一个SceneView如上代码所示。
然后我们需要创建Player,也就是那个球。
2 {
3 var entity:IEntity = allocateEntity();
4 entity.initialize(name);
5
6 var Spatial:SimpleSpatialComponent = new SimpleSpatialComponent();
7
8 Spatial.spatialManager = NameManager.instance.lookupComponentByName(scene, SCENE_SPATIAL_COMPONENT) as ISpatialManager2D;
9
10 Spatial.objectMask = new ObjectType("Renderable");
11 Spatial.position = new Point(0,0);
12 Spatial.size = new Point(50,50);
13
14 entity.addComponent( Spatial, "Spatial" );
15
16 var Render:SimpleShapeRenderComponent = new SimpleShapeRenderComponent();
17
18 Render.showCircle = true;
19 Render.radius = 25;
20 Render.positionReference = new PropertyReference("@Spatial.position");
21
22 entity.addComponent( Render, "Render" );
23
24 return entity;
25 }
26
27 }
28 }
读者会发现和Scene的创建非常的类似,在Spatial决定了大小和位置后,Render中指定了这是显示一个圆,并描述这个圆的半径是25,在这里我们需要注意的是在Render的定义中,我们需要与Spatial的属性进行关联, 比如这里我们需要这个物体的空间位置,所以出现了 Render.positionReference = new PropertyReference("@Spatial.position");
在后面我们还会遇到和大小相关联等等。
运行在FlexBuilder中运行我们的项目,您会得到一个圆,这时候,恭喜你,您已经迈出了第一步。
我很喜欢PushButton,希望您也可以继续。
以上部分内容,来自 Matthew Casperson的博客http://www.bukisa.com/articles/225827_pushbutton-tutorial-series-getting-started
Demo代码下载页面http://www.brighthub.com/hubfolio/matthew-casperson/media/p/61000.aspx
下一期我们将尝试让这个球随着我们的键盘动起来。
感谢 Matthew Casperson,感谢无私的分享。