PDA 个人数字助理

查看完全版本 : [转贴]Flash as2.0 编写自己的方法


皮皮狼
2004-02-25, 04:42 PM
转贴自闪客天堂。作者。wei386

在教程区发了之后,这里也发一篇,希望大家可以共同讨论,另外也是对脚本区的支持!呵呵


Flash as2.0 编写自己的方法
我把编写自己的方法放在开始,可能有些人会感到有点疑惑,因为按照一般逻辑,都应该先讲讲变量(variable),然后是类(class)、面向对象(oop),然后是方法(method),这才是正常的逻辑,层层深入。不过今天我想改变一下,首先因为我们接触flash as的编程都是从方法运用开始的,比如最简单的stop();所以既然是flash教程当然要遵守一下这个”惯例”。其二,因为有很多人并没有java c++的基础,所以上来先讲类什么的可能会觉得抓不着头脑,体会不到类的概念,不知类做什么用。所以我们今天从方法入手,让大家先了解方法,学会写方法,这样方便多多练习,今后我们再探讨类,这个抽象概念。

首先,我们来体会一下什么是方法。我们在编程中很容易用到方法,最简单的play();stop();这些就是flash写好的方法。我们用这些方法来做一些事情,play();开始,stop()停止。用方法来做一些我们想要作的事情从而达到我们的目的。换一种说法:方法就是行为。开始播放动画是一个行为,停止播放也是一个行为,依靠这个行为来做一些事情。可以反复阅读这段来体会方法是什么,因为这样有利于我们今后编写的方法是对我们确实有用的,而不是为了写方法而写方法。如果还难于理解,没有关系,因为在讲解oop(面向对象设计)时我们会仔细讲解,但现在一定要有这样的概念:方法是行为!

OK!知道了方法是行为之后,下面就好办了。Flash中定义了很多方法供我们使用stop();play();startDrag();stopDrag();duplicateMovieClip();等等。下面我们就来了解一下方法的格式。Flash as1.0中我们这样定义方法:

======================================================================
function name(parameter1, parameter2……)
{
…….//方法体
}

*function用来声明方法,name为方法的名字,parameter为方法的参数,也可没有,
视情况需要而定;
*1对大括号必须有,括号内为方法体,也就是说方法能做什么事情
*在flashMX2004中的as2.0编写时,定义方法可以加上方法的返回类型,可以把方法的结果返回给调用他的地方,比如返回类型为:String就是把结果返回一个字符串,调用时可以用一个变量来接收方法的结果,如:a=name();如果没有返回类型可以写上:Void(冒号一定不能少)(注:加上返回类型有利于面向对象编程,不过如果不好理解,也可以不写。对编写方法影响不大)下面是as2.0带返回类型方法的写法:
function name(parameter1, parameter2……) :retrunType
{
…….//方法体
return …….;//有返回类型时需要加上return
}
=====================================================================
知道了方法的写法,我们来试着通过一个实例来写一个方法,其实很容易就能做到。

我们知道在Flash中有一个方法duplicateMovieClip();和attachMovie();可以用来复制MovieClip(mc)。这个方法可以实现残影效果等其他很好的效果。但这两个方法用起来似乎不太好用,如果想复制多个mc就需要用两三个帧,每次都这样觉得很麻烦。我们就想办法写一个更方便自己使用方法来实现复制MC。

1 写方法的原因:
我们写一个复制mc的方法一般都是这样:
name.duplicateMovieClip(“newname”,1000);
//name为mc在属性栏中起的名字,newname为新名字,1000为复制后newname的层数
如果想复制多个mc要用更麻烦
第一帧初始化:i=0;
第二帧复制mc:
name.duplicateMovieClip(“newname”+i,100+i);
第三帧判断:
if(i<50)
{
gotoAndPlay(2);
}
stop();
每次都这样,觉得太累了!所以一定要自己写个方法简化一下

2 设计方法:
我们自己写方法的目的是为了以后使用的时候方便。我想用一个方法,只输入mc的名字和复制的数量就可以自动复制。这样方便很多,可以把精力放到更难的地方。好,我们开始设计一下怎样写这个方法。
首先确定一下方法的名字就叫copyMC()。然后,使用方法时需要两个参数一个是mcname用来确定需要复制的MC的名字,第二各参数是number,用来确定复制MC的个数。利用参数是为了可以复制不同名字的MC,今后在调用方法时只要输入不同的参数即可,如果不使用参数就不能自如的复制不同名字的MC。然后在方法中我们用for循环实现复制多个mc,让每个mc的坐标为随机抽取。大体框架已经搭好,我们就来实际的写方法了。

3 编写方法
按照设计好的想法来一步一步写出方法。首先声明方法,确定方法的名字,方法中有两个参数为mcname和number,按照as2.0的编写规范需要加上返回类型,返回值设为空。
function copyMC(mcname,number):Void
{
}
下面我们来编写方法体:方法传进来的参数mcname为被复制MC的名字,我们就可以用mcname.duplicateMovieClip()复制MC,为了实现复制多个mc,需要加上一个for循环,然后每个复制的MC的坐标为随机产生可以用Math.random()方法实现。

(1) for(i=1;i<number;)
(2) {
(3) mcname.duplicateMovieClip("ball"+i,i++);
(4) this["ball"+i]._x=Math.random()*400;
(5) this["ball"+i]._y=Math.random()*400;
(6) }

第1行:创建for循环,变量i小于总的复制个数就继续执行下面程序。
第3行:用传进来的参数mcname即指定的MC的名字调用duplicateMovieClip方法进行MC复制,"ball"+i是新复制的MC的名字,i++是设置每个MC的层数不一样
第4行:设置每一个复制后的MC的x坐标为0-400的随机数(因为场景的大小为400*400,可根据场景大小不同有所不同)
第5行:设置每一个复制后的MC的y坐标为0-400的随机数(因为场景的大小为400*400,可根据场景大小不同有所不同)

至此,我们已经写好了一个很简单的随机复制MC的方法。方法的整体如下:
function copyMC(mcname,number):Void
{

for(i=0;i<number;){
mcname.duplicateMovieClip("ball"+i,i++);
this["ball"+i]._x=Math.random()*400;
this["ball"+i]._y=Math.random()*400;}
}
方法的调用:把上面代码放入第一帧并加一句copyMC(ball,10);调用该方法。
参数得使用:传进来的参数ball是场景中MC的名字,如果想复制场景中其他的MC,将这个名字换成想复制的MC的名字就可以随心所欲的复制了,10是想复制几个MC。如图1:

http://www.flasher.cn/upload/forum/2004224202740.gif


新建一个MC,在MC里花一个圆形作从蓝到透明的放射渐变填充,并创建由小变大再变小的循环动画,如图2:

http://www.flasher.cn/upload/forum/2004224203007.jpg


返回场景,新建一层,将做好的MC放到主场景中,在属性面板中(Porperties)给MC起名为:ball(也可以起别的名字,但调用方法时要于这个名字一致)。ok!测试看看,是不是自动复制了10个mc都在那一闪一闪的?
这样只是一个很简单的方法,主要是让大家体会一下如何写方法,和调用方法以及方法中参数的作用。
这个copyMC的方法用的是duplicateMovieClip(),如果attachMovie()也可以实现:
function copyMC(mcname,number):Void
{

for(i=1;i<number;){
_root.attachMovie(mcname,"ball"+i, i++);
this["ball"+i]._x=Math.random()*400;
this["ball"+i]._y=Math.random()*400;}
}
_root.attachMovie(mcname,"ball"+i, i++);这一行中是用attachMovie来实现复制MC,我们都知道attachMovie()方法第一个参数是库中MC的linkage中的名字,使用时需要加上” ”,所以调用这个用他实现的copyMC()方法时,应该这样实现:copyMC(“ball”,10)
注:linkage设置方法:在库中选中MC,点右键选linkage,弹出对话框将Export for ActionScript2.0选中,在Identifier中输入名字即可

方法的完善:
写完一个方法后,我们就可以在任何时刻使用这个方法了。但可能根据情况不同需要修改方法,比如,我在第一帧调用copyMC()方法,然后在第5帧也调用copyMC()方法,这时原先的copyMC()方法复制的MC就会被更新。因为在方法体中的duplicateMovieClip()语句复制的MC都是在产生在相同的层。我想在不同时刻调用copyMC()方法而原来复制的不被更新,这时就需要另外一个参数layer来确定启始层。比如这样:
1.function copyMC(mcname,number,layers):Void
2.{
3.
4. for(i=1;i<number;){
5. _root.attachMovie(mcname,"ball"+i+layers,layers+i++);
6. this["ball"+i+layers]._x=Math.random()*400;
7. this["ball"+i+layers]._y=Math.random()*400;}
8.}
第5行:"ball"+i+layers表示复制后MC的名字,layers+i++为层数,如果调用方法时layers输入1000,则复制MC的层数就从1001开始。
调用这个方法:copyMC(“ball”,10,1000);ball表示linkage的名字,10表示个数,1000表示开始的层数,怎么样?不错吧?然后就这个方法可以复用了,在第一帧调用copyMC(“ball”,10,100);第10帧用copyMC(“ball”,10,1000);第20帧用copyMC(“ball”,10,2000);分别调用该方法,就可以不断产生新的MC了,对库中的mc修改一下就可以作成下面这样的效果。



http://www.flasher.cn/upload/forum/2004224203308.swf
http://www.flasher.cn/upload/forum/2004224203356.fla



谈谈方法的返回类型:
as2.0中加入了返回类型的概念,我们可以通过返回类型取得方法的返回结果。比如下面几个方法就是通过返回类型赋值,和判断:
function test():String
{
return "I like flash";
}
s=test();
这是通过方法给变量赋值,return就是返回的结果,在主场景中添加一个动态文本域接收s的值,测试一下,文本域中就会出现 I like flash了。这个是进行赋值,我们再看看进行判断的例子
function isTrue():Boolean
{
return true;
}
if(isTrue())
{
s="I like flash";
}
不过很遗憾的是,flash虽然引入了返回类型的概念,可对返回类型的支持并不很好,因为as2.0中的变量没有类型,没有java语言严谨,java中必须要声明对象的类型。所以,返回类型到有点鸡肋的感觉,不过随着as的不断升级相信,大家理解了返回类型还是有用的。

好了,方法讲到这应该也差不多了,希望大家可以通过这篇文章有所收获,编写一个方便自己的方法。如果大家有什么疑问可以来www.flasher.cn讨论,随时欢迎大家。

叶子
2004-02-28, 03:03 PM
收录闪客学堂。

wei386
2004-03-02, 07:33 PM
如果大家有什么问题,意见尽管提出

伤心的孤妖客
2004-03-02, 11:55 PM
我想学做Flash,请问谁可以教我!
我是一个刚刚受伤的女孩,请大家谅解,不是成心教我的不要和我联系!
我要学习Flash,是因为我要那个男人知道我是有能力的,和我分开他会后悔,我也想要他知道我会在原地等他,等他回头!

其实,我以来很喜欢网络,可是我为了他放弃了,如今我会把网络当成我的生命,我想请各位大虾帮帮我!
帮帮我这个无助的女孩!~~~

请想帮助我的大虾和我联系:
     我的QQ是:45621170
     
     我的E-mail是:yingying6178@163.com
             

伤心的孤妖客
2004-03-03, 01:07 AM
:mad: 为什么,我通过登陆的方式,却进不了闪客帝国交流中心论坛,谁可以帮我,谁能给我指引一条路,我真心的希望大家可以帮我:confused:

大家帮帮我:o

皮皮狼
2004-03-03, 07:15 AM
最初由 wei386 发布
如果大家有什么问题,意见尽管提出
加了10大分。有续集我会密切关注。早点写续集呀!

bluelife
2004-03-06, 01:27 PM
"因为as2.0中的变量没有类型,没有java语言严谨,java中必须要声明对象的类型。所以,返回类型到有点鸡肋的感觉,不过随着as的不断升级相信,大家理解了返回类型还是有用的"
我有点疑问。。AS2有严格的变量类型,和函数返回检测。可以避免很多错误。作者写的一些变量的申明,从来没使用过变量的类型,我觉得象是用AS1 在写代码。。。
请探讨。
发现这个帖子做了教程,有些较真了 :)

皮皮狼
2004-03-06, 04:50 PM
已经通知作者。改正。

谢谢提出中肯建议。

wei386
2004-03-07, 02:41 PM
首先,很高兴你能看我的文章,再者,知识就是在不断的探讨中获得的,呵呵。
下面我来就你说的问题解释一下。首先,as2.0虽然引入了变量类型的概念,但支持的并不好,这点我在文章中说过,即不声明也可以用,以前也有朋友提出应该加上变量类型,比如MovieClip:mcname,但我觉得这样对于一些没有面向对象思想的人来说理解起来可能有点困难,由于主要是让大家体会方法的写法,所以变量类型就没有加上。主要在方法的编写,所以在方法上我加上了返回类型。可能给大家造成了很多不便,请大家见谅,以后一定注意。
第二就是as2.0返回类型的不严禁:
function test():Boolean
{
return true;
}
function test2():String
{
return "true";
}
这两个方法有着不同的返回类型,但放到if里作判断却都可以:
if(test())
{s="i like flash";}
if(test1())
{s="i like flash";}
如果在java则会编译包错。因为if中的判断只能是boolean值。

谢谢你提出文章的不当之处,以后一定注意改正,如果有什么其他问题,也可提出,共勉。

bluelife
2004-03-09, 10:19 PM
"as2.0虽然引入了变量类型的概念,但支持的并不好,这点我在文章中说过,即不声明也可以用"
sure;因为play7是支持以前的AS1 语法的。很高兴和你一起探讨这个问题,有不当之处请指正。因为flash确实存在很多问题,,关键是我们如何避免。
if 判断的这个bug在以前就有了,即使你上面的语句用了:
function test2():String
{
return "trueasdddd2effff";
}
if(test1())
{s="i like flash";}
这个语句仍然被执行。
这样的话,我觉得避免错误,用表达式更好。
if(test1()==true)
{s=" don't throw error message";}
else{trace("var type noot match;")
//sth;
}
你会发现这时候,type match 将会起作用,因为" true"≠true;
你觉得呢?

皮皮狼
2004-03-09, 11:29 PM
哦.我也来参与讨论一下.wei386是在校学生.他学习java之余学习as2.并且把自己的心得写出来..是值得提倡的.

我把这个帖子转过来的时候,没有仔细看他的程序.今天仔细看看.
确实有点不足之处..当时没有仔细审核.就把这个帖子发了..

我的失职...

程序首先破坏了封装原则.程序在_root建立mc不妥.
并且命名都是ball[]

不妥.

加入图层参数想法好的.但是使用不当.
_root.attachMovie(mcname,"ball"+i+layers,layers+i++);
容易造成mc命名的混乱..还不如命名里边不加layers...

已经再次通知作者.....此贴暂时保留.发到学院的教程收回..

谢谢大哥指正..学习你的严谨!!

zjs35
2004-03-10, 07:41 AM
我来学习了

皮皮狼
2004-03-10, 07:54 AM
谢谢大哥啊!
题点意见啊!

叶子
2004-03-10, 01:06 PM
我也失职,呵呵~~该罚,减我100大分(本来这些分就是当初浪子测试积分的时候给我乱加的,HOHO~~)

叶子
2004-03-10, 01:08 PM
发现我的权限只能一次减9分,为了避免麻烦,就少减91分吧,嘿嘿~~;)
这是中场休息,大家继续讨论~~

wei386
2004-03-10, 07:45 PM
真对不起大家,因为我让大家丢分,失职。
呵呵,能够讨论一个问题,才能解决很多问题。
原来写这篇文章的意思,就是想让没有编程基础的朋友,慢慢进入编程领域,体会一下怎样写程序,为了以后的oop作准备。也确实顾此失彼,忽略了一些问题,不过能够有机会和大家探讨一下as,还是很荣幸的!
其实as1.0中的变量没有类型,什么类型都可以到处转化。在as2.0中,as2.0应该会是一个过度版,还是可以自由转化的。
bluepoint8101所说的,test()==true我觉得是一个比较的问题,两个类型之间的“比较”,这种类型应该是flash定义好的,而可能我所说的是“转换”,“比较”与“转换”的差异,我想就是flash as2今后应该改进的吧,今后让变量“转化”向“比较”发展。让变量类型更加有用武之地。

关于变量返回类型,基于oop来说,其实完全可以通过返回类型来判断一个变量的。我想as今后发展会越来越朝这方面发展。
对于类型,可能与每个人认为的“界”有关。因为我是一个java程序员,java中强调变量类型,所以对于as的所有变量可能就放宽了点。关于类型还是as2中比较值得讨论的,我会在好好看看,实验,然后和大家继续讨论。

bluelife
2004-03-10, 09:58 PM
呵呵,我只是想让坛子热闹热闹。AS 1里变量是可以互相转化的。当然,wei386写的文章还是不错,希望以后可以常常拜读。
我觉得if判断是个问题,只要返回的不是空值,他就会默认为是true;//从下面可以看出。
function test2():String
{
return "";
}
if(test2())
{trace("i like flash");}
当然0,1 都可以做真,假判断。反映了AS 1 的不严谨。
有趣的事,ASV's blog 发现了一个bug,和我们的论题也是相关的:
Strict Equality (===), for which a bytecode was introduced with SWF 6, works like the Equality operator (==) except that the data types must also be equal.

When you export to SWF 5, Strict Equals is converted to equivalent bytecodes.

For example, the following code when exported to Flash 5,
if (a === b) {}will compile to:
var _local1 = a;
var _local2 = b;
if (((typeof (_local1) == typeof (_local2)) ?
(_local1 == _local2) : true)) {}by Flash MX 2004; and to:
var _local1 = b;
if (((typeof (a) == typeof (_local1)) ?
(a == _local1) : false)) {}by Flash MX.

Notice the difference how one returns false and one returns true, if the types are not equal. Now, it seems what Flash MX doing is correct here.

You can test this by the following code, using Flash MX 2004 and exporting to SWF 5 and 7:
a=1;
b="1";
if (a===b){
trace("Yes");
} else {
trace("No");
}When exported to SWF 5 by Flash MX 2004, you'll see that it will trace 'Yes' unexpectedly...
天天愉快,每个人!

wei386
2004-03-11, 06:10 PM
"我觉得if判断是个问题,只要返回的不是空值,他就会默认为是true;//从下面可以看出。"
恩,这个我还真是不知道,一会试试,呵呵,又长了点知识。

其实我不怕出问题,问题就是要出的,因为有问题才会进步,呵呵,
也很高兴能与 bluepoint8101 相识,共同探讨,希望以后还能有机会,呵呵

z.k.r
2004-03-11, 07:04 PM
好帖,收!!!

皮皮狼
2004-03-15, 11:27 AM
我认为原因的根。是flash对数据类型的不够严谨。。
在flash 里边。1=ture 0=flase.
并且。完全可以通用。在返回的值中。只要不是0。全部认为是1。

在其他语言里边。数据类型很严格。。。。

顺便问一下。。在flash里边有没有"空值--null"..

as2.0对oop增加很多。数据类型。却没有很大改进。不知道as3。0会不会。。。我菜。。大家讨论。。

wei386
2004-03-16, 08:45 PM
应该有空值
我也这样觉得,as2.0会是一个过渡版,
其实对于flash来说,as不管版本是多少,都是一种面向对象的概念,想想我们在控制mc,button时都是用mc._x,mc.startDrag(),其实都用的是面向对象的概念,MovieClip也是一个类,然后我们创建的mc都是他的对象,所以可以用mc._x获得一些属性。然而当我们自己能够编程时,flash对类型支持不好,就体现出来了,然而这对于面向对象编程而言就有些不利了,不过对于初学者或许是个不错的地方。我觉得还是规范一下变量类型的好,方便于大型程序开发。