|
@@ -1,6 +1,6 @@
|
|
|
<!-- 组件使用文档: https://gitee.com/zuohuaijun/Admin.NET/pulls/1559 -->
|
|
<!-- 组件使用文档: https://gitee.com/zuohuaijun/Admin.NET/pulls/1559 -->
|
|
|
<script setup lang="ts">
|
|
<script setup lang="ts">
|
|
|
-import { reactive, watch } from 'vue';
|
|
|
|
|
|
|
+import { reactive, watch, PropType } from 'vue';
|
|
|
import { DictItem } from '/@/types/global';
|
|
import { DictItem } from '/@/types/global';
|
|
|
import { useUserInfo } from '/@/stores/userInfo';
|
|
import { useUserInfo } from '/@/stores/userInfo';
|
|
|
|
|
|
|
@@ -8,8 +8,8 @@ const emit = defineEmits(['update:modelValue']);
|
|
|
const dictList = useUserInfo().dictList;
|
|
const dictList = useUserInfo().dictList;
|
|
|
const props = defineProps({
|
|
const props = defineProps({
|
|
|
modelValue: {
|
|
modelValue: {
|
|
|
- type: [String, Number, Boolean, null],
|
|
|
|
|
- default: null,
|
|
|
|
|
|
|
+ type: [String, Number, Boolean, Array, null],
|
|
|
|
|
+ default: null,
|
|
|
required: true,
|
|
required: true,
|
|
|
},
|
|
},
|
|
|
code: {
|
|
code: {
|
|
@@ -28,21 +28,25 @@ const props = defineProps({
|
|
|
type: Function,
|
|
type: Function,
|
|
|
default: (dict: any): boolean => dict,
|
|
default: (dict: any): boolean => dict,
|
|
|
},
|
|
},
|
|
|
- onItemFormatter: {
|
|
|
|
|
- type: Function as (dict: any) => (string | undefined | null),
|
|
|
|
|
- default: () => undefined
|
|
|
|
|
- },
|
|
|
|
|
|
|
+ onItemFormatter: {
|
|
|
|
|
+ type: Function as PropType<(dict: any) => string | undefined | null>,
|
|
|
|
|
+ default: () => undefined,
|
|
|
|
|
+ },
|
|
|
renderAs: {
|
|
renderAs: {
|
|
|
type: String,
|
|
type: String,
|
|
|
default: 'tag',
|
|
default: 'tag',
|
|
|
validator(value: string) {
|
|
validator(value: string) {
|
|
|
- return ['tag', 'select', 'radio'].includes(value);
|
|
|
|
|
|
|
+ return ['tag', 'select', 'radio', 'checkbox'].includes(value);
|
|
|
},
|
|
},
|
|
|
},
|
|
},
|
|
|
|
|
+ multiple: {
|
|
|
|
|
+ type: Boolean,
|
|
|
|
|
+ default: false,
|
|
|
|
|
+ },
|
|
|
});
|
|
});
|
|
|
|
|
|
|
|
const state = reactive({
|
|
const state = reactive({
|
|
|
- dict: {} as DictItem | undefined,
|
|
|
|
|
|
|
+ dict: {} as DictItem | DictItem[] | undefined,
|
|
|
dictData: [] as DictItem[],
|
|
dictData: [] as DictItem[],
|
|
|
value: null as any,
|
|
value: null as any,
|
|
|
});
|
|
});
|
|
@@ -50,8 +54,22 @@ const state = reactive({
|
|
|
const setDictValue = (value: any) => {
|
|
const setDictValue = (value: any) => {
|
|
|
state.value = value;
|
|
state.value = value;
|
|
|
state.dictData = dictList[props.code]?.filter(props.onItemFilter) ?? [];
|
|
state.dictData = dictList[props.code]?.filter(props.onItemFilter) ?? [];
|
|
|
- state.dict = state.dictData.find((x: any) => x[props.propValue] == state.value);
|
|
|
|
|
- if (state.dict && !['success', 'warning', 'info', 'primary', 'danger'].includes(state.dict.tagType ?? '')) state.dict.tagType = 'primary';
|
|
|
|
|
|
|
+
|
|
|
|
|
+ if (Array.isArray(value)) {
|
|
|
|
|
+ state.dict = state.dictData.filter((x: any) => value.includes(x[props.propValue]));
|
|
|
|
|
+ if (state.dict) {
|
|
|
|
|
+ state.dict.forEach((item: any) => {
|
|
|
|
|
+ if (!['success', 'warning', 'info', 'primary', 'danger'].includes(item.tagType ?? '')) {
|
|
|
|
|
+ item.tagType = 'primary';
|
|
|
|
|
+ }
|
|
|
|
|
+ });
|
|
|
|
|
+ }
|
|
|
|
|
+ } else {
|
|
|
|
|
+ state.dict = state.dictData.find((x: any) => x[props.propValue] == state.value);
|
|
|
|
|
+ if (state.dict && !['success', 'warning', 'info', 'primary', 'danger'].includes((state.dict as DictItem).tagType ?? '')) {
|
|
|
|
|
+ (state.dict as DictItem).tagType = 'primary';
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
};
|
|
};
|
|
|
|
|
|
|
|
watch(
|
|
watch(
|
|
@@ -64,19 +82,38 @@ watch(
|
|
|
<template>
|
|
<template>
|
|
|
<!-- 渲染标签 -->
|
|
<!-- 渲染标签 -->
|
|
|
<template v-if="props.renderAs === 'tag'">
|
|
<template v-if="props.renderAs === 'tag'">
|
|
|
- <el-tag v-if="state.dict" v-bind="$attrs" :type="state.dict.tagType" :style="state.dict.styleSetting" :class="state.dict.classSetting">{{ onItemFormatter(state.dict) ?? state.dict[props.propLabel] }}</el-tag>
|
|
|
|
|
- <span v-else>{{ state.value }}</span>
|
|
|
|
|
|
|
+ <template v-if="Array.isArray(state.dict)">
|
|
|
|
|
+ <el-tag v-for="(item, index) in state.dict" :key="index" v-bind="$attrs" :type="item.tagType" :style="item.styleSetting" :class="item.classSetting" class="mr-1">
|
|
|
|
|
+ {{ onItemFormatter(item) ?? item[props.propLabel] }}
|
|
|
|
|
+ </el-tag>
|
|
|
|
|
+ </template>
|
|
|
|
|
+ <template v-else>
|
|
|
|
|
+ <el-tag v-if="state.dict" v-bind="$attrs" :type="state.dict.tagType" :style="state.dict.styleSetting" :class="state.dict.classSetting">
|
|
|
|
|
+ {{ onItemFormatter(state.dict) ?? state.dict[props.propLabel] }}
|
|
|
|
|
+ </el-tag>
|
|
|
|
|
+ <span v-else>{{ state.value }}</span>
|
|
|
|
|
+ </template>
|
|
|
</template>
|
|
</template>
|
|
|
<!-- 渲染选择器 -->
|
|
<!-- 渲染选择器 -->
|
|
|
<template v-if="props.renderAs === 'select'">
|
|
<template v-if="props.renderAs === 'select'">
|
|
|
- <el-select v-model="state.value" v-bind="$attrs" @change="(newValue: any) => emit('update:modelValue', newValue)">
|
|
|
|
|
- <el-option :label="onItemFormatter(item) ?? item[props.propLabel]" :value="item[props.propValue]" v-for="(item, index) in state.dictData" :key="index" />
|
|
|
|
|
|
|
+ <el-select v-model="state.value" v-bind="$attrs" :multiple="props.multiple" @change="(newValue: any) => emit('update:modelValue', newValue)">
|
|
|
|
|
+ <el-option v-for="(item, index) in state.dictData" :key="index" :label="onItemFormatter(item) ?? item[props.propLabel]" :value="item[props.propValue]" />
|
|
|
</el-select>
|
|
</el-select>
|
|
|
</template>
|
|
</template>
|
|
|
|
|
+ <!-- 渲染复选框(多选) -->
|
|
|
|
|
+ <template v-if="props.renderAs === 'checkbox'">
|
|
|
|
|
+ <el-checkbox-group v-model="state.value" v-bind="$attrs" @change="(newValue: any) => emit('update:modelValue', newValue)">
|
|
|
|
|
+ <el-checkbox v-for="(item, index) in state.dictData" :key="index" :label="item[props.propValue]">
|
|
|
|
|
+ {{ onItemFormatter(item) ?? item[props.propLabel] }}
|
|
|
|
|
+ </el-checkbox>
|
|
|
|
|
+ </el-checkbox-group>
|
|
|
|
|
+ </template>
|
|
|
<!-- 渲染单选框 -->
|
|
<!-- 渲染单选框 -->
|
|
|
<template v-if="props.renderAs === 'radio'">
|
|
<template v-if="props.renderAs === 'radio'">
|
|
|
<el-radio-group v-model="state.value" v-bind="$attrs" @change="(newValue: any) => emit('update:modelValue', newValue)">
|
|
<el-radio-group v-model="state.value" v-bind="$attrs" @change="(newValue: any) => emit('update:modelValue', newValue)">
|
|
|
- <el-radio :value="item[props.propValue]" v-for="(item, index) in state.dictData" :key="index">{{ onItemFormatter(item) ?? item[props.propLabel] }}</el-radio>
|
|
|
|
|
|
|
+ <el-radio v-for="(item, index) in state.dictData" :key="index" :value="item[props.propValue]">
|
|
|
|
|
+ {{ onItemFormatter(item) ?? item[props.propLabel] }}
|
|
|
|
|
+ </el-radio>
|
|
|
</el-radio-group>
|
|
</el-radio-group>
|
|
|
</template>
|
|
</template>
|
|
|
</template>
|
|
</template>
|