文章目录
前言
使用vue中的自定义指令来实现input框输入限制
- 其中关键代码强制触发input ,来避免,输入规则外的字符时,没触发vue的响应,导致实际值的不一致的问题。
- 使用debounce 来优化性能
具体实现分析
我们定义了一个 Vue 自定义指令,用于限制输入框中的值,以确保符合特定的格式要求。它包括一些关键组件和功能,以下是详细解析:
主要部分
-
导入必要模块和类型定义:
DirectiveBinding
:从 Vue 中导入,用于指令绑定时的类型定义。debounce
:从 lodash 库中导入,用于防抖处理输入事件。App
:从 Vue 中导入,用于 Vue 应用实例的类型定义。
-
定义
InputElement
接口:InputElement
接口扩展了HTMLInputElement
,增加了_validateInput
可选属性,用于存储验证函数。
-
定义
inputRestrictions
指令:mounted
钩子函数:在指令绑定到元素时触发,设置输入验证逻辑。unmounted
钩子函数:在指令从元素上解绑时触发,清除事件监听器。
详细解析
typescript
import { DirectiveBinding } from 'vue'
import { debounce } from 'lodash'
import type { App } from 'vue'
interface InputElement extends HTMLInputElement {
_validateInput?: (event: Event) => void
}
导入和类型定义
- 从
vue
和lodash
库中导入必要的类型和工具函数。 - 定义
InputElement
接口,扩展HTMLInputElement
以包含_validateInput
属性。
typescript
const inputRestrictions = {
mounted(el: InputElement, binding: DirectiveBinding) {
const validateInput = debounce((event: Event) => {
let value = (event.target as HTMLInputElement)?.value
if (value === undefined || value === null) {
value = ''
}
const restrictionType = binding.value
switch (restrictionType) {
case 'positiveDecimal':
value = value
.replace(/[^\d.]/g, '') // 删除非数字和非小数点字符
.replace(/^\./, '') // 删除开头的小数点
.replace(/\.{2,}/, '.') // 限制多个小数点
.replace('.', '$#$')
.replace(/\./g, '')
.replace('$#$', '.')
.replace(/^(\-)*(\d+)\.(\d\d).*$/, '$1$2.$3') // 保留两位小数点
case 'positiveInteger':
value = value.replace(/[^\d]/g, '') // 删除非数字字符
if (value === '0') {
value = ''
}
break
case 'customRestriction':
// 你的自定义限制逻辑
break
default:
break
}
if (event.target) {
(event.target as HTMLInputElement).value = value
}
event.target?.dispatchEvent(new Event('input')) // 关键代码 触发 input 事件更新 v-model
}, 300) // 300 毫秒的防抖延迟
el._validateInput = validateInput
el.addEventListener('input', validateInput)
},
unmounted(el: InputElement) {
if (el._validateInput) {
el.removeEventListener('input', el._validateInput)
}
}
}
mounted
钩子函数
- 防抖处理 :使用 lodash 的
debounce
函数创建validateInput
函数,防止在短时间内多次触发输入验证。 - 输入验证逻辑 :
- 根据
binding.value
确定的restrictionType
选择不同的验证逻辑:positiveDecimal
:允许输入正整数和最多两个小数点,去除多余字符。positiveInteger
:只允许输入正整数,去除非数字字符。customRestriction
:为将来可能的自定义限制保留。
- 根据
- 更新输入值 :在修改输入值后,触发
input
事件以确保 Vue 的双向绑定更新。
unmounted
钩子函数
- 清除事件监听器 :在指令解绑时,移除
input
事件监听器,防止内存泄漏。
typescript
const setupInputRestrictions = (app: App<Element>) => {
app.directive('inputRestrictions', inputRestrictions)
}
export default setupInputRestrictions
指令注册
- 定义
setupInputRestrictions
函数,用于将inputRestrictions
指令注册到 Vue 应用实例中。
使用
html
<el-input
v-model="variable.mainForm.xxx"
v-input-restrictions="'positiveInteger'"
placeholder="Please input positive Integer"
/>
总结
实现了一个 Vue 自定义指令,用于限制输入框中的值,确保输入符合特定格式(如正整数或带最多两位小数的正数)。通过防抖处理和自定义验证逻辑,避免了频繁的输入事件处理,同时确保输入值的实时验证和更新。