具体下载就不说了,http://code.google.com/p/bulk-loader/
拿个简单的例子来说,在加载图片的时候通常会用到Loader,但我们会发现当批量加载的时候,即使我们按照1、2、3、、、的顺序在complete 的时候总会得到不同的图片顺序,因为ProgressEvent 的影响,在执行for循环后会同时加载,因为bytesTotal的不同而导致加载完成的无序。
BulkLoader 一个开源的列队加载类很好的解决这一问题。
一个简单例子:
import br.com.stimuli.loading.*;
var loader:BulkLoader=new BulkLoader("main");
for(var i:int = 1;i<=11;i++){
var url:String = "images/" + i + ".jpg";
loader.add(url);
}
loader.addEventListener(BulkLoader.PROGRESS, onProgress);
loader.addEventListener(BulkLoader.COMPLETE, onComplete);
loader.start();
var oldTimer:Number = getTimer();
function onProgress(e: BulkProgressEvent):void {
//trace(loader.get("mp3").percentLoaded);}
function onComplete(evt : Event):void {
for(var i:int = 1;i<=11;i++){
var img:Bitmap = loader.getBitmap("images/" + i + ".jpg");
addChild(img);
img.width = 100;
img.height = 100;
img.x = 100 * (i-1);
}}
我们会发现加载的图片 按指定的1、2、3、、加载到舞台。
究其原因 我们会发现同样是是BulkLoader.PROGRESS 的作用。
再看一例子:
import br.com.stimuli.loading.BulkLoader;
import br.com.stimuli.loading.BulkProgressEvent;
var loader:BulkLoader=new BulkLoader("main");
loader.add("bg.jpg");
loader.add("soundtrack.mp3",{id:"mp3"});
//loader.add("intro.flv");
loader.addEventListener(BulkLoader.PROGRESS, onProgress);
loader.addEventListener(BulkLoader.COMPLETE, onComplete);
loader.start();
var oldTimer:Number = getTimer();
function onProgress(e: BulkProgressEvent):void {
trace(loader.get("mp3").percentLoaded);
//NaN
//0
//0.017519720244799166
//0.03503944048959833
//0.0525591607343975
//trace(e.loadingStatus());
//if(loader.get("mp3").percentLoaded == 1){
// trace(getTimer() - oldTimer);
// }
}
function onComplete(evt : Event):void {
//var bgBitmap=loader.getBitmap("bg.jpg");
//addChild(bgBitmap)看到trace的结果 第一行为NaN 因为我们先加载的bg.jpg 当加载完成时loader.get("mp3").percentLoaded才有值。
如果将loader.add("bg.jpg");
loader.add("soundtrack.mp3",{id:"mp3"});的位置换下 就没NaN的出现
以下转自 http://uh.9ria.com/link.php?url=http://www.po-min.com%2Farchives%2F15
BulkLoader 是个很好用的加载类库,用 BulkLoader实例的add()方法可以很方便地将素材地址加入加载列表。
当然,这里有一些地方要注意,我们一一的解决它。
在BulkLoader 的 add方法中,有下面这些参数:
url:* — 加载对象(String 或者 URLRequest 类型)
props:Object (default = null) — 一些加载对象的属性,有下面这些
preventCache:Boolean — 是否防止缓存
id:String — 添加加载对象时候,也可以给它添加一个id,方便以后调用
priority:int — 还可以通过priority属性调整加载对象的加载顺序,priority值越大,优先权越高,越早加载
maxTries:int — maxTries属性用于设定加载失败时的重试次数
weight:int — 每个文件的大小提前告诉BulkLoader(当你想更精确的得到加载进度的时候,这是一个好的办法)
headers:Array — URLRequest 的头信息,当你传入的url是一个String的时候,BulkLoader也会把这些信息添加到URLRequest里面
context:* — LoaderContext 或者 SoundLoaderContext,加载到ApplicationDomain程序域的时候常用的属性
pausedAtStart:Boolean — 如果是一个nestream 对象,控制对象是否暂停。
BulkLoader提供PROGRESS事件和COMPLETE事件,让我们监视加载状态,用法如下
1 2 3 4 5 6 7 8 | //添加一个PROGRESS事件,这个事件会在队列加载时不断触发。通常可以用于监听加载进度。 loader.addEventListener(BulkLoader.PROGRESS, onAllItemsProgress); //添加一个COMPLETE事件,这个事件会在队列里的所有对象都加载完毕后触发 loader.addEventListener(BulkLoader.COMPLETE, onAllItemsLoaded); //一切准备好后,只要调用start方法就可以开始加载我们添加的素材序列了。 loader.start(); |
好了,看完上面的大家应该对BulkLoader有了一定了解了,至于一些用法,可以看BulkLoader的文档,或者搜索一下,有很多教程,这里我要说的是我们会遇到的一些问题。
用 BulkLoader实例的add()方法可以很方便地将素材地址加入加载列表
但是当素材太多的时候,加载进度会不准确(progess事件中的totalBytes并不能同步获取所有资源的Bytes)
最精确解决的办法是将 每个文件的大小提前告诉BulkLoader,就是在add里面加入weight值。
但是,这显然不是一个最省事的解决方法。
其实文档里面有一些属性可以给我们使用,通过BulkProgressEvent的loadingStatus方法可以显示加载过程中的所有信息!
大家可以在函数中trace() loadingStatus方法看看,就像下面:
1 2 3 | public function onAllItemsProgress(e: BulkProgressEvent):void { trace(e.loadingStatus()); } |
你会发现 BulkProgressEvent 会有一个 weightPercent属性,通过这个值,差不多可以解决我们的问题了,如果发现加载进度还是有很大误差的话,大家再看看loadingStatus 里面的其他属性,通过自己的算法来解决,不然就只能在 add 的时候,把文件的大小提前告诉 BulkLoader了。
剩下一个会经常需要解决的问题就是程序域的问题了,也就是加载的时候ApplicationDomain的问题,大家都知道 在用 Loader 加载文件的时候,可以在通过LoaderContext开指定加载的域,如下(例子是加载到当前域):
1 2 3 | var context:LoaderContext = new LoaderContext(); context.applicationDomain = new ApplicationDomain(ApplicationDomain.currentDomain); loader.load(new URLRequest("text.swf"),context); |
在BulkLoader里面我们同样可以进行指定,方法也是差不多的。
1 2 3 4 5 6 | var loader : BulkLoader = new BulkLoader("config"); loader.addEventListener(BulkLoader.PROGRESS, loadProgress); loader.addEventListener(BulkLoader.COMPLETE, loadInit); var context : LoaderContext = new LoaderContext(true, ApplicationDomain.currentDomain); loader.add("EsCard.swf", {id:"main", context: context}); loader.start(); |