技术栈:Vue3+TypeScript+Ant Design Vue
因实际业务需求,频繁需要使用手机号输入,包含区号的选择。
简介
此组件为区号、手机号输入组件,开放出常用配置项与onChange事件。可单独使用,也可以结合表单使用。
Vue布局
<template>
<div>
<a-input-group compact>
<a-select
v-model:value="currCode"
:disabled="isDisabledCode"
:size="size"
style="width: 90px"
option-label-prop="dialCode"
:options="countryCode"
:field-names="{ label: 'label', value: 'selectedLabel' }"
popup-class-name="areaCodeDropdown"
@change="onChange"
>
<template #option="{ label }">
{{ label }}
</template>
</a-select>
<a-input
v-model:value="currPhone"
:disabled="isDisabledPhone"
:size="size"
class="areaCodePhoneInput"
:placeholder="isUndefined(placeholder) ? '' : placeholder"
:maxlength="11"
:allow-clear="isUndefined(allowClear) ? true : allowClear"
@change="onChange"
/>
</a-input-group>
</div>
</template>
TS逻辑
主要逻辑文件
<script lang="ts">
import { defineComponent, ref } from 'vue';
import { phoneCode } from '@/config/configData';
import { isUndefined } from '@/utils/common';
import type { ObjectT } from '@/config/interface';
export default defineComponent({
name: 'AreaPhone',
components: {},
props: {
// 区号字段
code: {
type: Number,
default: 86,
},
// 禁用区号选择
isDisabledCode: {
type: Boolean,
default: false,
},
// 手机号字段
phone: {
type: String,
},
// 禁用手机号输入
isDisabledPhone: {
type: Boolean,
default: false,
},
// 组件尺寸
size: {
type: String,
},
// 输入提示
placeholder: {
type: String,
},
// 允许清空手机号输入框
allowClear: {
type: Boolean,
},
},
emits: ['onChange'],
setup(props, context) {
// 区号
const currCode = ref(`+${props.code}`);
// 手机号
const currPhone = ref(props.phone);
/** 区号或手机号修改时触发 */
const onChange = () => {
context.emit('onChange', {
code: Number(currCode.value.split('+')[1]),
phone: currPhone.value,
});
};
/** 处理成需要的数据结构 */
const countryCode = phoneCode.map((item: ObjectT) => {
return {
value: item.dialCode,
label: `+${item.dialCode} ${item.name}`,
selectedLabel: `+${item.dialCode}`,
};
});
/** 表单重置 */
const resetPhone = () => {
currCode.value = `+${props.code}`;
currPhone.value = props.phone;
};
return {
currCode,
currPhone,
countryCode,
onChange,
isUndefined,
resetPhone,
};
},
});
</script>
配置文件
区号可选项
configData.ts中区号可选项的内容非常多,此处只写几个用于示例
export const phoneCode = [
{
code: 'af',
name: 'Afghanistan (افغانستان)',
dialCode: 93,
phoneFormat: '070 123 4567',
CNName: '阿富汗',
},
{
code: 'al',
name: 'Albania (Shqipëri)',
dialCode: 355,
phoneFormat: '066 123 4567',
CNName: '阿尔巴尼亚',
},
{
code: 'cn',
name: 'China (中国)',
dialCode: 86,
phoneFormat: '131 2345 6789',
CNName: '中国',
},
]
公共方法
common.ts中 isUndefined
// 是否未定义
export const isUndefined = (val: any) => {
return typeof val === 'undefined';
};
类型检测
export interface ObjectT {
[propName: string]: any // 额外类型检查
}
scss样式
.areaCodeDropdown {
width: 410px !important;
}
.areaCodePhoneInput {
width: calc(100% - 89px);
}
组件应用
<template>
<div>
<CodePhone :code="code" :phone="phone" placeholder="手机号" @onChange="onChangePhone"/>
</div>
</template>
<script setup lang='ts'>
import CodePhone from '@/components/CodePhone.vue';
import { ref } from 'vue';
const code = ref(86);
const phone = ref('2131');
const onChangePhone = (data: { code: number; phone: string}) => {
console.log('code and phone',data.code, data.phone)
}
</script>