10-26-2005, 12:48 AM
|
#1
|
|
Registered User
Join Date: Apr 2004
Location: France
Posts: 52
|
MovieClipLoader issues
Hi,
Does anyone know if there is any mechanism in the MovieClipLoader in order to queue the downloads? i.e. ,if I launch movieClipLoader.loadClip 40 times, will the flash plugin send 40 simultaneous requests to the server?
since downloads are cached by the navigator, perhaps there is such a mechanism in it?
|
|
|
10-26-2005, 02:20 AM
|
#2
|
|
Chick dig raccoons
Join Date: Apr 2005
Location: Maryland / Massachusetts
Posts: 1,104
|
If you launch it 40 times then flash will spin off 40 parallel threads for downloading.
What you can do to link them is called "daisy-chaining" by linking the tail of one to the head of the next.
So make an array of paths, then have one MCL. The MCL's onComplete listener should pop an element off the array and load it, until the array is empty. It's pretty simple, if you want me to write it, I can.
|
|
|
10-26-2005, 02:24 AM
|
#3
|
|
Super Moderator
Join Date: Jan 2002
Location: Centreville, VA
Posts: 26,666
|
|
|
|
10-26-2005, 05:45 AM
|
#4
|
|
Registered User
Join Date: Apr 2004
Location: France
Posts: 52
|
thanks for your help!
I'm finally writing my first class to create a queued MovieClip loader.
Here is a first shot:
Code:
/** This class extends the basic MovieClipLoader by adding a record of the url's that have already been loaded (and are therefore in the cache),
and by adding a queue mechanism for the url's that are not in the browser's cache.
It simulates a MovieClipLoader for each instance, but in fact there's a single MovieClipLoader for all of them.
static elements are needed to coordinate all the downloads (i.e. if an instance finishes downloading an url,
we need to tell all the instances that this url is in cache.)
*/
class queuedMovieClipLoader{
private static var loaded_urls:Array = new Array();//[url:String] = status:Number -- this array is used to list every url that has been loaded by various instances of this class. the URL's are the INDEX of the array while the values reflect the status of this url (NULL - unknown,0 - being loaded,1 - loaded and in navigator's cache).
private static var requests:Array = new Array();//[target_clip:MovieClip] = (url:String,instance:instance_of_this_class,dl_status:number):Object -- This array stores all the download requests that are made to all instances of this class.
private static var cliploader:MovieClipLoader = new MovieClipLoader(); //the MovieClipLoader we are extending.
private var broadcaster:Object; //used to simulate the MovieClipLoader built in broadcaster.
private var event_listener:Object;//this listener listens to the messages from the static MovieClipLoader.
private var simultaneous_downloads:Number;//This variable defines how many downloads at a time an instance class is allowed to perform.
private var free_download_slots:Number;//used to know if a download can be launched
public function queuedMovieClipLoader(){
this.broadcaster = new Object();
AsBroadcaster.initialize(this.broadcaster);
this.simultaneous_downloads = 1;
this.free_download_slots = this.simultaneous_downloads;
this.event_listener = new Object();
this.event_listener.this_instance = this;//we do this to solve scoping problems...
this.event_listener.onLoadComplete = function(target){
if(queuedMovieClipLoader.requests[target].instance == this.this_instance){//if the target movieclip was loaded using this instance...
this.this_instance.broadcaster.broadcastMessage("onLoadComplete",target);//We fire the onLoadComplete event
if(queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[target].url] == 0){//if this url has never been fully loaded (it was therefore a download from the server)...
queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[target].url] = 1;//We notify all the instances that this url has been fully loaded once
this.this_instance.free_download_slots++;//We free the download slot
}
for(var index in queuedMovieClipLoader.requests){//we walk the requests array to get of the queue any request concerning this url
if((queuedMovieClipLoader.requests[index].dl_status == 0)//if the request is waiting a download to finish,
&&(queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[index].url] == queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[target].url])){//and it is the same url...
queuedMovieClipLoader.cliploader.loadClip(queuedMovieClipLoader.requests[index].url,index);//we launch the download from the navigator's cache
queuedMovieClipLoader.requests[index].dl_status = 1;//we notify that this request is downloading
}
}
this.this_instance.load_next_request();//We try to launch a new download from the server.
}
}
this.event_listener.onLoadError = function(target:MovieClip, errorCode:String, httpStatus:Number){
if(queuedMovieClipLoader.requests[target].instance == this.this_instance){//if the target movieclip was loaded using this instance...
this.this_instance.broadcaster.broadcastMessage("onLoadError",target ,errorCode, httpStatus);//We fire the event
if(queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[target].url] == 0){//if it was a download from the server...
this.this_instance.free_download_slots++;//we free the download slot.
//queuedMovieClipLoader.requests.splice(target,0);//We take out the request
}
for(var index in queuedMovieClipLoader.requests){//now we walk the requests array to kill every request to the same url
if((queuedMovieClipLoader.requests[index].dl_status == 0)//if the request is waiting a download from the server to complete
&&(queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[index].url] == queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[target].url])){//and the url is the same...
queuedMovieClipLoader.requests[index].instance.broadcaster.broadcastMessage("onLoadError",target ,errorCode, httpStatus);//we broadcast the message FROM THE CONCERNED INSTANCE
queuedMovieClipLoader.requests.splice(index,0);//we take the request of the list.
}
}
this.this_instance.load_next_request();//we try to start a new download from the server.
}
}
this.event_listener.onLoadInit = function(target){
if(queuedMovieClipLoader.requests[target].instance == this.this_instance){//if this instance is concerned
this.this_instance.broadcaster.broadcastMessage("onLoadInit",target);//we broadcast the message
queuedMovieClipLoader.requests.splice(target,0);//we take the request off the list.
}
}
this.event_listener.onLoadProgress = function(target){
if(queuedMovieClipLoader.requests[target].instance == this.this_instance){
this.this_instance.broadcaster.broadcastMessage("onLoadProgress",target);
}
}
this.event_listener.onLoadStart = function(target){
if(queuedMovieClipLoader.requests[target].instance == this.this_instance){
this.this_instance.broadcaster.broadcastMessage("onLoadStart",target);
}
}
queuedMovieClipLoader.cliploader.addListener(this.event_listener);
}
public function addListener(listener:Object):Boolean{
return this.broadcaster.addListener(listener);
}
public function getProgress(target:Object):Object{
return queuedMovieClipLoader.cliploader.getProgress(target);
}
public function loadClip(url:String, target_clip:MovieClip):Boolean{
queuedMovieClipLoader.requests[target_clip] = new Object();//we setup the new request object
queuedMovieClipLoader.requests[target_clip].url = url;//with the requested url
queuedMovieClipLoader.requests[target_clip].instance = this;//this instance of the class
switch(queuedMovieClipLoader.loaded_urls[url]){//Now it depends on the requested url...
default:// this is the case where the url is unknown and has never been loaded
queuedMovieClipLoader.requests[target_clip].dl_status = 0;//we tell the request is awaiting to start
load_next_request();//we try to launch a new download.
break;
case 0: // this is the case where the url is already being loaded for another clip.
queuedMovieClipLoader.requests[target_clip].dl_status = 0;//the request is waiting...
break;
case 1:// this is the case where the url has already been fully loaded, therefore it should be in browser's cache and it hasn't to be queued.
queuedMovieClipLoader.cliploader.loadClip(url,target_clip);//we launch the download from the navigator's cache
queuedMovieClipLoader.requests[target_clip].dl_status = 1;//we notify that this request is downloading
break;
}
return true;
}
public function removeListener(listener:Object){
this.broadcaster.removeListener(listener);
}
public function get_simultaneous_downloads(){
return this.simultaneous_downloads;
}
public function set_simultaneous_downloads(new_value){
this.free_download_slots += new_value - this.simultaneous_downloads;
this.simultaneous_downloads = new_value;
this.load_next_request();
}
private function load_next_request(){
if(this.free_download_slots > 0){//if there is no free download slot, we do not even try
for(var index in queuedMovieClipLoader.requests){//we walk the requests array
if((this.free_download_slots > 0)//if there is a free download slot
&&(queuedMovieClipLoader.requests[index].instance == this)//and the request is from this instance
&&(queuedMovieClipLoader.requests[index].dl_status == 0)//and the request is waiting to start the download
&&(queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[index].url] == undefined)){//and the url of the request has never been asked for.
queuedMovieClipLoader.loaded_urls[queuedMovieClipLoader.requests[index].url] = 0;//we notify that this url has been asked for once, but is not fully loaded, therefore in the cache.
queuedMovieClipLoader.cliploader.loadClip(queuedMovieClipLoader.requests[index].url,index);//we launch the download
queuedMovieClipLoader.requests[index].dl_status = 1;//we notify that this request is downloading
this.free_download_slots--;//we take the slot.
}
}
}
}
}
It must still be full of nasty bugs, but it works for now...
There are still problems though. I don't know why, but the compiler throws me a "type mismatch" when I try to splice a download request, BUT ONLY in the "onLoadError" handler (this is the line in comments).
Any Idea?
Perhaps is that because I use MovieClip objects as the index of the request array?
General comments would also be appreciated.
Thanks!
Last edited by gring; 10-26-2005 at 05:51 AM.
Reason: corrected "splice" instead of "slice"
|
|
|
10-26-2005, 06:21 AM
|
#5
|
|
Registered User
Join Date: Apr 2004
Location: France
Posts: 52
|
Alright, the problem comes from the fact that an array index CANNOT be a MovieClip. In this case, the MovieClip must be automatically converted to a String (like when we try to trace a movieClip reference).
The problem is... is the string we get from a movieclip unique?
|
|
|
10-26-2005, 04:47 PM
|
#6
|
|
Chick dig raccoons
Join Date: Apr 2005
Location: Maryland / Massachusetts
Posts: 1,104
|
If you are getting the absolute path to the movie clip, as in trace, it would be unique, but if it only returns its name, it will not be unique. You could have:
_root.mc1
and
_root.mc2.mc1
So, two mc1s, but if you had their full path then they are unique.
Cool loading class  b
|
|
|
| Thread Tools |
|
|
| Display Modes |
Rate This Thread |
Linear Mode
|
|
Posting Rules
|
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts
HTML code is Off
|
|
|
All times are GMT. The time now is 06:13 AM.
///
|
|