[Vuejs]-How to enable/disable submit button based on form validation state in Element UI?

2👍

Here’s what I ended up doing:

I used the vue.js ‘watch’ facility to monitor the form data (the key being that ‘deep’ is set so it monitors the field values) and run a check on it, updating a variable that disables the submit button:

The data section contains my form model and the enable variable:

data() {
    return {
        loginForm: {
            username: "",
            password: ""
        },
        formValid: false,
        ...

Which is attached to the button:

<el-button @click="submit" type="primary" :disabled="!formValid">Log In</el-button>

And the validation code, which is very generic (and may be able to be moved to a plugin):

watch: {
  loginForm: {
    handler(){
      this.checkForm();
    },
    deep: true
  }
},
methods: {
    checkForm() {
        let fields = this.$refs.loginForm.fields;
        if (fields.find((f) => f.validateState === 'validating')) {
            setTimeout(() => {
                this.checkForm();
            }, 100);
        }
        this.$data.formValid = fields.every(f => {
            let valid = f.required && f.validateState === "success";
            let notErroring = !f.required && f.validateState !== "error";
            return valid || notErroring;
        }, true);
        console.log('valid:', this.$data.formValid);
    },
    ...

(got this last part from another very useful post. It craftily handles the possibility of in-flight validation)

👤Jim B.

0👍

Updated answer for Element Plus [2023] with the Vue Composition API;

Add state for form validity using the form item’s prop name (same name you use for the rules);

const formValidity = ref({
    oldPassword: false,
    newPassword: false,
    confirmPassword: false
});

Created a computed property which is based on these values;

const formValid = computed(() => {
    return (
        formValidity.value.oldPassword &&
        formValidity.value.newPassword &&
        formValidity.value.confirmPassword
    );
});

Create a handler for the form’s @validate period (this event is fired each time validation occurs);

function validateHandler(propName, isValid) {
    formValidity.value[propName] = isValid;
}

Bind the handler with the "validate" event;

<el-form
    :model="ruleForm"
    :rules="rules"
    ref="ruleFormRef"
    @validate="validateHandler"
>

Disable the button based on the computed property;

<button
    :class="`${!formValid ? 'disabled' : ''}`"
    @click="submitForm()"
>
    Save
</button>

or

<button
    :disabled="!formValid"
    @click="submitForm()"
>
    Save
</button>

Leave a comment