正则使用正则表达式:
可以输入数字和小数点后有两位以内的小数: /^(([^0][0-9]+|0)\.([0-9]{1,2})$)|^([^0][0-9]+|0)$/
只能输入非零开头的纯数字: /^([^0][0-9]+|0)$/
只能输入带小数点的小数: /^(([^0][0-9]+|0)\.([0-9]{1,2}))$/
Vue 指令:
directives: {
// 限制只能输入整数
inputInt: {
bind(el, binding, vnode) {
let input = vnode.elm;
input.addEventListener('compositionstart', () => {
vnode.inputLocking = true
})
input.addEventListener('compositionend', () => {
vnode.inputLocking = false
input.dispatchEvent(new Event('input'))
})
input.addEventListener('input', () => {
if(vnode.inputLocking) {
return;
}
let oldValue = input.value;
let newValue = input.value.replace(/[^\d]/g, '');
if(newValue && binding.value !== 'zeroBefore') {
newValue = newValue.replace(/^\b(0+)/gi, '') // 不指定可以以0开头的时候 去掉开头多余的0
}
// 判断是否需要更新,避免进入死循环
if(newValue !== oldValue) {
input.value = newValue
// 通知v-model更新 vue底层双向绑定实现的原理是基于监听input事件
input.dispatchEvent(new Event('input'))
}
})
}
},
// 限制能输入小数点后两位的正小数
inputFloat: {
bind(el, binding, vnode) {
let input = vnode.elm;
input.addEventListener('compositionstart', () => {
vnode.inputLocking = true
})
input.addEventListener('compositionend', () => {
vnode.inputLocking = false
input.dispatchEvent(new Event('input'))
})
input.addEventListener('input', () => {
if(vnode.inputLocking) {
return;
}
let oldValue = input.value;
let newValue = input.value;
newValue = newValue.replace(/[^\d.]/g, '');
newValue = newValue.replace(/^\./g, '');
newValue = newValue.replace('.', '$#$').replace(/\./g, '').replace('$#$', '.');
newValue = newValue.replace(/^(\-)*(\d+)\.(\d\d).*$/, '$1$2.$3')
if(newValue) {
newValue = newValue.replace(/^\b(0+)/gi, '') // 去掉开头多余的0
}
// 判断是否需要更新,避免进入死循环
if(newValue !== oldValue) {
input.value = newValue
input.dispatchEvent(new Event('input')) // 通知v-model更新
}
})
// input 事件无法处理小数点后面全是零的情况 因为无法确定用户输入的0是否真的应该清除,如3.02。放在blur中去处理
input.addEventListener('blur', () => {
let oldValue = input.value;
let newValue = input.value;
if(newValue) {
newValue = Number(newValue).toString()
}
// 判断是否需要更新,避免进入死循环
if(newValue !== oldValue) {
input.value = newValue
input.dispatchEvent(new Event('input')) // 通知v-model更新
}
})
}
}
}