You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

VueJS中@input仅失焦触发,需改为输入时实时触发的解决方案

解决Vue中@input事件未实时触发的问题

你的问题核心是绑定的@input事件没有在用户输入过程中实时触发,反而仅在失焦时执行,这是因为你在ValidateInput函数中直接修改了v-model绑定的inputValue,导致Vue重新渲染输入框DOM,打断了@input事件的连续触发逻辑。

以下是两种可行的解决方案:

方案一:使用@input事件参数获取输入值

直接通过事件对象获取当前输入框的原始值,处理后再赋值给inputValue,避免v-model的即时更新冲突:

修改模板

<input
    v-model="inputValue"
    type="text"
    :placeholder="placeholder"
    :class="['w-full !border-none !focus:border-none p-2.5 shadow-none', disabled ? 'text-[#969c9f]' : 'black']"
    @input="ValidateInput($event)"
    :disabled="disabled"
/>

修改ValidateInput函数

ValidateInput(event) {
    let value = event.target.value;
    if (!value) {
        this.inputValue = null;
        this.$emit('update:modelValue', null);
        return;
    }

    switch(this.valueType) {
        case "Number":
            value = value.replace(/[^0-9]/g, '');
            break;
        case "SP":
            value = value.replace(/^0+/, '').replace(/\D/g, '');
            break;
        case "Number_with_TS":
            value = value.replace(/[^0-9]/g, '');
            value = value.replace(/\B(?=(\d{3})+(?!\d))/g, ' ');
            break;
        case "SP_with_TS":
            value = value.replace(/^0+/, '').replace(/\D/g, '');
            value = value.replace(/\B(?=(\d{3})+(?!\d))/g, ' ');
            break;
        case "decimal":
            value = value.replace(/[^0-9.]/g, '');
            const parts = value.split('.');
            if (parts.length > 2) {
                value = parts[0] + '.' + parts.slice(1).join('');
            }
            break;
        case "ZipCode":
            value = value.replace(/[^0-9]/g, '');
            if (value.length > 4) {
                value = value.substring(0, 4);
            }
            break;
        case "disabled":
            value = 0;
            break;
        case "model_spec":
            if (value.length > 60) {
                value = value.substring(0, 60);
            }
            break;
        case "cylinder_volume":
            value = value.replace(/[^\d,.]/g, '');
            break;
    }

    this.inputValue = value === "" ? null : value;
    this.$emit('update:modelValue', this.inputValue);
}

方案二:使用watch监听inputValue变化

通过Vue的watch选项监听inputValue的每一次变化,不管是用户输入还是代码修改,都会实时触发验证逻辑:

添加watch配置

export default {
    // ...其他组件选项
    watch: {
        inputValue(newVal) {
            this.ValidateInput(newVal);
        }
    },
    methods: {
        ValidateInput(value) {
            if (!value) {
                this.inputValue = null;
                this.$emit('update:modelValue', null);
                return;
            }

            let processedValue = value;
            switch(this.valueType) {
                case "Number":
                    processedValue = processedValue.replace(/[^0-9]/g, '');
                    break;
                case "SP":
                    processedValue = processedValue.replace(/^0+/, '').replace(/\D/g, '');
                    break;
                case "Number_with_TS":
                    processedValue = processedValue.replace(/[^0-9]/g, '');
                    processedValue = processedValue.replace(/\B(?=(\d{3})+(?!\d))/g, ' ');
                    break;
                case "SP_with_TS":
                    processedValue = processedValue.replace(/^0+/, '').replace(/\D/g, '');
                    processedValue = processedValue.replace(/\B(?=(\d{3})+(?!\d))/g, ' ');
                    break;
                case "decimal":
                    processedValue = processedValue.replace(/[^0-9.]/g, '');
                    const parts = processedValue.split('.');
                    if (parts.length > 2) {
                        processedValue = parts[0] + '.' + parts.slice(1).join('');
                    }
                    break;
                case "ZipCode":
                    processedValue = processedValue.replace(/[^0-9]/g, '');
                    if (processedValue.length > 4) {
                        processedValue = processedValue.substring(0, 4);
                    }
                    break;
                case "disabled":
                    processedValue = 0;
                    break;
                case "model_spec":
                    if (processedValue.length > 60) {
                        processedValue = processedValue.substring(0, 60);
                    }
                    break;
                case "cylinder_volume":
                    processedValue = processedValue.replace(/[^\d,.]/g, '');
                    break;
            }

            processedValue = processedValue === "" ? null : processedValue;
            // 避免无限循环:仅当处理后的值与原value不同时才更新
            if (processedValue !== value) {
                this.inputValue = processedValue;
                this.$emit('update:modelValue', processedValue);
            }
        }
    }
}

模板调整

此方案下可以保留@input="ValidateInput",也可以直接移除,因为watch已经会自动监听inputValue的变化。


内容的提问来源于stack exchange,提问作者Anonymous

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.20 16:04:55