Browse Source
- 添加 Select 组件以支持下拉列表功能 - 在 DataFormConstant 中替换原有的 ElSelect 为自定义 Select - 在示例页面 DataForm01 中添加 Select 组件的使用master
3 changed files with 106 additions and 3 deletions
@ -0,0 +1,96 @@ |
|||||
|
<script setup lang="ts"> |
||||
|
import lodash from "lodash"; |
||||
|
import { computed, createVNode, defineExpose, onMounted, reactive, useAttrs, useSlots, useTemplateRef } from "vue"; |
||||
|
import { ElOption, ElSelect } from "element-plus"; |
||||
|
import { Typeof } from "@ease-forge/shared"; |
||||
|
import { mergeExpose } from "../DataFormUtils.tsx"; |
||||
|
|
||||
|
defineOptions({ |
||||
|
name: 'Select', |
||||
|
}); |
||||
|
|
||||
|
// 组件属性 |
||||
|
const attrs = useAttrs(); |
||||
|
// 组件插槽 |
||||
|
const slots = useSlots(); |
||||
|
|
||||
|
interface OptionItem { |
||||
|
value: string | number | boolean; |
||||
|
label: string; |
||||
|
|
||||
|
[key: string]: any; |
||||
|
} |
||||
|
|
||||
|
// 定义 Props 类型 |
||||
|
interface SelectProps { |
||||
|
options?: Array<OptionItem>; |
||||
|
} |
||||
|
|
||||
|
// 读取组件 props 属性 |
||||
|
const props = withDefaults(defineProps<SelectProps>(), { |
||||
|
options: () => ([]), |
||||
|
}); |
||||
|
|
||||
|
// 定义 State 类型 |
||||
|
interface SelectState { |
||||
|
} |
||||
|
|
||||
|
// state 属性 |
||||
|
const state = reactive<SelectState>({ |
||||
|
loading: false, |
||||
|
}); |
||||
|
// 输入组件实例 |
||||
|
const input = useTemplateRef<InstanceType<typeof ElSelect>>("inputRef"); |
||||
|
// 选项数据 |
||||
|
const options = computed(() => { |
||||
|
let opts: Array<OptionItem> = []; |
||||
|
let options = props.options; |
||||
|
if (options) { |
||||
|
if (Typeof.isArray(options)) { |
||||
|
opts = options; |
||||
|
} else { |
||||
|
console.log("options 配置必须是数组类型"); |
||||
|
} |
||||
|
} |
||||
|
return opts; |
||||
|
}); |
||||
|
// 输入组件 props 属性 |
||||
|
const inputProps = computed<any>(() => { |
||||
|
const res: any = { ...attrs }; |
||||
|
if (Typeof.hasValue(res.modelValue) && !Typeof.isStr(res.modelValue)) res.modelValue = lodash.toString(res.modelValue); |
||||
|
return res; |
||||
|
}); |
||||
|
|
||||
|
function toString(val: any) { |
||||
|
if (Typeof.hasValue(val) && !Typeof.isStr(val)) return lodash.toString(val); |
||||
|
return val; |
||||
|
} |
||||
|
|
||||
|
const expose = { |
||||
|
/** 组件状态 */ |
||||
|
state, |
||||
|
}; |
||||
|
|
||||
|
onMounted(() => { |
||||
|
if (input.value) mergeExpose(expose, input.value); |
||||
|
}); |
||||
|
|
||||
|
// 定义组件公开内容 |
||||
|
defineExpose(expose); |
||||
|
|
||||
|
export type { |
||||
|
OptionItem, |
||||
|
SelectProps, |
||||
|
SelectState, |
||||
|
} |
||||
|
</script> |
||||
|
|
||||
|
<template> |
||||
|
<component ref="inputRef" :is="createVNode(ElSelect, inputProps, slots)"> |
||||
|
<ElOption v-for="(item, idx) in options" v-bind="item" :value="toString(item.value)"/> |
||||
|
</component> |
||||
|
</template> |
||||
|
|
||||
|
<style scoped> |
||||
|
|
||||
|
</style> |
||||
Loading…
Reference in new issue