Activity Life Cycle
Activity class provides a core set of six callbacks: onCreate(), onStart()
, onResume()
, onPause()
, onStop()
, and onDestroy()
. The system invokes each of these callbacks as an activity enters a new state.
Orientation Changes
Nice Tutorial on Handling Orientation Changes
Fragment Life Cycle
Normal Behaviour
If you rotate your device when you have an Activity that is NOT using the configChanges
flag and a Fragment that IS being retained, the following lifecycle methods will be called on the Fragment:
onPause onSaveInstanceState onStop onDestroyView onDetach onAttach onCreateView onActivityCreated onStart onResume
Android does not call onCreate and onDestroy because we retained the Fragment; nor does it call the constructor, because the same Fragment instance will be used after the orientation change. Android will call all of the other callbacks because the Fragment’s parent Activity IS being destroyed and recreated, so the Fragment does have to go through the process of being detached then reattached.
Option 1 android:configChanges
Setting the android:configChanges flag on your Activity in AndroidManifest.xml as shown below:
<activity
android:name=".MyActivity"
android:label="@string/title_my_activity"
android:configChanges="orientation|screenSize|keyboardHidden" />
Cons:
Instead of destroying and recreating your Activity, Android will just rotate the screen and call one of the lifecycle methods: onConfigurationChanged
. You would have to implement onConfigurationChanged and manually discard the old layout/View, inflate the new layout and display it — which is a lot more work and can make your code difficult to work with in the future.
Fragment.setRetainInstance(true)
Calling setRetainInstance(true) on a Fragment is similar to setting the android:configChanges flag on an Activity. It signals to Android that you want to continue using the same instance of the current Fragment, so all of your member variables will remain untouched.
Option 2 : android:screenOrientation
<activity
android:name=".MyActivity"
android:label="@string/title_my_activity"
android:screenOrientation="portrait" />
This altogether prevents orientation changes from happening while the user is in the Activity with the flag set. So if you rotate your device the screen won’t rotate with it.
Option 3 : Saving State
This involves implementing the onSaveInstanceState
method (this could be in your Activity, Fragment or both) and placing the values you need to save in the Bundle argument that gets passed to the method.
This means that if you use any custom Views
, they should contain an implementation of onSaveInstanceState. Do note, that in order for a View’s state to be saved it MUST have an android:id
attribute because this is essentially used as the key for that particular View’s state.
private static final String STATE_COUNTER = "counter";
private int mCounter;
...
@Override
protected void onSaveInstanceState(Bundle outState) {
// Make sure to call the super method so that the states of our views are saved
super.onSaveInstanceState(outState);
// Save our own state now
outState.putInt(STATE_COUNTER, mCounter);
}
The same Bundle
object is used in onCreate of the Activity
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
...
// If we have a saved state then we can restore it now
if (savedInstanceState != null) {
mCounter = savedInstanceState.getInt(STATE_COUNTER, 0);
}
// Display the value of the counter
mCounterTextView = (TextView) findViewById(R.id.counter_text);
mCounterTextView.setText(Integer.toString(mCounter));
ListViews
poses extra requirements for restoring state. Watch the tutorial for details.
Using onRestoreInstanceState
if you want to wait for all of your onCreate initialization to be done before restoring state or if you want to allow subclasses to specifically handle restoring state. An Activity’s onRestoreInstanceState is called after onStart and before onResume.
|
|