@skyfox2000/webui 1.2.8 → 1.2.9
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/assets/modules/_plugin-vue_export-helper-CHgC5LLL.js +9 -0
- package/lib/assets/modules/file-upload-BYIvmkmy.js +204 -0
- package/lib/assets/modules/form-excel-BUX2QW11.js +235 -0
- package/lib/assets/modules/{index-CTVMLeDF.js → index-DcRkhkn2.js} +1 -1
- package/lib/assets/modules/index-jl5Ie2tZ.js +112 -0
- package/lib/assets/modules/{menuTabs-BtOiocOC.js → menuTabs-DY1XBq16.js} +134 -139
- package/lib/assets/modules/{toolIcon-B9Mw9Ktm.js → toolIcon-BDIOj_3l.js} +1 -1
- package/lib/assets/modules/uploadList-BPG5whz7.js +369 -0
- package/lib/assets/modules/{index-D9kzQ23e.js → uploadList-D2Ux4h1N.js} +553 -513
- package/lib/components/common/index.d.ts +2 -0
- package/lib/components/common/loading/index.vue.d.ts +3 -0
- package/lib/components/content/dialog/index.vue.d.ts +1 -0
- package/lib/components/content/drawer/index.vue.d.ts +2 -0
- package/lib/components/content/form/formItem.vue.d.ts +2 -0
- package/lib/components/form/autoComplete/index.vue.d.ts +41 -4
- package/lib/components/form/cascader/index.vue.d.ts +13 -2
- package/lib/components/form/checkbox/index.vue.d.ts +13 -2
- package/lib/components/form/index.d.ts +1 -0
- package/lib/components/form/propEditor/index.vue.d.ts +10 -1
- package/lib/components/form/radio/index.vue.d.ts +13 -2
- package/lib/components/form/select/index.vue.d.ts +13 -2
- package/lib/components/form/upload/uploadList.vue.d.ts +14 -3
- package/lib/components/index.d.ts +2 -2
- package/lib/es/AceEditor/index.js +3 -3
- package/lib/es/BasicLayout/index.js +15 -15
- package/lib/es/Error403/index.js +1 -1
- package/lib/es/Error404/index.js +1 -1
- package/lib/es/ExcelForm/index.js +4 -4
- package/lib/es/UploadForm/index.js +60 -87
- package/lib/index.d.ts +2 -2
- package/lib/typings/form.d.ts +18 -2
- package/lib/typings/option.d.ts +16 -2
- package/lib/typings/page.d.ts +1 -0
- package/lib/utils/file-upload.d.ts +4 -2
- package/lib/utils/form-excel.d.ts +3 -0
- package/lib/webui.css +1 -1
- package/lib/webui.es.js +1085 -1063
- package/package.json +1 -1
- package/scripts/userInput.py +2 -0
- package/src/components/common/index.ts +3 -0
- package/src/components/common/loading/index.vue +11 -0
- package/src/components/content/dialog/index.vue +15 -8
- package/src/components/content/dialog/uploadForm.vue +38 -79
- package/src/components/content/drawer/index.vue +26 -6
- package/src/components/content/form/formItem.vue +21 -5
- package/src/components/content/form/index.vue +4 -2
- package/src/components/content/search/searchItem.vue +1 -1
- package/src/components/form/autoComplete/index.vue +12 -4
- package/src/components/form/cascader/index.vue +1 -1
- package/src/components/form/datePicker/index.vue +1 -1
- package/src/components/form/index.ts +1 -0
- package/src/components/form/input/inputIcon.vue +1 -1
- package/src/components/form/propEditor/index.vue +113 -33
- package/src/components/form/select/index.vue +27 -17
- package/src/components/form/upload/uploadList.vue +174 -34
- package/src/components/index.ts +13 -1
- package/src/directives/permission.ts +2 -2
- package/src/index.ts +3 -1
- package/src/typings/form.d.ts +18 -2
- package/src/typings/option.d.ts +16 -2
- package/src/typings/page.d.ts +1 -0
- package/src/utils/download.ts +1 -1
- package/src/utils/eventbus.ts +1 -1
- package/src/utils/file-upload.ts +75 -14
- package/src/utils/form-excel.ts +50 -1
- package/src/utils/form-validate.ts +18 -1
- package/src/utils/form.ts +3 -1
- package/src/utils/options.ts +38 -12
- package/lib/assets/modules/file-upload-CZO-pMJd.js +0 -176
- package/lib/assets/modules/form-excel-N-2OYqKv.js +0 -211
- package/lib/assets/modules/index-BnHnS9ug.js +0 -111
- package/lib/assets/modules/uploadList-B4LxzsC6.js +0 -210
package/package.json
CHANGED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { Spin } from 'ant-design-vue';
|
|
3
|
+
import { useAttrs } from 'vue';
|
|
4
|
+
const attrs = useAttrs()
|
|
5
|
+
</script>
|
|
6
|
+
<template>
|
|
7
|
+
<div class="absolute z-999 w-full h-full top-0 flex flex-flow row items-center justify-center">
|
|
8
|
+
<Spin style="margin-top: -10%" v-bind="attrs">
|
|
9
|
+
</Spin>
|
|
10
|
+
</div>
|
|
11
|
+
</template>
|
|
@@ -26,6 +26,10 @@ const props = defineProps<{
|
|
|
26
26
|
* 自定义存储方法
|
|
27
27
|
*/
|
|
28
28
|
dialogSave?: () => void;
|
|
29
|
+
/**
|
|
30
|
+
* 自定义另存为方法
|
|
31
|
+
*/
|
|
32
|
+
dialogSaveAs?: () => void;
|
|
29
33
|
/**
|
|
30
34
|
* 宽度
|
|
31
35
|
*/
|
|
@@ -65,7 +69,7 @@ watch(
|
|
|
65
69
|
(newVal) => {
|
|
66
70
|
emit('update:open', newVal);
|
|
67
71
|
if (!newVal) {
|
|
68
|
-
|
|
72
|
+
doDialogClose();
|
|
69
73
|
}
|
|
70
74
|
},
|
|
71
75
|
);
|
|
@@ -74,14 +78,17 @@ onMounted(() => {
|
|
|
74
78
|
open.value = editorCtrl?.visible.value ?? false;
|
|
75
79
|
});
|
|
76
80
|
|
|
77
|
-
const
|
|
81
|
+
const doDialogSave = () => {
|
|
78
82
|
if (props.dialogSave) {
|
|
83
|
+
props.dialogSave();
|
|
79
84
|
} else if (editorCtrl) onFormSave(editorCtrl);
|
|
80
85
|
};
|
|
81
|
-
const
|
|
82
|
-
if (
|
|
86
|
+
const doDialogSaveAs = () => {
|
|
87
|
+
if (props.dialogSaveAs) {
|
|
88
|
+
props.dialogSaveAs();
|
|
89
|
+
} else if (editorCtrl) onFormSaveAs(editorCtrl);
|
|
83
90
|
};
|
|
84
|
-
const
|
|
91
|
+
const doDialogClose = () => {
|
|
85
92
|
if (editorCtrl) onFormClose(editorCtrl);
|
|
86
93
|
else open.value = false;
|
|
87
94
|
};
|
|
@@ -97,11 +104,11 @@ const dialogClose = () => {
|
|
|
97
104
|
</div>
|
|
98
105
|
<template #footer>
|
|
99
106
|
<Space>
|
|
100
|
-
<Button @click="
|
|
107
|
+
<Button @click="doDialogClose" v-if="cancelText !== ''">
|
|
101
108
|
{{ cancelText ?? '取消' }}
|
|
102
109
|
</Button>
|
|
103
110
|
<Button
|
|
104
|
-
@click="
|
|
111
|
+
@click="doDialogSaveAs"
|
|
105
112
|
v-if="saveAsText !== '' && editorCtrl?.saveAsBtnVisible !== false"
|
|
106
113
|
type="primary"
|
|
107
114
|
:loading="editorCtrl?.isFormSaving.value"
|
|
@@ -109,7 +116,7 @@ const dialogClose = () => {
|
|
|
109
116
|
{{ saveAsText ?? '另存为' }}
|
|
110
117
|
</Button>
|
|
111
118
|
<Button
|
|
112
|
-
@click="
|
|
119
|
+
@click="doDialogSave"
|
|
113
120
|
v-if="saveText !== '' && editorCtrl?.saveBtnVisible !== false"
|
|
114
121
|
type="primary"
|
|
115
122
|
:loading="editorCtrl?.isFormSaving.value"
|
|
@@ -2,18 +2,13 @@
|
|
|
2
2
|
import { watch, ref, onMounted } from 'vue';
|
|
3
3
|
import { Button } from '../../common';
|
|
4
4
|
import { Modal, Space } from 'ant-design-vue';
|
|
5
|
-
import {
|
|
5
|
+
import { EditorControl, GridControl, gridRowUpdate, UploadFile } from '@/index';
|
|
6
6
|
import { AnyData, ApiResponse, IUrlInfo, ResStatus } from '@skyfox2000/fapi';
|
|
7
|
-
import
|
|
7
|
+
import UploadList from '../../form/upload/uploadList.vue';
|
|
8
8
|
import message from 'vue-m-message';
|
|
9
|
+
import { AsyncUploader } from '@/utils/file-upload';
|
|
9
10
|
|
|
10
11
|
const props = defineProps<{
|
|
11
|
-
/**
|
|
12
|
-
* #### 使用模式
|
|
13
|
-
* - Row 数据行
|
|
14
|
-
* - Page 页面
|
|
15
|
-
*/
|
|
16
|
-
mode: 'Row' | 'Page';
|
|
17
12
|
/**
|
|
18
13
|
* 文件后缀限制
|
|
19
14
|
*/
|
|
@@ -69,7 +64,11 @@ const emit = defineEmits<{
|
|
|
69
64
|
/**
|
|
70
65
|
* 上传结束,处理上传后的文件
|
|
71
66
|
*/
|
|
72
|
-
'after:upload': [UploadFile[]];
|
|
67
|
+
'after:upload': [boolean, UploadFile[]];
|
|
68
|
+
/**
|
|
69
|
+
* 上传进度
|
|
70
|
+
*/
|
|
71
|
+
'on:progress': [UploadFile];
|
|
73
72
|
}>();
|
|
74
73
|
|
|
75
74
|
watch(
|
|
@@ -81,73 +80,29 @@ watch(
|
|
|
81
80
|
const uploadUrl = ref(props.uploadUrl);
|
|
82
81
|
const downloadUrl = ref(props.downloadUrl);
|
|
83
82
|
|
|
84
|
-
const
|
|
85
|
-
const url = uploadUrl.value;
|
|
86
|
-
if (!url) {
|
|
87
|
-
message.error('未配置文件上传地址!');
|
|
88
|
-
return;
|
|
89
|
-
}
|
|
90
|
-
|
|
83
|
+
const dialogSave = async () => {
|
|
91
84
|
emit('before:upload', fileList.value);
|
|
92
|
-
const uploader = new AsyncUploader(
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
(files) => {
|
|
106
|
-
uploadFormCtrl.isFormLoading.value = false;
|
|
107
|
-
let err_count = 0;
|
|
108
|
-
for (const file of files) {
|
|
109
|
-
if (file.status === UploadStatus.Error) {
|
|
110
|
-
err_count++;
|
|
85
|
+
const uploader = new AsyncUploader(uploadUrl.value!, maxConcurrent);
|
|
86
|
+
await uploader.doUpload(
|
|
87
|
+
fileList.value,
|
|
88
|
+
uploadFormCtrl.isFormLoading,
|
|
89
|
+
props.continueOnError,
|
|
90
|
+
async (result, files) => {
|
|
91
|
+
emit('after:upload', result, files);
|
|
92
|
+
if (result) {
|
|
93
|
+
if (uploadFormCtrl.formData.value) {
|
|
94
|
+
// 仅修改上传相关字段
|
|
95
|
+
const res: ApiResponse<any> = await gridRowUpdate(props.gridCtrl, uploadFormCtrl.formData.value);
|
|
96
|
+
if (res.status === ResStatus.SUCCESS) {
|
|
97
|
+
uploadFormCtrl.visible.value = false;
|
|
111
98
|
}
|
|
112
99
|
}
|
|
113
|
-
if (!err_count) {
|
|
114
|
-
message.success('全部文件上传成功!');
|
|
115
|
-
emit('after:upload', files);
|
|
116
|
-
dialogSave();
|
|
117
|
-
} else if (err_count < files.length) {
|
|
118
|
-
if (props.continueOnError) {
|
|
119
|
-
message.error('上传结束,部分文件上传失败!');
|
|
120
|
-
message.warning('保存上传成功的文件!');
|
|
121
|
-
emit('after:upload', files);
|
|
122
|
-
dialogSave();
|
|
123
|
-
} else {
|
|
124
|
-
message.error('上传结束,部分文件上传失败,取消保存!');
|
|
125
|
-
}
|
|
126
|
-
} else message.error('上传结束,所有文件上传失败!');
|
|
127
|
-
},
|
|
128
|
-
);
|
|
129
|
-
} catch (error) {
|
|
130
|
-
uploadFormCtrl.isFormLoading.value = false;
|
|
131
|
-
console.error('上传错误:', error);
|
|
132
|
-
message.error('上传错误,请稍后再试!');
|
|
133
|
-
emit('after:upload', fileList.value);
|
|
134
|
-
}
|
|
135
|
-
};
|
|
136
|
-
|
|
137
|
-
const dialogSave = async () => {
|
|
138
|
-
switch (props.mode) {
|
|
139
|
-
case 'Row':
|
|
140
|
-
if (uploadFormCtrl.formData.value) {
|
|
141
|
-
// 仅修改上传相关字段
|
|
142
|
-
const result: ApiResponse<any> = await gridRowUpdate(props.gridCtrl, uploadFormCtrl.formData.value);
|
|
143
|
-
if (result.status === ResStatus.SUCCESS) {
|
|
144
|
-
uploadFormCtrl.visible.value = false;
|
|
145
|
-
}
|
|
146
100
|
}
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
101
|
+
},
|
|
102
|
+
(file) => {
|
|
103
|
+
emit('on:progress', file);
|
|
104
|
+
},
|
|
105
|
+
);
|
|
151
106
|
};
|
|
152
107
|
|
|
153
108
|
onMounted(() => {
|
|
@@ -161,12 +116,10 @@ onMounted(() => {
|
|
|
161
116
|
if (!uploadUrl.value.api) uploadUrl.value.api = pageCtrl.api;
|
|
162
117
|
if (uploadUrl.value.authorize === undefined) uploadUrl.value.authorize = pageCtrl.authorize;
|
|
163
118
|
|
|
164
|
-
if (
|
|
165
|
-
|
|
166
|
-
|
|
119
|
+
if (downloadUrl.value) {
|
|
120
|
+
if (!downloadUrl.value.api) downloadUrl.value.api = pageCtrl.api;
|
|
121
|
+
if (downloadUrl.value.authorize === undefined) downloadUrl.value.authorize = pageCtrl.authorize;
|
|
167
122
|
}
|
|
168
|
-
if (!downloadUrl.value.api) downloadUrl.value.api = pageCtrl.api;
|
|
169
|
-
if (downloadUrl.value.authorize === undefined) downloadUrl.value.authorize = pageCtrl.authorize;
|
|
170
123
|
|
|
171
124
|
for (const key in uploadFormCtrl.formData.value) {
|
|
172
125
|
if (props.gridCtrl.rowData.value) uploadFormCtrl.formData.value[key] = props.gridCtrl.rowData.value[key];
|
|
@@ -189,11 +142,17 @@ const dialogClose = () => {
|
|
|
189
142
|
:wrapClassName="'modal mx-auto ' + ($attrs.width ? 'w-[' + $attrs.width + ']' : 'w-[430px]')"
|
|
190
143
|
@close="dialogClose"
|
|
191
144
|
>
|
|
192
|
-
<UploadList
|
|
145
|
+
<UploadList
|
|
146
|
+
v-model:file-list="fileList"
|
|
147
|
+
:upload-url="uploadUrl!"
|
|
148
|
+
:download-url="downloadUrl"
|
|
149
|
+
:max-count="maxCount"
|
|
150
|
+
:file-ext="fileExt"
|
|
151
|
+
/>
|
|
193
152
|
<template #footer>
|
|
194
153
|
<Space>
|
|
195
154
|
<Button @click="dialogClose">取消</Button>
|
|
196
|
-
<Button @click="
|
|
155
|
+
<Button @click="dialogSave" type="primary" :loading="uploadFormCtrl.isFormSaving.value">
|
|
197
156
|
上传文件并保存
|
|
198
157
|
</Button>
|
|
199
158
|
</Space>
|
|
@@ -33,6 +33,14 @@ const props = defineProps<{
|
|
|
33
33
|
* 保存数据请求配置
|
|
34
34
|
*/
|
|
35
35
|
editorCtrl: EditorControl<AnyData>;
|
|
36
|
+
/**
|
|
37
|
+
* 自定义保存方法
|
|
38
|
+
*/
|
|
39
|
+
drawerSave?: () => void;
|
|
40
|
+
/**
|
|
41
|
+
* 自定义另存为方法
|
|
42
|
+
*/
|
|
43
|
+
drawerSaveAs?: () => void;
|
|
36
44
|
}>();
|
|
37
45
|
|
|
38
46
|
const editorCtrl = props.editorCtrl;
|
|
@@ -49,7 +57,19 @@ onMounted(() => {
|
|
|
49
57
|
open.value = editorCtrl.visible.value ?? false;
|
|
50
58
|
});
|
|
51
59
|
|
|
52
|
-
const
|
|
60
|
+
const doDrawerSave = () => {
|
|
61
|
+
if (props.drawerSave) {
|
|
62
|
+
props.drawerSave();
|
|
63
|
+
} else if (editorCtrl) onFormSave(editorCtrl);
|
|
64
|
+
};
|
|
65
|
+
|
|
66
|
+
const doDrawerSaveAs = () => {
|
|
67
|
+
if (props.drawerSaveAs) {
|
|
68
|
+
props.drawerSaveAs();
|
|
69
|
+
} else if (editorCtrl) onFormSaveAs(editorCtrl);
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
const doDrawerClose = () => {
|
|
53
73
|
onFormClose(editorCtrl);
|
|
54
74
|
};
|
|
55
75
|
</script>
|
|
@@ -74,7 +94,7 @@ const drawerClose = () => {
|
|
|
74
94
|
boxShadow: 'rgba(0, 0, 0, 0.3) -2px 0px 8px',
|
|
75
95
|
}"
|
|
76
96
|
width="420px"
|
|
77
|
-
@close="
|
|
97
|
+
@close="doDrawerClose"
|
|
78
98
|
>
|
|
79
99
|
<template #extra>
|
|
80
100
|
<div class="hover:bg-gray-200 w-[24px] h-[24px] rounded-md">
|
|
@@ -86,7 +106,7 @@ const drawerClose = () => {
|
|
|
86
106
|
clickable
|
|
87
107
|
color="#666"
|
|
88
108
|
:position="[0, 0]"
|
|
89
|
-
@click="
|
|
109
|
+
@click="doDrawerClose"
|
|
90
110
|
/>
|
|
91
111
|
</div>
|
|
92
112
|
</template>
|
|
@@ -95,9 +115,9 @@ const drawerClose = () => {
|
|
|
95
115
|
</template>
|
|
96
116
|
<template #footer>
|
|
97
117
|
<Space>
|
|
98
|
-
<Button @click="
|
|
118
|
+
<Button @click="doDrawerClose" v-if="cancelText !== ''">{{ cancelText ?? '取消' }}</Button>
|
|
99
119
|
<Button
|
|
100
|
-
@click="
|
|
120
|
+
@click="doDrawerSaveAs"
|
|
101
121
|
v-if="saveAsText !== '' && editorCtrl.saveAsBtnVisible !== false"
|
|
102
122
|
type="primary"
|
|
103
123
|
:loading="editorCtrl.isFormSaving.value"
|
|
@@ -105,7 +125,7 @@ const drawerClose = () => {
|
|
|
105
125
|
{{ saveAsText ?? '另存为' }}
|
|
106
126
|
</Button>
|
|
107
127
|
<Button
|
|
108
|
-
@click="
|
|
128
|
+
@click="doDrawerSave"
|
|
109
129
|
v-if="saveText !== '' && editorCtrl.saveBtnVisible !== false"
|
|
110
130
|
type="primary"
|
|
111
131
|
:loading="editorCtrl.isFormSaving.value"
|
|
@@ -22,6 +22,10 @@ const props = defineProps<{
|
|
|
22
22
|
* 宽度
|
|
23
23
|
*/
|
|
24
24
|
width?: string;
|
|
25
|
+
/**
|
|
26
|
+
* 是否显示在独立行
|
|
27
|
+
*/
|
|
28
|
+
nextLine?: boolean;
|
|
25
29
|
}>();
|
|
26
30
|
|
|
27
31
|
// 关闭自动继承属性到根元素
|
|
@@ -31,6 +35,7 @@ defineOptions({
|
|
|
31
35
|
const attrs = useAttrs(); // 手动获取 $attrs
|
|
32
36
|
|
|
33
37
|
const editorCtrl = inject(ProviderKeys.EditorControl, undefined) as EditorControl<AnyData> | undefined;
|
|
38
|
+
const labelWidth = inject(ProviderKeys.LabelWidth, '85px');
|
|
34
39
|
const errInfo = useFormItemFactory(props, editorCtrl);
|
|
35
40
|
|
|
36
41
|
const visible = ref(false);
|
|
@@ -82,18 +87,18 @@ const required = computed(() => {
|
|
|
82
87
|
// });
|
|
83
88
|
</script>
|
|
84
89
|
<template>
|
|
85
|
-
<div :class="['
|
|
90
|
+
<div :class="['relative mb-1']">
|
|
86
91
|
<FormItem
|
|
87
92
|
v-if="visible"
|
|
88
93
|
:required="required"
|
|
89
|
-
class="
|
|
94
|
+
class="relative"
|
|
90
95
|
v-bind="attrs"
|
|
91
|
-
:class="[rule ? '' : 'mb-3']"
|
|
96
|
+
:class="[nextLine ? 'mb-0' : rule ? '' : 'mb-3']"
|
|
92
97
|
>
|
|
93
98
|
<template #label>
|
|
94
99
|
<span :class="[errInfo.errClass ? 'text-[#ff4d4f]' : '', 'w-full']"> {{ label }}</span>
|
|
95
100
|
</template>
|
|
96
|
-
<div class="
|
|
101
|
+
<div class="flex items-center" :class="width ? width : 'w-full'" v-if="!nextLine">
|
|
97
102
|
<div class="flex-grow">
|
|
98
103
|
<slot></slot>
|
|
99
104
|
</div>
|
|
@@ -104,7 +109,18 @@ const required = computed(() => {
|
|
|
104
109
|
</div>
|
|
105
110
|
</div>
|
|
106
111
|
</FormItem>
|
|
107
|
-
<
|
|
112
|
+
<div
|
|
113
|
+
v-if="nextLine"
|
|
114
|
+
class="w-[95%] flex items-center relative"
|
|
115
|
+
:class="[nextLine ? (rule ? 'mb-7' : 'mb-3') : '']"
|
|
116
|
+
>
|
|
117
|
+
<slot></slot>
|
|
118
|
+
</div>
|
|
119
|
+
<span
|
|
120
|
+
:style="{ left: labelWidth }"
|
|
121
|
+
class="absolute bottom-[3px] text-[12px] text-[#ff4d4fcc]"
|
|
122
|
+
v-if="errInfo.errClass"
|
|
123
|
+
>
|
|
108
124
|
{{ errInfo.msg }}
|
|
109
125
|
</span>
|
|
110
126
|
</div>
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
import { EditorControl, ProviderKeys, onFormSave } from '@/index';
|
|
3
3
|
import { AnyData } from '@skyfox2000/fapi';
|
|
4
4
|
import { Form } from 'ant-design-vue';
|
|
5
|
-
import { inject } from 'vue';
|
|
5
|
+
import { inject, provide } from 'vue';
|
|
6
6
|
// 使用以下统一控制表单显示
|
|
7
7
|
// :label-col="{ flex: '60px' }"
|
|
8
8
|
// :wrapper-col="{ flex: '200px' }"
|
|
@@ -24,12 +24,14 @@ const props = defineProps<{
|
|
|
24
24
|
|
|
25
25
|
const editorCtrl =
|
|
26
26
|
props.editorCtrl ?? (inject(ProviderKeys.EditorControl, undefined) as EditorControl<AnyData> | undefined);
|
|
27
|
+
|
|
28
|
+
provide(ProviderKeys.LabelWidth, props.labelWidth);
|
|
27
29
|
</script>
|
|
28
30
|
<template>
|
|
29
31
|
<Form
|
|
30
32
|
:label-col="{ flex: props.labelWidth ?? '85px' }"
|
|
31
33
|
:wrapper-col="{
|
|
32
|
-
flex: props.wrapperWidth ?? '1',
|
|
34
|
+
flex: props.wrapperWidth ?? '1 0 280px',
|
|
33
35
|
}"
|
|
34
36
|
:style="{
|
|
35
37
|
display: 'flex',
|
|
@@ -39,7 +39,7 @@ const errInfo = useFormItemFactory(props, editorCtrl);
|
|
|
39
39
|
<template #label v-if="label">
|
|
40
40
|
<span :class="[errInfo.errClass ? 'text-[#ff4d4f]' : '', 'w-full']"> {{ label }}</span>
|
|
41
41
|
</template>
|
|
42
|
-
<div class="flex items-center">
|
|
42
|
+
<div class="flex items-center w-[90%]">
|
|
43
43
|
<div class="flex-grow pl-1">
|
|
44
44
|
<slot></slot>
|
|
45
45
|
</div>
|
|
@@ -30,7 +30,7 @@ const props = defineProps({
|
|
|
30
30
|
* - 模糊查询
|
|
31
31
|
*/
|
|
32
32
|
searchField: {
|
|
33
|
-
type: String,
|
|
33
|
+
type: [String, Array<string>],
|
|
34
34
|
},
|
|
35
35
|
/**
|
|
36
36
|
* 自定义查询参数
|
|
@@ -105,9 +105,17 @@ const onSearch = (value: string) => {
|
|
|
105
105
|
},
|
|
106
106
|
};
|
|
107
107
|
if (props.searchField) {
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
108
|
+
if (Array.isArray(props.searchField)) {
|
|
109
|
+
props.searchField.forEach((field) => {
|
|
110
|
+
query.Query![field] = {
|
|
111
|
+
$like: '%' + search_value + '%',
|
|
112
|
+
};
|
|
113
|
+
});
|
|
114
|
+
} else {
|
|
115
|
+
query.Query![props.searchField] = {
|
|
116
|
+
$like: '%' + search_value + '%',
|
|
117
|
+
};
|
|
118
|
+
}
|
|
111
119
|
}
|
|
112
120
|
if (props.onsearch) {
|
|
113
121
|
props.onsearch(search_value, query);
|
|
@@ -85,7 +85,7 @@ onUnmounted(() => {
|
|
|
85
85
|
});
|
|
86
86
|
</script>
|
|
87
87
|
<template>
|
|
88
|
-
<div>
|
|
88
|
+
<div class="relative w-[248px] max-w-[248px]">
|
|
89
89
|
<div v-if="!selectOptions.length" class="absolute z-10 mt-[5px] mr-[10px] text-[#999] flex items-center">
|
|
90
90
|
<circleLoading class="text-[#555] mx-[5px] !ml-[10px] !w-4 !h-4" />
|
|
91
91
|
<span>数据加载中...</span>
|
|
@@ -19,8 +19,8 @@ const dateFormat = ref<string>(props.valueFormat ?? 'YYYY-MM-DD');
|
|
|
19
19
|
</script>
|
|
20
20
|
<template>
|
|
21
21
|
<DatePicker
|
|
22
|
-
:class="[errInfo?.errClass === 'error' ? 'error !border-red-300 shadow-[0_0_3px_0px_#ff4d4f]' : '']"
|
|
23
22
|
class="w-full"
|
|
23
|
+
:class="[errInfo?.errClass === 'error' ? 'error !border-red-300 shadow-[0_0_3px_0px_#ff4d4f]' : '']"
|
|
24
24
|
:placeholder="'请选择' + labelText"
|
|
25
25
|
:locale="locale"
|
|
26
26
|
:valueFormat="dateFormat"
|
|
@@ -23,6 +23,7 @@ import InputNumber from './input/inputNumber.vue';
|
|
|
23
23
|
export { InputNumber };
|
|
24
24
|
|
|
25
25
|
import PropEditor from './propEditor/index.vue';
|
|
26
|
+
export type { PropConfigItem } from './propEditor/index.vue';
|
|
26
27
|
export { PropEditor };
|
|
27
28
|
|
|
28
29
|
import Radio from './radio/index.vue';
|
|
@@ -24,7 +24,7 @@ watch(
|
|
|
24
24
|
);
|
|
25
25
|
</script>
|
|
26
26
|
<template>
|
|
27
|
-
<Input
|
|
27
|
+
<Input v-model:value="innerValue" v-bind="$attrs">
|
|
28
28
|
<template #addonBefore>
|
|
29
29
|
<ToolIcon class="!w-4 !h-4" :icon="innerValue" />
|
|
30
30
|
</template>
|