During navigation from Navhost, I found out that the composable screens are getting recomposition multiple times. Because of it, my ViewModel is calling API data source multiple times too.
@Composable
fun MainView() {
val scaffoldState = rememberScaffoldState(rememberDrawerState(DrawerValue.Closed))
val scope = rememberCoroutineScope()
val navController = rememberNavController()
Scaffold(
scaffoldState = scaffoldState,
topBar = { TopBar(
toolbarTitle = stringResource(id = R.string.app_name),
scope = scope,
scaffoldState = scaffoldState
) },
drawerContent = {
DrawerView(scope = scope, scaffoldState = scaffoldState, navController = navController)
},
) {
NavGraph(navController = navController)
}
}
@Composable
fun NavGraph(navController: NavHostController) {
NavHost(navController, startDestination = NavDrawerItem.Repositories.route) {
composable(NavDrawerItem.Repositories.route) {
RepoListView(getViewModel())
}
composable(NavDrawerItem.EmojiList.route) {
EmojiListView(getViewModel())
}
}
}
class RepoListViewModel(
private val repositoriesUseCase: GetRepositoriesUseCase
): ViewModel() {
init {
getRepositories()
}
@Composable
fun RepoListView(viewModel: RepoListViewModel) {
AppTheme {
RepoListContent(viewModel)
}
}
Is there a way to handle it? I mean, I know it's how Android Compose works. But, How can I handle an API call inside a navigation screen?
EDIT
The problem was Koin itself. A new version has come and now its working properly.
getViewModel
shouldn't create a new instance on each recomposition. My only guess is that you can callnavigate
multiple times, which will create a new route for each call - check out this answer for details. If this won't help, please update your code to minimal reproducible example, as right now it cannot be run. – CounterweightgetViewModel()
do? If it is doing anything other than calling theviewModel()
method, then that's your problem. It is expected, anytime you are animated between destinations, that they recompose on every frame. – CyclostylelaunchSingleTop = true
option when usingnavController.navigate()
. – Hopfinger