碎片onCreateView和onActivityCreated未在旋转时调用

时间:2014-04-30 15:14:06

标签: android android-fragments fragmenttransaction

我正在使用片段并在backstack上推送新片段但是当我将设备旋转两次片段的onCreateViewonActivityCreated等等时,片段生命周期方法永远不会被调用黑屏。只有在将一个片段添加到backstack或返回到Backstack中的第一个片段时才会发生这种情况。

这是我的活动的片段处理方法:

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

    // Injection
    MormonChannel.injectActivity(this);

    setDrawerIndicatorEnabled(true);

    // Do not set currentNavigationItem here.
    NavigationItemSelectedEvent.NavigationItem navItem = null;
    Intent intent = getIntent();
    if (intent != null) {
        navItem = (NavigationItemSelectedEvent.NavigationItem)
        intent.getSerializableExtra(EXTRA_NAV_ITEM);
    }

    if (savedInstanceState == null) {
        FragmentManager fm = getSupportFragmentManager();
        fm.beginTransaction().replace(R.id.container, new FeatureListFragment()).commit();
        if (navItem != null) {
            onNavigationItemSelected(new NavigationItemSelectedEvent(navItem));
        } else {
            currentNavigationItem = NavigationItemSelectedEvent.NavigationItem.FEATURES;
        }
    }

}

@Subscribe
public void onNavigationItemSelected(NavigationItemSelectedEvent event) {

    if (currentNavigationItem == event.getNavigationItem()) {
        return;
    }
    FragmentManager fragmentManager = getSupportFragmentManager();
    fragmentManager.popBackStack();
    NavigationItemSelectedEvent.NavigationItem navigationItem = event.getNavigationItem();
    String name = navigationItem.getName();
    switch (navigationItem) {
        default:
        case FEATURES:
            // Nothing needs to be done it is already there.
            break;
        case AUDIO:
            fragmentManager.beginTransaction().replace(R.id.container,
                    CollectionListFragment.newInstance(prefs.getLanguageId(), prefs.getAudioCollectionId()))
                    .addToBackStack
                            (name).commit();
            break;
        case VIDEO:
            fragmentManager.beginTransaction().replace(R.id.container,
                    CollectionListFragment.newInstance(prefs.getLanguageId(), prefs.getVideoCollectionId()))
                    .addToBackStack(name).commit();
            break;
        case RADIO:
            fragmentManager.beginTransaction().replace(R.id.container,
                    CollectionListFragment.newInstance(prefs.getLanguageId(), prefs.getRadioCollectionId()))
                    .addToBackStack(name).commit();
            break;
        case HISTORY:
            fragmentManager.beginTransaction().replace(R.id.container, new HistoryFragment()).addToBackStack(name).commit();
            break;
        case DOWNLOADS:
            fragmentManager.beginTransaction().replace(R.id.container, new DownloadsFragment()).addToBackStack(name).commit();
            break;
        case PLAYLISTS:
            fragmentManager.beginTransaction().replace(R.id.container, new PlaylistFragment()).addToBackStack(name).commit();
            break;
    }
    currentNavigationItem = navigationItem;
}

这是我的CollectionListFragment代码:

 @Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    MormonChannel.injectFragment(this);
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    View v = inflater.inflate(R.layout.collection_list_fragment, container, false);
    ButterKnife.inject(this, v);
    return v;
}

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

    listView.setDividerHeight(0);
    listView.setFastScrollEnabled(true);


    Bundle args = getArguments();
    if (args != null) {
        languageId = args.getLong(ARG_LANGUAGE_ID, -1L);
        collectionId = args.getLong(ARG_COLLECTION_ID, -1L);
        if (args.containsKey(ARG_SORT)) {
            sort = (Sort) args.getSerializable(ARG_SORT);
        }
    }

    if (collectionId == -1L || languageId == -1L) {
        // TODO Implement Empty Collection Text
    } else {
        collection = collectionManager.findByCollectionId(languageId, collectionId);
        getLoaderManager().initLoader(LOADER_ID, null, this);
    }

    titleEvent = new TitleChangeEvent(collection != null ? collection.getTitle() : getString(R.string.app_name));
    bus.post(titleEvent);
}

活动清单:

<activity
    android:name=".activity.MainActivity"
    android:launchMode="singleTask">
    <meta-data
        android:name="android.app.default_searchable"
        android:value=".activity.SearchActivity"/>
</activity>

1 个答案:

答案 0 :(得分:1)

在CollectionListFragment Code中,在onCreate()方法中添加对setRetainInstance()方法的调用,并将true作为参数:

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setRetainInstance(true);
    MormonChannel.injectFragment(this);

}

使用setRetainInstance(true)可确保在发生配置更改时,活动将被终止但android不会破坏它所托管的片段。

相反,android将保存片段状态并从活动中分离片段。它也不会破坏片段,所以它在以后创建托管活动时不会创建它。因此片段不会接收对其onDestroy()和onCreate()方法的调用。