onActivityCreated is deprecated, how to properly use LifecycleObserver?

As per the changelog here

The onActivityCreated() method is now deprecated. Code touching the fragment's view should be done in onViewCreated() (which is called immediately before onActivityCreated()) and other initialization code should be in onCreate(). To receive a callback specifically when the activity's onCreate() is complete, a LifeCycleObserver should be registered on the activity's Lifecycle in onAttach(), and removed once the onCreate() callback is received.

You can do something like this in your fragment class:

class MyFragment : Fragment(), LifecycleObserver {
    @OnLifecycleEvent(Lifecycle.Event.ON_CREATE)
    fun onCreated(){
        activity?.lifecycle?.removeObserver(this)
    }

    override fun onAttach(context: Context) {
        super.onAttach(context)
        activity?.lifecycle?.addObserver(this)
    }
}

I did it in next way:

class MyActivityObserver(
    private val update: () -> Unit
) : DefaultLifecycleObserver {

    override fun onCreate(owner: LifecycleOwner) {
        super.onCreate(owner)
        owner.lifecycle.removeObserver(this)
        update()
    }
}

and use it in fragments onAttach (or another lifecycle method) like:

myActivity.lifecycle.addObserver(MyActivityObserver {
    myOnActivityCreated()
})

You can consider the Lifecycle.State as the nodes in a graph and Lifecycle.Event as the edges between these nodes.

So you will never reached the State.Created on your ON_CREATE function.

Solution

class YourFragment : Fragment(), LifecycleObserver {
    @OnLifecycleEvent(Lifecycle.Event.ON_RESUME)
    fun onCreated(){
        Log.i("tag","reached the State.Created")
    }

    override fun onAttach(context: Context) {
        super.onAttach(context)
        lifecycle.addObserver(this)
    }

    override fun onDetach() {
        super.onDetach()
        lifecycle.removeObserver(this)
    }
}

For more details

https://developer.android.com/topic/libraries/architecture/lifecycle#lc


The best way to solve the issue is to use lifecycleScope which is present in the activity lifecycle. Below is the code snippet

override fun onAttach(context: Context) {
    super.onAttach(context)
    activity?.lifecycleScope?.launchWhenCreated {
        setupActionbar()
    }
}

How does it work? launchWhenXxx runs the launch block when it automatically reaches the specified state(in this case it is Created) and if the lifecycle goes to the destroyed state it cancels the launched coroutine automatically. Internally lifecycleScope uses Dispatchers.Main.immediate and hence there is no penalty of thread switching

Pros of this approach are following:

  1. You don't have to manually maintain registering and deregistering of the observer
  2. No need to overwrite two lifecycle methods

You have to latest activity and fragment dependencies to use lifecycleScope attached to the lifecycle