Acceder el Stage desde cualquier clase AS3

Posted in: ActionScript, AS3- nov 13, 2008 5 Comments

Al trabajar con clases AS3 en nuestros proyectos hay ocasiones en los que debemos acceder al stage principal de nuestra aplicación desde clases que no extienden a “DisplayObject”, haciendo que debamos pasar como parámetro dicho stage a las clases, esto funciona pero en realidad es un poco “sucio”.

Una solución simple es crear una clase singleton, en la cual, podemos almacenar no solo el stage principal, sino cualquier otro valor que necesitemos en varias clases. Algo así como _global de AS2, lo recuerdan?
Aquí la clase

[as]
package net.tmeister.utils
{
public dynamic class Global
{
private static var global : Global

public static function getInstance() : Global
{
if ( global == null )
{
global = new Global( arguments.callee );
}
return global;
}

public function Global( caller : Function = null )
{
if ( caller != Global.getInstance )
{
throw new Error (“Global is a singleton class, use getInstance() instead”);
}
if ( Global.global != null )
{
throw new Error( “Only one Global instance should be instantiated” );
}
}
}
}
[/as]

Y su modo de uso.

[as]
package
{
import flash.display.MovieClip;
import net.tmeister.utils.Global
public class Main extends MovieClip
{
private var global:Global;

public function Main()
{
global = Global.getInstance();
global.stage = stage
trace(‘global.stage’ + global.stage)
global.algunOtroValor = new MovieClip()
trace(‘global.algunOtroValor ‘ + global.algunOtroValor)
}
}
}
[/as]

Simple.

  • http://www.ccbng.com/blog Andros

    Interesante.
    Yo siempre había usado una clase Global donde almacenaba las variables estáticas tan solo.

    Pero para saber el Stage de cada clase lo que hacia era iniciar el metodo ADDED_TO_STAGE antes de hacer nada, entonces el Stage ya era accesible:

    ...
    public function Main():void {
        addEventListener(Event.ADDED_TO_STAGE, init);
    }
    private function init(e:Event):void {
        _stage = this.stage;
        ...
    }
    

    No se, siempre me ha funcionado bien.

  • Eliseo

    ¿Puedes poner un ejemplo de cómo se usaría en otra clase diferente a la Clase del Documento?
    Sinceramente es que no veo muy claro qué tratas de hacer. El mismo modo te hubiera bastado con que la variable global fuera del tipo Object.

  • http://www.tmeister.net Tmeister

    @Eliseo:

    De la misma forma que la clase Main, En la clase Main haces la asignacion, ya tienes tus valores por ejemplo stage, ahora desde cualquier otra clase solo debes pedir dicho valor algo asi

    package
    {
    	import flash.display.MovieClip;
    	import net.tmeister.utils.Global
    	public class OtraClase extends MovieClip
    	{
    		private var global:Global;
    		public function OtraClase()
    		{
    			global = Global.getInstance();
    			trace('global.stage' + global.stage)
    			trace('global.algunOtroValor ' + global.algunOtroValor)
    		}
    	}
    }
    

    Si te das cuenta es exactamente lo mismo, solo que ya no estamos asignando valores, solo accediendo a ellos.

    Me explico?

  • Eliseo

    Entendido y aplicado, gracias

  • http://www.insomnio.eu Tx

    Pues yo lo hago exactamente como pones (en Flash CS3) y me salta “global.stage: null
    global.algunOtroValor: [object MovieClip]“.

    No sé qué hago mal, pero me veo incapaz de acceder al Stage desde una clase. (estoy empezando en esto del as3).

    Os explico exactamente mi circunstancia por si alguien me puede echar una mano.

    Tengo un archivo llamado escenario.fla cuyo código en el primer fotograma es el siguiente:
    import clases.*;
    var miEscenario:Escenario=new Escenario();

    Dentro de la carpeta clases tengo 2 archivos .as (Escenario.as y Global.as).

    El código de Escenario.as es el siguiente:
    package clases{
    import flash.display.MovieClip;
    import clases.Global;
    public class Escenario extends MovieClip {
    private var global:Global;
    public function Escenario() {

    global = Global.getInstance();

    global.stage = stage;

    trace(‘global.stage: ‘ + global.stage);

    global.algunOtroValor = new MovieClip();

    trace(‘global.algunOtroValor: ‘ + global.algunOtroValor);

    }
    }

    }

    y el de Global.as:
    package clases{

    public dynamic class Global {

    private static var global : Global;

    public static function getInstance():Global {

    if ( global == null ) {

    global = new Global( arguments.callee );

    }

    return global;

    }

    public function Global( caller : Function = null ) {

    if ( caller != Global.getInstance ) {

    throw new Error(“Global is a singleton class, use getInstance() instead”);

    }

    if ( Global.global != null ) {

    throw new Error(“Only one Global instance should be instantiated”);

    }

    }

    }

    }

    ¿Alguien me puede decir qué estoy haciendo mal?

    Muchas gracias por adelantado.

    Tx