进入旧版 | 服务项目 | 成功案例 | 联系方式 | 过客留言 | 友情链接
   
设为首页
加入收藏
联系我们
网站首页 | 新闻资讯 | 操作系统 | 办公软件 | 网络软件 | 工具软件 | 媒体动画 | 网页制作 | 网站开发 | 程序开发 | 平面设计
Photoshop视频教程 | Word入门 | Flash入门 | JScript | VBScript | ASP | PHP | ADO | 网页特效 | 3DS MAX6.0命令 | 系统进程
您当前的位置:GOODSGY电脑学习网 -> 网页制作 -> Flash -> 文章内容  
鼠标特效--弹性框架的制作,同时给菜鸟一些建议

在送上教程之前,我想先感谢一位经典的网友,他介绍了一个数学公式编辑软件MATHTYPE,对我这次写教程有了很大的帮助.但是是谁一时想不起来,又找不到.如果找到的话,我一定会把他的大名公布出来,以示感激.
这是两个月前答应一位网友写的教程,但是当初没有时间,所以拖到现在.而且这个效果还是有相当一部分的人曾经在论坛上问过怎么做的.现在笔者挤出了点时间,给大家送上这个教程.
效果预览:
download.incoo.com/blueidea/hbro/mousewave/mousewave.swf
这基本上是用AS实现的.主要用了MovieClip对象的lineTo和curveTo方法,此外还有很多人都很熟悉的韩式弹性菜单的算法.
在这里,先给大家介绍比较简单的韩式弹性菜单算法.框架弹性动作就是通过这种算法实现的.
它要达到的效果就是让一个物体在目标位置两侧振动,而且振幅越来越小,最终停止在目标位置.
它的算法如下:
ObjPos=targetPos-deceleration*(ObjPos-targetPos)
你尝试让ObjPos是任意的一个数,然后让deceleration取0~1(不包括0,1),然后targetPos取一个跟ObjPos相差比较大的数,不断地代入上式算一下,你会发现ObjPos会在targetPos两侧振动,并且当前一次大于targetPos时候,这一次将小于targetPos,而且无限接近于targetPos,于是就达到弹性振动的目的了.
当然明眼人一观察就出结果.不过这个认识是感性的,如果有兴趣的话,可以看下我对这条式子的证明过程(对数学没兴趣的可以跳过)
在证明之前,先解释一点,上式两边的ObjPos是不一样的,在AS里,它并不代表相等,而是先把ObjPos当前的值代到右边,算出结果后重新对ObjPos赋值.因此,假设ObjPos原始值为a1,该式子运行一次后左边的ObjPos的值记为a2,依此类推,执行到n次后左边ObjPos的值记为an+1,所以,在数学上,实际上是进行这么一个数列的递推运算:
an=t-d(an-1-t)(其中d,t是常数)
当代码执行n次时,物体的位置就位于数列{an}的第n+1项.
因此,我们需要证明数列当a1!=t的时候,an两个相邻项之间的数值跟t的差的符号相反,并且当n趋向于无穷的时候,an=t
click for full sizehttp://www.blue1000.com/upload/2006_03/060308232773201.gif" width=223 onload="javascript:if(this.width>document.body.clientWidth-300) {this.height=(document.body.clientWidth-300)*this.height/this.width;this.width=document.body.clientWidth-300}" border=0>
题外话:据说中国的数学是学得最难的,而这个题目印象中也在高考备考的时候曾做过类似的,也许对于搞数学的中国人来说,要证明这么个式子完全没有问题,可能韩国人还没有谁证明出来呢,但是把这条式子应用到这个实际问题上的居然是韩国人!唉,中国的教育有待改进.www.goodsgy.com

由此可知,如果把这段代码用setInterval调用,或者在onEnterFrame里调用的话,ObjPos的值将在targetPos两边振动,并且无限接近targetPos.这个式子用到我的鼠标效果里,这里要控制的点就是整个框的最高点.最高点的变动带动整个形状的变动,当然带动形状变动是后面的事情,我们当前先要把最高点振动的效果实现.因此,targetPos就是框架最高点最终停留的位置,而ObjPos则是框架最高点当前的位置.
下面笔者介绍的将是如何根据算出的最高点把图形描绘出来.
首先,矩形的四个顶点都是常量,而且有三条边都是直线,因此,这里用lineTo就可以实现了.
lineTo(x,y)方法比较简单,对MC调用该方法时,lineTo将在点x,y和当前MC的画图标记点连一直线,一开始默认为(0,0),所以第一次对该MC调用lineTo的时候,将在该MC上画一条从(0,0)到(x,y)的直线,然后画图标记点就改为(x,y)了.如果不希望一开始画上这条线的话,或者画完一根线以后,希望再画一根,并且不要跟现在的线连在一起的话,可以先用moveTo(x,y)方法改变画图标记点.
curveTo(controlX,controlY,anchorX, anchorY)方法则是该教程的一个重点,因为波形的绘制都是通过该方法实现的.而且过两点有无数条曲线,所以,如何保证波形曲线的平滑性,是个很重要的问题.
下面先做一个小测试:
新建一个Flash文档,在帧上添加下面的代码:
var initX = 100;
var inity = 200;
var controlX;
var controlY;
var anchorX = 50;
var anchorY = 50;
this.onMouseMove = function() {
this.createEmptyMovieClip("curve", 1);
with (curve) {
lineStyle(1, 000000, 50);
moveTo(initX, initY);
ControlX = _xmouse;
ControlY = _ymouse;
lineTo(controlX, controlY);
lineTo(anchorX, anchorY);
moveTo(initX, inity);
curveTo(controlX, controlY, anchorX, anchorY);
}
updateAfterEvent(this.onMouseMove)
};
然后,测试影片,在舞台上移动鼠标,观察曲线的变化(其中,鼠标所在的点是控制点)
也可以直接在这里预览:
download.incoo.com/blueidea/hbro/mousewave/test.swf

你会发现,不管控制点怎样变化,画出来的曲线都有一个特点,就是控制点跟曲线两个顶点的连线都和曲线相切,并且弧线总是C形,不是S形.这就是指导我们画出平滑曲线的重要结论.
观察下面的图:

click for full sizehttp://www.blue1000.com/upload/2006_03/060308232773202.jpg" width=223 onload="javascript:if(this.width>document.body.clientWidth-300) {this.height=(document.body.clientWidth-300)*this.height/this.width;this.width=document.body.clientWidth-300}" border=0>

可以发现,在除红线以外的所有曲线中,跟红线的切线相切,并且方向跟红线相反的两根蓝线是可以跟红线平滑过渡的,数学上这种现象称为连接.另外,切线本身也能跟红线实现平滑过渡.

由此可以正确控制波形的形状.

波形的草图如下:

click for full sizehttp://www.blue1000.com/upload/2006_03/060308232773203.jpg" onload="javascript:if(this.width>document.body.clientWidth-300) {this.height=(document.body.clientWidth-300)*this.height/this.width;this.width=document.body.clientWidth-300}" border=0>

红色是曲线部分,一看就知道不是个简单的C形,你尝试在Flash,或FW或者PS里把这条路径画出来,再看看锚点的组成,你就可以发现,这么条曲线可以分成三条C形曲线.

click for full sizehttp://www.blue1000.com/upload/2006_03/060308232773204.jpg" width=223 onload="javascript:if(this.width>document.body.clientWidth-300) {this.height=(document.body.clientWidth-300)*this.height/this.width;this.width=document.body.clientWidth-300}" border=0>

如果就这样画三段,那么,波形最高点的坐标是由控制点决定的,很难精确,所以,最好在最高点再添加一个锚点,这样最高点的位置就准确了.

click for full sizehttp://www.blue1000.com/upload/2006_03/060308232773205.jpg" onload="javascript:if(this.width>document.body.clientWidth-300) {this.height=(document.body.clientWidth-300)*this.height/this.width;this.width=document.body.clientWidth-300}" border=0>

但是,其它锚点怎么确定呢?

其实根据已知的条件,是无法得出其它锚点的位置的,这个一般凭感觉来确定就好了.姑且让整条曲线的宽度为width,然后假设最高点的横坐标是xm,那么,曲线最左点的横坐标是xm-width/2,最右点的横坐标是xm+width/2,中间两个过渡点的横坐标,一个在xm-width/2和xm之间,一个在xm和xm+width/2之间,为了方便,也为了自然,选取中点,xm+width/4,xm+3*width/4,纵坐标的选取也相似.

现在要讨论的是控制点的问题,就是怎么让每段曲线之前能实现平滑的连接.

首先,作出曲线各锚点的切线.那么,相邻曲线段的切线之间的交点(A,B,C,D)就是相应曲线的控制点.

click for full sizehttp://www.blue1000.com/upload/2006_03/060308232773206.jpg" width=223 onload="javascript:if(this.width>document.body.clientWidth-300) {this.height=(document.body.clientWidth-300)*this.height/this.width;this.width=document.body.clientWidth-300}" border=0>

可见,A,D均位于波形最低点,而B,C位于波形最高点.另外,A,A1,B三点共线,C,C1,D三点也共线,这样就可以保证整个波形都是平滑的.
但是,这样A,B,C,D的位置还是不能确定下来,但可以肯定的一点是,四个点的横坐标从左到右的顺序依次是A,B,C,D.那么,比较方便而且比较美观的选择是让A的横坐标位于A0和A1的中间,那么可以算出B点的位置恰好位于A1和顶点的中间,同样道理,C点在顶点和和C1点的中间,D点在C1点和D0点的中间.

理论基础基本齐全,下面可以开始动手写程序了.

不过笔者发现,有个这个基础原来还不足够,依然会遇到很多很棘手的问题.在测试的时候才发现的.
做法:
1 新建一个Flash文档,大小用默认的550*400好了.
2 然后,在舞台上画一个全透明的矩形,大小:550*100,位置0,300)
3 转换为元件,实例名bg.虽然叫bg,但是是用来检测碰撞的时候用的,也是测试出问题以后才加的.
4 就是添加帧代码了,这里将会结合上面的理论对重要的代码添加注释.
代码如下:
var deceleration = 0.5;
//deceleration是控制缓冲的一个变量,取值在0~1之间,decleration越大,弹性运动越持久.deceleration=0的话,就会一下子停住,decerlation=1的话,就会不停地作等幅振动.如果小于0大于-1,将做非弹性缓冲运动,大于1或小于-1将做振幅越来越大的弹性运动,有兴趣的话可以从上面公式的证明过程里得出这些结论.
//不过简单来说,要实现我们需要的效果,decelertaion根据你的感觉,在0~1之间取一个数就好了
var ypos = 300;
//ypos是波形最低点的纵坐标.在该文档里,建议取200~320范围以内的值.
//下面的函数就是绘制曲线的函数
function drawCurve(name, depth, highpointx, highpointy, width, alpha) {
//画一个图,就要创建一个MC,name就是MC的名称,depth就是MC的深度,然后highpointx,highpointy则是最高点的坐标值,width是波形的宽度,这个值之所以设为变量,是因为框架拉得越厉害,波形的宽度越高,这样动作才不致于过分的生硬,这个读者可以尝试让width为常量.然后,alpha是MC的透明度,当然,你还可以把颜色之类的数值放到参数里面,不过这个不是重点,所以笔者就没放进去了.
this.createEmptyMovieClip(name, depth);
//创建名为name,深度为depth的一个MC
with (this[name]) {
lineStyle(1, 0x666666, alpha);//定义线条样式
beginFill(0xff9900, alpha);//定义填充样式
moveTo(0, ypos);//首先,从矩形做上角的点P1开始画线(见上面的图),参数是P1点的坐标,这是自定的.
lineTo(highpointx-width/2, ypos);//把直线P1A0画出来,参数则是A0点的坐标,算法参照上面的介绍,下同.
curveTo(highpointx-width/2+width/8, ypos, highpointx-width/4, (ypos+highpointy)/2);//画曲线A0A1,前两个参数是A的坐标,后两个参数是A1的坐标
curveTo(highpointx-width/8, highpointy, highpointx, highpointy);//画曲线A1H,前两个参数是B的坐标,后两个参数是H的坐标
curveTo(highpointx+width/8, highpointy, highpointx+width/4, (ypos+highpointy)/2);//画曲线HC0,前两个参数是C的坐标,后两个参数是C0的坐标
curveTo(highpointx+width/2-width/8, ypos, highpointx+width/2, ypos);//画曲线C0D0,前两个参数是D的坐标,后两个参数是D0的坐标
lineTo(550, ypos);//画直线D0P2
lineTo(550, 400);//画直线P2P3
lineTo(0, 400);//画直线P3P4
lineTo(0, ypos);//画直线P4P1,至此框架绘制完成.
endFill();//标记填充操作结束
}
}
this.createEmptyMovieClip("curve", 2);//创建名为curve的空MC
this.onEnterFrame = function() {
var targetx = _xmouse;//targetx框架最高点最终达到的位置的横坐标
var trendy = (Math.abs(_ymouse-ypos)<60 && (curve.hitTest(_xmouse, _ymouse, true) || bg.hitTest(_xmouse, _ymouse, true) || curvebg.hitTest(_xmouse, _ymouse, true))) ? (_ymouse) : (ypos);
var targety = trendy-deceleration*(tempy-trendy);
//targety是框架最高点达到的位置的纵坐标,本来按照算法,trendy直接用targety就行的了,但是总遇到碰撞等诸多问题,为了防止框架过度拉伸和框架自动弹起来,要计算Math.abs(_ymouse-ypos)<60,然后还要检测碰撞的问题,Math.abs(_ymouse-ypos)<60之后的那么长的检查,都是测试的时候才加上去的,笔者无法用理论解释,只能说实践才是检验真理的唯一标准,理论还不能完全指导实践.
if (targetx>0 && targetx<550) {
drawCurve("curve", 2, targetx, targety, Math.max(30, Math.abs(targety-ypos)*10), 40);//这里调用画曲线的函数,targetx和targety已经在上面算好了,现在再解释下width,本来以为让width随波形高度(就是targety-ypos的绝对值)变化而线性增大就完事了,不过发现波形太窄不好看,所以只好让波形宽度不能小于30.
drawCurve("curvebg", 1, _xmouse, targety-20, width=Math.max(30, Math.abs(targety-ypos)*10), 0);//curvebg完全是为了增强碰撞检测的准确性而创建的,它其实就比curveMC高20像素,根据需要可以适当调整第四个参数,所以alpha参数设为0,使之不可见.
}
tempx = targetx;//把当前的targetx赋予tempx,实现数列的递推运算.关于递推,可以参照上面关于弹性算法的介绍
tempy = targety;//同上.
};

这样,文件就完成了,才800多字节就可以把效果实现了.
当然,这只是一些简单的图形,没有任何美工成分,这靠大家去发挥了!
源文件也就这么段代码和一个矩形的MC,我想也不用传给大家了.www.goodsgy.com

还有,这里涉及数学的东西比较多.大家如果对数学不感兴趣,只对效果感兴趣的话,就直接用它好了.当然了解一下还是对大家在程序上发挥创意有一定的帮助.不过作为Flash创作者,数学就没必要学得太精,懂得应用才是最重要的.
中国的数学教育哪怕到了大学,也只重视把具体问题抽象化了,然后教学生去解题,解完以后,应用的问题早就忘得一干二净了.所以,在学校,数学很多时候显得特别枯燥乏味,考试的失利更让很多的学生丧失了对数学的兴趣.哪怕是学的很好的学生,甚至数学家,也有大部分只不过是数学的奴隶,是为了学数学而学数学的.
从考试的角度说,我的数学学得并不好.为了证明缓冲公式,我花了近4小时,而这则是高考会考到的东西,所以数学高考成绩并不好,689分(满分900),但是跟很多700多800多的学生比起来,我更会把数学应用到实际的问题上面,直接应用缓冲公式,我10分钟就把程序写出来了,当然,为了一些BUG我又花了10分钟.因此,分数跟我差不多,在500~700左右分数段的学生就有不少写这些数学程序写得比我好的.所以,在此教程的末尾,我想给大家一些建议:
不要因为自己是菜鸟,就觉得AS好难学,很多时候,AS是应用性的东西,做一些程序是靠自己对事物的观察,然后产生一些想法而实现的,而并不是说你对AS理解得越透彻,就越能做出好的程序来.因此,我觉得,衡量学好AS的标准是你对AS的应用能力,而不是你对它内容理解,掌握的透彻性.所以,有人用Flash4就能做出很酷的AS效果,有人用Flash8还比不上呢!Flash4的AS很少,所以,这说明其中的差异在于你能否把学到知识的应用到位,而非学到知识的多少.
不要觉得自己数学,物理,或者英语学不好而丧失对AS学习的信心.在中国的教育模式下,很多东西对于除了极少数的学专科以外的大部分的人来说,其实都是垃圾.现在,不少的人以自己的学习成绩作为衡量自己学得好否的重要标准,导致自己潜能一直埋没在深处,无法挖掘.所以,自认为学得不好的朋友们,你们也许是最优秀的,也许最能够学以致用,用学到的知识,用AS为Flash作品添加光芒的也许就是你们!
最后补充一点就是我上面所说的并不是否定学习成绩优异的朋友们.你们也许应该问问自己,有没有曾经为了"其所以然"而一直在某个抽象的问题上钻牛角尖.如果有,最好走出来,看看"知其然"能否会对实际应用已经有很大帮助了.当然,如果钻牛角尖能钻出成绩,钻出名气来(像华罗庚,陈景润等),也可以试试,不过能有好结果的毕竟占极少数.
PS:其实我在缓冲公式方面我觉得自己也有点钻牛角尖了,也不知道钻出来的结果有什么用.www.goodsgy.com

在百度中搜索:鼠标特效--弹性框架的制作,同时给菜鸟一些建议
在Google中搜索:鼠标特效--弹性框架的制作,同时给菜鸟一些建议
在Yahoo中搜索:鼠标特效--弹性框架的制作,同时给菜鸟一些建议

收藏到网摘:新浪VIVI 365key 我摘 POCO网摘 博采中心 YouNote 和讯网摘 天天收藏
[] [返回上一页] [打 印] [收 藏]
上一篇文章:用FLASH读经典BLOG的RSS
下一篇文章:flash 高级编程指南

 相关文章    最新文章
· [图文] Flash制作鼠标感应Tween类动画效果..
· [组图] Photoshop鼠标绘制美女剑客插画教程..
· [图文] 让XP也用上Windows Vista鼠标动画
· 在Vista系统中任意设定鼠标滚动行数
· [图文] 鼠标一拖 Vista用户文件夹全至其他..
· [图文] Windows Vista下快速定位鼠标指针位..
· [组图] LiveMotion完全教程(五)对象层及鼠..
· [组图] LiveMotion完全教程(七)对象层及鼠..
· 网页特效放送:跟随鼠标的图片的网页代码..
· 如何用CSS层叠样式表控制鼠标显示的样式
 
· [图文] Flash制作鼠标感应Tween类动画效果..
· [组图] Flash实例:可爱的小青蛙闹钟
· [组图] Flash也能制作特色小图标
· [组图] Flash实例教程:卡通MM眨眼睛动画
· [图文] Flash基础:了解动画基础知识
· [组图] Flash实例:打造佛光效果
· 实现flash站整个网页且flash总是居中
· Flash中如何调用exe可执行文件?
· Flash与Photoshop合作制作模糊渐变动画
· 用Flash AS代码制作按钮弹出窗口

∷相关文章评论∷    (评论内容只代表网友观点,与本站立场无关!) [更多评论…]
站内搜索

精彩图文
  网站导航  
操作系统 办公软件 网络软件
Vista Windows2003 WindowsXP Windows2000/NT Windows9X/ME Linux 其他 Word Excel Powerpoint Outlook 金山系列 其他 网页浏览 上传下载 联络聊天 邮件工具 服务器软件 网络辅助
工具软件 媒体动画 网页制作
系统工具 媒体工具 压缩工具 图文处理 文件管理 其他 3DMAX Authorware Director Maya 视频处理 其他 Flash Dreamweaver FireWorks FrontPage LiveMotion Golive HTML/CSS 其它
网站开发 平面设计 程序设计
ASP JSP PHP CGI JavaScript VBScript XML/SOAP Web服务器 Photoshop PhotoImpact CorelDraw Illustrator Freehand 设计欣赏 其他 VB VC .NET C/C++ DELPHI JAVA

冀ICP备05019428号
Copyright © 2004-2008 电脑学习网 Inc.All rights reserved.
TEL:13832340607
QQ:39873155
E_Mail:goodsgy(#)hotmail.com   (把(#)替换成@)
MSN:goodsgy(#)hotmail.com   (把(#)替换成@)