package { import flash.display.DisplayObject; import flash.display.Sprite; import flash.display.StageQuality; import flash.events.Event; import flash.filters.BlurFilter; import Services.*; import Screens.*; /* SystemController is responsible for the following: * - bootstrapping once the preloader has finished * - start services * - managing screens */ public class SystemController extends Sprite { private static var controller:SystemController; //Services public var clientService:ClientService; public var debugService:DebugService; public var userService:UserService; public var soundService:SoundService; public var weaponPanelService:WeaponPanelService; public var levelService:LevelService; public var musicService:MusicService; //Screens public var screens:Array = new Array(); //Other Variables public var singlePlayerMode:Boolean = false; public var currentScreen:DisplayObject = null; /** * Constructor - Initializes one instance of the SystemController. * * Multiple calls like the following: * var controller:SystemController = new SystemController(); * will return the same instance. */ public function SystemController() { if (controller == null) { controller = this; addEventListener(Event.ADDED_TO_STAGE, bootstrap); } } // Static method to get instance of the SystemController public static function getInstance():SystemController { return controller; } // Bootstraps the project by starting services and // showing the logo while server connections are made private function bootstrap(e:Event = null):void { removeEventListener(Event.ADDED_TO_STAGE, bootstrap); soundService = new SoundService(); debugService = new DebugService(); userService = new UserService(); levelService = new LevelService(); clientService = new ClientService(); weaponPanelService = new WeaponPanelService(); musicService = new MusicService(); parent.addChild(controller.debugService); DebugService.init(stage, parent); screens[ScreenIndex.LOGO] = new LogoScreen(); screens[ScreenIndex.LOGIN] = new LoginScreen(); screens[ScreenIndex.MAIN] = new MainScreen(); screens[ScreenIndex.HELP] = new HelpScreen(); screens[ScreenIndex.SCORE] = new ScoreScreen(); screens[ScreenIndex.LEVEL] = new LevelScreen(); screens[ScreenIndex.SINGLE] = new SingleScreen(); screens[ScreenIndex.BUY] = new BuyScreen(); screens[ScreenIndex.LOBBY] = new LobbyScreen(); screens[ScreenIndex.ROOM] = new RoomScreen(); screens[ScreenIndex.MULTI] = new MultiScreen(); changeScreen(ScreenIndex.LOGO); } // Shows the screen indicated by index public function changeScreen(index:int):void { debugService.log("SystemController | changeScreen: " + index); addChild(screens[index]); currentScreen = DisplayObject(screens[index]); } //Fade through black Animation transition private var animating : Boolean = false; private var blackness : black = new black(); public function fadeChangeScreen(previous : DisplayObject, index : int):void { if (!animating) { debugService.log("SystemController | changeScreen: " + index); animating = true; currentScreen = DisplayObject(screens[index]); addChild(blackness); blackness.alpha = 0; frame_counter = 0; previous.addEventListener(Event.ENTER_FRAME, fadeTransition); } } //Event.ENTER_FRAME Handler private function fadeTransition(e:Event):void { frame_counter++; if (frame_counter < 50) { blackness.alpha = frame_counter / 50.0; } else if (frame_counter == 50) { blackness.alpha = 1; DisplayObject(e.currentTarget).removeEventListener(Event.ENTER_FRAME, fadeTransition); removeChild(DisplayObject(e.currentTarget)); addChild(currentScreen); currentScreen.dispatchEvent(new Event("ADDED_TO_STAGE")); swapChildren(currentScreen, blackness); currentScreen.addEventListener(Event.ENTER_FRAME, fadeTransition); } else if (frame_counter < 100) { blackness.alpha = (100-frame_counter) / 50.0; } else { blackness.alpha = 0; removeChild(blackness); DisplayObject(e.currentTarget).removeEventListener(Event.ENTER_FRAME, fadeTransition); animating = false; debugService.log("done with fading" + currentScreen.x + "," + currentScreen.y); } } //Slide Animation transition private var frame_counter : int = 0; private var reverseAnimate : Boolean = false; public function animateChangeScreen(previous : DisplayObject, index : int, reverse : Boolean = false):void { if (stage.quality == "LOW") { removeChild(previous); changeScreen(index); } else if (!animating) { animating = true; debugService.log("SystemController | changeScreen: " + index); var next : DisplayObject = DisplayObject(screens[index]); reverseAnimate = reverse; next.x = 1.2*stage.stageWidth; addChild(next); currentScreen = next; frame_counter = 0; previous.addEventListener(Event.ENTER_FRAME, animateTransition); } } //Event.ENTER_FRAME Handler private function animateTransition(e:Event):void { var previous : DisplayObject = DisplayObject(e.currentTarget); var offset : Number, noffset : Number, foffset : Number, fnoffset : Number; frame_counter++; if (frame_counter < 85) { // Calculate offsets offset = Math.min(1, Math.max(0, Math.pow(frame_counter, 2.5) / Math.pow(50, 2.5))); noffset = Math.min(1, Math.pow(Math.min(50, 85 - frame_counter), 2.5) / Math.pow(50, 2.5)); foffset = Math.min(1, Math.max(0, Math.pow(frame_counter, 3) / Math.pow(50, 3))); fnoffset = Math.min(1, Math.pow(Math.min(50, 85 - frame_counter), 3) / Math.pow(50, 3)); previous.filters = [new BlurFilter(foffset*800, 0, 1)]; currentScreen.filters = [new BlurFilter(fnoffset*800, 0, 1)]; if (reverseAnimate) { previous.x = offset * 1.2 * stage.stageWidth; currentScreen.x = - noffset * 1.2 * stage.stageWidth; } else { previous.x = - offset * 1.2 * stage.stageWidth; currentScreen.x = noffset * 1.2 * stage.stageWidth; } } else { // Remove previous and erase filters currentScreen.filters = []; previous.filters = []; previous.removeEventListener(Event.ENTER_FRAME, animateTransition); previous.x = 0; removeChild(previous); currentScreen.x = 0; animating = false; } } } }