0

我的 android 应用程序首先加载所有必要的数据,同时显示一个加载对话框:

// Load data in background, while updating the loading dialog.
(new AsyncTask<Void, String, Void>() {
    @Override
    protected Void doInBackground(Void... params) {
        publishProgress(getString(R.string.loading_a));
        if!(loadA())
            showErrorDialogAndQuit();
        publishProgress(getString(R.string.loading_b));
        if(!loadB())
            showErrorDialogAndQuit();
        publishProgress(getString(R.string.loading_c));
        if(!loadC())
            showErrorDialogAndQuit();
        return null;
    }

    protected void onProgressUpdate(String... progress) {
        dialog.setMessage(progress[0]);
    }

    protected void onPostExecute(Void result) {
        // Update the UI.
        updateUI();
        dialog.dismiss();
    }
}).execute();

方法loadA()loadB()loadC()可能会失败,返回 false。此时,我希望显示一条错误消息,并在方法中退出应用程序showErrorDialogAndQuit()

我尝试按如下方式创建它,但在应用程序退出后它似乎总是抛出错误,这与加载对话框不再有窗口有关。

public void showErrorDialogAndQuit() {
    runOnUiThread(new Runnable() {
        @Override
        public void run() {
            AlertDialog aDialog = new AlertDialog.Builder(MyActivity.this).setMessage("Fatal error.").setTitle("Error")
                    .setNeutralButton("Close", new AlertDialog.OnClickListener() {
                        public void onClick(final DialogInterface dialog, final int which) {
                            // Exit the application.
                            finish();
                        }
                    }).create();
            aDialog.setOnKeyListener(new OnKeyListener() {
                @Override
                public boolean onKey(DialogInterface dialog, int keyCode, KeyEvent event) {
                    // Disables the back button.
                    return true;
                }

            });
            aDialog.show();
        }
    });
}

实现这一目标的最佳方法是什么?

4

2 回答 2

0

如果您只能在成功 loadA 后执行 loadB,我建议您更改代码的逻辑。您可以使用具有 3 个状态的最终状态机方法,其中在 stateA 完成后触发 stateB。

使用处理程序也可以很好地更新 UI。逻辑可能如下所示:

  1. 在主体开始线程加载A
  2. 在 threadA 中,如果成功,则将 msg A_success 发送到主体,否则将 msg A_failed 发送到主体 threadA 到此结束
  3. 主体通过处理程序接收 msg,如果收到 A_success -> start Thread loadingB else end (或任何你想要的),则继续

启动线程 A 如下所示:

  new Thread(new Runnable() {
    public void run() {
        loadingA();
    }
    }).start();

在 loadingA 中,您将 msg 发送回主体,如下所示:

 public void loadingA() {
    ...do your loading...

    then to inform the main body...

    Message msg = mHandlerToReceiveTheResultFromLoadingThread
            .obtainMessage(MESSAGE_UPDATE_RESULT_OF_LOADING_A);
        Bundle bundle = new Bundle();
        bundle.putBoolean(RESULT_OK_INFO, true or false);
        msg.setData(bundle);
        mHandlerToReceiveTheResultFromLoadingThread
            .sendMessage(msg);

        }

在主体中mHandlerToReceiveTheResultFromLoadingThread看起来像:

public final Handler mHandlerToReceiveTheResultFromLoadingThread = new Handler() {
    @Override
    public void handleMessage(Message msg) {

        if (DEBUG)
        Log.i(this.getClass().getSimpleName(),
            "-> "
                + Thread.currentThread().getStackTrace()[2]
                    .getMethodName() );
        switch (msg.what) {
        case MESSAGE_UPDATE_RESULT_OF_LOADING_A: {
        boolean result_ok = msg.getData().getBoolean(RESULT_OK_INFO);

        if (result_ok)
            ...continue with loadingB;
            else
               show your message that it failed and exit;
        }
        break;

        }

    }

希望这可以帮助...

编辑:在活动的逻辑结束时调用完成:

        this.myBtn.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {   
                String msg = "Hello, I have finished and started another activity";
                doOtherActivit(msg); 
                finish();
            }
        });
    }

public void doOtherActivity(String msg) {
        Intent i;
        i = new Intent(this, OtherActivity.class);
        i.putExtra("Task", msg);        
        startActivity(i);
    }
于 2012-04-17T21:27:56.337 回答
0

原来我需要做的就是在finish()被调用之前让进度对话框自然关闭:

if(!loadA()) {
    showErrorDialogAndQuit();
    return null;
}

这通过创建错误对话框来工作,该对话框在另一个线程中运行,然后返回 null 以AsyncTask使其运行onPostExecute()并关闭进度对话框。然后,当按下并finish()调用错误对话框中的关闭按钮时,一切都可以正常关闭。

这种方法的唯一缺点是,如果在onPostExecute(). 在这种情况下,您可以修改参数类型并对其进行测试以查看要执行的操作。

于 2012-04-17T23:55:30.813 回答