Flash原创:打造震撼人心的破碎过渡特效【AS 3.0】

4 篇文章 0 订阅

在2016年寒假,《复仇者联盟2》上映后,网上也推出了Flash小游戏。这是我当年根据效果自己模拟的破碎效果,可能稍微逊色。

在舞台上创建实例名称为img的影片剪辑,文件类填写Fragment。

package 
{
	//2016.02.11
	//正弦前锋
	
	import flash.display.DisplayObject;
	import flash.display.Graphics;
	import flash.geom.Point;
	import flash.display.Shape;
	import flash.display.MovieClip;
	import flash.events.Event;
	import flash.display.BitmapData;
	import flash.display.Bitmap;
	import flash.geom.Rectangle;
	import flash.events.MouseEvent;
	import flash.display.Sprite;
	import flash.utils.Timer;
	import flash.events.TimerEvent;
	import fl.transitions.Tween;
	import flash.geom.ColorTransform;
	import flash.filters.GlowFilter;

	public class Fragment extends Sprite
	{
		public var img:MovieClip;

		private var pstartr:Number = Math.random() * 2;
		private var pcenter:Point = new Point(400,300);
		private var rounds:Array = [];
		private var breakpoints:Number = 18;
		private var pieces:Array = [];
		private var pieces2:Array = [];
		private var sps:Number;
		private var stateW:Number = 800;
		private var stateH:Number = 600;
		private var lastR:Number;
		private var lengths:Array;
		private var played:Boolean = false;
		private var compNum:Number = 0;
		private var timer:Timer = new Timer(5);

		public function Fragment()
		{
			img.gotoAndStop(1);

			stage.addEventListener(MouseEvent.CLICK,onClick);
			timer.addEventListener(TimerEvent.TIMER,onTimer);
		}

		private function getRound(r:Number,p:Number):Array
		{
			var angle:Number = 2 * Math.PI / p;
			var pstart:Number = pstartr * Math.PI;
			var pp:Array = [];
			var i:Number;

			for (i=1; i<=p; i++)
			{
				var vp:Number = pstart + angle * (i - 1);
				var vx:Number = Math.cos(vp) * r + Math.random() / 5 * r;
				var vy:Number = Math.sin(vp) * r + Math.random() / 5 * r;
				pp[i] = new Point(Math.round(vx),Math.round(vy));
			}
			return pp;
		}
		private function getMost(p:Array):Object  //找出坐标取最值的碎片
		{
			var t:Point = new Point  ;
			var i:Number;
			var u:Array = new Array  ;
			var o:Object = new Object  ;
			var xmin:Number = 0;
			var ymin:Number = 0;

			t.x = p[1].x;
			t.y = p[1].y;

			for (i=1; i<p.length; ++i)
			{
				u[i] = new Point  ;
				u[i].x = p[i].x;
				u[i].y = p[i].y;
			}

			for (i=2; i<p.length; ++i)
			{
				if (t.x > p[i].x)
				{
					t.x = p[i].x;
				}
				if (t.y > p[i].y)
				{
					t.y = p[i].y;
				}
			}

			xmin = t.x;
			ymin = t.y;

			for (i=1; i<u.length; ++i)
			{
				u[i].x -=  xmin;
				u[i].y -=  ymin;
			}

			o.arr = u;
			o.x = xmin;
			o.y = ymin;

			return o;
		}
		private function getPieces(r:Array):MovieClip  //绘制碎片多边形轮廓
		{
			var k:MovieClip = new MovieClip  ;

			k.graphics.beginFill(0x000000,1);
			k.graphics.lineStyle(0,0x000000);
			k.graphics.moveTo(r[1].x,r[1].y);
			for (var i=2; i<r.length; ++i)
			{
				k.graphics.lineTo(r[i].x,r[i].y);
			}
			k.graphics.endFill();

			return k;
		}
		public function breakIt(mc:MovieClip):void  //破裂
		{
			var sp_z:Number = (Math.random()>0.2?-1:1)*Math.random() * 5;
			var sp_y:Number = (mc.y - pcenter.y) * Math.random() / 7-40;
			var sp_x:Number = (mc.x - pcenter.x) * Math.random() / 7;

			sp_y = (sp_y < -40) ? -40:40;


			var sp_rx:Number = (Math.random()>0.2?-1:1)*Math.random() * 10;
			var sp_ry:Number = (Math.random()>0.2?-1:1)*Math.random() * 10;
			var sp_rz:Number = (Math.random()>0.2?-1:1)*Math.random() * 10;
			var dec_x:Number = (mc.x-pcenter.x)/Math.abs(mc.x-pcenter.x)*2;

			mc.addEventListener(Event.ENTER_FRAME,fl_run);

			function fl_run(e:Event):void  //运动效果,每帧一循环
			{
				mc.z +=  sp_z / sps;
				mc.y +=  sp_y / sps;
				mc.x +=  sp_x / sps;
				mc.rotationX +=  sp_rx / sps;
				mc.rotationY +=  sp_ry / sps;
				mc.rotationZ +=  sp_rz / sps;

				sp_y +=  10 / sps;
				sp_x -=  dec_x * 2 / sps;
				if (sps>=4)
				{
					sps -=  0.01;
				}
				if (mc.y > stateH)
				{
					mc.removeEventListener(Event.ENTER_FRAME,fl_run);
					mc.visible = false;
					removeChild(mc);

					++compNum;
					if (compNum>=(lengths.length-1)*breakpoints)
					{
						played = false;
					}
				}
			}
		}
		public function main():void
		{
			var i:Number;
			var j:Number;

			rounds = [];

			for (i=0; i<=lengths.length-1; ++i)
			{
				rounds.push(getRound(lengths[i],breakpoints));
			}

			for (i=0; i<=lengths.length-2; ++i)
			{
				var ar:Array = [];
				pieces[i] = new Array  ;
				pieces2[i] = new Array  ;

				for (j=1; j<=breakpoints; ++j)
				{
					var m:Number= (j+1>breakpoints)?1:(j+1);
					var ok:Object = new Object  ;
					var br:Number=((Math.random()>0.6)?15:-15)*Math.random()*2;  //随机生成各个近似同心圆碎片组合

					ar[1] = rounds[i][j];
					ar[2] = rounds[i + 1][j];
					ar[3] = rounds[i + 1][m];
					ar[4] = rounds[i][m];
					ok = getMost(ar);
					ar = ok.arr;


					pieces[i][j] = getPieces(ar);

					pieces[i][j].x = ok.x;
					pieces[i][j].y = ok.y;

					pieces[i][j].x +=  pcenter.x;
					pieces[i][j].y +=  pcenter.y;

					pieces2[i][j] = attachBitmap(img,pieces[i][j],br);
					addChild(pieces2[i][j]);
				}
			}
		}
		public function onClick(e:MouseEvent):void
		{
			if (! played)
			{
				pcenter.x = stage.mouseX;
				pcenter.y = stage.mouseY;

				if (pcenter.x > stateW / 2)
				{
					lastR = pcenter.x * Math.sqrt(2);
				}
				else
				{
					lastR = (stateW - pcenter.x) * Math.sqrt(2);
				}
				lengths = new Array(20,80,240,lastR);

				main();

				sps = 6;
				compNum = 0;
				played = true;

				img.gotoAndStop(img.currentFrame==img.totalFrames?1:(img.currentFrame+1));

				timer.start();
			}
		}
		public function onTimer(e:TimerEvent):void
		{
			timer.reset();

			for (var i=0; i<=lengths.length-2; ++i)
			{
				for (var j=1; j<=breakpoints; ++j)
				{
					breakIt(pieces2[i][j]);
				}
			}
		}
		public function attachBitmap(mc:MovieClip,shape:MovieClip=null,brightness:Number=0):MovieClip
		{
			var datax:Number = shape.x;
			var datay:Number = shape.y;
			var rect:Rectangle = new Rectangle(datax,datay,shape.width,shape.height);
			var bmp:BitmapData = new BitmapData(stateW*Math.sqrt(2),stateH*Math.sqrt(2),true,0x000000);
			var nbmp:BitmapData = new BitmapData(shape.width,shape.height,true,0x000000);
			var gf:GlowFilter=new GlowFilter((Math.random()>0.4)?(0x000000):(0xFFFFFF));
			var bmp2:Bitmap = new Bitmap  ;
			var mc2:MovieClip = new MovieClip  ;
			var mc3:MovieClip = new MovieClip  ;

			gf.blurX = 2;
			gf.blurY = 2;
			gf.strength = 10;

			bmp.fillRect(bmp.rect,0x000000);
			bmp.draw(mc);

			nbmp.lock();
			nbmp.copyPixels(bmp,rect, new Point(0,0));
			nbmp.unlock();

			bmp2.bitmapData = nbmp;

			mc2.addChild(bmp2);

			shape.x = 0;
			shape.y = 0;

			mc3.addChild(mc2);
			mc3.addChild(shape);
			mc2.mask = shape;

			mc3.z = 20 - Math.random() * 40;
			mc3.x = datax;
			mc3.y = datay;

			mc3.filters = new Array(gf);
			setBrightness(mc3,brightness);

			return mc3;
		}
		public function setBrightness(obj:DisplayObject,value:Number):void  //亮度调节
		{
			var colorTransformer:ColorTransform = obj.transform.colorTransform;
			var backup_filters:* = obj.filters;

			value /=  100;
			if (value >= 0)
			{
				colorTransformer.blueMultiplier = 1 - value;
				colorTransformer.redMultiplier = 1 - value;
				colorTransformer.greenMultiplier = 1 - value;
				colorTransformer.redOffset = 255 * value;
				colorTransformer.greenOffset = 255 * value;
				colorTransformer.blueOffset = 255 * value;
			}
			else
			{
				value = Math.abs(value);
				colorTransformer.blueMultiplier = 1 - value;
				colorTransformer.redMultiplier = 1 - value;
				colorTransformer.greenMultiplier = 1 - value;
				colorTransformer.redOffset = 0;
				colorTransformer.greenOffset = 0;
				colorTransformer.blueOffset = 0;
			}
			obj.transform.colorTransform = colorTransformer;
			obj.filters.push(backup_filters);
		}
	}

}

资源地址:http://pan.baidu.com/s/1dEiCj0P

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值