1

I have a app using Jetpack Compose.

I have two screens:

1. NewsScreen
2. SettingsScreen

The default is NewsScreen.

I have a NavHost called AppNavigation.kt:

@Composable
fun AppNavigation() {
val navController = rememberNavController()
val settingsViewModel: SettingsViewModel = viewModel()
NavHost(
    navController = navController,
    startDestination = AppScreens.NewsScreen.name
) {
    composable(AppScreens.NewsScreen.name) {
        NewsScreen(navController = navController, settingsViewModel)
    }
    composable(AppScreens.SettingsScreen.name) {
        SettingsScreen(navController = navController, settingsViewModel)
    }
}
}

And also enum class:

enum class AppScreens {
NewsScreen,
SettingsScreen;
companion object {
    fun fromRoute(route: String): AppScreens
        = when (route?.substringBefore("/")) {
            NewsScreen.name -> NewsScreen
            SettingsScreen.name -> SettingsScreen
            else -> throw  IllegalArgumentException("Unknown route: $route")
    }
}
}

My Scaffold looks like this in HomePage.kt:

@Composable
fun HomeScreen(navController: NavController, settingsViewModel: SettingsViewModel) {
val scaffoldState = rememberScaffoldState()
val scope = rememberCoroutineScope()
Scaffold(
    Modifier.background(Color.Transparent),
    scaffoldState = scaffoldState,
    drawerContent = {
        CompositionLocalProvider(LocalLayoutDirection provides LayoutDirection.Rtl) {
            Card(
                modifier = Modifier.padding(vertical = 15.dp),
                shape = RoundedCornerShape(15.dp, 0.dp, 0.dp, 15.dp),
            ) {
                Column(
                    modifier = Modifier.fillMaxHeight(),

                    verticalArrangement = Arrangement.SpaceBetween
        ) {
/* ... */
                }
            }
        }
    },
    bottomBar = {
        BottomAppNavigationBar(navController = navController)
    },
    floatingActionButton = {
        FloatingActionButton(
            backgroundColor = Color.White,
            modifier = Modifier.size(75.dp),
            onClick = { /* ... */ }
        ) {
            /* FAB content */
        }
    },
    floatingActionButtonPosition = FabPosition.Center,
    isFloatingActionButtonDocked = true,


    )
{ contentPadding ->
    // Screen content
    Box(
        modifier = Modifier
            .padding(contentPadding)
            .background(
                Color("#C8DBE2".toColorInt())
            )
    ) {
        TopAppBar(
            modifier = Modifier.padding(20.dp, 10.dp),
            backgroundColor = Color.Transparent,
            elevation = 0.dp
        ) {
            Row(
                Modifier.fillMaxWidth(),
                horizontalArrangement = Arrangement.SpaceBetween
            ) {
                NavMenuButton(scope, scaffoldState)
                ProfileMenuButton()
            }
        }

        CompositionLocalProvider(LocalLayoutDirection provides LayoutDirection.Rtl) {
            NewsScreen(navController = navController)

        }
    }

}

}

And finally, BottomAppNavigationBar

@Composable
fun BottomAppNavigationBar(navController: NavController) {
val navTextList = listOf(
    AppScreens.NewsScreen.name,
    AppScreens.SettingsScreen.name,
)
var selectIndex by remember { mutableStateOf(0) }
val iconList = listOf(
    painterResource(id = R.drawable.news),
    painterResource(id = R.drawable.settings),
)
BottomAppBar(
    // Defaults to null, that is, No cutout
    cutoutShape = MaterialTheme.shapes.small.copy(
        CornerSize(percent = 50)
    ),
    backgroundColor = Color.Transparent,
    elevation = 90.dp,
    modifier = Modifier
        .height(80.dp)
        .fillMaxWidth()
        .shadow(50.dp)
        .clip(
            (RoundedCornerShape(15.dp, 15.dp, 0.dp, 0.dp))
        )
) {
    Card(
        modifier = Modifier
            .fillMaxWidth()
            .padding(top = 5.dp)
            .background(Color.Transparent),
        shape = RoundedCornerShape(15.dp, 15.dp, 0.dp, 0.dp),
    ) {
        Row(
            horizontalArrangement = Arrangement.SpaceEvenly,
            modifier = Modifier.fillMaxWidth()
        ) {
            navTextList.forEachIndexed { index, str ->
                BottomNavigationItem(
                    label = { Text(str) },
                    selected = index == selectIndex,
                    modifier = Modifier.background(Color.White),
                    selectedContentColor = Color.LightGray,
                    unselectedContentColor = Color.Gray,
                    onClick = {
                        navController.navigate(str) {

                            navController.graph.startDestinationRoute?.let { screen_route ->
                                popUpTo(screen_route) {
                                    saveState = true
                                }
                            }
                            launchSingleTop = true
                            restoreState = true
                        }
                    },
                    icon = {
                        Icon(
                            modifier = Modifier
                                .size(47.dp)
                                .padding(top = 15.dp),
                            tint = Color.Black,
                            painter = iconList[index],
                            contentDescription = null
                        )
                    })
                if (index == 0) {
                    Spacer(modifier = Modifier.size(90.dp))
                }
            }
        }
    }
}

}

How do I make it change to all NewsScreen and SettingsScreen when clicking bottom nav bar?

Palantiir
  • 55
  • 5

1 Answers1

0

You just need to call navController.navigate("ROUTE") to go to the specific route. Note that the route must be a registered route in the app's navigation.

Raul Lucaciu
  • 132
  • 7