Skip to content

Instantly share code, notes, and snippets.

@vargasgabriel
Forked from carlosezam/LiveDataValidator.kt
Last active May 20, 2021 02:02
Show Gist options
  • Select an option

  • Save vargasgabriel/cd07e32c17d5517f856c2f536951b46c to your computer and use it in GitHub Desktop.

Select an option

Save vargasgabriel/cd07e32c17d5517f856c2f536951b46c to your computer and use it in GitHub Desktop.

Revisions

  1. vargasgabriel revised this gist May 20, 2021. 1 changed file with 11 additions and 12 deletions.
    23 changes: 11 additions & 12 deletions ViewModel.kt
    Original file line number Diff line number Diff line change
    @@ -1,17 +1,16 @@
    val biometric = MutableLiveData<Agreement>()
    val biometricValidator = LiveDataValidator<Agreement>( biometric ).apply{
    addRule( messageOf("must acept or decline") ){ it == null }
    addRule( messageOf( "must accept or devline")){ it == Agreement.Agreed }
    val password = MutableLiveData<String>()
    val passwordValidator = LiveDataValidator<String>(password).apply{
    addRule("password is required") { it.isNullOrBlank() }
    addRule("password length must be 7") { it?.length != 7 }
    }

    val isAgreementFormValid = MediatorLiveData<Boolean>()

    init {
    isAgreementFormValid.value = false
    isAgreementFormValid.addSource(biometric){ validateForm() }
    val isFormValid = MediatorLiveData<Boolean>().apply {
    value = false
    addSource(username) { value = validateForm() }
    }

    fun validateForm(){
    val validators = listOf( biometricValidator )
    isAgreementFormValid.value = validators.all { it.isValid() }
    private fun validateForm() : Boolean {
    val validators = listOf(passwordValidator)
    val validatorResolver = LiveDataValidatorResolver(validators)
    return validatorResolver.isValid()
    }
  2. vargasgabriel revised this gist May 20, 2021. 1 changed file with 10 additions and 6 deletions.
    16 changes: 10 additions & 6 deletions LiveDataValidator.kt
    Original file line number Diff line number Diff line change
    @@ -1,20 +1,24 @@
    // https://oozou.com/blog/modern-android-form-validations-with-data-binding-147

    typealias Predicate<T> = (value: T?) -> Boolean

    class LiveDataValidator<T>(private val liveData: LiveData<T>){
    private val validationRules = mutableListOf< (T?) -> Boolean >()
    private val errorMessages = mutableListOf< Message >()
    private val validationRules = mutableListOf<Predicate<T>>()
    private val errorMessages = mutableListOf<String>()

    var error = MutableLiveData<Message?>()

    fun addRule(errorMsg: Message, predicate: (T?) -> Boolean ){
    fun addRule(errorMsg: String, predicate: Predicate<T>) {
    validationRules.add(predicate)
    errorMessages.add(errorMsg)
    }

    private fun emitErrorMessage(message: Message?){
    error.value = message
    private fun emitErrorMessage(messageRes: String?) {
    error.value = messageRes
    }

    fun isValid(): Boolean {
    for( i in 0 until validationRules.size){
    for(i in 0 until validationRules.size){
    if(validationRules[i](liveData.value) ){
    emitErrorMessage(errorMessages[i])
    return false
  3. vargasgabriel revised this gist May 19, 2021. 1 changed file with 1 addition and 1 deletion.
    2 changes: 1 addition & 1 deletion LiveDataValidator.kt
    Original file line number Diff line number Diff line change
    @@ -15,7 +15,7 @@ class LiveDataValidator<T>(private val liveData: LiveData<T>){

    fun isValid(): Boolean {
    for( i in 0 until validationRules.size){
    if( ! validationRules[i](liveData.value) ){
    if(validationRules[i](liveData.value) ){
    emitErrorMessage(errorMessages[i])
    return false
    }
  4. @carlosezam carlosezam created this gist Mar 30, 2021.
    27 changes: 27 additions & 0 deletions LiveDataValidator.kt
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,27 @@
    class LiveDataValidator<T>(private val liveData: LiveData<T>){
    private val validationRules = mutableListOf< (T?) -> Boolean >()
    private val errorMessages = mutableListOf< Message >()

    var error = MutableLiveData<Message?>()

    fun addRule(errorMsg: Message, predicate: (T?) -> Boolean ){
    validationRules.add(predicate)
    errorMessages.add(errorMsg)
    }

    private fun emitErrorMessage(message: Message?){
    error.value = message
    }

    fun isValid(): Boolean {
    for( i in 0 until validationRules.size){
    if( ! validationRules[i](liveData.value) ){
    emitErrorMessage(errorMessages[i])
    return false
    }
    }

    emitErrorMessage(null)
    return true
    }
    }
    3 changes: 3 additions & 0 deletions LiveDataValidatorResolver.kt
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,3 @@
    class LiveDataValidatorResolver(private val validators: List<LiveDataValidator<*>>){
    fun isValid() : Boolean = validators.all { it.isValid() }
    }
    17 changes: 17 additions & 0 deletions ViewModel.kt
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,17 @@
    val biometric = MutableLiveData<Agreement>()
    val biometricValidator = LiveDataValidator<Agreement>( biometric ).apply{
    addRule( messageOf("must acept or decline") ){ it == null }
    addRule( messageOf( "must accept or devline")){ it == Agreement.Agreed }
    }

    val isAgreementFormValid = MediatorLiveData<Boolean>()

    init {
    isAgreementFormValid.value = false
    isAgreementFormValid.addSource(biometric){ validateForm() }
    }

    fun validateForm(){
    val validators = listOf( biometricValidator )
    isAgreementFormValid.value = validators.all { it.isValid() }
    }