I am attempting to use NavigationUI to create a navigation drawer in my app. I am trying to follow the Android Developers implementation at the above link to a tee. However, one issue I am facing is that I am unable to get the hamburger button in the action bar to open/close my navigation drawer. This probably has to do with the way I override onSupportNavigateUp()
in my CategoryActivity
, but I'm unsure how to fix.
I hate to throw this much code at someone, but can someone with experience with the API take a look if I am missing something? Much appreciated. Thanks.
My navigation graph (nav_graph_category.xml
):
<?xml version="1.0" encoding="utf-8"?>
<navigation xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/nav_graph_category"
app:startDestination="@id/people_fragment">
<fragment
android:id="@+id/people_fragment"
android:name="com.davidread.starwarsdatabase.view.EmptyFragment"
android:label="@string/people_category_label" />
<fragment
android:id="@+id/films_fragment"
android:name="com.davidread.starwarsdatabase.view.EmptyFragment"
android:label="@string/films_category_label" />
<fragment
android:id="@+id/starships_fragment"
android:name="com.davidread.starwarsdatabase.view.EmptyFragment"
android:label="@string/starships_category_label" />
<fragment
android:id="@+id/vehicles_fragment"
android:name="com.davidread.starwarsdatabase.view.EmptyFragment"
android:label="@string/vehicles_category_label" />
<fragment
android:id="@+id/species_fragment"
android:name="com.davidread.starwarsdatabase.view.EmptyFragment"
android:label="@string/species_category_label" />
<fragment
android:id="@+id/planets_fragment"
android:name="com.davidread.starwarsdatabase.view.EmptyFragment"
android:label="@string/planets_category_label" />
</navigation>
My drawer menu (drawer_menu_category.xml
):
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<item android:title="@string/categories_label">
<menu>
<group android:checkableBehavior="single">
<item
android:id="@+id/people_category_action"
android:title="@string/people_category_label" />
<item
android:id="@+id/films_category_action"
android:title="@string/films_category_label" />
<item
android:id="@+id/starships_category_action"
android:title="@string/starships_category_label" />
<item
android:id="@+id/vehicles_category_action"
android:title="@string/vehicles_category_label" />
<item
android:id="@+id/species_category_action"
android:title="@string/species_category_label" />
<item
android:id="@+id/planets_category_action"
android:title="@string/planets_category_label" />
</group>
</menu>
</item>
</menu>
My main layout (activity_category.xml
):
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
tools:context=".view.CategoryActivity">
<androidx.drawerlayout.widget.DrawerLayout
android:id="@+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true">
<androidx.fragment.app.FragmentContainerView
android:id="@+id/nav_host_fragment"
android:name="androidx.navigation.fragment.NavHostFragment"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:defaultNavHost="true"
app:navGraph="@navigation/nav_graph_category" />
<com.google.android.material.navigation.NavigationView
android:id="@+id/navigation_view"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
android:fitsSystemWindows="true"
app:menu="@menu/drawer_menu_category" />
</androidx.drawerlayout.widget.DrawerLayout>
</layout>
My main activity (activity_category.xml
):
package com.davidread.starwarsdatabase.view
import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import androidx.navigation.NavController
import androidx.navigation.fragment.NavHostFragment
import androidx.navigation.ui.*
import com.davidread.starwarsdatabase.R
import com.davidread.starwarsdatabase.databinding.ActivityCategoryBinding
class CategoryActivity : AppCompatActivity() {
private val binding: ActivityCategoryBinding by lazy {
ActivityCategoryBinding.inflate(layoutInflater)
}
private val navController: NavController by lazy {
val navHostFragment: NavHostFragment =
supportFragmentManager.findFragmentById(R.id.nav_host_fragment) as NavHostFragment
navHostFragment.navController
}
private val appBarConfiguration: AppBarConfiguration by lazy {
AppBarConfiguration(navController.graph, binding.drawerLayout)
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_category)
setupActionBarWithNavController(navController, appBarConfiguration)
binding.navigationView.setupWithNavController(navController)
}
override fun onSupportNavigateUp(): Boolean {
return navController.navigateUp(appBarConfiguration) || super.onSupportNavigateUp()
}
}
A snippet from my build.gradle dependencies, in case it's a version thing:
dependencies {
// Material Components library. Contains modular and customizable Material Design UI components.
implementation 'com.google.android.material:material:1.7.0'
// Android Jetpack's Navigation API. Required for navigation drawer.
implementation "androidx.navigation:navigation-fragment-ktx:2.5.3"
implementation "androidx.navigation:navigation-ui-ktx:2.5.3"
}
Note, I am able to open the navigation drawer by swiping from the left side of the screen as expected. That is why navigation drawer is open in second screenshot.
Your problem is with this line:
setContentView(R.layout.activity_category)
What that means is that you are inflating a brand new copy of R.layout.activity_category
- you aren't actually using your binding
variable at all, which means that the binding.drawerLayout
you've set on your AppBarConfiguration
isn't actually the DrawerLayout
that you've set as your content view.
Instead, you'll want to actually set your binding
as the content view of your activity by using the code from the data binding documentation:
setContentView(binding.root)