确定解压缩数据库zip的时间

时间:2010-04-16 09:47:34

标签: sqlite flex3 air unzip

我在AIR应用程序的初始启动时(第一次安装后)获取了一个db zip,然后我通过FZip解压缩。 在这个操作之后,我立即需要从生成的sqlite db加载数据,因为我似乎无法确定zip完全解压缩和/或sqlite是否已经创建。

有什么建议吗? THX!

  • 为了清楚起见:我在结果操作结束后在Cairngorm内派出了一个事件,但这似乎不够。

1 个答案:

答案 0 :(得分:1)

嗯,你有问题的答案。

我快速浏览了FZip docs并发现有一个事件在发送时被调度 zip文件已加载。

只需扫描代码,在FZipLibrary.as中就有 processNext()方法 其中包含一个while循环来遍历归档中的文件。你可以在FZipEvent中添加一个FILE_PARSED常量,并在while循环结束后从那里调度这样的事件。

我目前无法尝试测试,但这就是我的意思:

/*
 * Copyright (C) 2006 Claus Wahlers and Max Herkender
 *
 * This software is provided 'as-is', without any express or implied
 * warranty.  In no event will the authors be held liable for any damages
 * arising from the use of this software.
 *
 * Permission is granted to anyone to use this software for any purpose,
 * including commercial applications, and to alter it and redistribute it
 * freely, subject to the following restrictions:
 *
 * 1. The origin of this software must not be misrepresented; you must not
 *    claim that you wrote the original software. If you use this software
 *    in a product, an acknowledgment in the product documentation would be
 *    appreciated but is not required.
 * 2. Altered source versions must be plainly marked as such, and must not be
 *    misrepresented as being the original software.
 * 3. This notice may not be removed or altered from any source distribution.
 */

package deng.fzip
{
    import deng.fzip.FZipFile;
    import flash.events.Event;

    /**
     * FZip dispatches FZipEvent objects when a file contained in the
     * ZIP archive has finished loading and can be accessed. There is 
     * only one type of FZipEvent: FZipErrorEvent.FILE_LOADED.
     */     
    public class FZipEvent extends Event
    {
        /**
        * The file that has finished loading.
        */      
        public var file:FZipFile;

        /**
        * Defines the value of the type property of a FZipEvent object.
        */      
        public static const FILE_LOADED:String = "fileLoaded";

        /**
        * Zip contents were parsed
        */      
        public static const FILE_PARSED:String = "fileParsed";

        /**
         * Constructor
         * 
         * @param type The type of the event. Event listeners can 
         * access this information through the inherited type property. 
         * There is only one type of FZipEvent: 
         * FZipEvent.PARSE_ERROR.
         * 
         * @param file The file that has finished loading.
         * 
         * @param bubbles Determines whether the Event object participates 
         * in the bubbling stage of the event flow. Event listeners can 
         * access this information through the inherited bubbles property.
         * 
         * @param cancelable Determines whether the Event object can be 
         * canceled. Event listeners can access this information through 
         * the inherited cancelable property.
         */     
        public function FZipEvent(type:String, file:FZipFile = null, bubbles:Boolean = false, cancelable:Boolean = false) {
            this.file = file;
            super(type, bubbles, cancelable);
        }

        /**
         * Creates a copy of the FZipEvent object and sets the value 
         * of each property to match that of the original.
         * 
         * @return A new FZipEvent object with property values that 
         * match those of the original.
         */     
        override public function clone():Event {
            return new FZipEvent(type, file, bubbles, cancelable);
        }
    }
}

这只是为事件添加常量。

/*
 * Copyright (C) 2006 Claus Wahlers and Max Herkender
 *
 * This software is provided 'as-is', without any express or implied
 * warranty.  In no event will the authors be held liable for any damages
 * arising from the use of this software.
 *
 * Permission is granted to anyone to use this software for any purpose,
 * including commercial applications, and to alter it and redistribute it
 * freely, subject to the following restrictions:
 *
 * 1. The origin of this software must not be misrepresented; you must not
 *    claim that you wrote the original software. If you use this software
 *    in a product, an acknowledgment in the product documentation would be
 *    appreciated but is not required.
 * 2. Altered source versions must be plainly marked as such, and must not be
 *    misrepresented as being the original software.
 * 3. This notice may not be removed or altered from any source distribution.
 */

package deng.fzip {
    import flash.events.*;
    import flash.display.Bitmap;
    import flash.display.BitmapData;
    import flash.display.DisplayObject;
    import flash.display.Loader;
    import flash.utils.ByteArray;

    /**
     * Dispatched when all pending files have been processed. 
     *
     * @eventType flash.events.Event.COMPLETE 
     */
    [Event(name="complete", type="flash.events.Event")]

    /**
     * <p>FZipLibrary works with a FZip instance to load files as
     * usable instances, like a DisplayObject or BitmapData. Each file
     * from a loaded zip is processed based on their file extentions.
     * More than one FZip instance can be supplied, and if it is
     * currently loading files, then FZipLibrary will wait for incoming
     * files before it completes.</p>
     * 
     * <p>Flash's built-in Loader class is used to convert formats, so the
     * only formats currently supported are ones that Loader supports.
     * As of this writing they are SWF, JPEG, GIF, and PNG.</p>
     * 
     * <p>The following example loads an external zip file, outputs the
     * width and height of an image and then loads a sound from a SWF file.</p>
     * 
     * <pre>
     * package {
     *  import flash.events.*;
     *  import flash.display.BitmapData;
     *  import deng.fzip.FZip;
     *  import deng.fzip.FZipLibrary;
     *  
     *  public class Example {
     *      private var lib:FZipLibrary;
     *      
     *      public function Example(url:String) {
     *          lib = new FZipLibrary();
     *          lib.formatAsBitmapData(".gif");
     *          lib.formatAsBitmapData(".jpg");
     *          lib.formatAsBitmapData(".png");
     *          lib.formatAsDisplayObject(".swf");
     *          lib.addEventListener(Event.COMPLETE,onLoad);
     *          
     *          var zip:FZip = new FZip();
     *          zip.load(url);
     *          lib.addZip(zip);
     *      }
     *      private function onLoad(evt:Event) {
     *          var image:BitmapData = lib.getBitmapData("test.png");
     *          trace("Size: " + image.width + "x" + image.height);
     *          
     *          var importedSound:Class = lib.getDefinition("data.swf", "SoundClass") as Class;
     *          var snd:Sound = new importedSound() as Sound;
     *      }
     *  }
     * }</pre>
     * 
     * @see http://livedocs.macromedia.com/flex/201/langref/flash/display/Loader.html
     */
    public class FZipLibrary extends EventDispatcher {
        static private const FORMAT_BITMAPDATA:uint = (1 << 0);
        static private const FORMAT_DISPLAYOBJECT:uint = (1 << 1);

        private var pendingFiles:Array = [];
        private var pendingZips:Array = [];
        private var currentState:uint = 0;
        private var currentFilename:String;
        private var currentZip:FZip;
        private var currentLoader:Loader;

        private var bitmapDataFormat:RegExp = /[]/;
        private var displayObjectFormat:RegExp = /[]/;
        private var bitmapDataList:Object = {};
        private var displayObjectList:Object = {};

        /**
         * Constructor
         */
        public function FZipLibrary() {
        }
        /**
         * Use this method to add an FZip instance to the processing queue.
         * If the FZip instance specified is not active (currently receiving files)
         * when it is processed than only the files already loaded will be processed.
         * 
         * @param zip An FZip instance to process
         */
        public function addZip(zip:FZip):void {
            pendingZips.unshift(zip);
            processNext();
        }
        /**
         * Used to indicate a file extension that triggers formatting to BitmapData.
         * 
         * @param ext A file extension (".jpg", ".png", etc)
         */
        public function formatAsBitmapData(ext:String):void {
            bitmapDataFormat = addExtension(bitmapDataFormat,ext);
        }
        /**
         * Used to indicate a file extension that triggers formatting to DisplayObject.
         * 
         * @param ext A file extension (".swf", ".png", etc)
         */
        public function formatAsDisplayObject(ext:String):void {
            displayObjectFormat = addExtension(displayObjectFormat,ext);
        }
        /**
         * @private
         */
        private function addExtension(original:RegExp,ext:String):RegExp {
            return new RegExp(ext.replace(/[^A-Za-z0-9]/,"\\$&")+"$|"+original.source);
        }

        /**
         * Request a file that has been formatted as BitmapData.
         * A ReferenceError is thrown if the file does not exist as a
         * BitmapData.
         * 
         * @param filename The filename of the BitmapData instance.
         */
        public function getBitmapData(filename:String):BitmapData {
            if (!bitmapDataList[filename] is BitmapData) {
                throw new Error("File \""+filename+"\" was not found as a BitmapData");
            }
            return bitmapDataList[filename] as BitmapData;
        }
        /**
         * Request a file that has been formatted as a DisplayObject.
         * A ReferenceError is thrown if the file does not exist as a
         * DisplayObject.
         * 
         * @param filename The filename of the DisplayObject instance.
         */
        public function getDisplayObject(filename:String):DisplayObject {
            if (!displayObjectList.hasOwnProperty(filename)) {
                throw new ReferenceError("File \""+filename+"\" was not found as a DisplayObject");
            }
            return displayObjectList[filename] as DisplayObject;
        }
        /**
         * Retrieve a definition (like a class) from a SWF file that has
         * been formatted as a DisplayObject.
         * A ReferenceError is thrown if the file does not exist as a
         * DisplayObject, or the definition does not exist.
         * 
         * @param filename The filename of the DisplayObject instance.
         */
        public function getDefinition(filename:String,definition:String):Object {
            if (!displayObjectList.hasOwnProperty(filename)) {
                throw new ReferenceError("File \""+filename+"\" was not found as a DisplayObject, ");
            }
            var disp:DisplayObject = displayObjectList[filename] as DisplayObject;
            try {
                return disp.loaderInfo.applicationDomain.getDefinition(definition);
            } catch (e:ReferenceError) {
                throw new ReferenceError("Definition \""+definition+"\" in file \""+filename+"\" could not be retrieved: "+e.message);
            }
            return null;
        }

        /**
         * @private
         */
        private function processNext(evt:Event = null):void {
            while (currentState === 0) {
                if (pendingFiles.length > 0) {
                    var nextFile:FZipFile = pendingFiles.pop();
                    if (bitmapDataFormat.test(nextFile.filename)) {
                        currentState |= FORMAT_BITMAPDATA;
                    }
                    if (displayObjectFormat.test(nextFile.filename)) {
                        currentState |= FORMAT_DISPLAYOBJECT;
                    }
                    if ((currentState & (FORMAT_BITMAPDATA | FORMAT_DISPLAYOBJECT)) !== 0) {
                        currentFilename = nextFile.filename;
                        currentLoader = new Loader();
                        currentLoader.contentLoaderInfo.addEventListener(Event.COMPLETE, loaderCompleteHandler);
                        currentLoader.contentLoaderInfo.addEventListener(IOErrorEvent.IO_ERROR, loaderCompleteHandler);
                        var content:ByteArray = nextFile.content;
                        content.position = 0;
                        currentLoader.loadBytes(content);
                        break;
                    }
                } else if (currentZip == null) {
                    if (pendingZips.length > 0) {
                        currentZip = pendingZips.pop();
                        var i:uint = currentZip.getFileCount();
                        while (i > 0) {
                            pendingFiles.push(currentZip.getFileAt(--i));
                        }
                        if (currentZip.active) {
                            currentZip.addEventListener(Event.COMPLETE, zipCompleteHandler);
                            currentZip.addEventListener(FZipEvent.FILE_LOADED, fileCompleteHandler);
                            currentZip.addEventListener(FZipErrorEvent.PARSE_ERROR, zipCompleteHandler);
                            break;
                        } else {
                            currentZip = null;
                        }
                    } else {
                        dispatchEvent(new Event(Event.COMPLETE));
                        break;
                    }
                } else {
                    break;
                }
            }
            dispatchEvent(new FZipEvent(FZipEvent.FILE_PARSED));
        }

        /**
         * @private
         */
        private function loaderCompleteHandler(evt:Event):void {
            if ((currentState & FORMAT_BITMAPDATA) === FORMAT_BITMAPDATA) {
                if (currentLoader.content is Bitmap && (currentLoader.content as Bitmap).bitmapData is BitmapData) {
                    var bitmapData:BitmapData = (currentLoader.content as Bitmap).bitmapData
                    bitmapDataList[currentFilename] = bitmapData.clone();
                    //trace(currentFilename+" -> BitmapData ("+bitmapData.width+"x"+bitmapData.height+")");
                } else if (currentLoader.content is DisplayObject) {
                    var width:uint = uint(currentLoader.content.width);
                    var height:uint = uint(currentLoader.content.height);
                    if (width && height) {
                        var bitmapData2:BitmapData = new BitmapData(width,height,true,0x00000000);
                        bitmapData2.draw(currentLoader);
                        bitmapDataList[currentFilename] = bitmapData2;
                        //trace(currentFilename+" -> BitmapData ("+bitmapData2.width+"x"+bitmapData2.height+")");
                    } else {
                        trace("File \""+currentFilename+"\" could not be converted to BitmapData");
                    }
                } else {
                    trace("File \""+currentFilename+"\" could not be converted to BitmapData");
                }
            }
            if ((currentState & FORMAT_DISPLAYOBJECT) === FORMAT_DISPLAYOBJECT) {
                if (currentLoader.content is DisplayObject) {
                    //trace(currentFilename+" -> DisplayObject");
                    displayObjectList[currentFilename] = currentLoader.content;
                } else {
                    currentLoader.unload();
                    trace("File \""+currentFilename+"\" could not be loaded as a DisplayObject");
                }
            } else {
                currentLoader.unload();
            }
            currentLoader = null;
            currentFilename = "";
            currentState &= ~(FORMAT_BITMAPDATA | FORMAT_DISPLAYOBJECT);
            processNext();
        }
        /**
         * @private
         */
        private function fileCompleteHandler(evt:FZipEvent):void {
            pendingFiles.unshift(evt.file);
            processNext();
        }
        /**
         * @private
         */
        private function zipCompleteHandler(evt:Event):void {
            currentZip.removeEventListener(Event.COMPLETE, zipCompleteHandler);
            currentZip.removeEventListener(FZipEvent.FILE_LOADED, fileCompleteHandler);
            currentZip.removeEventListener(FZipErrorEvent.PARSE_ERROR, zipCompleteHandler);
            currentZip = null;
            processNext();
        }
    }
}

这将是为调度FILE_PARSED事件而添加的另一行代码。

脏版本将是一个 try / catch 块并尝试重复访问该文件(在计时器或enter_frame中)。当文件最终准备就绪时,停止此检查循环并继续。

HTH