冒险岛论文
序号:_____________
编码:_____________
XXX大学第一届学生科技文化节
课外学术科技作品竞赛
Flash游戏《超级冒险岛》 作品类别:发明制作(应用软件)
二零零六年九月
XXX大学第一届学生科技文化节组委会
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
目 录
摘 要 ................................................................................................................................................... 4
第一章 绪论 ........................................................................................................................................ 5
1.1 Flash游戏的现状 ................................................................................................................... 5
1.2 Macromedia Flash介绍 .......................................................................................................... 5
1.3 Flash游戏应具有的特征 .................................................................................................... 5
1.4 本游戏背景介绍.................................................................................................................... 5 第二章 开发环境及相关技术的介绍 ................................................................................................. 7
2.1 开发环境 ............................................................................................................................... 7
2.2程序设计语言概述及特点 ..................................................................................................... 7 第三章 程序结构、思想和相关技术 ................................................................................................. 9
3.1 本程序需要解决的主要技术问
........................................................................................ 9
3.2游戏制作过程中遇到的问题 ................................................................................................. 9
3.3游戏的实现........................................................................................................................... 10
3.3.1设计主人公角色影片片段架构 ................................................................................ 10
3.3.2主人公血条的实现方法: ........................................................................................ 13
3.3.3利用键盘控制主人公角色: .................................................................................... 15
3.3.4设计敌人角色影片片段框架: ................................................................................ 15
3.3.5让敌人角色动起来:................................................................................................... 16
3.3.6处理各对象之间的相互冲突: ................................................................................ 17
3.3.7声音处理方法:........................................................................................................... 19
3.4 游戏的制作流程.................................................................................................................. 19
3.4.1建立主角 .................................................................................................................... 19
3.4.2让主人公动起来 ........................................................................................................ 22
3.4.3制作敌人角色 ............................................................................................................ 29
3.4.4设计主人公打到敌人的程序 .................................................................................... 36
3.4.5设计敌人打到主人公的程序 .................................................................................... 37
3.4.6多个敌人复制与场景的移动 .................................................................................... 39
3.4.7声音的添加 ................................................................................................................ 56
3.5 GIF图片格式简介 ............................................................................................................... 57
3.6 玩家人物的控制方式和敌人方的智能运行 ...................................................................... 57
第四章 程序分析和具体实现 ........................................................................................................... 61
4.1地图的创建........................................................................................................................... 61
4.2地图的移动........................................................................................................................... 61
4.3对象的碰撞检测及相关属性 ............................................................................................... 67
4.4玩家3次游戏机会的实现方法 ........................................................................................... 68
4.5普通敌人相关属性............................................................................................................... 69
4.6白云的实现原理................................................................................................................... 74
4.7关尾BOSS及相关属性 ....................................................................................................... 74
4.8玩家人物的控制方式和敌人方的智能运行 ....................................................................... 80
第五章 游戏测试............................................................................................................................... 84
5.1游戏测试概述....................................................................................................................... 84
5.2 游戏测试目的...................................................................................................................... 84
5.3游戏测试与开发过程的关系 ............................................................................................... 85 2
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
5.4游戏可玩性测试................................................................................................................... 85
5.5游戏的运行环境................................................................................................................... 85 第六章 总结 ...................................................................................................................................... 86
【参考文献】..................................................................................................................................... 86
3
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 摘 要:这款游戏的名字叫《超级冒险岛》,所用的开发工具是Macromedia Flash 6.0。Macromedia Flash技术是近年来比较热门的一项功能强大的动画游戏开发技术。它已经成为游戏制作,网站开发的有利工具。
随着电脑的日益普及,Flash已经对丰富人们的生活
、加快网络信息的传播以及游戏娱乐中起着不可忽视的作用。本论文着眼于Flash技术的应用,开发一款游戏程序。本程序将网络游戏《冒险岛》移植到Flash中,为广大游戏爱好者尤其是喜爱Flash游戏的爱好者提供一个单机版的“超级冒险岛”。本论文介绍了Flash的相关技术及本程序的结构分析和具体功能的实现。
关键字:Flash;游戏;超级冒险岛;单机版
4
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 第一章 绪论
1.1 Flash游戏的现状
游戏是Flash制作中很重要的一部分,主要应用的是flash内嵌的action编程脚本。近期国内涌现出了很多优秀的FLASH游戏,譬如小小的《过关斩将II》,JQ的《狙击手I代》和《狙击手II代》等。由于Flash是一种基本上不受运行环境影响的,可在多平台上运行的程序,并可以通过网络实现实时游戏,因此受到了广大Flash游戏爱好者的喜欢。越来越多的Flash游戏爱好者不仅仅是玩Flash游戏,有些爱好者还参与到了Flash游戏的制作和开发中,从而推动了Flash游戏的迅速发展。
1.2 Macromedia Flash介绍
Macromedia Flash 是一种创作工具,设计人员和开发人员可使用它来创建演示文稿、应用程序和其它允许用户交互的内容。Flash中可以包含简单的动画、视频内容、复杂演示文稿和应用程序以及介于它们之间的任何内容。通常,使用 Flash 创作的各个内容单元称为应用程序,即使它们可能只是很简单的动画。您可以通过添加图片、声音、视频和特殊效果,构建包含丰富媒体的Flash应用程序。它的前身是FutureSplash,是早期网上流行的矢量动画插件。后来由于Macromedia公司收购了FutureSplash以后便将其改名为Flash2。它是针对矢量图形编辑和动画创作的专业软件,目前,它已经升级到Flash MX版本,功能十分强大。正是因为它采用了矢量图形编辑制作,使得Flash输出的电影动画(*.swf)具有文件小、效果好、图像细腻、对网络带宽要求低以及可无损放大等诸多优点,从而,深受广大电脑动画设计者和网页设计者的喜爱。可以说,Flash已经渐渐成为交互式矢量的
,未来游戏和网页的一大主流。
1.3 Flash游戏应具有的特征
一个Flash游戏应该具有以下特征:
易于操作: 既然Flash游戏面向的是普通玩家而不是计算机专家,那么他们不可能深入的学习游戏技巧。玩家不会花几个小时去研究一个游戏的操作方法。保持游戏的简单是最基本的要求。
游戏体积较小:Flash游戏是一种可以在网页浏览中就可以快速运行的小游戏,为了满足在网页中就可以快速浏览,所以它的体积必须要很小。
丰富的社会交互:不管一个游戏设计得多好,只要玩家找到了它的根本模式或者玩完了所有的游戏路径很快就会厌烦这个游戏。在今天纷繁复杂的多玩家游戏中具有丰富社会交互的游戏证明是成功的。
利用网络技术的优点:当今社会中发达和可靠的网络技术为Flash游戏的发展拓宽了一个平台,作为一个好的Flash游戏应该充分利用网络游戏,实现实时在线游戏。
1.4 本游戏背景介绍
5
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
主人公阿宝来到一座充满怪物的小岛上,那些怪物对阿宝两面夹击,为了逃出荒岛,主人公进行了英勇的奋战,以此为故事情节制作游戏。
主人公的进攻方式有站立攻击、跳跃攻击、卧下攻击三种招式,被怪物击中会减少一定血量,如果消耗所有血量就会出现游游戏结束画面并结束游戏。敌人被主人公击打到一定程度后便会死去,当打到一定数量的敌人后,则在屏幕 上会出现胜利的画面。
决斗游戏比较复杂,需要注意相互间动作及冲突,各对象状态等。首先设计出主人公进行攻击的结构和敌人的进攻结构,当然要以各对象为单位制作影片片段。用Flash制作游戏(最重要的是要把各个对象设计成影片片段。
6
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 第二章 开发环境及相关技术的介绍 2.1 开发环境
操作系统:Microsoft Windows 2000
程序语言:Flash ActionScript3.0
开发平台:Macromedia Flash 6.0
2.2程序设计语言概述及特点
本游戏的开发采用了ActionScript3.0,ActionScript3.0包括二部分: 核心语言和flash player API 。核心语言用于定义编程语言的结构,譬如声明、 表示、条件、循环和类型 。flash player API是由一系列精确定义flash player功能的类组成。
ActionScript3.0拥有尽可能的挖掘出计算机剩余性能的新特点。规则表示支
ECMAScript for XML (E4X) 使得XML 成为通用数持使操作性更加强大的XML。
据类型, 将大大地简化XML 处理。新的Display ListAPI将使虚拟对象更加的协
事件模型使得那些对象的表示和响应结合的更加强劲。 调一致。规范化的DOM
ActionScript 3.0的出现是ActionScript 2.0 的核心语言方面融入ECMAScript 以遵守其标准和引入新的改进的一些功能区域的结合。
下面是一些Actionscript3.0语言特点:
1.增强处理运行错误的能力
应用ActionScript 2.0时, 许多表面上“完美无暇”的运行错误无法得到记载。这使得flash player无法弹出提示错误的对话框, 就象javascript语言在早期的浏览器中所表现的一样。也就是说, 这些缺少的错误
使得我们不得不花更多精力去调试ActionScript 2.0程序。ActionScript 3.0 引入在编译当中容易出现的更加广泛的错误的情形, 改进的调试方式使得能够健壮地处置应用项目当中的错误。提示的运行错误提供足够的附注(例出出错的源文件)和以数字提示的时间线, 帮助开发者迅速的定位产生错误的位置。
2.对运行错误的处理方式
在ActionScript 2.0中,运行错误的注释主要提供给开发者一个帮助,所有的帮助方式都是动态的。而在ActionScript且是3.0中, 这些信息将被保存到一定的数量,Flash player将提供时间型检查以提高系统的运行安全。这些信息将记录下来用于监视变量在电脑中的运行情况, 以使得开发者能够让自己的应用项目得到改进以减少对内存的使用。
3.密封的类
ActionScript 3.0 将引入密封的类的概念。在编译时间内的的密封类拥有唯一固定的特征和方法,其它的特征和方法不可能被加入。这使得比较严密的编译时间检查成为可能, 创造出健壮的项目。因而它当然可以提高对内存的使用效率, 因为不需要为每一个对象实例增加内在的杂乱指令。当然动态类依然可以使用只要声明为dynamic的关键字。
4.代理方式
在ActionScript 3.0中事件处理变的更加简化归功于它的嵌入式代理方式。而在ActionScript 2.0中, 方法关闭后并没有记住什么对象事例引用了它们, 当
7
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 调用已经关闭的方法时将导致意想不到的后果。
5.ECMAScript 中的 XML (E4X)
ActionScript 3.0 特点之一是全面支持ECMAScript中的 XML (E4X), 最新的规范标准为ECMA-357 。E4X 提供一种自然, 流利的语言使得能够快速的构造XML 。而不是象传统XML的解析接口一样, E4X使得XML成为通用的数据类型。E4X 简化操作XML将大大的减少相当数量的代码以适用应用项目需要的发展。
规范的表达方式 6.
ActionScript 3.0 引入支持通用规则使得能够迅速搜寻和快速的操作字符(串)。ActionScript 3.0实施规则定义在第三版的ECMAScript 语言说明书当中(ECMA-262) 。
7.命名空间(Namespaces)
Namespaces 是一种创新新机制用以控制声明的可见性。 Namespaces 与传统通过指定类型用以控制声明(公开的, 私有的, 保护的)是相似的 。他们本质是通过自定义路径, 能够使用你所选择的名字。Flex, 例如, 使用一mx_internal 命名空间为它的内部数据来源。命名空间使用统一的资源标识符(URI)以避免冲突 ,当与E4X一起使用时同样可以使用XML命名空间。
8.新的整数类型
ActionScript 2.0用Number定义有单精度数字类型和双精度浮点数字类型。受欢迎的新的Int数据类型将加入到ActionScript3.0当中。int是一个32位有符号整型数据类型, 使得CPU将提高ActionScript代码中处理整数运算的能力,int将提高循环运算以及几乎其它不带小数点的整数运算。另一个新的数据类型是uint, 一个与int相似的无符号32位整数型 。uint 主要用于表现象索颜色和其它一些int所不能很好工作的领域。
8
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 第三章 程序结构、思想和相关技术 3.1 本程序需要解决的主要技术问题
1. 玩家主角的运行可以通过键盘响应事件控制,但敌方则因为是自动运行,就需要有一定的智能性;敌人的运行算法也要进行相关的设置,已免游戏过于简单。
2.对于双方的行走应该赋予不同的速度,同时,程序应该设定敌人与敌人不会发生碰撞检测,以免重叠运行,而对敌人进行攻击时也应可以同时攻击数个敌人,以增加游戏的可玩性。
3.为了增加界面的美观,在程序中添加了白云。由于手机屏幕大小有限,所以白云的数量和出现的位置要经过相关的设置,才能实现白云不规则出现的效果。
4.玩家主角的前进应与地图相结合,由于是ACT动作游戏,因此玩家主角应与地图同步,否则会使游戏失真。
5.Flash软件主要针对的是失量图形,而在本游戏中使用了位图,因此如果图片太大,则会导致游戏体积增大,影响游戏的运行速度。因此要利用效少的图片以达到最好的效果。
. 游戏的结束、开始、动态信息画面作为构成一个程序都是必不可少的重6
要部分。良好的用户界面更是吸引用户的硬指标,相关的美术构图和人性化设置也需要有一定的考虑。
以上相关技术细节和整体流程将分别在以下小节阐述。
3.2游戏制作过程中遇到的问题
主人公的跳跃:
当主人公跳跃后如何使他能够与地面接触并停止呢,在Flash中可以通过检测碰撞来实现,程序如下:
if (_root.stage.land.hitTest(_x, _y, true)) {
this.standUp.gotoAndStop("行走");
this._x -= xSpeed;
//取消原速度
xSpeed = 0;
ySpeed = 0;
jump = false;
} else if (!_root.stage.land.hitTest(_x+12, _y+1, true)
and !_root.stage.land.hitTest(_x-12, _y+1, true) and jump == false) {
jump = true;
}
程序中的_root.stage.land指的是地面,而hitTest()中的坐标则是指主人公的某点的坐标,当主人公与地面接触后,通过xSpeed=0 和 ySpeed=0 来使主角停下来。然而当运行此段程序后,出现了一个致命的问题。如图:
9
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
可以看到主人公竟然跳到地面下去了,这是什么原因呢,我思考了许久,发现this._x-=xSpeed这条语句中的xSpeed的值比较大,使得主人公影片剪辑一直向下运动,而碰撞检测语句无法及时对主角反应,因此主角会跳到寺面下去了。在以上代码中我加上了一条语句,情况就改变了,代码如下:
for (; _root.stage.land.hitTest(_x, _y, true); ) {
_y = _y-1;
}
此段代码是利用for循环语句使得主人公影片剪辑向上运动,从而抵消向下运动的“惯性”,这样,主角看上去就好像是跳到地面后就立即停止。效果如图:
3.3游戏的实现
3.3.1设计主人公角色影片片段架构
首先要考虑主人公的各种动作,即进攻动作有哪些,什么时候被敌人击打,什么情况下
主人公会牺牲等。首先制作处理主人公一切动作的具有代表性的“主人公影片”的影片片段,然后制作主人公基本动作中的坐姿或站姿。但坐着和站着时的进攻方式不同,这一点正是两者的区别。
10
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
把影片剪辑分为战姿和坐姿,站着和坐着时候动作不一样,所以在“战姿”影片片段应集中主人公所有能做的动作。
11
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
把主人公所有动作以Label方式区分开来,这样只需要简单移动到Label处就能完成进攻动作。其他方法也是同样的道理。另外“坐姿”影片片段也使用同一种方法制作。
12
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
根据动作的不同分为各自的Label,然后插入动作动画。接下来以各个片段为单位添加实例,从面可以在外部制约。
3.3.2主人公血条的实现方法:
如图可以看到血条带有渐变的效果,这是如何做出来的呢,
在该血条影片剪辑中,使用了三个图层,如图:
最底层(xie):
中间层(yie):
最上层:
最底层的图片是固定不动的,而只需要上面两层的图片进行渐进就可以了。利用_xScale属性就可以很容易的做到这一点。
首先需要对该影片剪辑进行初始化:代码如下:
onClipEvent (load) {
finish=false;
13
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
xzd = yzd=0; //xzd代表最上层血条的当前值,yzd代表中间层血条的当前值
bhz = 0; //bhz表示总的减少的血量值
this.xie._xscale = xzd; //xie._xscale是最上层图片的缩放比率,当为0时该图片不可见
this.yie._xscale = yzd; //yie._xscale是中间层图片的缩放比率,当为0时该图片不可见
function energySub() { //函数enerySub启到的主要作用是使最上层图片进行渐进,也
if (xzd != bhz) { 就是表示血量减少的过程
if (xzd<100) {
xzd++;
}
} else {
finish = true; //此处是关键,使得血条产生游戏中的效果
}
this.xie._xscale = xzd;
}
}
下面就是当主角被击中后血量减少的方法:
首先利用检测碰撞来判断主人公是否被击中,然后利用代码对上面的两个图层的图片进行控制,代码如下:
if (this.hitTest(_root.chman.standUp.bodyhit) == true) { //this代表敌人的身体,表示碰撞攻击
if (_root.energyLine.xzd<100 and _root.energyLine.finish ==
true) { //用来判断主人公血条的血量是否达到最大值,即死亡
_root.energyLine.finish = false; //防止程序重复执行
_root.energyLine.bhz = _root.energyLine.xzd+5; //主角减少5点血
if (_root.energyLine.bhz>=100) { //判断当主角的血量减少到100后执行以下代码
_root.energyLine.yie._xscale = 100; //血条影片剪辑的中间层图片的缩放比率为100
root.chman.standUp.gotoAndPlay("死亡"); //主角跳转到“死亡”帧
} else {
_root.energyLine.yie._xscale += 5; //血条影片剪辑的中间层放大5,
_root.onEnterFrame = function() { //调用energySub()函数,血条影片剪辑的中间层图片产生渐近效果
_root.energyLine.energySub();
};
_root.chman.standUp.gotoAndPlay("受伤"); //主角跳转到“受伤”帧
14
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
}
}
} else if (this.hitTest(_root.chman.sitDown.bodyhit) == true) { //
当趴下时执行的受伤效果
"); _root.chman.gotoAndStop("站姿
//_root.chman.standUp.gotoAndPlay("受伤");
}
在以上的代码中,血条影片剪辑中的中间层和最上层两层图片分别起到不同的效果,中间层是使图片的缩放率快速增大5%,而最上层是使图片以1%的缩放率逐渐增大,从而产生一种比效好的视觉效果。总的来说血条的渐近效果就是利用图片的遮挡和缩放比率的变化来实现的。
3.3.3利用键盘控制主人公角色:
按键的处理主要是在“主人公影片”的影片片段实例中添加CljpAction和enterFrame事件,这是每次更新时激发Key处理方法的一种方式。该方式根据帧频的数值来检查键的输入,是一般的arcade性游戏中处理键盘输入的最常用的方法之一。
onClipEvent(load){
//键输入处理方法
Function keyInMove(){
If(key.isDown(key.RIGHT)){
//当按下右方向键时处理
}
If(key.isDown(keyLEFT)){
//当按下左方向键时处理
}
onClipEvent(enterFrame){
keyInMove()
}
3.3.4设计敌人角色影片片段框架:
制作敌人的影片片段过程与制作主人公时的几乎相同,因为主人公和敌人的进攻动作规律相同。
15
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
在本游戏中共制作了8种怪,此处只例举一种怪的动作,敌人动作共分为走动、头顶、(跳跃)、挨打、死掉五种Label。需要制作一个执行这种动作的影片片段。不需要向主人公影片片段那样分为两个阶段来制作。因为敌人的影片片段不像主人公影片片段那样分为坐姿和站姿(它只有一种站立的形式,所以只需把五种动作动画以LabeI为单位制作即可。
3.3.5让敌人角色动起来:
敌人角色刚开始还没有生成在舞台中,要等到游戏开始后利用attachMovie来直接添加到舞台中。首先设定好Linkage,然后将库中的影片片段直接拖到舞台中。 16
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
之后把生成的敌人角色以适当大小添加到舞台中。如果敌人角色生成在舞台的左方,则让他向右移动,如果生成在右方(则让他向左移动、使他慢慢接近主人公角色。即向主人公接近的过程中,要检查主人公是否从旁边经过,并且走到一定距离后主动进攻主人公。
moveArrow = random(2)+1;
if (moveArrow == 1) {
//从左端出现
this._xscale = -math.abs(this._xscale);
this._x = -20;
} else {
//从右端出现
this._xscale = math.abs(this._xscale);
this._x = 540;
}
this._y = 404;
3.3.6处理各对象之间的相互冲突:
17
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
严格来说这里的冲突是一个不可见的小方框与敌人角色之间的冲突。
而且敌人角色也同主人公角色一样,通过一个不可见的小方框来实现相互间的冲18
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 突处理。
If(this.hitTest(主人公实例){
Trace(“主人公被头顶”)
}
可利用hitTest来简单处理冲突问题。
3.3.7声音处理方法:
在Flash中输出声音的方法大体有两种。第一种,是直接施放到舞台中。这种方法较简单。只要将声音文件从库中拖到舞台中即可。我们在决斗游戏中也使用了此方法。另一种方法是使用代码来控制声音。这种方法与将库中的影片片段以Action的形式插入到舞台的方法非常相似。首先定义Linkage的Identifier, 然后通过该标识符来控制SoundClip。
MySound=new Sound(this); //生成相应时间轴的声音对象
MySound.attachSound(标识符名称) //将影片片段中的标识符名添加进去 MySound.start(); //开始播放声音
就用这种方式来控制声音。举个例子,像主人公角色的声音,他在攻击敌人时要发出
“嗖”的声音,而在被敌人挨打时要发出。“呃”的声音,而两种声音可能重叠在一
起,此时用Action来控制的话效果会很理想。即使用“声音对象(stop()”Action来停止
“嗖”声音,再用声音对象attachSound(标识符名称)来添加“呃”。声音片段后, 使用“声音对象.start“来播放声音即可。
3.4 游戏的制作流程
3.4.1建立主角
1(执行[修改]->[文档]命令,将Frame Rate设置为12fps, 尺寸的宽属性设置
为552,高属性设置为502后,单击[确定]按钮。
19
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
2(执行[插入]->[新建元件]命令,制作主角影片剪辑。
3.点击,文件,,>,导入,,将主角的图片导入到舞台中,并设置主角的尺寸为W:87,H:103
4.用鼠标右控单击主人公角色,执行[Edit]命令。
5. 制作“主角“影片片段的编辑画面由站姿和坐姿两个Label构成。并且为两种姿势的影片剪辑分别命名,站着时为StandUp,坐着时为SitDown。 20
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
6.进入“StandUp”影片剪辑中,为主角制作各种站姿的动作:
7(进入“SitDown”影片剪辑中,为主角制作各种坐姿的动作:
21
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
3.4.2让主人公动起来
这次接着上例来制作新的影片片段。利用“主人公影片”来实现坐、站、行
的效果。现在就开始一步步地了解。 1(为主角添加走动的动作帧:
从第一帧到第七帧为主角走动的动画 ?第一帧代码:
this.stop();
?第二帧代码:
this.play();
?第七帧代码:
this.gotoAndPlay("行走"); 2(为主角添加攻击的动作帧: 22
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
从第八帧到第三十四帧为主角攻击的动画,一共包括三种攻击动作 第十三帧,第二十三帧,第三十四帧添加帧动作:
this.gotoAndStop("行走");
其他帧上写上代码:
this.play();
3(为主角添加受伤的动作帧:
从第三十五帧到第三十七帧为主角受伤的动作帧
?第三十五帧代码为:
_parent.attackNumber = 0; _parent.attackFlag = 1;
_parent.attackDead = 1;
speed_x = 20;
speed_y = 20;
diejump = false;
_parent.ySpeed = 0;
this.play();
?第三十六帧代码为:
dx = this._parent._x-snail_x; function deadjump() {
if (_root.stage.land.hitTest(this._parent._x, this._parent._y+1,
true) and diejump == true) {
for (; _root.stage.land.hitTest(this._parent._x, this._parent._y,
true); ) {
this._parent._y = this._parent._y-1;
}
diejump = false;
23
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_global.testBit = false;
_global.bridge = true;
_global.time = 30;
this.gotoAndStop("行走");
} else {
if (dx>=0) {
this._parent._x += speed_x;
speed_y -= 5;
this._parent._y -= speed_y;
} else {
this._parent._x -= speed_x;
speed_y -= 5;
this._parent._y -= speed_y;
}
diejump = true;
}
if (this._parent._x<=0 or this._parent._x>=552) {
speed_x = 0;
speed_y = 0;
}
if (random(2) == 0) {
this._parent._alpha = 20;
} else {
this._parent._alpha = 80;
}
}
this.deadjump();
?第三十七帧代码为:
this.gotoAndPlay(36);
4(为主角添加死亡的动作帧:
第三十八帧为主角死亡的动作帧
代码为:
this.stop();
_parent.attackFlag = 1; _parent.attackDead = 1; 24
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
5(为主角添加跳跃的动作帧:
第三十九帧为主角跳跃的动作帧
代码为:
this.stop();
_parent.attackFlag = 0; 6(主角的坐姿动作同上。
?为主角添加坐下的动作
第一帧为主角坐下的动作帧
代码为:
this.stop();
?为主角添加攻击的动作
第二帧到第七帧为主角卧下攻击的动作
第七帧代码为:
_parent.attackFlag = 0; _parent.attackNumber = 0; this.gotoAndStop("坐下");
其他帧代码为:
this.play();
25
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
7(重新回到_root中,赋予ActionScript。用鼠标右键单击放在舞台中的“主人公影片”,执行Action命令来赋予动作。
代码如下:
onClipEvent (load) {
_global.testBit = false;
_global.bridge = false;
jump = true;
attackDead = 0;
beforeState = 0;
nowState = 0;
attackFlag = 0;
attackNumber = 0;
this.swapDepths(600);
function stateCheck() {
//状态函数
if (attackFlag == 0) {
if (beforeState != 2 and nowState == 2) {
this.gotoAndStop("站姿");
this._xscale = math.abs(this._xscale);
this.standUp.gotoAndStop("行走");
} else if (beforeState != 4 and nowState == 4) {
this.gotoAndStop("站姿");
this._xscale = -math.abs(this._xscale);
this.standUp.gotoAndStop("行走");
} else if (beforeState != 3 and nowState == 3) {
this.gotoAndStop("坐姿");
this.sitDown.gotoAndStop("坐下");
}
}
}
function attackCheck() {
//攻击函数
if (attackFlag == 0) {
if (attackNumber == 1) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击1");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
26
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
} else if (attackNumber == 2) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击2");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
} else if (attackNumber == 3) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击3");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
}
}
}
function keyInMove() {
if (attackFlag == 0) {
if (Key.isDown(Key.RIGHT) and 552>(this._x)) {
xSpeed = 6;
nowState = 2;
stateCheck();
beforeState = 2;
this.standUp.play();
} else if (Key.isDown(Key.LEFT) and 0<(this._x)) {
xSpeed = -6;
nowState = 4;
stateCheck();
beforeState = 4;
this.standUp.play();
} else if (Key.isDown(Key.DOWN) and jump == false) {
standDo = 1;
nowState = 3;
stateCheck();
beforeState = 3;
} else {
if (standDo == 1) {
27
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
standDo = 0;
nowState = 0;
beforeState = 0;
this.gotoAndStop("站姿");
this.standUp.gotoAndStop("行走");
}
}
}
}
function keyInJump() {
this._y -= ySpeed;
if (jump == false) {
xSpeed = 0;
}
if (nowState == 4 or nowState == 2 or nowState == 0) {
if (Key.isDown(90) and jump == false and attackDead == 0 and
testBit == false) {
ySpeed = 30;
jump = true;
this.standUp.gotoAndStop("跳跃");
}
}
if (_root.stage.land.hitTest(_x, _y, true)) {
_root.jumpMusic = new Sound();
_root.jumpMusic.attachSound("sound10");
_root.jumpMusic.start(0, 1);
for (; _root.stage.land.hitTest(_x, _y, true); ) {
_y = _y-1;
}
this.standUp.gotoAndStop("行走");
this._x -= xSpeed;
//取消原速度
xSpeed = 0;
ySpeed = 0;
jump = false;
} else if (!_root.stage.land.hitTest(_x+12, _y+1, true)
and !_root.stage.land.hitTest(_x-12, _y+1, true) and jump == false) {
jump = true;
}
if (jump == true) {
ySpeed -= 5;
}
}
function keyInAttack() {
28
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
if (attackFlag == 0) {
if (Key.isDown(88)) {
if (jump == false) {
attackNumber = Math.ceil(Math.random()*3);
attackCheck();
} else {
attackNumber = Math.ceil(Math.random()*2)+1;
attackCheck();
}
}
}
}
function dieBridge() {
if (bridge == true) {
if (random(2) == 0) {
_root.chman._alpha = 20;
} else {
_root.chman._alpha = 80;
}
_global.time -= 1;
if (time<=0) {
_root.chman._alpha = 100;
_global.bridge = false;
}
}
}
}
onClipEvent (enterFrame) {
this.keyInMove();
this.keyInJump();
this.keyInAttack();
this.dieBridge();
}
8(按Ctrl+Enter键执行制作好的范例,用方向键左右移动。若向下移动则角色
慢慢蹲下来。
这些值是刚才在前面保存了输入键值的变量,就是用它来完成主人公按方向键左
右移动和坐下的动作。
3.4.3制作敌人角色
制作完主人公的基本动作之后,开始制作敌人的角色。 基本制作流程:
1. 执行[插入]->[新建元件]命令,制作敌人影片剪辑。
29
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
2.点击,文件,,>,导入,,将蓝蜗牛的图片导入到舞台中
3.为蓝蜗牛添加走动的动作帧:
? 第一帧代码为:
function init() {
//xMove表示向左,yMove表示向右
var deer;
xMove = -1;
yMove = 1;
turning = 5;
oldspeed = speed=random(2)+1;
state = 1;
moveArrow = random(2)+1;
stickHit = false;
myName = getProperty(this, _name);
stickName = eval("_root." add myName add "-blood");
if (moveArrow == 1) {
//从左端出现
this._xscale = -math.abs(this._xscale);
this._x = -20;
} else {
//从右端出现
this._xscale = math.abs(this._xscale);
this._x = 540;
}
this._y = 404;
}
this.init();
? 第二帧代码为:
30
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 function moveChar(dirx) {
if (dirx == -1) {
this._xscale = math.abs(this._xscale);
this._x += speed*dirx;
}
if (dirx == 1) {
this._xscale = -math.abs(this._xscale);
this._x += speed*dirx;
}
}
function moveing(numk) {
//从右端出现
if (numk == 2) {
if (this._x>=552) {
this._x -= speed;
if (xMove == 1) {
xMove = -xMove;
moveChar(xMove);
}
}
if (this._x<=0) {
xMove = -xMove;
moveChar(xMove);
}
if (this._x<552 and this._x>0) {
if (random(200)>turning) {
if (!this.range.hitTest(_root.chman._x, _root.chman._y-26,
true)) {
moveChar(xMove);
} else {
this.gotoAndPlay("头顶");
}
} else {
if (xMove != 0) {
deer = xMove;
}
xMove = random(3)-1;
}
}
//从左端出现
} else if (numk == 1) {
if (this._x<=0) {
this._x += speed;
if (yMove == -1) {
31
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
yMove = -yMove;
moveChar(yMove);
}
}
f (this._x>=552) { i
yMove = -yMove;
moveChar(yMove);
}
if (this._x<552 and this._x>0) {
if (random(200)>turning) {
if (!this.range.hitTest(_root.chman._x, _root.chman._y-26,
true)) {
moveChar(yMove);
} else {
this.gotoAndPlay("头顶");
}
} else {
if (yMove != 0) {
deer = yMove;
}
yMove = random(3)-1;
}
}
}
}
function loseing() {
timer -= 1;
if (timer<=0) {
_global.arrayStick[j] = 0;
stickHit = false;
stickName._x = 378;
stickName._y = -20;
clearInterval(missing);
}
}
function hitCheck(targetObj, targetScore) {
if (this.snailHit.hitTest(targetObj)) {
if (stickName.finish == true) {
_root.damageMusic_1 = new Sound();
_root.damageMusic_1.attachSound("sound16");
_root.damageMusic_1.start(0, 1);
}
timer = 5;
if (stickHit == false) {
32
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
stickHit = true;
for (i=0; i<5; i++) {
if (arrayStick[i] == 0) {
_global.arrayStick[i] = 1;
j = i;
stickName._x = 378;
stickName._y = 20*(i+1)+15;
missing = setInterval(loseing, 1000);
break;
}
}
}
if (stickName.xzt<100 and stickName.finish == true) {
stickName.finish = false;
stickName.zzt = stickName.xzt+targetScore;
if (stickName.zzt>=100) {
stickName.fuller = true;
stickName.onEnterFrame = function() {
stickName.monEnergySub();
};
_global.arrayStick[j] = 0;
stickHit = false;
clearInterval(missing);
this.gotoAndPlay("死掉");
} else {
stickName.onEnterFrame = function() {
stickName.monEnergySub();
};
this.gotoAndPlay("受伤");
}
}
}
}
this.moveing(moveArrow);
this.hitCheck(_root.chman.standUp.attackHit, random(10)+15);
this.hitCheck(_root.chman.sitDown.attackHit, 20);
? 第三帧代码为:
this.gotoAndPlay("走动");
4(为蓝蜗牛添加攻击的动作帧:
33
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
第四帧到第五帧为蓝蜗牛攻击的动作帧
? 第四帧代码为:
var speed = 3;
var dx;
tracker = function () {
manx = getProperty("/chman", _x);
dx = manx-this._x;
25, true)) { if (this.range.hitTest(_root.chman._x, _root.chman._y-
if (this.snailHit.hitTest(_root.chman.standUp.attackHit) == false
and this.snailHit.hitTest(_root.chman.sitDown.attackHit) == false) {
if (Math.abs(dx)>=speed+23) {
this._x += ((dx>=0) ? speed : -speed);
}
} else {
this.hitCheck(_root.chman.standUp.attackHit, random(10)+15);
this.hitCheck(_root.chman.sitDown.attackHit, 20);
}
} else {
speed = oldspeed;
gotoAndPlay("走动");
}
updateAfterEvent();
};
/* run it*/
this.tracker();
? 第五帧代码为:
this.gotoAndPlay("头顶");
5.为蓝蜗牛添加受伤的动作帧:
34
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
第六帧到第七帧为蓝蜗牛攻击的动作帧
? 第六帧代码为:
function hitSinceMove() {
manxx = getProperty("/chman", _x);
dxx = manxx-this._x;
if (moveArrow == 2) {
if (dxx>=0) {
this._xscale = -math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
this._x -= speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
if (dxx<0) {
this._xscale = math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
this._x += speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
}
if (moveArrow == 1) {
if (dxx>=0) {
this._xscale = -math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
this._x -= speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
35
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
if (dxx<0) {
this._xscale = math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
this._x += speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
}
}
this.hitSinceMove();
? 第七帧代码为:
this.gotoAndPlay("受伤");
6(为蓝蜗牛添加死亡的动作帧:
第作帧为蓝蜗牛死亡的动作帧
代码为:
this.stop();
7.现在按Ctrl+Enter键确认结果,屏幕上会看到敌人角色从左边或右边出来向
主人公进行头颅攻击。
3.4.4设计主人公打到敌人的程序
1.在玩家主角影片剪辑中增加新的图层,并添加一新的影片剪辑,将其命名为
attackHit.。
如图:
36
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
1onClipEvent (enterframe){
//主人公站着时的实例。站着时为
_parent.chMainHitCheck(_root.chMan.standup.attackHit);
公坐着时的实例。坐着时为 //主人
_parent.chMainHitCheck(_root.chMan..sitDown.attackHit);
}
此行为的作用是在首先判断攻击时是否与方框发生冲突,然后决定是否调出“chMainStroke”。
2(将attackHit实例的Alpha值设置为0,使黑色方框变透明。 3.在“主人公影片”影片片段中“站姿”影片片段的ActionScript图层第17帧处插入帧动作。
_parent.attackFlag=0;
this.gotoAndStop(“走动”);
其作用是被打到以后初始化为原来的状态。
4.在“坐姿”影片片段的ActionScript图层的第42帧处插入帧动作。 _parent.attackFlag=0;
this.gotoAndStop(“坐姿”);
上述两组代码的第2行中定义了站着时和坐着时的初始化过程。当站着时转到相应的时间轴的“走动”Label处,当坐着时转到“坐姿”Label处,使受到攻击后也处于坐姿状态。
3.4.5设计敌人打到主人公的程序
首先在蓝蜗牛影片剪辑中增加一层,并添加一新的影片剪辑,将其命名为snailHit.。
如图:
37
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
在该影片剪辑中添加代码为:
onClipEvent (load) {
this._visible = false;
}
onClipEvent (enterFrame) {
if (bridge == false) {
if (this.hitTest(_root.chman.standUp.bodyhit) == true) {
_global.snail_x = getProperty(_parent, _x);
_global.testBit = true;
_root.chman.attackFlag = 1;
_root.chman.attackDead = 1;
if (_root.energyLine.xzd<100 and _root.energyLine.finish ==
true) {
_root.energyLine.finish = false;
_root.energyLine.bhz = _root.energyLine.xzd+5;
if (_root.energyLine.bhz>=100) {
_root.energyLine.yie._xscale = 100;
_root.onEnterFrame = function() {
_root.energyLine.energySub();
};
_root.chman.standUp.gotoAndPlay("死亡");
} else {
_root.energyLine.yie._xscale += 5;
_root.onEnterFrame = function() {
_root.energyLine.energySub();
};
_root.chman.standUp.gotoAndPlay("受伤");
}
}
} else if (this.hitTest(_root.chman.sitDown.bodyhit) == true) {
38
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_root.chman.gotoAndStop("站姿");
//_root.chman.standUp.gotoAndPlay("受伤");
}
}
}
通过此代码可以盘断主人公是否与蓝蜗牛发生碰撞,从而使主角执行“受伤”或“死亡”的动作。
3.4.6多个敌人复制与场景的移动
1(执行[插入]->[新建元件]命令,制作一空影片剪辑,并将其拖到舞台上。
2(在此影片剪辑中添加如下代码:
onClipEvent (load) {
game_1 = false;
game_2 = false;
game_3 = false;
game1_1 = false;
game1_2 = false;
game1_3 = false;
game2_1 = false;
game2_2 = false;
game2_3 = false;
game3_1 = false;
game3_2 = false;
game3_3 = false;
game3_4 = false;
game4_1 = false;
game4_2 = false;
game4_3 = false;
game4_4 = false;
game5_1 = false;
game5_2 = false;
_global.nummer = false;
m1 = m2=0;
hx1 = hx2=hx3=hx4=hx5=0;
}
onClipEvent (enterFrame) {
if (life == 1) {
m1 += 1;
if (m1 == 30) {
_root.ding.start(0, 1);
_root.chman.standUp.gotoAndStop("行走");
_root.chman._y = 365.6;
_root.chman._visible = true;
39
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_root.energyLine.finish = true;
_root.energyLine.xzd = _root.energyLine.yzd=0;
_root.energyLine.bhz = 0;
_root.energyLine.xie._xscale = 0;
_root.energyLine.yie._xscale = 0;
_root.lifeText.live.text = 1;
_global.bridge = true;
_global.time = 30;
}
} else if (life == 0) {
m2 += 1;
if (m2 == 30) {
_root.ding.start(0, 1);
_root.chman.standUp.gotoAndStop("行走");
_root.chman._y = 365.6;
_root.chman._visible = true;
_root.energyLine.finish = true;
_root.energyLine.xzd = _root.energyLine.yzd=0;
_root.energyLine.bhz = 0;
_root.energyLine.xie._xscale = 0;
_root.energyLine.yie._xscale = 0;
_root.lifeText.live.text = 0;
_global.bridge = true;
_global.time = 30;
}
}
if (Sourse == 10) {
_global.numberz = 1;
if (hx1 == 0) {
hx1 = 1;
_root.attachMovie("GoGo", "GoGo", 500);
_root.GoGo._x = 490;
_root.GoGo._y = 280;
}
} else if (Sourse == 21) {
_global.numberz = 2;
if (hx2 == 0) {
hx2 = 1;
_root.attachMovie("GoGo", "GoGo", 500);
_root.GoGo._x = 490;
_root.GoGo._y = 280;
}
} else if (Sourse == 32) {
_global.numberz = 3;
40
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
if (hx3 == 0) {
hx3 = 1;
_root.attachMovie("GoGo", "GoGo", 500);
_root.GoGo._x = 490;
_root.GoGo._y = 280;
}
} else if (Sourse == 46) {
_global.numberz = 4;
if (hx4 == 0) {
hx4 = 1;
_root.attachMovie("GoGo", "GoGo", 500);
_root.GoGo._x = 490;
_root.GoGo._y = 280;
}
} else if (Sourse == 60) {
_global.numberz = 5;
_global.numberc = 5;
if (hx5 == 0) {
hx5 = 1;
_root.attachMovie("GoGo", "GoGo", 500);
_root.GoGo._x = 490;
_root.GoGo._y = 280;
}
}
switch (numberc) {
case 1 :
if (Sourse == 10 and game1_1 == false) {
game1_1 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("blueSnail", "blueSnail"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blueSnail"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("greenSnake", "greenSnake"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenSnake"+enemys_num+"-blood", enemys_num*10);
}
} else {
41
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 13 and game1_2 == false) {
game1_2 = true;
createEnemys = function () {
if (enemys_num<3) {
_global.enemys_num += 1;
_root.attachMovie("greenSnake",
"greenSnake"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenSnake"+enemys_num+"-blood", enemys_num*10);
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 16 and game1_3 == false) {
game1_3 = true;
createEnemys = function () {
if (enemys_num<5) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("blueSnail",
"blueSnail"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blueSnail"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("greenSnake",
"greenSnake"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenSnake"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
}
break;
case 2 :
if (Sourse == 21 and game2_1 == false) {
42
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
game2_1 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("greenSnake", "greenSnake"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenSnake"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("greenFairy", "greenFairy"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenFairy"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 24 and game2_2 == false) {
game2_2 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("greenFairy", "greenFairy"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenFairy"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("redCrab",
"redCrab"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCrab"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 27 and game2_3 == false) {
43
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
game2_3 = true;
createEnemys = function () {
if (enemys_num<5) {
if (random(3) == 0) {
_global.enemys_num += 1;
_root.attachMovie("greenSnake", "greenSnake"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenSnake"+enemys_num+"-blood", enemys_num*10);
} else if (random(3) == 1) {
_global.enemys_num += 1;
_root.attachMovie("greenFairy", "greenFairy"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenFairy"+enemys_num+"-blood", enemys_num*10);
} else if (random(3) == 2) {
_global.enemys_num += 1;
_root.attachMovie("redCrab", "redCrab"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCrab"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
}
break;
case 3 :
if (Sourse == 32 and game3_1 == false) {
game3_1 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("greenFairy", "greenFairy"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenFairy"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("yellowFungus", "yellowFungus"+enemys_num, enemys_num);
44
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_root.attachMovie("smallMonster", "yellowFungus"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 35 and game3_2 == false) {
game3_2 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("redCrab",
"redCrab"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCrab"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("yellowFungus", "yellowFungus"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "yellowFungus"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 38 and game3_3 == false) {
game3_3 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("yellowFungus", "yellowFungus"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "yellowFungus"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("blackBat",
"blackBat"+enemys_num, enemys_num);
45
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_root.attachMovie("smallMonster", "blackBat"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 41 and game3_4 == false) {
game3_4 = true;
createEnemys = function () {
if (enemys_num<5) {
if (random(4) == 0) {
_global.enemys_num += 1;
_root.attachMovie("greenFairy", "greenFairy"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenFairy"+enemys_num+"-blood", enemys_num*10);
} else if (random(4) == 1) {
_global.enemys_num += 1;
_root.attachMovie("redCrab",
"redCrab"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCrab"+enemys_num+"-blood", enemys_num*10);
} else if (random(4) == 2) {
_global.enemys_num += 1;
_root.attachMovie("yellowFungus", "yellowFungus"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "yellowFungus"+enemys_num+"-blood", enemys_num*10);
} else if (random(4) == 3) {
_global.enemys_num += 1;
_root.attachMovie("blackBat",
"blackBat"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blackBat"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
}
break;
46
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
case 4 :
if (Sourse == 46 and game4_1 == false) {
game4_1 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("yellowFungus", "yellowFungus"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "yellowFungus"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("redCap",
"redCap"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCap"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 49 and game4_2 == false) {
game4_2 = true;
createEnemys = function () {
if (enemys_num<3) {
_global.enemys_num += 1;
_root.attachMovie("redCap", "redCap"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCap"+enemys_num+"-blood", enemys_num*10);
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 52 and game4_3 == false) {
game4_3 = true;
createEnemys = function () {
if (enemys_num<3) {
if (random(2) == 0) {
_global.enemys_num += 1;
_root.attachMovie("redCap",
47
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
"redCap"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCap"+enemys_num+"-blood", enemys_num*10);
} else {
_global.enemys_num += 1;
_root.attachMovie("blackBat",
"blackBat"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blackBat"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 55 and game4_4 == false) {
game4_4 = true;
createEnemys = function () {
if (enemys_num<5) {
if (random(3) == 0) {
_global.enemys_num += 1;
_root.attachMovie("redCap",
"redCap"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCap"+enemys_num+"-blood", enemys_num*10);
} else if (random(3) == 1) {
_global.enemys_num += 1;
_root.attachMovie("blackBat",
"blackBat"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blackBat"+enemys_num+"-blood", enemys_num*10);
} else if (random(3) == 2) {
_global.enemys_num += 1;
_root.attachMovie("yellowFungus", "yellowFungus"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "yellowFungus"+enemys_num+"-blood", enemys_num*10);
}
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
}
48
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
break;
case 5 :
if (game5_1 == false) {
game5_1 = true;
_root.attachMovie("kingStick", "kingStick", 300);
_root.kingStick._visible = false;
_root.attachMovie("bigKing", "bigKing", 200);
}
if (nummer == true and game5_2 == false) {
game5_2 = true;
_root.kingStick._visible = true;
_root.bigKing.play();
createEnemys = function () {
if (enemys_num == 0) {
pop = true;
} else if (enemys_num == 3) {
pop = false;
}
if (enemys_num<3 and pop == true) {
if (random(7) == 0) {
_global.enemys_num += 1;
_root.attachMovie("blueSnail", "blueSnail"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blueSnail"+enemys_num+"-blood", enemys_num*10);
} else if (random(7) == 1) {
_global.enemys_num += 1;
_root.attachMovie("greenSnake", "greenSnake"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenSnake"+enemys_num+"-blood", enemys_num*10);
} else if (random(7) == 2) {
_global.enemys_num += 1;
_root.attachMovie("greenFairy", "greenFairy"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "greenFairy"+enemys_num+"-blood", enemys_num*10);
} else if (random(7) == 3) {
_global.enemys_num += 1;
_root.attachMovie("redCrab", "redCrab"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCrab"+enemys_num+"-blood", enemys_num*10);
} else if (random(7) == 4) {
49
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_global.enemys_num += 1;
_root.attachMovie("yellowFungus", "yellowFungus"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "yellowFungus"+enemys_num+"-blood", enemys_num*10);
} else if (random(7) == 5) {
_global.enemys_num += 1;
_root.attachMovie("redCap", "redCap"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "redCap"+enemys_num+"-blood", enemys_num*10);
} else if (random(7) == 6) {
_global.enemys_num += 1;
_root.attachMovie("blackBat", "blackBat"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blackBat"+enemys_num+"-blood", enemys_num*10);
}
}
};
clearEnemy = setInterval(createEnemys, 2000);
}
break;
default :
if (Sourse == 0 and game_1 == false) {
game_1 = true;
_root.music1_1 = new Sound();
_root.music1_1.attachSound("sound27");
_root.music1_1.start(0, 99);
createEnemys = function () {
if (enemys_num<2) {
_global.enemys_num += 1;
_root.attachMovie("blueSnail", "blueSnail"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blueSnail"+enemys_num+"-blood", enemys_num*10);
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 2 and game_2 == false) {
game_2 = true;
createEnemys = function () {
50
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
if (enemys_num<3) {
_global.enemys_num += 1;
_root.attachMovie("blueSnail", "blueSnail"+enemys_num, enemys_num);
_root.attachMovie("smallMonster",
blood", enemys_num*10); "blueSnail"+enemys_num+"-
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
} else if (Sourse == 5 and game_3 == false) {
game_3 = true;
createEnemys = function () {
if (enemys_num<5) {
_global.enemys_num += 1;
_root.attachMovie("blueSnail", "blueSnail"+enemys_num, enemys_num);
_root.attachMovie("smallMonster", "blueSnail"+enemys_num+"-blood", enemys_num*10);
} else {
clearInterval(clearEnemy);
}
};
clearEnemy = setInterval(createEnemys, 1000);
}
break;
}
}
在主角影片剪辑中添加如下代码:
function sceneMoving() {
switch (numberz) {
case 1 :
if (_root.stage._x>-238) {
if (this._x<_root.scene_X) {
tim_1 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_1 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
51
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-238) {
_root.stage._x = -238;
}
if (_root.stage._x == -238) {
_root.GoGo.removeMovieClip();
_global.numberc = 1;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
case 2 :
if (_root.stage._x>-790) {
if (this._x<_root.scene_X) {
tim_2 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_2 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
52
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-790) {
_root.stage._x = -790;
}
if (_root.stage._x == -790) {
_root.GoGo.removeMovieClip();
_global.numberc = 2;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
case 3 :
if (_root.stage._x>-1342) {
if (this._x<_root.scene_X) {
tim_3 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_3 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
53
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-1342) {
_root.stage._x = -1342;
}
if (_root.stage._x == -1342) {
_root.GoGo.removeMovieClip();
_global.numberc = 3;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
case 4 :
if (_root.stage._x>-1894) {
if (this._x<_root.scene_X) {
tim_4 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_4 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
54
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-1894) {
_root.stage._x = -1894;
}
if (_root.stage._x == -1894) {
_root.GoGo.removeMovieClip();
_global.numberc = 4;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
case 5 :
if (_root.stage._x>-2446) {
if (this._x<_root.scene_X) {
tim_5 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_5 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
_root.bigKing._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
55
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
_root.bigKing._x -= 6;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-2446) {
_root.stage._x = -2446;
_root.bigKing._x = 480;
}
if (_root.stage._x == -2446) {
_root.GoGo.removeMovieClip();
_global.nummer = true;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
default :
this._x += xSpeed;
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
}
}
onClipEvent (enterFrame) {
this.sceneMoving();
,
通过这两段代码的作用可以使主角移动到不同的场景画面时,产生许多个不
同的敌人。
3.4.7声音的添加
56
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
声音是游戏中必不可少的要素,有了声音,游戏才会更加多姿多彩。在根场景中添加如下代码,便能够使游戏播放出美妙的声音。
_root.mainMusic = new Sound();
_root.mainMusic.attachSound("mainSound");
_root.mainMusic.start(0, 99);
3.5 GIF图片格式简介
本游戏中采用的图片素材大部分均为GIF格式。
GIF是英文Graphics Interchange Format(图形交换格式)的缩写。顾名思义,这种格式是用来交换图片的。事实上也是如此,上世纪80年代,美国一家著名的在线信息服务机构CompuServe针对当时网络传输带宽的限制,开发出了这种GIF图像格式。
GIF格式的特点是压缩比高,磁盘空间占用较少,所以这种图像格式迅速得到了广泛的应用。 最初的GIF只是简单地用来存储单幅静止图像(称为GIF87a),后来随着技术发展,可以同时存储若干幅静止图象进而形成连续的动画,使之成为当时支持2D动画为数不多的格式之一(称为GIF89a),而在GIF89a图像中可指定透明区域,使图像具有非同一般的显示效果,这更使GIF风光十足。目前Internet上大量采用的彩色动画文件多为这种格式的文件,也称为GIF89a格式文件。
此外,考虑到网络传输中的实际情况,GIF图像格式还增加了渐显方式,也就是说,在图像传输过程中,用户可以先看到图像的大致轮廓,然后随着传输过程的继续而逐步看清图像中的细节部分,从而适应了用户的"从朦胧到清楚"的观赏心理。目前Internet上大量采用的彩色动画文件多为这种格式的文件。 但GIF有个小小的缺点,即不能存储超过256色的图像。尽管如此,这种格式仍在网络上大行其道应用,这和GIF图像文件短小、下载速度快、可用许多具有同样大小的图像文件组成动画等优势是分不开的。
3.6 玩家人物的控制方式和敌人方的智能运行
玩家人物的动作是通过键盘来实现的:
利用Key.isDown()函数可以实现当按下某按键后令玩家人物执行相应的动作,并且利用此方法可以对键般进行响应,判断按键是否被持续按下。对玩家主角的控制需要判断向左,向右,跳跃,攻击。
具体代码如下:
function keyInMove() { //控制主角的行走
if (attackFlag == 0) {
if (Key.isDown(Key.RIGHT) and 552>(this._x)) {
xSpeed = 6;
nowState = 2;
stateCheck();
beforeState = 2;
this.standUp.play();
} else if (Key.isDown(Key.LEFT) and 0<(this._x)) {
xSpeed = -6;
57
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
nowState = 4;
stateCheck();
beforeState = 4;
this.standUp.play();
} else if (Key.isDown(Key.DOWN) and jump == false) {
standDo = 1;
nowState = 3;
stateCheck();
beforeState = 3;
} else {
if (standDo == 1) {
standDo = 0;
nowState = 0;
beforeState = 0;
this.gotoAndStop("站姿");
this.standUp.gotoAndStop("行走");
}
}
}
}
function keyInJump() { //判断主角的跳跃
this._y -= ySpeed;
if (jump == false) {
xSpeed = 0;
}
if (nowState == 4 or nowState == 2 or nowState == 0) {
if (Key.isDown(90) and jump == false and attackDead == 0 and
testBit == false) {
ySpeed = 30;
jump = true;
this.standUp.gotoAndStop("跳跃");
}
}
if (_root.stage.land.hitTest(_x, _y, true)) {
_root.jumpMusic = new Sound();
_root.jumpMusic.attachSound("sound10");
_root.jumpMusic.start(0, 1);
for (; _root.stage.land.hitTest(_x, _y, true); ) {
_y = _y-1;
}
this.standUp.gotoAndStop("行走");
this._x -= xSpeed;
//取消原速度
xSpeed = 0;
58
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
ySpeed = 0;
jump = false;
} else if (!_root.stage.land.hitTest(_x+12, _y+1, true)
and !_root.stage.land.hitTest(_x-12, _y+1, true) and jump == false) {
jump = true;
}
if (jump == true) {
ySpeed -= 5;
}
}
function keyInAttack() { //判断主角的攻击
if (attackFlag == 0) {
if (Key.isDown(88)) {
if (jump == false) {
attackNumber = Math.ceil(Math.random()*3);
attackCheck();
} else {
attackNumber = Math.ceil(Math.random()*2)+1;
attackCheck(); //调用攻击函数
}
}
}
}
function attackCheck() {
//攻击函数
if (attackFlag == 0) {
if (attackNumber == 1) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击1");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
} else if (attackNumber == 2) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击2");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
59
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
this.sitDown.gotoAndPlay("攻击4");
}
} else if (attackNumber == 3) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击3");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
}
}
}
敌人的智能主要是当主角接近敌人时,敌人会跟踪主角:
manx = getProperty("/chman", _x);
dx = manx-this._x;
if (Math.abs(dx)>=speed+23) {
this._x += ((dx>=0) ? speed : -speed);
}
以上的函数就是通过判断主角与敌人之间的距离,从而使敌人向主角靠拢。
60
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 第四章 程序分析和具体实现
4.1地图的创建
在本游戏中由于地图元素不多,为了减小游戏制作的复杂性,因此使用了一整张大的位图。
场景:
地图:
502px
3109px
4.2地图的移动
在这一个模块中要考虑的东西比较多,由于场景的大小为(552,502),因此我将地图划分成了6个区域:
? 0px,238px为第一个区域
? 238px,790px为第二个区域
? 790px,1342px为第三个区域
? 1342px,1894px为第四个区域
? 1894px,2466px为第五个区域
? 2466px,3109px为第六个区域
当每一个区域中的所有怪被玩家主角杀死以后,才能进入下一区域,因此地图的移动需要进行间断式的移动,另外地图在移动过程中必须与主角同步,否则会使游戏显的不协调。
具体分析如下:
<一> 地图从第一区域向第二区域过渡:
? 当玩家主角在场景的左边时,即x坐标为0px,276px之间时: 主角向左右两边走,地图不移动
61
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 ? 当玩家主角在场景的中间时,即x坐标为276px时:
主角向左边走,地图不移动
主角向右边走,地图移动
? 当玩家主角在场景的右边时,即x坐标为276px,552px之间时: 主角同地图以相同的速度向左移动
二> 地图到达第二区域: <
玩家主角向左右两边走,地图不移动
其它区域的过渡同上
利用switch case 语句进行分段:
具体代码如下:
function sceneMoving() {
switch (numberz) {
case 1 :
if (_root.stage._x>-238) {
if (this._x<_root.scene_X) {
tim_1 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_1 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-238) {
_root.stage._x = -238;
}
if (_root.stage._x == -238) {
_root.GoGo.removeMovieClip(); 62
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_global.numberc = 1;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
case 2 :
if (_root.stage._x>-790) {
if (this._x<_root.scene_X) {
tim_2 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_2 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-790) {
_root.stage._x = -790;
}
if (_root.stage._x == -790) {
_root.GoGo.removeMovieClip();
_global.numberc = 2;
this._x += xSpeed;
63
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
}
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
case 3 :
if (_root.stage._x>-1342) {
if (this._x<_root.scene_X) {
tim_3 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_3 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-1342) {
_root.stage._x = -1342;
}
if (_root.stage._x == -1342) {
_root.GoGo.removeMovieClip();
_global.numberc = 3;
this._x += xSpeed;
}
if (this._x<10) {
64
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
case 4 :
if (_root.stage._x>-1894) {
if (this._x<_root.scene_X) {
tim_4 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_4 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-1894) {
_root.stage._x = -1894;
}
if (_root.stage._x == -1894) {
_root.GoGo.removeMovieClip();
_global.numberc = 4;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
}
65
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
if (this._x>540) {
this._x = 540;
}
break;
case 5 :
if (_root.stage._x>-2446) {
if (this._x<_root.scene_X) {
tim_5 = 1;
this._x += xSpeed;
}
if (this._x>_root.scene_X) {
if (tim_5 == 1) {
this._x = _root.scene_X;
} else {
attackFlag = 1;
this._x -= 6;
_root.stage._x -= 6;
= 6; _root.bigKing._x -
if (this._x<_root.scene_X) {
this._x = _root.scene_X;
}
}
}
if (this._x == _root.scene_X) {
attackFlag = 0;
if (xSpeed>0) {
_root.stage._x -= xSpeed;
_root.bigKing._x -= 6;
} else if (xSpeed<0) {
this._x += xSpeed;
}
}
}
if (_root.stage._x<-2446) {
_root.stage._x = -2446;
_root.bigKing._x = 480;
}
if (_root.stage._x == -2446) {
_root.GoGo.removeMovieClip();
_global.nummer = true;
this._x += xSpeed;
}
if (this._x<10) {
this._x = 10;
66
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
}
if (this._x>540) {
this._x = 540;
}
break;
default :
this._x += xSpeed;
if (this._x<10) {
this._x = 10;
}
if (this._x>540) {
this._x = 540;
}
break;
}
}
4.3对象的碰撞检测及相关属性
在本游戏中有两种碰撞:
一种是玩家主角被敌人攻击,另一种是敌人被玩家主角攻击。 先分析第一种攻击,由于玩家主角被攻击时只能被一个敌人击中,因此只需检测主角攻击方块与敌人的身体是否碰撞,如下图:
上图中绿色方块为主角身体,蓝色方块为敌人的身体,利用hitTest语句进行碰撞判断。将代码写在蓝色方块中,并使用影片剪辑的onEnterFrame可以进行不间断的检测。
代码如下:
onClipEvent (enterFrame) {
if (this.hitTest(_root.chman.standUp.bodyhit) == true) {
_root.chman.standUp.gotoAndPlay("受伤");
,
if (this.hitTest(_root.chman.sitDown.bodyhit) == true) {
_root.chman.standUp.gotoAndPlay("受伤");
,
}
67
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 现在分析第二种攻击,由于玩家主角可以攻击多个敌人,因此将碰撞代码写在每个敌人影片剪辑中。如图红色方块为主角的攻击方块,蓝色方块为敌人身体。
代码如下:
function hitCheck(targetObj, targetScore) {
if (this.snailHit.hitTest(targetObj)) {
this.gotoAndPlay("受伤");
,
,
this.hitCheck(_root.chman.standUp.attackHit, random(10)+15);
4.4玩家3次游戏机会的实现方法
由于游戏设置的比较难,因此我给主角提供了3条命,那么玩就可以有3次游戏机会了。
首先需要在根场景声明一个全局变量:
_gobla.life=3;
当主角死亡之后,生命减少一条,使得
_global.life-=1;
同时主角不可见,即
This._visible=false;
并打开计时器,对主角血条进行初始化,令血量值由死亡时的100变回0 。 当计时器的值到达一定的数值后,使的主角可见。
具体代码如下:
if (life == 1) {
m1 += 1;
if (m1 == 30) {
_root.ding.start(0, 1);
_root.chman.standUp.gotoAndStop("行走");
_root.chman._y = 365.6;
_root.chman._visible = true;
_root.energyLine.finish = true;
_root.energyLine.xzd = _root.energyLine.yzd=0;
_root.energyLine.bhz = 0;
_root.energyLine.xie._xscale = 0;
_root.energyLine.yie._xscale = 0; 68
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
_root.lifeText.live.text = 1;
_global.bridge = true;
_global.time = 30;
}
} else if (life == 0) {
m2 += 1;
(m2 == 30) { if
_root.ding.start(0, 1);
_root.chman.standUp.gotoAndStop("行走");
_root.chman._y = 365.6;
_root.chman._visible = true;
_root.energyLine.finish = true;
_root.energyLine.xzd = _root.energyLine.yzd=0;
_root.energyLine.bhz = 0;
_root.energyLine.xie._xscale = 0;
_root.energyLine.yie._xscale = 0;
_root.lifeText.live.text = 0;
_global.bridge = true;
_global.time = 30;
}
}
4.5普通敌人相关属性
敌人是游戏中必不可少的要素,如果失去了敌人,那么游戏就毫无乐趣了。 在此游戏添加了7种普通敌人:
蓝蜗牛 绿水灵: 红螃蟹: 小青黄蘑菇: 红帽子: 黑蝙蝠:
蛇:
各种敌人的属性动作基本相似,包括行走,跳跃,攻击,受伤,死亡。
敌人进入场景时由于是随机的,因此利用随机数random(2)使得敌人可以从左方或右方进入,
代码如下:
function init() {
//xMove表示向左,yMove表示向右
var deer;
69
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
xMove = -1;
yMove = 1;
turning = 5;
oldspeed = speed=random(2)+1;
state = 1;
moveArrow = random(2)+1;
stickHit = false;
myName = getProperty(this, _name);
stickName = eval("_root." add myName add "-blood");
if (moveArrow == 1) {
//从左端出现
this._xscale = -math.abs(this._xscale);
this._x = -20;
} else {
//从右端出现
this._xscale = math.abs(this._xscale);
this._x = 540;
}
this._y = 404;
}
this.init();
敌人进入场景后,要使其看上去有生命,则需要让他能够自已做出各种动作,比如敌人可以向左走,向右走,或是停下来,在此也需要用到随机数来控制敌人。 function moveChar(dirx) {
if (dirx == -1) {
this._xscale = math.abs(this._xscale);
this._x += speed*dirx;
}
if (dirx == 1) {
this._xscale = -math.abs(this._xscale);
this._x += speed*dirx;
}
}
function moveing(numk) {
//从右端出现
if (numk == 2) {
if (this._x>=552) {
this._x -= speed;
if (xMove == 1) {
xMove = -xMove;
moveChar(xMove);
}
}
if (this._x<=0) {
70
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
xMove = -xMove;
moveChar(xMove);
}
if (this._x<552 and this._x>0) {
if (random(200)>turning) {
if (!this.range.hitTest(_root.chman._x, _root.chman._y-26,
true)) {
moveChar(xMove);
} else {
this.gotoAndPlay("攻击");
}
} else {
if (xMove != 0) {
deer = xMove;
}
xMove = random(3)-1;
}
}
//从左端出现
} else if (numk == 1) {
if (this._x<=0) {
this._x += speed;
if (yMove == -1) {
yMove = -yMove;
moveChar(yMove);
}
}
if (this._x>=552) {
yMove = -yMove;
moveChar(yMove);
}
if (this._x<552 and this._x>0) {
if (random(200)>turning) {
if (!this.range.hitTest(_root.chman._x, _root.chman._y-26,
true)) {
moveChar(yMove);
} else {
this.gotoAndPlay("攻击");
}
} else {
if (yMove != 0) {
deer = yMove;
}
yMove = random(3)-1;
71
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
}
}
}
}
-1=-1时表示敌人向左走,当random(3)-1=1时表示敌人以上代码中当ranom(3)
向右走,而当random(3)-1=0时表示敌人在原地观望。
敌人的攻击则是使得帧跳转到“攻击“,在此帧中添加检测碰撞的函数语句,敌人就具有攻击的能力。
代码如下:
tracker = function () {
manx = getProperty("/chman", _x);
dx = manx-this._x;
if (this.range.hitTest(_root.chman._x, _root.chman._y-25, true)) {
if (this.snailHit.hitTest(_root.chman.standUp.attackHit) == false
and this.snailHit.hitTest(_root.chman.sitDown.attackHit) == false) {
if (Math.abs(dx)>=speed+23) {
this._x += ((dx>=0) ? speed : -speed);
}
} else {
this.hitCheck(_root.chman.standUp.attackHit, random(10)+15);
this.hitCheck(_root.chman.sitDown.attackHit, 20);
}
} else {
speed = oldspeed;
gotoAndPlay("走动");
}
updateAfterEvent();
};
敌人的受伤则要复杂一些,由于当玩家主角击中敌人后,会产生方向的问题: 1、当敌人面朝主角时,被击中后会向后退一段距离,而方向不变
2、当敌人背朝主角时,被击中后会向后退一段距离,而方向改变
因此在代码中就要针对这两种情况来进行分别判断。
具体代码如下:
function hitSinceMove() {
manxx = getProperty("/chman", _x);
dxx = manxx-this._x;
if (moveArrow == 2) {
if (dxx>=0) {
this._xscale = -math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
72
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
this._x -= speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
if (dxx<0) {
this._xscale = math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
this._x += speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
}
if (moveArrow == 1) {
if (dxx>=0) {
this._xscale = -math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
this._x -= speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
if (dxx<0) {
this._xscale = math.abs(this._xscale);
if (speed>0) {
speed -= 0.5;
this._x += speed*10;
} else {
this.gotoAndPlay("头顶");
}
}
}
}
敌人的死亡则只需要运行一小段影片剪辑动画即可。
而在最后一帧加上如下代码就能使敌人在死亡后消失掉。 _parent.removeMovieClip();
73
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 4.6白云的实现原理
在游戏中可以看到有三朵云一直在游戏画面的上方运行,而且云之间的相对位置也是在不断改变的。实现原理如下:
云3三个云的影片剪辑: 在云的影片剪辑中放置云1,云2,
如图:
云1
云2
云3
分别在每个云的影片剪辑中制作补间动画;
云1:
云2:
云3:
利用每个云影片剪辑中各自独立的时间线来使云在游戏画面上重复移动,最终达到游戏上的效果。
4.7关尾BOSS及相关属性
BOSS的制作同以上的小怪的制作方式基本相似,有两点是不同的: 第一点需要制作BOSS的跳跃,此处需要两帧动画:
第一帧:
74
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
代码如下:
speed_x = 20;
speed_y = 30;
diejump = false;
if (random(100)>59) {
jjmp = 1;
} else {
if (dx<=0) {
this._xscale = Math.abs(this._xscale);
} else {
this._xscale = -Math.abs(this._xscale);
}
jjmp = 2;
}
第二帧:
75
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
代码如下:
function move_jump() {
if (_root.stage.land.hitTest(this._x, this._y+2, true) and diejump ==
true) {
for (; _root.stage.land.hitTest(this._x, this._y, true); ) {
this._y = this._y-1;
}
diejump = false;
if (this._x == 50) {
xMove = -2;
} else if (this._x == 502) {
xMove = 2;
} else {
xMove = random(5)-2;
}
this.gotoAndPlay("走动");
} else {
if (jjmp == 1) {
speed_y -= 5;
this._y -= speed_y;
} else {
if (dx>0) {
this._x += speed_x;
speed_y -= 5;
this._y -= speed_y;
} else if (dx<=0) {
this._x -= speed_x;
speed_y -= 5;
this._y -= speed_y;
}
if (this._x<=50) {
speed_x = 0;
this._x = 50;
}
if (this._x>=502) {
speed_x = 0;
this._x = 502;
}
}
diejump = true;
}
}
this.move_jump();
this.hitCheck(_root.chman.standUp.attackHit, random(5)+10);
76
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
this.hitCheck(_root.chman.sitDown.attackHit, 12);
第二点是要给BOSS设置3行血量,当第一行的血条达到最大值后,第二行血条继续运行,接着最后一条血条运行,当3条血条都达到最大值后,BOSS死亡。
77
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
BOSS血条的做法同主角的做法相似:
首先对血条进行初始化:
代码如下:
xzt = 0;
zzt = 0;
fulling = false;
finish = true;
_global.arrayStick[0] = 1; _global.state = 0;
this._x = 370;
this._y = 35;
this.nie._xscale = xzt; this.mie._xscale = xzt; this.wie._xscale = xzt; function monEnergySub() {
if (xzt != zzt) {
if (xzt<100) {
xzt++;
}
} else {
finish = true;
}
if (state == 0) {
this.nie._xscale = xzt;
if (this.nie._xscale == 100) {
_global.state = 1;
xzt = zzt=0;
}
} else if (state == 1) {
this.mie._xscale = xzt; 78
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
if (this.mie._xscale == 100) {
_global.state = 2;
xzt = zzt=0;
}
} else {
if (fulling == true) {
this.wie._xscale = 100;
} else {
this.wie._xscale = xzt;
}
}
}
然后当BOSS被玩家主角攻击后血条进行变化,实现代码如下:
function hitCheck(targetObj, targetScore) {
if (this.snailHit.hitTest(targetObj)) {
if (stickName.finish == true) {
_root.damageMusic_8 = new Sound();
_root.damageMusic_8.attachSound("sound16");
_root.damageMusic_8.start(0, 1);
}
if (state == 0) {
if (kingStick.xzt<100 and kingStick.finish == true) {
kingStick.finish = false;
kingStick.zzt = kingStick.xzt+targetScore;
kingStick.onEnterFrame = function() {
kingStick.monEnergySub();
};
this.gotoAndPlay("受伤");
_root.king_demage = new Sound();
_root.king_demage.attachSound("sound11");
_root.king_demage.start(0, 1);
}
} else if (state == 1) {
if (kingStick.xzt<100 and kingStick.finish == true) {
kingStick.finish = false;
kingStick.zzt = kingStick.xzt+targetScore;
kingStick.onEnterFrame = function() {
kingStick.monEnergySub();
};
this.gotoAndPlay("受伤");
_root.king_demage.start(0, 1);
}
} else {
if (kingStick.xzt<100 and kingStick.finish == true) {
79
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
kingStick.finish = false;
kingStick.zzt = kingStick.xzt+targetScore;
if (kingStick.zzt>=100) {
kingStick.fulling = true;
_global.arrayStick[0] = 0;
"); this.gotoAndPlay("死掉
} else {
kingStick.onEnterFrame = function() {
kingStick.monEnergySub();
};
this.gotoAndPlay("受伤");
_root.king_demage.start(0, 1);
}
}
}
}
}
this.hitCheck(_root.chman.standUp.attackHit, random(5)+10);
this.hitCheck(_root.chman.sitDown.attackHit, 12);
4.8玩家人物的控制方式和敌人方的智能运行
玩家人物的动作是通过键盘来实现的:
利用Key.isDown()函数可以实现当按下某按键后令玩家人物执行相应的动作,并且利用此方法可以对键般进行响应,判断按键是否被持续按下。 对玩家主角的控制需要判断向左,向右,跳跃,攻击。
具体代码如下:
function keyInMove() { //控制主角的行走
if (attackFlag == 0) {
if (Key.isDown(Key.RIGHT) and 552>(this._x)) {
xSpeed = 6;
nowState = 2;
stateCheck();
beforeState = 2;
this.standUp.play();
} else if (Key.isDown(Key.LEFT) and 0<(this._x)) {
xSpeed = -6;
nowState = 4;
stateCheck();
beforeState = 4;
this.standUp.play();
} else if (Key.isDown(Key.DOWN) and jump == false) {
standDo = 1;
nowState = 3;
80
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
stateCheck();
beforeState = 3;
} else {
if (standDo == 1) {
standDo = 0;
nowState = 0;
beforeState = 0;
"); this.gotoAndStop("站姿
this.standUp.gotoAndStop("行走");
}
}
}
}
function keyInJump() { //判断主角的跳跃
this._y -= ySpeed;
if (jump == false) {
xSpeed = 0;
}
if (nowState == 4 or nowState == 2 or nowState == 0) {
if (Key.isDown(90) and jump == false and attackDead == 0 and
testBit == false) {
ySpeed = 30;
jump = true;
this.standUp.gotoAndStop("跳跃");
}
}
if (_root.stage.land.hitTest(_x, _y, true)) {
_root.jumpMusic = new Sound();
_root.jumpMusic.attachSound("sound10");
_root.jumpMusic.start(0, 1);
for (; _root.stage.land.hitTest(_x, _y, true); ) {
_y = _y-1;
}
this.standUp.gotoAndStop("行走");
this._x -= xSpeed;
//取消原速度
xSpeed = 0;
ySpeed = 0;
jump = false;
} else if (!_root.stage.land.hitTest(_x+12, _y+1, true)
and !_root.stage.land.hitTest(_x-12, _y+1, true) and jump == false) {
jump = true;
}
if (jump == true) {
81
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
ySpeed -= 5;
}
}
function keyInAttack() { //判断主角的攻击
if (attackFlag == 0) {
if (Key.isDown(88)) {
if (jump == false) {
attackNumber = Math.ceil(Math.random()*3);
attackCheck();
} else {
attackNumber = Math.ceil(Math.random()*2)+1;
attackCheck(); //调用攻击函数
}
}
}
}
function attackCheck() {
//攻击函数
if (attackFlag == 0) {
if (attackNumber == 1) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击1");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
} else if (attackNumber == 2) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击2");
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
} else if (attackNumber == 3) {
if (nowState == 4 or nowState == 2 or nowState == 0) {
attackFlag = 1;
attackNumber = 0;
this.standUp.gotoAndPlay("攻击3"); 82
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
} else if (nowState == 3) {
attackFlag = 1;
attackNumber = 0;
this.sitDown.gotoAndPlay("攻击4");
}
}
}
}
敌人的智能主要是当主角接近敌人时,敌人会跟踪主角:
manx = getProperty("/chman", _x);
dx = manx-this._x;
if (Math.abs(dx)>=speed+23) {
this._x += ((dx>=0) ? speed : -speed);
}
以上的函数就是通过判断主角与敌人之间的距离,从而使敌人向主角靠拢。
83
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 第五章 游戏测试
5.1游戏测试概述
很多人有这样一个观点:“就是在软件开发完毕后,再进行测试。”殊不知,这种关点是有悖于软件开发的生命周期的,软件缺陷的发现必须是越早越好,这样才可以有效的规避风险,而在“最后进行测试”的测试观念的指导下测试工作必将会产生很多问题,这种观念的错误在于:生命周期中的“测试阶段”表明在该阶段测试工作是主要的工作,而不是说,测试工作只发生在“测试阶段”。通常,到了测试阶段,测试的主要任务是运行测试,形成测试报告。而想要提高游戏的质量,则必需要做到测试的早期介入,诸如测试
,测试用例的确定以及测试代码的编写等等都是要在更早的阶段进行。如果你把测试完全放在最后阶段,就错过了发现构架设计和游戏逻辑设计中存在严重问题的最好时机,到那时,要修复这些缺陷将很不方便,因为缺陷已经扩散到系统中去了,所以这样的错误将很难寻找与修复,代价更高。
要了解如何测试游戏必需了解如何做游戏,了解它的开发过程,才能真正的测好游戏。游戏要成功,其基本的必要条件有三。分别为Vision(设计)、
和Process(过程)。三个条件,缺一不可如图所示: technology(技术)
Vision:则是对游戏还没有实现的总体上的把握,前瞻性的理解与策略的考量。
Technology:有了vision,如果没有技术的话,则各种美妙的想法只能停留在虚无缥缈的阶段,通过技术来实现Vision。
Process:有了Vision作为指导,有了技术作为保证,也不一定能够把好的想法转换成高质量的游戏。要创造高品质的游戏,尚缺重要的一环,即过程,制造游戏是一个非常是一个长时间的动态过程。游戏产品的质量则是要靠动态过程的动态质量来进行保证。过程由很多复杂的相互牵制的环节与部件组成,如果任意的环节或者是部件出了问题都会对最终的产品形成质量上的影响。因此对这个动态的过程,一定要有规划与控制,以保证按步就班,按质按时完成工作。
5.2 游戏测试目的
测试的目的是发现软件中存在的缺陷。测试都是需要测试人员按照产品行为描述来实施。产品行为描述可以是书面的规格说明书,需求文档,产品文件,或是用户手册,源代码,或是工作的可执行程序。每一种测试都需要产品运行于真实的或是模拟环境之下。每一种测试都要求以系统方法展示产品功能,以证明测84
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品 试结果是否有效,以及发现其中出错的原因,从而让程序人员进行改进。
总而言之,测试就是发现问题并进行改进,从而提升软件产品的质量。游戏测试也具备了以上的所有特性,不过由于游戏的特殊性,所以游戏测试则主要分为两部分组成,一是传统的软件测试,二游戏本身的测试,由于游戏相当于网上的虚拟世界,是人类社会的另一种方式的体现,所以也包含了人类社会的一部分特性,同时它又是游戏所以还涉及到娱乐性,可玩性等独有特性,所以测试的面相当的广。我们称之为游戏世界测试,主要有以下几个特性:
游戏情节的测试,主要指游戏世界中的任务系统的组成,有人也称为游戏世界的事件驱动,我喜欢称为游戏情感世界的测试。
游戏世界的平衡测试,主要表现在经济平衡,能力平衡(包含技能,属性等等),保证游戏世界竞争公平。
游戏文化的测试,比如整个游戏世界的风格,是中国文化主导,还是日韩风格等等,大到游戏整体,小到NPC(游戏世界人物)对话等语言必须要得体。
5.3游戏测试与开发过程的关系
M(Software Capability Maturity Model)软件成熟模型,大家都比较熟悉了,但在实施的过程中却存在这样那样的问题,对于游戏开发就更没有一个固定的路可以讲了,我们的团队是一个长期的游戏开发团队,对游戏开发有着很深的
)实际上也是软件过程,不过是特殊的游戏软认识,我们认为游戏的Process(过程
件开发过程,各个生命周期还是相通的。
5.4游戏可玩性测试
游戏可玩性测试也是非常重要的一块,主要包含四个方面:
1.游戏世界的搭建,包含聊天功能,交易系统,组队等可以让玩家在游戏世界交互的平台。
2.游戏世界事件的驱动,主要指任务。
3.游戏世界的竞争与平衡。
4.游戏世界文化蕴涵,游戏的风格与体现。
这种测试主要体现在游戏可玩性方面,虽然策划时我们对可玩性作了一定的评估,但这是总体上的,但一些具体的涉及到某个数据的分析,比如PK参数的调整,技能的增加等一些增强可玩性的测试则需要职业玩家对它进行分析。 5.5游戏的运行环境
游戏运行的环境windows/Linux等,最低要求Macromedia Flash 6.0 player
播放。
85
XXX大学第一届学生科技文化节学生课外学术科技作品竞赛参赛作品
第六章 总结
本次游戏的制作周期大概有两三个月,刚刚开始决定此类游戏时确实感到困难挺大,由于自已学FLASH的时间不长,而且对于绘图也比较生疏,然而通过以前试做过几个FLASH游戏的基础和一些经验,最终还是将这个游戏作品完成了。在制做过程中遇到了许多功能不能实现,但通过查阅书籍以及自已的思考,最后还是实现了几些功能。在游戏制做完成后,通过朋友的测试,发现了一些BUG,有些问题令我思考了好几天才发现了造成问题出现的原因,但还是有一两个BUG解决不了,但不会对游戏的运行造成太在的影响。当完成了这个作品之后,我觉得非常高兴,因为这是我迈向理想的第一步。
【参考文献】
[1] 黄晶编著. FLash5.0动画与特效实例演练. 出版日期:2001年3月第1版 [2] 金虎植 金东根等编著.中青电脑艺术
[3] 宋侃达 王辉等编著. Flash5创意与实例.2001年1月第1版 [4] 天心工作室编著. Flash 5.0网页动画闪客实战. 2001年4月第1版 [5] Shan Bhangal Igor Choromanski著.Flash游戏设计宝典. 2002年06月第1版
86