编写带千位分隔符的整数正则,解决Vue v-mask数字显示异常问题
问题原因
你当前使用的是固定位置的静态掩码数组,v-mask 会从左到右依次匹配你定义的占位符规则,自然会把前两位数字放在第一个小数点前,和千位分隔符从右往左每3位加一个分隔符的逻辑完全相悖,所以才会出现错位问题。
解决方案
不要用固定数组的静态掩码,改用以下两种适配千位分隔符规则的实现方式:
方案1:自定义格式化逻辑(兼容性最好)
模板部分修改为:
<v-text-field v-model="displayValue" @input="formatNumber" />
Script 逻辑:
export default { data() { return { rawValue: '', // 存储纯数字原始值,表单提交直接用该字段 displayValue: '' // 存储带千位分隔符的显示值 } }, methods: { formatNumber(input) { // 过滤所有非数字字符,保证仅匹配整数 this.rawValue = input.replace(/\D/g, '') // 从右往左每3位插入点作为千位分隔符 this.displayValue = this.rawValue.replace(/\B(?=(\d{3})+(?!\d))/g, '.') } } }
核心正则/\B(?=(\d{3})+(?!\d))/g会自动匹配需要插入分隔符的位置,输入5123456时会直接输出5.123.456的预期效果。
方案2:Vuetify 动态掩码函数(需 Vuetify 2.6+ 版本支持)
如果要继续使用v-mask属性,可以改成动态生成掩码的函数形式:
<v-text-field v-model="value" :v-mask="numberMask" />
Script 逻辑:
export default { computed: { numberMask() { const pureNum = this.value.replace(/\D/g, '') const mask = [] let remainingLen = pureNum.length // 从右往左计算分隔符位置,动态生成掩码数组 while (remainingLen > 0) { if (remainingLen % 3 === 0 && remainingLen !== pureNum.length) { mask.push('.') } mask.push(/\d/) remainingLen-- } return mask } } }
内容的提问来源于stack exchange,提问作者Alan
相关产品推荐
相关产品推荐

