• Registrati
Benvenuto su codeinvaders.net la community italiana dedicata agli sviluppatori!
Puoi partecipare alle discussioni anche attraverso facebook, twitter e google+.
JS Day
  • google plus
  • facebook
  • twitter
Codeinvaders.net, domande e risposte per sviluppatori!
Partecipa a questa community rispettando tutti i suoi membri che, per il puro piacere di condividere, forniscono risposte e suggerimenti.
Classifica migliori utenti del mese 05/2017
  1. 4240 Punti

  2. 3980 Punti

  3. 3480 Punti

  4. Luca Rainone

    2400 Punti

I premi del mese
Posizione 1: Buono Amazon da 10 euro
Posizione 2: Sconto 40% su un libro O'Reilly

caricare classi al runtime

Ciao
Sembra che il richiamo di una classe al runtime sia possibile con la funzione:
getDefinitionByName(String):Class
in effetti se inserisco nei parametri la stringa della mia classe ( eg. "myClass"), mi da errore perchè non la riconosce, ma sono riuscito a farla funzionare solo in questomodo:

    private function getClassObj(obj:*):*
    {   
      var objClass:Class = Class(getDefinitionByName(getQualifiedClassName(obj)));
      return new objClass();
    }   

con il richiamo:
var cl = getClassObj(myClass);
addChild(cl);

In effetti getDefinitionByName riconosce la stringa solo se generata da getQualifiedClassName che utilizza il nome classe e, quindi, la incorpora nell'esecuzione.
Poiché la ragione recondita per cui sto cercando una soluzione è un po' lunga da spiegare, la rimando a una vostra eventuale richiesta.
Grazie.

quesito posto 31 Luglio 2013 in actionscript da anonimo
   

3 Risposte

+1 voto

Il nome della classe deve essere della forma pakageCompleto::NomeClasse, inoltre la classe deve essere dichiarata in qualche punto del codice

var mockInstance:NomeClasse;

perché il compilatore ne sia "informato", oppure passata come direttiva al compilatore

-includes=pakageCompleto.NomeClasse

risposta inviata 1 Agosto 2013 da anonimo

 

Grazie per la risposta!
Il codice che mi suggerisci è giusto, ma equivalente alla funzione getClassObj che ho indicato.
Come è equivalente a :

    var cls:myClass;
    var prv:Class = getDefinitionByName("myClass");
    var cl = new prv();

Tutte funzionano, ma prevedono l'inclusione della classe nello swf generato dalla compilazione e se inserisco un codice che permette di scegliere se eseguire la classe locale (inclusa) o quella presente nell' SWF memorizzato su un db, esegue sempre la classe locale; per esempio:

    var loc:Boolean = false;
    if (loc)     cl = new prv();    else    cl = new remot();       

dove remot() richiama la classe memorizzata in un db.
A prescindere dal valore della variabile loc, viene eseguita sempre la classe locale.
E' sufficiente rendere commenti le righe che definiscono la classe locale per eseguire quella memorizzata sul db, ma mi piacerebbe far funzionare il tutto con pulsanti.
Ma ho paura non sia possibile. :-((

 

Intendevo dire che se hai il nome di classe, non è necessario ricorrere a getQualifiedClassName poiché sufficiente getDefinitionByName a patto di utilizzare il corretto formato nel nome:
 
    var MyClass:Class = getDefinitionByName(net.codeinvaders::MyLocalClass) as Class;
    var classInstance:ISampleRunTimeClass = new MyClass();
 
Come dicevo, sei ovviamente obbligato a dichiararla in qualche modo al compilatore, direttamente tramite codice od indirettamente tramite direttiva allo stesso. Potresti ovviare al problema del caricamento della classe remota archiviando, oltre al nome di classe anche l'URL di un swf che implementa quella classe e caricarla dinamicamente con un Loader. In questo modo la compilazione della classe è risolta dall'swf esterno, sempre che  alla tua applicazione sia consentito caricare risorse dinamicamente (su tablet ad esempio non puoi).
 
------------
0 voti

risposta inviata 2 Agosto 2013 da anonimo
rivisti 4 Agosto 2013 da anonimo
0 voti

Ciao Francesco.
Ho inteso perfettamente ciò che volevi dire e, per inciso, la funzione remot(), che ho indicato nella risposta, ritorna la classe caricata con Loader.
E' che, visto che getDefinitionByName vuole come parametro una stringa, ho provato a passargliela usando getQualifiedClassName che ha come parametro il nome di classe, per vedere se non la prendeva come dichiarazione esplicita, ma purtroppo:

var cl:Class = Class(getDefinitionByName(getQualifiedClassName(miaCl)));        

equivale a:

var cls:miaCl;
var cl:Class = Class(getDefinitionByName("miaCl"));

Tutte e due funzionano, ma tutte e due dichiarano esplicitamente miaCl al compilatore.
Questo comporta che anche un'eventuale caricamento da remoto della classe, utilizzando Loader, non viene considerato, per esempio:

var sw:Boolean;
var cls:miaCl;
var cl:Class

sw = false;
if (sw) 
    cl = Class(getDefinitionByName("miaCl"));
    else
    cl = remot();   // ritorna la classe caricata con Loader
var prv = new cl();
prv.init();         

esegue il codice presente nella "miaCl" locale, anche se "prv" dovrebbe puntare a quella caricata da remoto.
Per intenderci, Loader carica la classe da remoto ma, visto che è già presente nella compilazione, semplicemente non la considera!
Se faccio diventare commento la variabile cls, allora viene eseguita la classe caricata con Loader ma, naturalmente, se metto sw = true dovrò togliere il commento, pena errore durante l'esecuzione.

Ma davvero la classe Loader non funziona sui Tablet?
Se è così non potrò mai veder funzionare il mio sito su quel dispositivo!
Mannaggia! :-((

risposta inviata 3 Agosto 2013 da anonimo
Ma infatti il problema è chi istanzia cosa. Se ad istanziare è la tua applicazione allora fa fede la dichiarazione su quest'ultima che ha sempre precedenza, mentre se vuoi che il riferimento di classe sia quello proveniente dal Loader, allora è il componente esterno che dovrà istanziare. Dovrai utilizzarlo quindi come una factory per quella classe: passi a questo il riferimento di classe e ti tornerà l'istanza in base a quello che lui conosce di quella classe e non in base a quello che conosce la tua applicazione.

Per i Tablet intedevo dire sul compilato. Se deploy su iOS ad esempio non funziona ma se l'OS prevede l'utilizzo del plugin nel browser non hai problemi, funziona come su qualsiasi altro flash player.
Puoi partecipare alle discussioni anche attraverso facebook e twitter.
...