Kişisel web sayfamda yazılım, teknoloji ve genel hayat hakkında paylaşımlar yapmayı hedefliyorum.

StateFlow – New Form Validation Way with Kotlin Flows


Hi everyone, in this article we will implement a form validation with Kotlin Flow and StateFlow.

Kotlin Flows, is a type that can emit multiple values sequentially. It’s like channels but the most important difference a flow represens a cold stream of values

(need more? cold flows, hot channels)

Firstly, we need a form layout for collect a StateFlow source.

And I added two backgroundTint color for form states:

private val defaultButtonTintColor = "#1B1717"
private val onFormValidButtonTintColor = "#4F774F"

Now we create StateFlow variables for form elements and bind text listeners:

private val email = MutableStateFlow("")
private val password = MutableStateFlow("")
private val passwordAgain = MutableStateFlow("")
// onCreate
with(mBinding) {

    txtEmail.doOnTextChanged { text, _, _, _ ->
        email.value = text.toString()
    txtPassword.doOnTextChanged { text, _, _, _ ->
        password.value = text.toString()
    txtPasswordAgain.doOnTextChanged { text, _, _, _ ->
        passwordAgain.value = text.toString()

Here is the validation area. We give our StateFlow variables to the combine function. So we will get the final version of all data at the same time

private val formIsValid = combine(
) { email, password, passwordAgain ->
    mBinding.txtErrorMessage.text = ""
    val emailIsValid = email.length > 6
    val passwordIsValid = password.length in 7..15
    val passwordAgainIsValid = passwordAgain == password
    errorMessage = when {
        emailIsValid.not() -> "email not valid"
        passwordIsValid.not() -> "Password not valid"
        passwordAgainIsValid.not() -> "Passwords do not match"
        else -> null
    errorMessage?.let {
        mBinding.txtErrorMessage.text = it
    emailIsValid and passwordIsValid and passwordAgainIsValid

Ok, but how I can observe StateFlow?

with Flows, observe —> collect

  • observe → liveData
  • collect → flow

Suspend function ‘collect’ should be called only from a coroutine or another suspend function

If you have ktx extensions you can use lifecycleScope

lifecycleScope.launch {
    formIsValid.collect {
        mBinding.btnLogin.apply {
            backgroundTintList = ColorStateList.valueOf(
                    if (it) onFormValidButtonTintColor else defaultButtonTintColor
            isClickable = it

So, here is the final code

That’s all.

If you saw wrong anything mention it in the comments. It would be very useful.

Was it helpful? If yes, leave some claps 👏




ViewBinding: Kotlin Synthetic is Dead, Long Live ViewBinding (Kotlin Android Extensions Deprecated)


You may also like...

Bir cevap yazın

E-posta hesabınız yayımlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir