主要的两个步骤
- 自定义组件创建 props属性 modelValue
- 自定义组件触发
update:modelValue
事件,并把值传出去
<template>
<div class="validate-input-container pb-3">
<input
class="form-control"
:class="{'is-invalid':inputRef.error}"
:value="inputRef.val"
@blur="validateEmail"
@input="updateValue"
>
<div class="invalid-feedback" v-if="inputRef.error">
{{inputRef.message}}
</div>
</div>
</template>
<script lang="ts">
import { defineComponent, reactive, PropType } from 'vue'
const emailReg = /^[A-Za-z\d]+([-_.][A-Za-z\d]+)*@([A-Za-z\d]+[-.])+[A-Za-z\d]{2,4}$/
interface RuleProp {
type: 'required' | 'email'
message: string
}
export type RulesProp = RuleProp[]
export default defineComponent({
name: 'ValidateInput',
props: {
rules: Array as PropType<RulesProp>,
modelValue: String
},
setup (props, context) {
const inputRef = reactive({
val: props.modelValue || '',
error: false,
message: ''
})
const updateValue = (e:KeyboardEvent) => {
const targetValue = (e.target as HTMLInputElement).value
inputRef.val = targetValue
context.emit('update:modelValue', targetValue)
}
const validateEmail = () => {
if (props.rules) {
// 因为需要每个规则都通过才可以,所以用数组的every方法
const allPassed = props.rules.every(rule => {
let passed = true
inputRef.message = rule.message
switch (rule.type) {
case 'required':
passed = (inputRef.val.trim() !== '')
break
case 'email':
passed = emailReg.test(inputRef.val.trim())
break
default:
break
}
return passed
})
inputRef.error = !allPassed
}
}
return {
inputRef,
validateEmail,
updateValue
}
}
})
</script>
然后就是调用组件的地方 v-model就可以使用了
<template>
<div class="container">
<global-header :user="currentUser"></global-header>
<form>
<div class="mb-3">
<label for="exampleInputEmail1" class="form-label">邮箱地址</label>
<validate-input :rules="emailRules" v-model="emailVal"></validate-input>
{{emailVal}}
</div>
</form>
</div>
</template>
<script lang="ts">
import { defineComponent, reactive, ref } from 'vue'
import 'bootstrap/dist/css/bootstrap.min.css'
import GlobalHeader, { UserProps } from './components/GlobalHeader.vue'
import ValidateInput, { RulesProp } from './components/ValidateInput.vue'
const currentUser:UserProps = {
isLogin: true,
name: 'weiyang'
}
export default defineComponent({
name: 'App',
components: {
GlobalHeader,
ValidateInput
},
setup () {
const emailVal = ref('weiyang')
const emailRules: RulesProp = [
{ type: 'required', message: '电子邮箱地址不能为空' },
{ type: 'email', message: '请输入正确的电子邮箱格式' }
]
return {
currentUser,
emailRules,
emailVal
}
}
})
</script>
<style>
</style>
网友评论