I want to pass the result from viewModelScope into my activity. I created viewModel which has 2 methods.
class CurrencyConverterViewModel : ViewModel() {
lateinit var response: CurrencyCodesModel
var listOfNames : List<String> = emptyList()
init {
viewModelScope.launch {
getListOfCurrencyNamesApi()
}
}
suspend fun getCurrencyCodes() {
response = CurrencyConverterInstance
.currencyApiService
.getCurrencyCodes()
}
private suspend fun getListOfCurrencyNamesApi() {
getCurrencyCodes()
listOfNames = response.supported_codes.map { it[1] }
}
}
One of them calls my api service and stores result in a response variable. The second method called getListOfCurrencyNamesApi is supposed to take supported_codes from response and split them into list of strings.
Then I create viewModel object in my Composable function. At this point the init function in viewModel is called and I see in Logcat that the list has some records but when I want to put it into currencyListOfNames.value it is empty
@Composable
fun CurrencyConverter() {
val myViewModel: CurrencyConverterViewModel = viewModel()
val currencyListOfNames = remember { mutableStateOf<List<String>>(emptyList()) }
currencyListOfNames.value = myViewModel.listOfNames
}
here is a solution for you to solve your problem, the reason why you did not see the update of your data is because they are in different threads and therefore you had no way to know your composable that it was being updated and that it was recomposed again.
class CurrencyConverterViewModel : ViewModel() {
lateinit var response: CurrencyCodesModel
// Here you are creating the variable with a stateFlow but you can also do it with a SharedFlow the difference you can see here https://developer.android.com/kotlin/flow/stateflow-and-sharedflow
private var _listOfNames = MutableStateFlow<List<String>>(listOf())
val listOfNames = _listOfNames.asStateFlow()
init {
viewModelScope.launch {
getListOfCurrencyNamesApi()
}
}
suspend fun getCurrencyCodes() {
response = CurrencyConverterInstance
.currencyApiService
.getCurrencyCodes()
}
private suspend fun getListOfCurrencyNamesApi() {
getCurrencyCodes()
//here you update the change
_listOfNames.emit(
response.supported_codes.map { it[1] }
)
}
}
@Composable
fun CurrencyConverter() {
val myViewModel: CurrencyConverterViewModel = viewModel()
//Here every time you call your getCurrencyCodes function and issue _listOfNames your composable will recompose and update the data.
val listOfNames by myViewModel.listOfNames.collectAsState()
}