📄 animator.as
字号:
package de.alex_uhlmann.animationpackage.utility {import flash.utils.getTimer;import de.alex_uhlmann.animationpackage.APCore;import de.alex_uhlmann.animationpackage.animation.IAnimatable;import de.alex_uhlmann.animationpackage.animation.ISingleAnimatable;import de.alex_uhlmann.animationpackage.animation.IMultiAnimatable;import de.alex_uhlmann.animationpackage.animation.AnimationCore;import de.alex_uhlmann.animationpackage.animation.AnimationEvent;import de.alex_uhlmann.animationpackage.utility.TweenAction;import de.alex_uhlmann.animationpackage.utility.Tween;import de.alex_uhlmann.animationpackage.utility.TimeTween;import de.alex_uhlmann.animationpackage.utility.FrameTween;import flash.events.Event;import flash.display.MovieClip;import flash.display.Sprite;public class Animator extends AnimationCore implements ISingleAnimatable, IMultiAnimatable { public static var animations:Object; public var caller:Object; public var start:Array; public var end:Array; public var setter:Array; public var multiStart:Array; public var multiSetter:Array; public var myTween:Tween; private var startPause:Number; private var pausedTime:Number = 0; private var elapsedDuration:Number = 0; public var stopped:Boolean = false; public var finished:Boolean = false; private var arrayMode:Boolean; private var arrayLength:Number; /*relaxed type to accommodate numbers or arrays*/ private var initVal:*; private var endVal:*; private var identifierToken:Number = 2; public var startPercent:Number; public var endPercent:Number; private var hiddenCaller:Object; private var perc:Number; public function Animator() { super(); this.animationStyle(AnimationCore.duration_def); } public function run(...arguments:Array):void { if (arguments.length > 0) { this.animationStyle(arguments[0], arguments[1]); } else { this.animationStyle(this.duration, this.easing); } if(this.initAnimator() == false) { return; } this.initAnimation(0, 100); } public function animate(start:Number, end:Number):void { if(this.initAnimator() == false) { return; } this.initAnimation(start, end); } public function setCurrentPercentage(percentage:Number):void { if(this.initAnimator() == false) { return; } //percentage = Math.round(percentage); this.perc = percentage; /* * setCurrentPercentage would usually only dispatch onUpdate events. The * following is done to dispatch all events depending on * the state of the animation. * Prevent event dispatching of TweenAction * with temporalily overwriting the caller property * with a clone object of Animator. Fetch onUpdate events * of the clone, modify them accordingly and dispatch them to the caller. */ this.hiddenCaller = this.caller; var hiddenAnimator:Animator = this.cloneAnimator(this); if(!this.caller.omitEvent) { hiddenAnimator.addEventListener(AnimationEvent.UPDATE, onUpdate); } this.caller = hiddenAnimator; this.initStartEndValues(percentage, percentage); var myTweenAction:TweenAction = this.initTweenAction(); /*this is usually done in TweenAction*/ if(!this.arrayMode) { this.hiddenCaller.setCurrentValue(this.initVal); } else { this.hiddenCaller.setCurrentValues(this.initVal); } myTweenAction[this.retrieveSetters().update](this.initVal); this.caller = this.hiddenCaller; } /* private function between(num:Number, min:Number, max:Number):Boolean { return (num > min && num < max); } */ private function cloneAnimator(animator:Animator):Animator { var cloneObj:Animator = new Animator(); cloneObj.omitEvent = animator.omitEvent; cloneObj.caller = animator.caller; cloneObj.start = animator.start; cloneObj.end = animator.end; cloneObj.setter = animator.setter; cloneObj.multiStart = animator.multiStart; cloneObj.multiSetter = animator.multiSetter; cloneObj.roundResult(animator.caller.isRounded()); return cloneObj; } private function onUpdate(event:AnimationEvent):void { //e.target = this.hiddenCaller; var newEvent:AnimationEvent; if(this.perc == 0) { newEvent = new AnimationEvent(AnimationEvent.START); newEvent.value = event.value; this.dispatch(newEvent); } else if(this.perc == 100) { newEvent = new AnimationEvent(AnimationEvent.END); newEvent.value = event.value; this.dispatch(newEvent); } else { newEvent = new AnimationEvent(AnimationEvent.UPDATE); newEvent.value = event.value; this.dispatch(newEvent); } } private function dispatchOnStart():void { if(!this.arrayMode) { this.caller.setCurrentValue(this.initVal); } else { this.caller.setCurrentValues(this.initVal); } this.caller.dispatchEvent(new AnimationEvent(AnimationEvent.START, this.initVal)); } private function dispatch(e:Object):void { this.hiddenCaller.dispatchEvent.apply(this.hiddenCaller, [ e ]); } private function initAnimator():Boolean { //initialize caller. if(this.caller == null) { this.caller = this; } //check if multiple animation targets have been supplied if(this.multiSetter != null) { this.createMultiSetter(this.multiSetter); } //deletion of equivalent values. if(this.caller.equivalentsRemoved == true) { if(this.splitEquivalents() == "ALL") { return false; } } if(AnimationCore.equivalentsRemoved_static == true && this.caller.equivalentsRemoved == null) { if(this.splitEquivalents() == "ALL") { return false; } } saveAnimation(); //initialize start/end values. var len:Number = this.end.length; if(this.start.length != len) { return false; } this.startInitialized = false; if(len > 1) { this.arrayMode = true; this.initVal = this.start; this.endVal = this.end; this.setStartValues(this.initVal); this.setEndValues(this.endVal); } else { this.arrayMode = false; this.initVal = this.start[0]; this.endVal = this.end[0]; this.setStartValue(this.initVal); this.setEndValue(this.endVal); } this.arrayLength = len; return true; } private function saveAnimation():void { if(AnimationCore.getOverwriteModes()) { var i:Number = this.setter.length; while(--i>-1) { var key:String = makeKey(this.setter[i]); if(key == "0")return; if(Animator.animations == null) { Animator.animations = new Object(); } if(Animator.animations[key] != null) { var animation:IAnimatable = Animator.animations[key]; animation.stop(); } Animator.animations[key] = this.caller; } } } private function makeKey(setter:Array):String { var o:String; if(setter[0] is Sprite) { o = String(setter[0]); } else { if(this.caller.overwriteProperty == null) { return "0"; } else { o = setter[0][this.caller.overwriteProperty]; } } return (o + setter[1]); } public function deleteAnimation():void { if(Animator.animations == null) { return; } var i:Number = this.setter.length; while(--i>-1) { var key:String = makeKey(this.setter[i]); if(key == "0")return; delete Animator.animations[key]; } } /* * deletion of equivalent values. Returns "NONE" to indicate * that zero values have been removed. "SOME" that some have been * removed and "ALL" that all have been removed. */ private function splitEquivalents():String { /*extract values that won't animate*/ var len:Number = this.end.length; var i:Number = len; while(--i>-1) { if(this.start[i] == this.end[i]) { this.start.splice(i,1); this.end.splice(i,1); this.setter.splice(i,1); } } if(this.start.length == 0) { this.caller["dispatchEvent"]({type:"onEnd", target:this.caller, value: null}); return "ALL"; } else if(this.end.length == len) { return "NONE"; } else if(this.end.length < len) { return "SOME"; } else { return ""; } } public function hasEquivalents():Boolean { var hasEquivalentsBool:Boolean; var splitResult:String = simulateSplitEquivalents(); if(splitResult == "NONE") { hasEquivalentsBool = false; } else { hasEquivalentsBool = true; } return hasEquivalentsBool; } private function simulateSplitEquivalents():String { var startLen:Number = this.start.length; var endLen:Number = this.end.length; var setterLen:Number = this.setter.length; var len:Number = this.end.length; var i:Number = len; while(--i>-1) { if(this.start[i] == this.end[i]) { startLen--; endLen--; setterLen--; } } if(startLen == 0) { return "ALL"; } else if(endLen == len) { return "NONE"; } else if(endLen < len) { return "SOME"; } else { return ""; } } private function initAnimation(start:Number, end:Number):void { this.startPercent = start; this.endPercent = end; if(this.caller.getTweenMode() == AnimationCore.INTERVAL) { this.invokeAnimation(start, end); } else if(this.caller.getTweenMode() == AnimationCore.FRAMES) { prepareForDurationMode(start, end); } } private function prepareForDurationMode(start:Number, end:Number):void { if(this.caller.getDurationMode() == AnimationCore.MS) { prepareForDurationModeMS(); } else if(this.caller.getDurationMode() == AnimationCore.FRAMES) { prepareForDurationModeFRAMES(start, end); } } private function prepareForDurationModeMS():void { var fps:Number = APCore.getFPS(); this.onFPSCalculated(fps); } private function prepareForDurationModeFRAMES(start:Number, end:Number):void { this.durationInFrames = this.duration; this.invokeAnimation(start, end); } private function onFPSCalculated(fps:Number):void { /*calculate frames with fps.*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -