• ProgressiveLoader 渐进式加载图像


    转自:http://www.lite3.cn/blog/?p=616

    渐进式加载类,用法跟Loader差不多.

    不同点:

    1. 当加载流错误时只能获取到 "Error #2124: 加载的文件为未知类型。"
    2. 侦听contentLoaderInfo的Progress事件的bytesLoaded,bytesTotal是整个文件的已加载字节和总字节.
    3. contentLoaderInfo.bytesLoaded, contentLoaderInfo.bytesTotal指当前loader里的字节数和总字节.
    代码
    package cn.lite3.net 
    {
        
    import flash.display.LoaderInfo;
        
    import flash.errors.IOError;
        
    import flash.events.Event;
        
    import flash.events.IOErrorEvent;
        
    import flash.events.ProgressEvent;
        
    import flash.events.SecurityErrorEvent;
        
    import flash.system.LoaderContext;
        
    import flash.display.Loader;
        
    import flash.net.URLRequest;
        
    import flash.net.URLStream;
        
    import flash.utils.ByteArray;
     
        
    /**
         * 渐进式加载类
         * 用法跟Loader一样,
         * <p><b>不同点:</b></p>
         * 1.当加载流错误时只能获取到 "Error #2124: 加载的文件为未知类型。" <br/>
         * 2.侦听contentLoaderInfo的Progress事件的bytesLoaded,bytesTotal是整个文件的已加载字节和总字节.<br/>
         * 3.contentLoaderInfo.bytesLoaded, contentLoaderInfo.bytesTotal指当前loader里的字节数和总字节
         * 
         * 
    @author lite3
         
    */
        
    public class ProgressiveLoader extends Loader
        {
            
    private var bytesLoaded:uint = 0;            // 已加载的字节数
            private var bytesToal:uint = 0;             // 总字节数
     
            
    private var dataChange:Boolean = false;        // buffer的数据是否改变    
            private var streamComplete:Boolean = false;    // 文件是否加载完成
     
            
    private var context:LoaderContext;            // 
     
            
    private var buffer:ByteArray;                // 数据缓存
            private var stream:URLStream;                // 流
     
            
    /**
             * 关闭流,并清理所有侦听器
             
    */
            override 
    public function close():void 
            {
                
    // 清除流相关
                if (stream)
                {
                    
    if (stream.connected) stream.close();
                    streamRemoveEvent(stream);
                }
                
    // 清除conentLoaderInfo相关的事件
                if (contentLoaderInfo.hasEventListener(Event.COMPLETE))
                {
                    loaderInfoRemoveEvent(
    super.contentLoaderInfo);
                }
                
    // 清除显示数据事件
                if (hasEventListener(Event.ENTER_FRAME))
                {
                    removeEventListener(Event.ENTER_FRAME, showData);
                }
                buffer 
    = null;
            }
            
    /**
             * 加载字节数据,不会在内部触发contentLoaderInfo相关事件
             * 
    @param    bytes
             * 
    @param    context
             
    */
            override 
    public function loadBytes(bytes:ByteArray, context:LoaderContext = null):void
            {
                close();
                
    super.unload();
                
    super.loadBytes(bytes, context);
            }
     
            
    /**
             * 加载一个url文件,并渐进显示(如果是渐进格式)
             * 
    @param    request
             * 
    @param    context
             
    */
            override 
    public function load(request:URLRequest, context:LoaderContext = null):void 
            {
                streamComplete 
    = false;
                
    if (!stream) stream = new URLStream();
                
    if (stream.connected) stream.close();
                
    this.context = context;
                dataChange 
    = false;
     
                buffer 
    = new ByteArray();
                
    super.unload();
                addEventListener(Event.ENTER_FRAME, showData);
                loaderInfoAddEvent(
    super.contentLoaderInfo);
                streamAddEvent(stream);
                stream.load(request);
            }
     
            
    // 将缓存中的数据显示为图像
            private function showData(e:Event = null):void 
            {
                
    if (!dataChange || !stream.connected) return;
     
                dataChange 
    = false;
                
    if (stream.bytesAvailable > 0)
                {
                    stream.readBytes(buffer, buffer.length, stream.bytesAvailable);
                }
                
    if (buffer.length > 0)
                {
                    
    super.unload();
                    
    super.loadBytes(buffer, context);
                }
     
                
    // 加载完成
                if (streamComplete)
                {
                    close();
                    streamComplete  
    = false;
                }
            }
            
    // 修正contentLoaderInfo的ProgressEvent.PROGRESS事件的进度值
            private function loaderProgressHandler(e:ProgressEvent):void 
            {
                e.bytesLoaded 
    = bytesLoaded;
                e.bytesTotal 
    = bytesToal;
            }
     
            
    // 显示完成
            private function loaderCompleteHandler(e:Event):void 
            {
                
    if (streamComplete)
                {
                    streamComplete 
    = false;
                    loaderInfoRemoveEvent(
    super.contentLoaderInfo);
                }
    else
                {
                    e.stopImmediatePropagation();
                }
            }
     
            
    // 数据加载完成
            private function streamCompleteHandler(e:Event):void 
            {
                streamRemoveEvent(stream);
                
    // 这里不删除EnterFrame事件,最后一段总是不会显示,
                
    // 并且complete事件里showData也不行,
                
    // 所以最后延时显示一次,
                streamComplete = true;
                dataChange 
    = true;
            }
            
    // 数据加载中,保存数据加载的值
            private function streamProgressHandler(e:ProgressEvent):void 
            {
                bytesLoaded 
    = e.bytesLoaded;
                bytesToal 
    = e.bytesTotal;
                dataChange 
    = true;
            }
            
    // 数据流错误, 但是也会加载400K左右的数据,
            
    // 然后由contentLoaderInfo抛出IOError或者IOErrorEvent
            
    // 但不会是流错误,而是未知文件类型
            private function streamErrorHandler(e:IOError):void 
            {
                close();
            }
     
            
    private function streamAddEvent(stream:URLStream):void
            {
                stream.addEventListener(Event.COMPLETE, streamCompleteHandler);
                stream.addEventListener(ProgressEvent.PROGRESS, streamProgressHandler);
                stream.addEventListener(IOErrorEvent.IO_ERROR, streamErrorHandler);
            }
     
            
    private function streamRemoveEvent(stream:URLStream):void
            {
                stream.removeEventListener(Event.COMPLETE, streamCompleteHandler);
                stream.removeEventListener(ProgressEvent.PROGRESS, streamProgressHandler);
                stream.removeEventListener(IOErrorEvent.IO_ERROR, streamErrorHandler);
            }
     
            
    private function loaderInfoAddEvent(loaderInfo:LoaderInfo):void
            {
                loaderInfo.addEventListener(Event.COMPLETE, loaderCompleteHandler, 
    falseint.MAX_VALUE);
                loaderInfo.addEventListener(ProgressEvent.PROGRESS, loaderProgressHandler, 
    falseint.MAX_VALUE);
            }
     
            
    private function loaderInfoRemoveEvent(loaderInfo:LoaderInfo):void
            {
                loaderInfo.removeEventListener(Event.COMPLETE, loaderCompleteHandler);
                loaderInfo.removeEventListener(ProgressEvent.PROGRESS, loaderProgressHandler);
            }
        }
    }
  • 相关阅读:
    蚂蚁金服SOFAMesh在多语言上的实践
    2018第48周日
    git只拉取github部分代码的方法
    深入理解brew link命令
    openssl/ssl.h file not found
    react热加载失败
    pycharm批量清楚pyc、$py.class文件
    Hash history cannot PUSH the same path; a new entry will not be added to the history stack
    JavaScript indexOf() 方法,获取元素的位置;Object.keys()获取对象的所有key的数组
    JavaScript删除数组里的某个元素
  • 原文地址:https://www.cnblogs.com/sevenyuan/p/1748976.html
Copyright © 2020-2023  润新知