0

phonegap アプリケーション (Android) があります。プラグインDownloaderを使用してxml ファイルをダウンロードします。ファイルをダウンロードすると、ダウンロードが完了するまでアプリケーションが「一時停止」します。何もクリックできない、ローダーが機能しないなど。

以前は正常に動作していましたが、アプリを cordova 1.8.0 から新しいバージョン (2.7.0) にアップグレードする必要がありました。

また、新しいコルドバで動作するようにプラグイン自体も変更しました。

何が原因なのかわかりません。何か案は?。

----------編集: 追加されたコード---------

これが私のダウンローダープラグインクラスです

public class Downloader extends CordovaPlugin {

public boolean execute(String action, JSONArray args, CallbackContext callbackContext) {


    if (!action.equals("downloadFile")){
        callbackContext.sendPluginResult(new PluginResult(PluginResult.Status.INVALID_ACTION));
        return true;
    }
    try {

        String fileUrl = args.getString(0);
        JSONObject params = args.getJSONObject(1);

        String fileName = params.has("fileName") ? 
                params.getString("fileName"):
                fileUrl.substring(fileUrl.lastIndexOf("/")+1);

        String dirName = params.has("dirName") ?
                params.getString("dirName"):
                    Environment.getExternalStorageDirectory().toString();

        Boolean overwrite = params.has("overwrite") ? params.getBoolean("overwrite") : false;

        callbackContext.sendPluginResult(this.downloadUrl(fileUrl, dirName, fileName, overwrite, callbackContext));
        return true;

    } catch (JSONException e) {

        e.printStackTrace();
        callbackContext.sendPluginResult(new PluginResult(PluginResult.Status.JSON_EXCEPTION, e.getMessage()));
        return false;

    } catch (InterruptedException e) {
        e.printStackTrace();
        callbackContext.sendPluginResult(new PluginResult(PluginResult.Status.ERROR, e.getMessage()));
        return false;
    }

}
private PluginResult downloadUrl(String fileUrl, String dirName, String fileName, Boolean overwrite, CallbackContext callbackContext) throws InterruptedException, JSONException {


    try {

        Log.d("PhoneGapLog", "Downloading "+fileUrl + " into " + dirName + "/" + fileName);

        File dir = new File(dirName);
        if (!dir.exists()) {
            Log.d("PhoneGapLog", "directory " + dirName + " created");
            dir.mkdirs();
        }

        File file = new File(dirName, fileName);

        if (!overwrite && file.exists()) {
            Log.d("DownloaderPlugin", "File already exist");

            JSONObject obj = new JSONObject();
            obj.put("status", 1);
            obj.put("total", 0);
            obj.put("file", fileName);
            obj.put("dir", dirName);
            obj.put("progress", 100);

            return new PluginResult(PluginResult.Status.OK, obj);
        }

        URL url = new URL(fileUrl);
        HttpURLConnection ucon = (HttpURLConnection) url.openConnection();
        ucon.setRequestMethod("GET");
        ucon.connect();

        Log.d("PhoneGapLog", "Download start");

        InputStream is = ucon.getInputStream();
        byte[] buffer = new byte[1024];
        int readed = 0, 
            progress = 0,
           // totalReaded = 0,
            fileSize = ucon.getContentLength();

        FileOutputStream fos = new FileOutputStream(file);

        while ((readed = is.read(buffer)) > 0) {

            fos.write(buffer, 0, readed);
            //totalReaded += readed;

            //int newProgress = (int) (totalReaded*100/fileSize);               
            //if (newProgress != progress)
            // progress = informProgress(fileSize, newProgress, dirName, fileName, callbackId);

        }

        fos.close();

        Log.d("PhoneGapLog", "Download finished");

        JSONObject obj = new JSONObject();
        obj.put("status", 1);
        obj.put("total", fileSize);
        obj.put("file", fileName);
        obj.put("dir", dirName);
        obj.put("progress", progress);

        return new PluginResult(PluginResult.Status.OK, obj);


    }
    catch (FileNotFoundException e) {
        Log.d("PhoneGapLog", "File Not Found: " + e);
        return new PluginResult(PluginResult.Status.ERROR, 404);
    }
    catch (IOException e) {
        Log.d("PhoneGapLog", "Error: " + e);
        return new PluginResult(PluginResult.Status.ERROR, e.getMessage());
    }
}

}

これが私のダウンローダープラグインjavascriptです

function Downloader() {}

Downloader.prototype.downloadFile = function(fileUrl, params, win, fail) {
//Make params hash optional.
if (!fail) win = params;
return cordova.exec(win, fail, "Downloader", "downloadFile", [fileUrl, params]);
};

 if(!window.plugins) {
    window.plugins = {};
 }
 if (!window.plugins.downloader) {
   window.plugins.downloader = new Downloader();
 }

そして、私がそれを呼び出すとき

$.mobile.showPageLoadingMsg();
window.plugins.downloader.downloadFile("URL",
                        {overwrite: true,
                        dirName: dir, fileName: "File.xml"}, 
                      function() {
                            alert("finished");      
                    }, function(error) {
                        alert("fail");
                );

showPageLoadingMsg によって表示されるローダーは、ダウンロードが完了するまでフリーズするか、ダウンロードが完了すると表示されます。

4

1 に答える 1

1

PhoneGap プラグイン メソッドは、アプリケーション全体の UI スレッドで呼び出されます。UI スレッドで長時間のアクティビティを実行しないでください。そうしないと、ブロックされ、UI の更新が行われず、アプリ全体が無責任になります。ドキュメントを読んでください - UI スレッドを PhoneGap に解放して、別のスレッドで長いタスクを実行する必要があります。2 つのステップで作成されます - 新しいスレッドを開始して戻る

PluginResult r = new PluginResult(PluginResult.Status.NO_RESULT);
r.setKeepCallback(true);
callContext.sendPluginResult(r);

非同期プラグイン呼び出しになるフラグを付けます。スレッドが終了したら、呼び出しを終了します

callContext.success(json);

編集:

Cordova プラグイン メソッドが UI スレッドで呼び出され、UI スレッドと同じではない WebCore スレッドで呼び出されることは間違いでした (プラグインで UI を表示する必要があるかどうかを覚えておくことが重要です)。とにかく、WebCore スレッドもブロックしないでください。ドキュメントを参照してください。

ねじ切り

WebView の JavaScript はUI スレッドで実行されません。WebCore スレッドで実行されます。execute メソッドも WebCore スレッドで実行されます。

http://docs.phonegap.com/en/2.2.0/guide_plugin-development_android_index.md.html

于 2013-09-11T19:50:52.757 に答える