Schemaphic Systems Blog

Sharing experiences in Flash, Flex and AIR

Global TImer in ActionScript

leave a comment »

With my experience with RIA using actionscript, I have come most applications where multiple timers are required.
As the application grows complex, the more and more timers added does slow up the application performance to lot.

That is where I thought of developing a utility class called GlobalTimer. It is a singleton class and runs only a single timer. So where ever in your application a timer is necessary, just add a timer name to this global timer with other parameters and you are done without hitting the application performance.

This class is a pure actionscript class and hence can be used both for flash, flex and AIR projects.

GlobalTimer.as

package com.te.utilities
{
import flash.events.EventDispatcher;
import flash.events.TimerEvent;
import flash.utils.Dictionary;
import flash.utils.Timer;

public class GlobalTimer extends EventDispatcher
{
public static const EQUALS : String = "equals";
public static const DIFFERENCE_FROM_CURRENT_TIME : String = "differs";
public static const CALL_IN_INTERVALS : String = "intervals";

public static var TIME_INTERVAL : int = 100;
public static var instance : GlobalTimer;

private var timer:Timer;
private var currentDate:Date;
private var currentTime:int;//in milliseconds
private var _running:Boolean = false;

private var timersForCheck:Dictionary;

public function GlobalTimer( enf:SingletonEnforcer )
{
timersForCheck = new Dictionary();

super();
}

public static function getInstance() : GlobalTimer
{
if( instance == null ) instance = new GlobalTimer( new SingletonEnforcer() );
return instance;
}

public function start() : void
{
if( _running )    return;

timer = new Timer( TIME_INTERVAL );
timer.addEventListener(TimerEvent.TIMER, onTimerHandler, false, 0, true );
timer.start();

_running = true;
}

private function onTimerHandler( event:TimerEvent ) : void
{
currentDate = new Date();
currentTime = ( currentDate.getHours() * 60 * 60 ) + ( currentDate.getMinutes() * 60 ) + ( currentDate.getSeconds() );

for each( var prop:* in timersForCheck ){
if( prop != null ){
switch( prop[2] ){
case EQUALS:
if( currentTime == ( prop[0] + prop[1] ) ){
//AUTO UPDATE CHECK
prop[3][ String( prop[4] ) ]();
}
break;

case DIFFERENCE_FROM_CURRENT_TIME:
//IDLE TIME CHECK
if( prop[5] != null ){
prop[3][ String( prop[5] ) ]();
}
if( ( currentTime - prop[0] ) == prop[1] && prop[4] != null ){
prop[3][ String( prop[4] ) ]();
}
break;

default:
//CALL_IN_INTERVALS:
if( ( timer.currentCount - prop[0] ) == prop[1] && prop[5] != null ){
prop[0] = timer.currentCount;
prop[3][ String( prop[5] ) ]();
}
break;
}
}
}
}

public function addTimer( name:String, time:Number, check:String, object:*, functionOnComplete:String=null, functionOnTimer:String=null ) : void
{
//timersForCheck[name] = [   0,      1,    2,     3,            4,                 5        ];
timersForCheck[name] = [ timer.currentCount, time, check, object, functionOnComplete, functionOnTimer ];
}

public function removeTimer( name:String ) : void
{
timersForCheck[name] = null;
}

public function isTimerRunning( name:String ) : Boolean
{
var prop:* = timersForCheck[ name ];
if( prop == null ){
return false;
}
return true;
}

public function getTimerData( name:String ) : Object
{
var prop:* = timersForCheck[ name ];
if( prop == null ){
return null;
}
var data:Object = {};
data.currentTime = ( currentTime - prop[0] );
data.remainingTime = ( prop[1] - data.currentTime );
return data;
}

public function stop() : void
{
if( timer != null ){
timer.stop();
timer.reset();
timer.removeEventListener( TimerEvent.TIMER, onTimerHandler, false );
timer = null;

_running = false;

for each( var prop:* in timersForCheck ){
if( prop != null ){
prop = null;
}
}
timersForCheck = null;
timersForCheck = new Dictionary();
}
}

public function get running() : Boolean
{
return _running;
}

protected function reset():void
{
stop();
}
}
}
internal class SingletonEnforcer{}

In the application use the following code:

//Code to be used in your application
private var globalTimer:GlobalTimer;

globalTimer = GlobalTimer.getInstance();
if( !globalTimer.running ){
globalTimer.start();//starts timer
}

//checks if the timer is already running
if ( !globalTimer.isTimerRunning( "game_timer" ) ) {
globalTimer.addTimer( "game_timer", _asuraThrowWeaponInterval, GlobalTimer.CALL_IN_INTERVALS, this, null, "onIntervalEventHandler" );
}

globalTimer.removeTimer( "game_timer" );//removes/clears the particular timer
globalTimer.stop();//stops all the timers
Advertisements

Written by Deepanjan Das

November 22, 2011 at 1:22 PM

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: