State update in compose dialog android

64 Views Asked by At

I am stuck in Android compose StateFlow. I have a project in XML and I am converting it to compose. I want to show a composable dialog from an activity using state in ViewModel. On API success I am updating the state of the dialog which is collectAsState in activity, but I couldn't open the dialog from activity.

ViewModel code

    private val _state: MutableStateFlow<GenericDialogState> =
        MutableStateFlow(GenericDialogState())
    val state: StateFlow<GenericDialogState>
        get() = _state.asStateFlow()
_state.update { _state.value.copy(showDialog = true) } //On API response

MyActivity Code: (How to cause compose function here or how to define state for composable function)

  lifecycleScope.launch(Dispatchers.Main) {
                    repeatOnLifecycle(state = Lifecycle.State.STARTED) {
                       
                        mainActivityViewModel.state.collect { uiState ->
                            // New value received
                            if (uiState.showDialog)
                                Log.i(uiState.toString(), uiState.showDialog.toString())
    //                            ComposeGenericDialog(myParameter = MyParameter())
                        }
                    }

            }

Please rectify if I am wrong

data class GenericDialogState(
    var showDialog: Boolean = false
)
1

There are 1 best solutions below

0
Chirag Thummar On

You can make a SharedFlow object in ViewModel and update its value when you complete an API call or other operation.

On The UI side, you need to collect SharedFlow and when the value satisfies the condition it will show Dialog Or Toast.

@Composable
fun Stack026(shareFlowExampleViewModel1: ShareFlowExampleViewModel1) {
    val context = LocalContext.current
    var showDialog by remember {
        mutableStateOf(false)
    }


    LaunchedEffect(true) {
        shareFlowExampleViewModel1.showDialog.collect { show ->
            if (show) {
                showDialog = true
            }
        }
    }


    if (showDialog) {
        Dialog(onDismissRequest = { showDialog = false }) {
            Surface(
                shape = RoundedCornerShape(16.dp),
            ) {
                Column(modifier = Modifier.padding(20.dp)) {
                    Text(text = "My Custom Dialog Example")
                }
            }
        }
    }

    Box(modifier = Modifier.fillMaxSize(), contentAlignment = Alignment.Center) {
        Button(onClick = { shareFlowExampleViewModel1.makeAPICall() }) {
            Text(text = "Call API")
        }
    }
}


class ShareFlowExampleViewModel1 : ViewModel() {
    private val _showDialog = MutableSharedFlow<Boolean>()
    val showDialog = _showDialog.asSharedFlow()

    fun makeAPICall() {
        viewModelScope.launch {
            //API call simulation
            delay(2000)
            _showDialog.emit(true)
        }
    }
}