如何在基於Flex的AIR應用程序中從互聯網上下載文件。使用Adobe AIR下載文件
我試過使用url設置爲地址的文件,但是當我試圖保存它時,我得到了一個不存在的文件錯誤。谷歌真的很難在這個問題上尋求幫助。
如何在基於Flex的AIR應用程序中從互聯網上下載文件。使用Adobe AIR下載文件
我試過使用url設置爲地址的文件,但是當我試圖保存它時,我得到了一個不存在的文件錯誤。谷歌真的很難在這個問題上尋求幫助。
你想從2個api組合中選擇來完成這個任務。
版1是URLLoader和的FileStream
使用類的結合,你會通過URLLoader對象加載從服務器的文件中的空氣。這會將文件下載到內存中,然後在下載完成時通知您。確保使用URLLoaderDataFormat.BINARY的dataFormat啓動下載。然後,您將啓動Filestream對象,並使用writeBytes()將其寫入磁盤。
版本2 URLStream在和的FileStream
URLStream在非常類似的URLLoader,但不是等待文件使用結果之前完全下載,數據在下載時提供給您。這種方法適用於大文件,因爲您不必等待完整下載開始將其保存到磁盤,並且您還可以節省內存,因爲一旦播放器將其釋放給您,它可以釋放與該數據相關的內存。 YOu會以完全相同的方式使用文件流,您只需在文件流入時對文件的每個塊執行writeBytes()。
查看flash.net.URLRequest
類,它可以幫助您下載文件。
要在seanalltogether的第二個想法基礎上構建,下面是一個函數,從互聯網文件,並將其保存到磁盤(在指定的文件名在桌面上):
downloadFile: function (url, fileName) {
var urlStream = new air.URLStream();
var request = new air.URLRequest(url);
var fileStream = new air.FileStream();
// write 50k from the urlstream to the filestream, unless
// the writeAll flag is true, when you write everything in the buffer
function writeFile(writeAll) {
if (urlStream.bytesAvailable > 51200 || writeAll) {
alert("got some");
var dataBuffer = new air.ByteArray();
urlStream.readBytes(dataBuffer, 0, urlStream.bytesAvailable);
fileStream.writeBytes(dataBuffer, 0, dataBuffer.length);
}
// do clean up:
if (writeAll) {
alert("done");
fileStream.close();
urlStream.close();
// set up the next download
setTimeout(this.downloadNextFile.bind(this), 0);
}
}
urlStream.addEventListener(air.Event.COMPLETE, writeFile.bind(this, true));
urlStream.addEventListener(air.ProgressEvent.PROGRESS, writeFile.bind(this, false));
var file = air.File.desktopDirectory.resolvePath(fileName);
fileStream.openAsync(file, air.FileMode.WRITE);
urlStream.load(request);
}
注:該解決方案使用原型的AIRAliases.js和。
我用seanalltogether的答案,並寫了這個類來處理文件下載。
這很簡單。創建一個var downloader = new FileDownloader("url", "Local/Path");
並致電downloader.load()
開始下載。
它還支持設置完成時調用的函數以及下載時的點。傳遞onProgress函數已經下載的字節數。 (我無法弄清楚如何讓一小部分,因爲我無法弄清楚如何查詢文件的大小,它被下載之前)
package com.alex{
import flash.filesystem.File;
import flash.filesystem.FileMode;
import flash.filesystem.FileStream;
import flash.net.URLRequest;
import flash.net.URLStream;
import flash.utils.ByteArray;
public class FileDownloader
{
// Class to download files from the internet
// Function called every time data arrives
// called with an argument of how much has been downloaded
public var onProgress :Function = function(t:uint):void{};
public var onComplete :Function = function():void{};
public var remotePath :String = "";
public var localFile :File = null;
private var stream :URLStream;
private var fileAccess :FileStream;
public function FileDownloader(remotePath :String = "" , localFile :File = null) {
this.remotePath = remotePath;
this.localFile = localFile;
}
public function load() :void {
if(!stream || !stream.connected) {
stream = new URLStream();
fileAccess = new FileStream();
var requester :URLRequest = new URLRequest(remotePath);
var currentPosition :uint = 0;
var downloadCompleteFlag :Boolean = false;
// Function to call oncomplete, once the download finishes and
// all data has been written to disc
fileAccess.addEventListener("outputProgress", function (result) :void {
if(result.bytesPending == 0 && downloadCompleteFlag) {
stream.close();
fileAccess.close();
onComplete();
}
});
fileAccess.openAsync(localFile, FileMode.WRITE);
stream.addEventListener("progress" , function() :void {
var bytes :ByteArray = new ByteArray();
var thisStart :uint = currentPosition;
currentPosition += stream.bytesAvailable;
// ^^ Makes sure that asyncronicity does not break anything
stream.readBytes(bytes, thisStart);
fileAccess.writeBytes(bytes, thisStart);
onProgress(currentPosition);
});
stream.addEventListener("complete", function() :void {
downloadCompleteFlag = true;
});
stream.load(requester);
} else {
// Do something unspeakable
}
}
}}
也請您查看URLLoader類用於下載文件。一個很好的例子是:http://www.adobe.com/devnet/air/flex/articles/exploring_file_capabilities.html
對於我來說,這相當於花費了很長時間的URLStream類以及大量的CPU來下載文件。
我想補充一下:1.如果我們用URLStream加載一些文件,並且不用FileStream把它寫入文件 - 應用程序的大小增長到我們加載的文件的大小。但是,如果我們從流中讀取字節並將它們寫入文件 - 一切正常。應用程序不增長。要獲取應用程序大小,請使用System.privateMemory。 – yozhik 2011-11-03 15:28:13
@Seanalltogether,你能舉一個例子但不使用包嗎? – 2012-08-20 02:09:59