如何妥善保留通过转动DialogFragment? [英] How to properly retain a DialogFragment through rotation?

查看:123
本文介绍了如何妥善保留通过转动DialogFragment?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有承载DialogFragment一个FragmentActivity。

在DialogFragment进行网络请求并处理Facebook的身份验证,所以我需要在旋转过程中把它保留下来。

我读过所有关于这一问题的其他问题,但他们都没有真正解决了这个问题。

我使用putFragment和getFragment保存片段实例和活动的再创作过程中再次得到它。

不过,我总是因为在onRestoreInstanceState调用getFragment一个空指针异常。我也想保持对话框,在旋转过程中被解雇,但到目前为止,我甚至不能保持它的实例。

任何想法是怎么回事?

下面就是我的code目前是这样的:

 公共类OKLoginActivity扩展FragmentActivity实现OKLoginDialogListener
{

    私人OKLoginFragment一个LoginDialog;
    私有静态最后弦乐TAG_LOGINFRAGMENT =OKLoginFragment;


    @覆盖
    公共无效的onCreate(包savedInstanceState){
        super.onCreate(savedInstanceState);

        FragmentManager FM = getSupportFragmentManager();

        如果(savedInstanceState == NULL)
        {
            一个LoginDialog =新OKLoginFragment();
            loginDialog.show(FM,TAG_LOGINFRAGMENT);
        }
    }


    @覆盖
    公共无效的onSaveInstanceState(包outState)
    {
        。getSupportFragmentManager()putFragment(outState,TAG_LOGINFRAGMENT,一个LoginDialog);
    }

    @覆盖
    公共无效onRestoreInstanceState(束安置)
    {
        FragmentManager FM = getSupportFragmentManager();
        一个LoginDialog =(OKLoginFragment)fm.getFragment(inState,TAG_LOGINFRAGMENT);
    }

}
 

这是异常堆栈跟踪:

  02-01 16:31:13.684:E / AndroidRuntime(9739):致命异常:主要
02-01 16:31:13.684:E / AndroidRuntime(9739):java.lang.RuntimeException的:无法启动的活动ComponentInfo {io.openkit.example.sampleokapp / io.openkit.OKLoginActivity}:显示java.lang.NullPointerException
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2180)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2230)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.ActivityThread.handleRelaunchActivity(ActivityThread.java:3692)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.ActivityThread.access $ 700(ActivityThread.java:141)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.ActivityThread $ H.handleMessage(ActivityThread.java:1240)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.os.Handler.dispatchMessage(Handler.java:99)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.os.Looper.loop(Looper.java:137)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.ActivityThread.main(ActivityThread.java:5039)
02-01 16:31:13.684:E / AndroidRuntime(9739):在java.lang.reflect.Method.invokeNative(本机方法)
02-01 16:31:13.684:E / AndroidRuntime(9739):在java.lang.reflect.Method.invoke(Method.java:511)
02-01 16:31:13.684:E / AndroidRuntime(9739):在com.android.internal.os.ZygoteInit $ MethodAndArgsCaller.run(ZygoteInit.java:793)
02-01 16:31:13.684:E / AndroidRuntime(9739):在com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560)
02-01 16:31:13.684:E / AndroidRuntime(9739):在dalvik.system.NativeStart.main(本机方法)
02-01 16:31:13.684:E / AndroidRuntime(9739):由:显示java.lang.NullPointerException
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.support.v4.app.FragmentManagerImpl.getFragment(FragmentManager.java:528)
02-01 16:31:13.684:E / AndroidRuntime(9739):在io.openkit.OKLoginActivity.onRestoreInstanceState(OKLoginActivity.java:62)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.Activity.performRestoreInstanceState(Activity.java:910)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.Instrumentation.callActivityOnRestoreInstanceState(Instrumentation.java:1131)
02-01 16:31:13.684:E / AndroidRuntime(9739):在android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2158)
 

解决方案

在你的DialogFragment,叫<一href="http://developer.android.com/reference/android/app/Fragment.html#setRetainInstance%28boolean%29">Fragment.setRetainInstance(boolean) true值。你并不需要保存的片段手动,该框架已经采取了这一切的照顾。调用此将$ P $从旋转被破坏pvent你的片段和你的网络请求将不会受到影响。

您可能需要添加这个code,从被解雇的旋转停止你的对话,由于的错误与兼容性库:

  @覆盖
公共无效onDestroyView(){
  如果(getDialog()= NULL和放大器;!&安培; getRetainInstance())
    getDialog()setDismissMessage(空)。
  super.onDestroyView();
}
 

I have a FragmentActivity that hosts a DialogFragment.

The DialogFragment perform network requests and handles Facebook authentication, so I need to retain it during rotation.

I've read all the other questions relating to this issue, but none of them have actually solved the problem.

I'm using putFragment and getFragment to save the Fragment instance and get it again during activity re-creation.

However, I'm always getting a null pointer exception on the call to getFragment in onRestoreInstanceState. I would also like to keep the dialog from being dismissed during rotation, but so far I can't even retain the instance of it.

Any ideas what's going wrong?

Here's what my code currently looks like:

public class OKLoginActivity extends FragmentActivity implements OKLoginDialogListener
{

    private OKLoginFragment loginDialog;
    private static final String TAG_LOGINFRAGMENT = "OKLoginFragment";


    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        FragmentManager fm = getSupportFragmentManager();

        if(savedInstanceState == null)
        {
            loginDialog = new OKLoginFragment(); 
            loginDialog.show(fm, TAG_LOGINFRAGMENT);
        }
    }


    @Override
    public void onSaveInstanceState(Bundle outState)
    {
        getSupportFragmentManager().putFragment(outState,TAG_LOGINFRAGMENT, loginDialog);
    }

    @Override
    public void onRestoreInstanceState(Bundle inState)
    {
        FragmentManager fm = getSupportFragmentManager();
        loginDialog = (OKLoginFragment) fm.getFragment(inState, TAG_LOGINFRAGMENT);
    }

}

This is the exception stack trace:

02-01 16:31:13.684: E/AndroidRuntime(9739): FATAL EXCEPTION: main
02-01 16:31:13.684: E/AndroidRuntime(9739): java.lang.RuntimeException: Unable to start activity ComponentInfo{io.openkit.example.sampleokapp/io.openkit.OKLoginActivity}: java.lang.NullPointerException
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2180)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2230)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.ActivityThread.handleRelaunchActivity(ActivityThread.java:3692)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.ActivityThread.access$700(ActivityThread.java:141)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1240)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.os.Handler.dispatchMessage(Handler.java:99)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.os.Looper.loop(Looper.java:137)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.ActivityThread.main(ActivityThread.java:5039)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at java.lang.reflect.Method.invokeNative(Native Method)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at java.lang.reflect.Method.invoke(Method.java:511)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:793)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at dalvik.system.NativeStart.main(Native Method)
02-01 16:31:13.684: E/AndroidRuntime(9739): Caused by: java.lang.NullPointerException
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.support.v4.app.FragmentManagerImpl.getFragment(FragmentManager.java:528)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at io.openkit.OKLoginActivity.onRestoreInstanceState(OKLoginActivity.java:62)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.Activity.performRestoreInstanceState(Activity.java:910)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.Instrumentation.callActivityOnRestoreInstanceState(Instrumentation.java:1131)
02-01 16:31:13.684: E/AndroidRuntime(9739):     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2158)

解决方案

Inside your DialogFragment, call Fragment.setRetainInstance(boolean) with the value true. You don't need to save the fragment manually, the framework already takes care of all of this. Calling this will prevent your fragment from being destroyed on rotation and your network requests will be unaffected.

You may have to add this code to stop your dialog from being dismissed on rotation, due to a bug with the compatibility library:

@Override
public void onDestroyView() {
  if (getDialog() != null && getRetainInstance())
    getDialog().setDismissMessage(null);
  super.onDestroyView();
}

这篇关于如何妥善保留通过转动DialogFragment?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆