I've started learning architecture components, but can't find one thing.
LifecycleFragment just creates a new LifecycleRegistry object, which does not start observing the fragment's lifecycle.
I guess the LifecycleRegistry object starts listening to the fragment's lifecycle when we, for example, put it into LiveData.observe() as first param, but I haven't found any proof of this in source code.
Question: When and how does a LifecycleRegistry object start to observe a fragment's lifecycle and refresh LifecycleRegistry.mState
?
There is a ContentProvider
called LifecycleRuntimeTrojanProvider
that is merged into the app's AndroidManifest.xml
. In its onCreate
method it initializes a singleton called LifecycleDispatcher
, which is responsible for updating all LifecycleRegistry
instances.
LifecycleDispatcher
uses the Application.registerActivityLifecycleCallbacks method that has been around since API 14 to get notified when a new activity is created. At this point it injects an instance of ReportFragment
into the activity. The ReportFragment
uses the Fragment
lifecycle callbacks to update the activity's LifecycleRegistry
if necessary, like this:
@Override
public void onStop() { // Showing onStop as example
super.onStop();
dispatch(Lifecycle.Event.ON_STOP);
}
private void dispatch(Lifecycle.Event event) {
if (getActivity() instanceof LifecycleRegistryOwner) {
((LifecycleRegistryOwner) getActivity()).getLifecycle().handleLifecycleEvent(event);
}
}
If the new activity is a FragmentActivity
, the LifecycleDispatcher
calls FragmentManager.registerFragmentLifecycleCallbacks to get notified of the activity's fragments lifecycle events. It relays the onFragmentCreated
, onFragmentStarted
and onFragmentResumed
callbacks to the LifecycleRegistry
in case the fragment is a LifecycleRegistryOwner
, in the same way as before.
The onFragmentPaused
, onFragmentStopped
, and onFragmentDestroyed
callbacks are called after the corresponding callbacks are called on the fragment, but the LifecycleObserver
callbacks must be called before. So whenever a fragment is created, the LifecycleDispatcher
injects an instance of LifecycleDispatcher.DestructionReportFragment
into it. The DestructionReportFragment
's lifecycle callbacks are used to update the registry for the pause, stop and destroy events.
I can't link to the code because it hasn't been released yet, but you can browse it in Android Studio after you add the library to your project.
As Mordag said, as of now, both the LifecycleActivity and LifecycleFragment are not yet implemented. In their documentation Google says:
Any custom fragment or activity can be turned into a LifecycleOwner by implementing the built-in LifecycleRegistryOwner interface (instead of extending LifecycleFragment or LifecycleActivity).
However, that is only half the story, because naturally you are using these Lifecycle Aware components to be able to react to your Activity/Fragment lifecycles and with their code snippet it just doesn't work, because initialising a LifecycleRegistry with the Activity/Fragment like this
LifecycleRegistry lifecycleRegistry = new LifecycleRegistry(this);
only gets you a Lifecycle in the INITIALIZED state.
So, long story short, in order for this to work right now (BEFORE their 1.0-release) it is you who have to implement the Lifecycle of the Activity/Fragment that implements the LifecycleRegistry. So, for each callback of the Activity/Fragment you need to do this:
public class ScoreMasterFragment extends Fragment
implements LifecycleRegistryOwner {
private LifecycleRegistry lifecycle;
@Override
public LifecycleRegistry getLifecycle() {
return lifecycle;
}
public ScoreMasterFragment(){
lifecycle = new LifecycleRegistry(this);
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//more code here
lifecycle.handleLifecycleEvent(Lifecycle.Event.ON_CREATE);
}
@Override
public void onStart() {
super.onStart();
//more code here
lifecycle.handleLifecycleEvent(Lifecycle.Event.ON_START);
}
@Override
public void onResume() {
super.onResume();
//more code here
lifecycle.handleLifecycleEvent(Lifecycle.Event.ON_RESUME);
}
@Override
public void onPause() {
super.onPause();
//more code here
lifecycle.handleLifecycleEvent(Lifecycle.Event.ON_PAUSE);
}
@Override
public void onStop() {
super.onStop();
//more code here
lifecycle.handleLifecycleEvent(Lifecycle.Event.ON_STOP);
}
@Override
public void onDestroy() {
super.onDestroy();
//more code here
_lifecycle.handleLifecycleEvent(Lifecycle.Event.ON_DESTROY);
}
This will likely be in the code of the future LifecycleActivity and LifecycleFragment, but until then, if you put your Activities/Fragments observing some LifecycleAware object (like LiveData) you will have to do this.
In the case of LiveData, because it will not notify its observers unless they are at least in the STARTED state and in other cases because other LifecycleAware components cannot react to a Lifecycle if its only state is INITIALIZED.
The LifecycleFragment and LifecycleActivity are currently not fully implemented. Those classes will be implemented when the lib is reaching 1.0-release. Currently you can use those LifecycleRegistry to observe LiveData objects. Those objects are based on a future result which could e.g. be an object from your database.
The official documentation can be found here: https://developer.android.com/topic/libraries/architecture/index.html
Official statement regarding the two classes you mentioned:
Lifecycle Fragment and ActivityCompat in the Support Library do not yet implement LifecycleOwner interface. They will when Architecture Components reaches 1.0.0 version.
LifecycleActivity ,LifecycleFragment and LifecycleRegistryOwner interface are deprecated in API level 1.0.0. Use android.support.v7.app.AppCompatActivity and android.support.v4.app.Fragment instead of it. Official documentation here LifecycleActivity LifeCycleFragment
来源:https://stackoverflow.com/questions/44594919/when-does-a-lifecycleregistry-instance-start-listening-to-lifecycleowners-lifec