Brown Movement:
Varnumdots: uint = 50; varfriction: Number = 0.9; vardots: array; varlife: uint = 0; functioninit () {graphics. linestyle (0, 0 xffffff ,. 5); DOTS = newarray (); For (vari: uint = 0; I <numdots; I ++) {vardot: ball = newball (2, 0x00ff00); dot. X = math. random () * stage. stagewidth; dot. y = math. random () * stage. stageheight; dot. VX = 0; dot. vy = 0; dots. push (DOT); addchild (DOT); checkbound (DOT);} addeventlistener (event. enter_frame, enterframehandler);} // check the boundary functioncheckbound (B: ball) {If (B. x <B. width/2) {B. X = B. width/2;} elseif (B. x> stage. stageWidth-b.width/2) {B. X = stage. stageWidth-b.width/2;} If (B. Y <B. height/2) {B. y = B. height/2;} elseif (B. y> stage. stageHeight-b.height/2) {B. y = stage. stageHeight-b.height/2 ;}} functionenterframehandler (E: Event): void {// trace (LIFE); If (Life> = 200) {graphics. clear (); graphics. linestyle (0, 0 xffffff ,. 5); LIFE = 0 ;}for (vari: uint = 0; I <numdots; I ++) {vardot: ball = dots [I]; graphics. moveTo (Dot. x, Dot. y); dot. VX + = math. random ()-0.5; dot. vy + = math. random ()-0.5; dot. X + = dot. VX; dot. Y + = dot. vy; dot. VX * = friction; dot. vy * = friction; checkbound (DOT); graphics. lineto (Dot. x, Dot. y);} Life ++;} Init ();
Rectangular distribution:
vardotNumber:uint=500;vardots:Array;varcenterX:uint=stage.stageWidth/2;varcenterY:uint=stage.stageHeight/2;varlimitX:uint=50;varlimitY:uint=100;functioninit():void{dots=newArray();for(vari:uint=0;i<dotNumber;i++){vardot:Ball=newBall(3*Math.random(),0x00ff00);dot.x=centerX+(Math.random()*2-1)*limitX;dot.y=centerY+(Math.random()*2-1)*limitY;addChild(dot);dots.push(dot);}addEventListener(Event.ENTER_FRAME,enterframeHandler);}functionenterframeHandler(e:Event):void{for(vari:uint=0;i<dotNumber;i++){vardot:Ball=dots[i];dot.x=centerX+(Math.random()*2-1)*limitX;dot.y=centerY+(Math.random()*2-1)*limitY;/*varix:Number=dot.x;variy:Number=dot.y;dot.y=ix;dot.x=iy*/}}init();
Round random distribution:
vardotNumber:uint=500;vardots:Array;varcenterX:uint=stage.stageWidth/2;varcenterY:uint=stage.stageHeight/2;varradius:uint=75;functioninit():void{dots=newArray();for(vari:uint=0;i<dotNumber;i++){vardot:Ball=newBall(3*Math.random(),0x00ff00);varangle:Number=2*Math.random()*Math.PI;varr:Number=Math.random()*radius;dot.x=centerX+r*Math.cos(angle);dot.y=centerY+r*Math.sin(angle);addChild(dot);dots.push(dot);}addEventListener(Event.ENTER_FRAME,enterframeHandler);}functionenterframeHandler(e:Event):void{for(vari:uint=0;i<dotNumber;i++){vardot:Ball=dots[i];varangle:Number=2*Math.random()*Math.PI;varr:Number=Math.random()*radius;dot.x=centerX+r*Math.cos(angle);dot.y=centerY+r*Math.sin(angle);}}init();
More even round random distribution:
Vardotnumber: uint = 200; varcenterx: uint = stage. stagewidth/2; varcentery: uint = 100; varradius: uint = 50; functioninit (): void {for (vari: uint = 0; I <dotnumber; I ++) {vardot: ball = newball (2, 0x00ff00); varangle: Number = 2 * Math. random () * Math. pi; varr: Number = math. random () * radius; dot. X = centerx + R * Math. cos (angle); dot. y = centery + R * Math. sin (angle); addchild (DOT) ;}// more evenly distributed random for (I = 0; I <dotnumber; I ++) {vardot1: ball = newball (2, 0x00ff00); varangle1: Number = 2 * Math. random () * Math. pi; varr1: Number = math. SQRT (math. random () * radius; // The key here is the math. after random () is taken as the square root, the distribution becomes more even. dot1.x = centerx + R1 * Math. cos (angle1); dot1.y = centery + 200 + R1 * Math. sin (angle1); addchild (dot1) ;}} Init ();
Biased distribution: (that is, in the specified region, the center is the most concentrated, and the farther away from the center, the more sparse the distribution)
Vardotnumber: uint = 600; varcenterx: uint = stage. stagewidth/2; varmaxwidth: uint = 75; varbils: array = newarray (); functioninit (): void {for (vari: uint = 0; I <dotnumber; I ++) {vardot: ball = newball (2, 0x00ff00); // take two values in the Y axis and calculate the average value as the Y coordinate vary1 = stage. stageheight * Math. random (); vary2 = stage. stageheight * Math. random (); varty = (Y1 + y2)/2; // the X axis performs similar processing. varx1 = centerx + (math. random () * 2-1) * maxwidth; varx2 = centerx + (math. random () * 2-1) * maxwidth; vartx = (X1 + x2)/2; dot. X = TX; dot. y = ty; addchild (DOT); bils. push (DOT);} stage. framerate = 1; addeventlistener (event. enter_frame, enterframehandler);} Init (); functionenterframehandler (E: Event) {for (vari: uint = 0; I <dotnumber; I ++) {vardot: ball = bils [I]; vary1 = stage. stageheight * Math. random (); vary2 = stage. stageheight * Math. random (); varty = (Y1 + y2)/2; varx1 = centerx + (math. random () * 2-1) * maxwidth; varx2 = centerx + (math. random () * 2-1) * maxwidth; vartx = (X1 + x2)/2; dot. X = TX; dot. y = ty ;}}
Biased distribution of multiple iterations (similar to the nebula distribution)
vardotNumber:uint=100;variterations:uint=6;varballs:Array=newArray();functioninit():void{for(vari:uint=0;i<dotNumber;i++){vardot:Ball=newBall(2,0x00ff00);varxpos:Number=0;varypos:Number=0;for(varj:uint=0;j<iterations;j++){xpos+=stage.stageWidth*Math.random();ypos+=stage.stageHeight*Math.random();}dot.x=xpos/iterations;dot.y=ypos/iterations;addChild(dot);balls.push(dot);}stage.frameRate=1;addEventListener(Event.ENTER_FRAME,enterFrameHandler);}init();functionenterFrameHandler(e:Event){for(vari:uint=0;i<dotNumber;i++){vardot:Ball=balls[i];varxpos:Number=0;varypos:Number=0;for(varj:uint=0;j<iterations;j++){xpos+=stage.stageWidth*Math.random();ypos+=stage.stageHeight*Math.random();}dot.x=xpos/iterations;dot.y=ypos/iterations;}}
Redraw settings of the Timer class:
Varball: ball = newball (); varvx: Number = 5; vartimer = newtimer (20); stage. framerate = 1; // set the number of frames of the Flash animation to 1 frame/second ball. y = stage. stageheight/2; ball. VX = 5; addchild (ball); timer. addeventlistener (timerevent. timer, timerhandler); functiontimerhandler (E: timerevent): void {ball. X + = ball. VX; If (ball. x> stage. stagewidth + ball. width/2) {ball. X =-ball. width/2;} e. updateafterevent (); // after the event is triggered, redraw the entire stage (we recommend that you remove this line and check the effect)} timer. start ();
Note: the timing of the Timer class is not as accurate as in C #, because it is associated with the frame rate.
Time-based animation:
Flash animation is frame-based (that is, objects on the stage will be re-painted and enter_frame events will be triggered), which is totally different from Silverlight's time-based design. In general, this is not a problem, but it may produce inconsistent playback effects on machines with different configurations, for example, for a simple animation, "a simple ball moves from left to right", if the enter_frame event uses ball. X + = ball. on a classic server, SWF animation can only play 10 frames per second. On a 4-Core High-configuration machine, it can play 100 frames per second. The question is: If ball. if VX is 5, then on the old man's machine, the ball eventually moved 5x10 = 50 pixels per second. On the high-configuration machine, the ball moved 5x100 = 500 pixels per second, this is not the same as what developers expect. The following Code demonstrates how to create a time-based animation, and finally make the ball speed consistent on machines with different configurations. (Note: At this point, we have to admit that Silverlight is better than flash in design)
Varball: ball = newball (); varvx: Number = 5; stage. framerate = 100; // usually in a time-based animation, the number of frames can be set a little higher (although the machine can not reach the number of frames .) ball. y = stage. stageheight/2; ball. VX = 10; addchild (ball); vartimer = gettimer (); addeventlistener (event. enter_frame, enterframehandler); functionenterframehandler (E: Event): void {varelapsed: Number = gettimer ()-timer; // calculate the time difference between frames (in milliseconds) ball. X + = (ball. VX * elapsed/1000); // converts milliseconds to seconds and then multiplied by the "Speed". The final effect is: if the number of frames is low, the animation is played too slowly, it moves more distances at a time, and vice versa, it moves less distances to achieve dynamic adjustment. if (ball. x> stage. stagewidth + ball. width/2) {ball. X =-ball. width/2;} timer = gettimer ();}
You can try to set the number of frames above to 200 or 50, and then test the playback effect. This will show that the ball moves at the same speed and is not affected by the number of frames. (But the number of frames is recommended not to be less than 10, because the human eye's visual limit is about 0.1 seconds, the animation below this value will look very stuck)
In addition, the comparison code of Silverlight is provided here:
Usingsystem; usingsystem. windows; usingsystem. windows. controls; usingsystem. windows. interOP; usingsystem. windows. threading; namespacesilverlightapplication1 {publicpartialclassmainpage: usercontrol {dispatchertimertmr; ballb; publicmainpage () {initializecomponent (); this. loaded + = newroutedeventhandler (mainpage_loaded);} voidmainpage_loaded (objectsender, routedeventargse) {settingssettings = application. current. host. settings; settings. enableframeratecounter = true; settings. maxframerate = 1; B = newball (); // ball is a custom control, which contains a Circle C. children. add (B); B. setvalue (canvas. leftproperty, C. width/2); B. setvalue (canvas. topproperty, C. height/2); TMR = newdispatchertimer (); TMR. interval = newtimespan (0, 0, 0, 20); TMR. tick + = neweventhandler (tmr_tick); TMR. start ();} voidtmr_tick (objectsender, eventargse) {double_left = (double) B. getvalue (canvas. leftproperty); B. setvalue (canvas. leftproperty, _ left + 5 );}}}
Ball collision of the same quality:
Flash/flex learning notes (43): in the conservation of momentum and energy, we learned how to use as3.0 to simulate the conservation of small ball traffic, but the calculation is also very complicated, collision of the same quality can be implemented more simply. The basic principle is that two objects exchange their speed along the collision line (if you want to study it, you can solve the equation and verify it yourself ). In this way, we can simplify some of the calculations when dealing with such special cases. The complete code is as follows:★)
Package {importflash. display. sprite; importflash. events. event; importflash. geom. point; points {privatevarbils: array; privatevarnumbils: uint = 8; privatevarbounce: Number =-1.0; publicfunctionsamemass () {Init ();} privatefunctioninit (): void {bils = newarray (); For (vari: uint = 0; I <numbils; I ++) {// varradius: Number = math. random () * 40 + 10; varradius: Number = 20 ;//★★★★★Force all quality to the same varball: ball = newball (radius, math. random () * 0 xffffff); ball. mass = radius; ball. X = I * 100; ball. y = I * 50; ball. VX = math. random () * 10-5; ball. vy = math. random () * 10-5; addchild (ball); bils. push (ball);} addeventlistener (event. enter_frame, onenterframe);} privatefunctiononenterframe (Event: Event): void {for (vari: uint = 0; I <numbils; I ++) {varball: ball = bils [I]; ball. X + = ball. VX; ball. Y + = ball. vy; checkwils (ball);} for (I = 0; I <numBalls-1; I ++) {varballa: ball = bils [I]; for (varj: number = I + 1; j <numbils; j ++) {varballb: ball = bils [J]; checkcollision (Balla, ballb );}}} // stage Boundary Detection functioncheckwils (B: ball) {If (B. x <B. radius) {B. X = B. radius; B. VX * = bounce;} elseif (B. x> stage. stageWidth-b.radius) {B. X = stage. stageWidth-b.radius; B. VX * = bounce;} If (B. Y <B. radius) {B. y = B. radius; B. vy * = bounce;} elseif (B. y> stage. stageHeight-b.radius) {B. y = stage. stageHeight-b.radius; B. vy * = bounce;} privatefunctionrotate (X: Number, Y: Number, sin: Number, cos: Number, reverse: Boolean): point {varresult: Point = newpoint (); if (reverse) {result. X = x * Cos + y * sin; result. y = y * Cos-x * sin;} else {result. X = x * Cos-y * sin; result. y = y * Cos + x * sin;} returnresult;} privatefunctioncheckcollision (ball0: ball, ball1: ball): void {vardx: Number = ball1.x-ball0.x; vardy: number = ball1.y-ball0.y; vardist: Number = math. SQRT (dx * dx + dy * Dy); If (Dist <ball0.radius + ball1.radius) {// calculation angle and positive cosine varangle: Number = math. atan2 (dy, dx); varsin: Number = math. sin (angle); varcos: Number = math. cos (angle); // rotate ball0 position varpos0: Point = newpoint (); // rotate ball1 speed varpos1: Point = rotate (dx, Dy, sin, cos, true); // rotate the speed of ball0 varvel0: Point = rotate (ball0.vx, ball0.vy, sin, cos, true); // rotate the speed of ball1 varvel1: Point = rotate (ball1.vx, ball1.vy, sin, cos, true); // the force of the collision varvxtotal: Number = vel0.x-vel1.x; vel0.x = (ball0.mass-ball1.mass) * vel0.x + 2 * ball1.mass * vel1.x)/(ball0.mass + ball1.mass); vel1.x = vxtotal + vel0.x ;*///★★★★★Change to speed switch★★★★★Vartemp: Point = vel0; vel0 = vel1; vel1 = temp; // update location varabsv: Number = math. ABS (vel0.x) + math. ABS (vel1.x); varoverlap: Number = (ball0.radius + ball1.radius)-math. ABS (pos0.x-pos1.x); pos0.x + = vel0.x/absv * overlap; pos1.x + = vel1.x/absv * overlap; // rotate the position back to varpos0f: Object = rotate (pos0.x, pos0.y, sin, cos, false); varpos1f: Object = rotate (pos1.x, pos1.y, sin, cos, false ); // adjust the position to the actual position of the screen ball1.x = ball0.x + pos1f. x; ball1.y = ball0.y + pos1f. y; ball0.x = ball0.x + pos0f. x; ball0.y = ball0.y + pos0f. y; // rotate the speed back varvel0f: Object = rotate (vel0.x, vel0.y, sin, cos, false); varvel1f: Object = rotate (vel1.x, vel1.y, sin, cos, false); ball0.vx = vel0f. x; ball0.vy = vel0f. y; ball1.vx = vel1f. x; ball1.vy = vel1f. Y ;}}}}
Sound usage:
Sound usage is actually nothing special, similar to images, videos, and other resources.
For example, when importing a sound, you can specify a class name, and then in the code, you can create an instance of this class. In addition, remote sound can be directly loaded. The complete code is as follows:
varbgMusic=newSound(newURLRequest("http://210.51.38.234/music/sophie_zelmani_Going_Home.mp3"));varstf:SoundTransform=newSoundTransform();stf.volume=0.3;bgMusic.play(0,0,stf);varbing:Bing=newBing();varball:Ball=newBall(30);ball.vx=5;ball.vy=5;ball.x=stage.stageWidth/2;ball.y=stage.stageHeight/2;addChild(ball);addEventListener(Event.ENTER_FRAME,EnterFrameHandler);functionEnterFrameHandler(e:Event):void{ball.x+=ball.vx;ball.y+=ball.vy;if(ball.x>=stage.stageWidth-ball.radius){ball.x=stage.stageWidth-ball.radius;ball.vx*=-1;bing.play();}elseif(ball.x<=ball.radius){ball.x=ball.radius;ball.vx*=-1;bing.play();}if(ball.y>=stage.stageHeight-ball.radius){ball.y=stage.stageHeight-ball.radius;ball.vy*=-1;bing.play();}elseif(ball.y<=ball.radius){ball.y=ball.radius;ball.vy*=-1;bing.play();}}
Animationinactionscript3.0/makingthingsmove! The book has finally been fully completed. Thanks to the author master keithpeters for writing such a good book, and thanks to the careful translation of [fl Ji Li Wen] Over the past four months! It is strongly recommended to friends who want to study Silverlight/Flash Animation. Many of the ideas and processing methods in this article are common in animation programming and are not limited to a specific language! "The master leads the door and practices each person." How far can he go on the road of animation programming in the future, he can only see his own creation.