// haxe -swf-header 500:500:10:eeeeee -swf9 FileRef.swf -main tests.FileRef -debug import flash.events.Event; import flash.events.MouseEvent; import flash.events.ProgressEvent; import flash.events.IOErrorEvent; import flash.events.SecurityErrorEvent; import flash.text.TextField; import flash.text.TextFormat; import flash.net.URLRequest; import flash.net.FileReference; import flash.net.FileReferenceList; import flash.external.ExternalInterface; /* classe de base du programme. Cette classe est dérivée de EventDispatcher pour pouvoir lui ajouter des évenements. */ class Upload extends flash.events.EventDispatcher { static var n:Int; // numéro du fichier (de list) en cours d'envoi static var f:FileReference; // fichier en cours d'envoi static var list:FileReferenceList; // liste des fichiers à envoyer static var log:TextField; // champ texte de log utilisé en cours d'envoi ou en cas d'erreur static var btn:TextField; // bouton à cliquer pour lancer la selection de fichier static var postData:String; // parametres à poster en plus du fichier (ex:id_session) static var format:TextFormat; // format des textes affichés /*********************************************************************/ /* Cette fonction sert en ExternalInterface avec JavaScript. Elle est donc appelée depuis la page HTML contenant le flash avec un code ressemblant à : document.getElementById('monflash').reset(); Elle permet de mettre de remettre le bouton de selection de fichier à la place des logs. Elle est normalement utilisé dans le gestionnaire d'évennement JavaScript:UploadEvent(e) avec les messages de 'finish' ou 'cancel'. */ public static function reset() { log.visible = false; btn.visible = true; } /*********************************************************************/ /* Cette fonction sert en ExternalInterface avec JavaScript. Elle est donc appelée depuis la page HTML contenant le flash avec un code ressemblant à : document.getElementById('monflash').setPostData("id_session=45&titre=coucou"); Elle permet de mettre d'autre variables que le fichier a envoyer au script d'upload */ public static function setPostData(data:String) { postData = data; btn.text = "Envoyez plusieurs fichiers..."; btn.setTextFormat(format); flash.external.ExternalInterface.call("UploadEvent","debug setPostData('"+postData+"');"); } /* Constructeur de la class Upload, est le point d'entrée du programme */ public function new() { super(); // Appelle le constructeur par défaut hérité (donc EventDispatcher) format = new TextFormat("sans-serif",16); list = new FileReferenceList(); log = new TextField(); log.text = "Information sur le fichier"; log.selectable = false; log.x = 5; log.y = 5; log.width = 250; log.height = 20; log.visible = false; flash.Lib.current.addChild(log); btn = new TextField(); btn.text = "Envoyez plusieurs fichiers"; btn.selectable = false; btn.x = 5; btn.y = 5; btn.width = 240; btn.height = 20; btn.setTextFormat(format); /* L'evenement 'nextfile' est spécifique à Upload et permet */ addEventListener("nextfile",ev_nextfile); /* Gestion de l'événement fichiers sélectionnés après un list.browse() */ list.addEventListener("select",ev_list_select); /* Gestion de l'événement annulation d'un list.browse() */ list.addEventListener("cancel",ev_list_cancel); /* Gestion du click sur le seul bouton de l'application, lance la sélection de fichiers */ btn.addEventListener(flash.events.MouseEvent.CLICK,ev_btn_click); flash.Lib.current.addChild(btn); if(ExternalInterface.available) /* vérifié que le parametre allowScriptAccess="allways" est mis */ { ExternalInterface.addCallback("setPostData",setPostData ); ExternalInterface.addCallback("reset",reset ); } else { btn.visible = false; log.visible = true; log.text = "ExternalInterface not available"; } /* UploadEvent('init') est appelé à la fin du constructeur car il faut que les callback est été définit. Normalement, UploadEvent('init') sert a envoyer les variables indispensables, comme le numéro de session, avec setPostData. L'evenement est donc un "fin d'init flash" permettant de garantir que le flash est lancer et initialisé avant de faire la moindre opération sur celui-ci. */ flash.external.ExternalInterface.call("UploadEvent","init"); } /*********************************************************************/ /* Gestion de l'événement 'nextfile' de la Upload. L'événement 'nextfile' est appelé lorsqu'une sélection à été faite (pour le premier fichier), et après qu'un fichier est été transmis si il reste des fichiers à transmettre dans list. */ public function ev_nextfile(e:Event) { if(list.fileList.length==0) // on ne sait jamais, cela ne devrait pas arriver { flash.external.ExternalInterface.call("UploadEvent","cancel"); } else if(n 0)) { /* Cas normal, puisque habituelement on ne laisse la posibilité d'upload qu'aux utilisateurs authentifiés. Les sessions par cookie et les login/mot de passe HTTP ne fonctionnent pas en flash. On doit donc ajouter au moins le numéro de session. */ request = new URLRequest( url + "?" + postData ); //flash.external.ExternalInterface.call("UploadEvent","debug send to "+url+"?"+postData); } else { /* postData n'est pas forcément fixé */ request = new URLRequest( url ); //flash.external.ExternalInterface.call("UploadEvent","debug send to "+url); } f = list.fileList[n]; f.addEventListener(flash.events.Event.COMPLETE,ev_file_complete); f.addEventListener(Event.OPEN, ev_open); f.addEventListener(Event.CANCEL, ev_cancel); f.addEventListener(ProgressEvent.PROGRESS,ev_progress); f.addEventListener(IOErrorEvent.IO_ERROR,ev_io_error); f.addEventListener(SecurityErrorEvent.SECURITY_ERROR,ev_security_error); f.upload(request,"FILE",false); } else { /* on ne doit pas arriver ici, car si la liste est fini, on ne lance pas d'event nextfile */ flash.external.ExternalInterface.call("UploadEvent","nextfile error"); } } /*********************************************************************/ function ev_open(e:Event) { flash.external.ExternalInterface.call("UploadEvent","file open" ); log.text = "OPEN"; } /*********************************************************************/ function ev_cancel(e:Event) { flash.external.ExternalInterface.call("UploadEvent","file cancel" ); log.text = "ANNULATION !!"; } /*********************************************************************/ function ev_io_error(e:IOErrorEvent) { flash.external.ExternalInterface.call("UploadEvent","error io : "+e.text ); log.text = "IO ERROR : " + e.text; } /*********************************************************************/ function ev_security_error(e:SecurityErrorEvent) { flash.external.ExternalInterface.call("UploadEvent","error security : "+e.text ); log.text = "SECURITY ERROR : " + e.text; } /*********************************************************************/ public function ev_progress(e:ProgressEvent) { flash.external.ExternalInterface.call("UploadEvent", "progress " + n + "/" + list.fileList.length + " " + (e.bytesLoaded * 100 / e.bytesTotal) + "%" ); log.text = "Fichier " + n + "/" + list.fileList.length + " -> " + e.bytesLoaded + " octets envoyés sur " + e.bytesTotal ; } /*********************************************************************/ public function ev_file_complete(e:Event) { flash.external.ExternalInterface.call("UploadEvent","file complete"); if((++n)==list.fileList.length) { log.text = "Transfert terminé"; flash.external.ExternalInterface.call("UploadEvent","finish"); } else { flash.external.ExternalInterface.call("UploadEvent","next"); dispatchEvent(new Event("nextfile")); } } /*********************************************************************/ public function ev_list_select(e:Event) { btn.visible = false; log.visible = true; log.text = "Fichiers sélectionnés (" + list.fileList.length + ")\n" ; flash.external.ExternalInterface.call("UploadEvent","selected"); dispatchEvent(new Event("nextfile")); } /*********************************************************************/ public function ev_list_cancel(e:Event) { flash.external.ExternalInterface.call("UploadEvent","cancel"); } /*********************************************************************/ public function ev_btn_click(e:MouseEvent) { n=0; flash.external.ExternalInterface.call("UploadEvent","begin"); if(list.browse()==false) { btn.visible = false; log.visible = true; log.text = "Erreur de sélecteur de fichier"; flash.external.ExternalInterface.call("UploadEvent","error file slector"); } } /*********************************************************************/ /* Point d'entrée obligatoire à tout programme flash. Ne fait qu'instencier l'application définit dans la classe Upload. */ public static function main() { var app = new Upload(); } }