【发布时间】:2018-08-16 17:28:42
【问题描述】:
在我的应用程序中,我在单击按钮以选择文档时使用ACTION_OPEN_DOCUMENT 启动意图。
private static final int READ_REQUEST_CODE = 42;
public void performFileSearch() {
// ACTION_OPEN_DOCUMENT is the intent to choose a file via the system's file
// browser.
Intent intent = new Intent(Intent.ACTION_OPEN_DOCUMENT);
intent.addCategory(Intent.CATEGORY_OPENABLE);
intent.setType("*/*");
String[] mimeTypes = {
"image/*",
"text/plain",
"application/pdf"
};
intent.putExtra(Intent.EXTRA_MIME_TYPES, mimeTypes);
startActivityForResult(intent, READ_REQUEST_CODE);
}
之后,我在onActivityResult 中获取用户选择的文档的Uri,并将其传递给AsyncTask,其中选定的文档被压缩。
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == READ_REQUEST_CODE && resultCode == Activity.RESULT_OK) {
if (data != null) {
dialog = new ProgressDialog(getActivity());
dialog.setMessage(getString(R.string.upload_dialog));
dialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
dialog.setIndeterminate(true);
dialog.setCancelable(false);
dialog.show();
// The document selected by the user won't be returned in the intent.
// Instead, a URI to that document will be contained in the return intent
// provided to this method as a parameter.
// Pull that URI using resultData.getData().
new ZipFile().execute(data.getData());
}
}
}
下面是我的AsyncTask类:
private class ZipFile extends AsyncTask<Uri, Void, String> {
@Override
protected String doInBackground(Uri... uris) {
Uri uri = uris[0];
String fileName = null;
try {
fileName = zm.createPath("user");
zm.zipFromUri(uri, fileName, commonMethods.getFileName(uri));
} catch (NullPointerException | IOException e) {
e.printStackTrace();
}
return fileName;
}
@Override
protected void onPostExecute(String fileName) {
dialog.dismiss();
if (fileName != null) {
renderView(view);
}
}
}
在renderView 函数中,我显示了一个snackbar 并更新了我的片段的UI。
private void renderView(View view) {
CoordinatorLayout fileSnackbarView = view.findViewById(R.id.filesCoordinatorLayout);
//Exception at this line
fileSnackbar = Snackbar.make(fileSnackbarView, String.format(getResources().getString(R.string.snackbarMessage), FILE_COUNT), Snackbar.LENGTH_INDEFINITE)
.setAction(getResources().getString(R.string.snackbarAction), new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(getActivity(), ViewSelectedFilesActivity.class);
Bundle bundle = new Bundle();
ArrayList<String> selectedFileName = new ArrayList<>();
selectedFileName.add(commonMethods.getFromPreferences(Constants.originalFileNameKey, "string"));
bundle.putStringArrayList("fileList", selectedFileName);
intent.putExtras(bundle);
startActivity(intent);
}
});
... code
}
但是,我的应用程序崩溃了,但 Fragment not attached to a context 除外。以下是完整的堆栈跟踪:
03-08 12:09:20.647 11490-11490/com.zeetim.zeeprintmobile.android E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.zeetim.zeeprintmobile.android, PID: 11490
java.lang.IllegalStateException: Fragment HomeFragment{674af0} not attached to a context.
at android.support.v4.app.Fragment.requireContext(Fragment.java:611)
at android.support.v4.app.Fragment.getResources(Fragment.java:675)
at com.zeetim.zeeprintmobile.fragment.HomeFragment.renderView(HomeFragment.java:287)
at com.zeetim.zeeprintmobile.fragment.HomeFragment.access$700(HomeFragment.java:51)
at com.zeetim.zeeprintmobile.fragment.HomeFragment$ZipFile.onPostExecute(HomeFragment.java:595)
at com.zeetim.zeeprintmobile.fragment.HomeFragment$ZipFile.onPostExecute(HomeFragment.java:563)
at android.os.AsyncTask.finish(AsyncTask.java:695)
at android.os.AsyncTask.-wrap1(Unknown Source:0)
at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:712)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loop(Looper.java:164)
at android.app.ActivityThread.main(ActivityThread.java:6494)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:807)
在一些调试中,我发现isAdded()返回false和getActivity(),getContext()是null。
流程看起来非常简单,但它不起作用。那么我在这方面有什么遗漏吗?
如何从onActivityResult 调用的onPostExecute 更新片段的UI?
谢谢。
【问题讨论】:
-
Activity是否有可能被销毁并重新创建?您是否在多个设备中检查过这种行为?如果没有,请尝试检查其他设备。 -
@ADM 在其他设备上也是如此。关于活动,我可以看到
onResume在onActivityResult之后被调用。但我不确定AsyncTask类是否引用了新活动。 -
请显示您的 renderView() 代码。删除所有语句,然后逐个添加,看看哪个语句导致了问题。
-
@greenapps 我已经用 renderView 方法更新了问题
-
是的,我后来看到了。你怎么不说清楚!?
String.format(getResources().getString(R.string.snackbarMessage)。导致问题的语句对于两个这样的参数来说非常复杂。在调用该行之前取出该代码并执行此操作。找出究竟是什么导致了你的问题。看起来是资源问题。
标签: android android-fragments android-asynctask