I'm using navigation component and want to connect drawer layout with toolbar in each fragment, not the activity.
I tried this answer which is called on onViewCreated() but any view referenced from the activity is null. I guess it's because fragment is inflated in the layout before returning from the activity's onCreate method.
I use this extension function to connect the drawer with the fragment's toolbar, I tried to call it from onCreateView() and onViewCreated() but did't work and the activity's drawer layout is always null. I works only if it's called from onStart() but I don't think it's the right way:
private fun AppCompatActivity.setToolbar() {
setSupportActionBar(binding.toolbar)
setHasOptionsMenu(true)
val drawer = findViewById<DrawerLayout>(R.id.drawer)
binding.toolbar.setupWithNavController(findNavController(), drawer)
}
What's the right place to call this function?
When you call
setContentView(R.id.activity_layout)
, the entire view hierarchy is first inflated, then attached to the Activity. It is only aftersetContentView()
returns thatfindViewById()
will find any of the newly inflated views.When you use the
<fragment>
tag, the Fragment's view and the views of all of its child fragments are synchronously created as part of that inflation call. This means thatsetContentView()
has not completed by the time theonCreateView()
andonViewCreated()
methods are called. This is why that callingfindViewById()
returns null - the activity's view hasn't actually finished being created.FragmentContainerView
was specifically built to avoid these special cases and instead use the same mechanisms as other fragments - namely, it just uses a normalFragmentTransaction
to add your Fragment - the same as if you calledbeginTransaction()
+commitNow()
in youronCreate()
method yourself. This means that the Fragment is not forced to synchronously create its view as part ofsetContentView()
, but can do it alongside every other Fragment aftersetContentView()
returns. This is what allowsfindViewById()
fromonCreateView()
oronViewCreated()
work.