LoaderInfo.parameters immutable ?
Par Cédric Tabin le lundi 13.04.2009, 08:00 - ActionScript - Lien permanent
Il est facile de transmettre des variables à un SWF en passant par les FlashVars. Elles sont récupérables via la propriété parameters de la classe LoaderInfo. Celle-ci étant de type Object, il devrait être possible de pouvoir lui ajouter des paires clés/valeurs... Et bien ce n'est pas si simple !
Le bout de code suivant démontre bien la problématique :
public class RootDocument extends Sprite { public function RootDocument():void { trace(loaderInfo.parameters); //[object Object] loaderInfo.parameters["test1"] = "value1"; loaderInfo.parameters.test2 = "value2"; trace(loaderInfo.parameters.test1); //undefined trace(loaderInfo.parameters.test2); //undefined } }
De toute évidence, l'objet pointé via loadInfo.parameters ne se laisse pas apprivoiser. Et on est en droit de se demander pourquoi...
En poussant le test un peu plus loin, le résultat est suprenant :
public class RootDocument extends Sprite { public function RootDocument():void { var obj:Object = loaderInfo.parameters; trace(obj == loaderInfo.parameters); //false } }
Visiblement, à chaque fois que la propriété parameters est appelée, un nouvel Object est généré ! Je dois dire que j'ai du mal à comprendre pourquoi cela a été implémenté de la sorte...
Pourtant il serait utile de pouvoir ajouter des propriétés dynamiques (style références sur des objets) pour éviter de compiler des classes redondantes.
Dans l'intervalle, on devra se contenter de faire une classe avec des données statiques, pour autant que le contexte le permette
Commentaires
Hello
C'est surement une propriété virtuelle qui va chercher ses données "ailleurs" (la vérité est ailleurs) et du coup il doit y avoir une incidence directe sur le contenu de l'objet et donc sa référence générée à chaque appel.
Par contre du coup tu me fais penser qu'il est préférable de faire une copie de l'objet pour le stocker dans une référence fixe dans l'application. Je vais m'y coller dans mon framework pour optimiser un peu tout cela
PS : je ne m'étais pas rendu compte de ce comportement. Merci pour l'info
EKA+
Ola
j'ai rencontrer le même souci, mais dans la doc la propriété est bien marquée en lecture seul du coup normal que l'on ne puisse pas la modifier...
Tbo
Hello,
et si tu mets ton loaderinfo dans une variable ?
comme dans cet exemple :
var tf : TextField = addChild(new TextField()) as TextField;
tf.width=500;
var recup:String=loaderInfo.parameters.maVar="theCaptain";
if (recup) {
tf.text=recup;
} else {
tf.text="Erreur : maVar est non définie";
}
ce qui donne dans ton exemple :
var recup:String=loaderInfo.parameters"test1"="value1";
var recup2:String=loaderInfo.parameters.test2="value2";
trace(recup);
trace(recup2);
Hello,
Oui tu peux le faire, mais ça ne change rien au problème... Je voulais passer par LoaderInfo.parameters pour Masapi afin de pouvoir transmettre l'instance ILoadableFile de manière générique. Hors si tu fais une classe statique, tu auras de problème suivant le contexte dans lequel le SWF est chargé. J'ai une petite idée en tête pour contourner cela (hériter de Loader et overrider LoaderInfo), mais faut que je teste
@++
salut Cédric,
comme tout ce qui est implémenté en natif dans Flash, on ne asit pas vraiment ce qui se passe sous le capot. Mais ça doit être un getter plutôt qu'une propriété qui existe vraiment. En attendant des vrais specs de la part d'Adobe ou un flash open source...
Ariel
Hello,
Oui je ne discute pas le fait que ce soit un getter ou non, c'est clair Par contre ce qui m'étonne, c'est que du processing soit fait dans ce getter... Le standard ne voudrait-il pas que nous ayons plutot une méthode getParameters():Object, ce qui rendrait le comportement plus intuitif ?
Logiquement un getter se contente de retourner une valeur et ne devrait pas faire du calcul derrière (enfin ce n'est que mon opinion).
@++
Il faut passer par la classe ExternalInterface pour pouvoir mettre à jour les propriétés en question. Exemple :
@@ExternalInterface.call("function(){this.params'test' = 'bob';}");
trace(loaderInfo.parameters'test');@@
Pour que ça fonctionne correctement, il faut préalablement donner les droits d'accès à l'interface externe, via le paramètre allowScriptAccess.
Salut,
Ah tiens intéressant ça Par contre tu ne peux pas passer de référence vers une instance d'une classe AS... Faut que je creuse un peu, y a peut-être moyen de faire quelque chose !
@++