Commit 815250ed341ccaec23e7ea34db6cc478a47ad065
1 parent
c8ef82b2
fix: update upload component
Showing
7 changed files
with
183 additions
and
34 deletions
src/components/Upload/src/FileList.less
0 → 100644
1 | +@import (reference) '../../../design/index.less'; | ||
2 | + | ||
3 | +.file-table { | ||
4 | + width: 100%; | ||
5 | + border-collapse: collapse; | ||
6 | + // border: 1px solid @border-color-light; | ||
7 | + | ||
8 | + .center { | ||
9 | + text-align: center; | ||
10 | + } | ||
11 | + | ||
12 | + .left { | ||
13 | + text-align: left; | ||
14 | + } | ||
15 | + | ||
16 | + .right { | ||
17 | + text-align: right; | ||
18 | + } | ||
19 | + | ||
20 | + &-th, | ||
21 | + &-td { | ||
22 | + padding: 12px 8px; | ||
23 | + } | ||
24 | + | ||
25 | + thead { | ||
26 | + background-color: @background-color-dark; | ||
27 | + } | ||
28 | + | ||
29 | + table, | ||
30 | + td, | ||
31 | + th { | ||
32 | + border: 1px solid @border-color-light; | ||
33 | + } | ||
34 | +} |
src/components/Upload/src/FileList.tsx
0 → 100644
1 | +import { defineComponent } from 'vue'; | ||
2 | +import { fileListProps } from './props'; | ||
3 | +import { isFunction } from '/@/utils/is'; | ||
4 | +import './FileList.less'; | ||
5 | + | ||
6 | +export default defineComponent({ | ||
7 | + name: 'FileList', | ||
8 | + props: fileListProps, | ||
9 | + setup(props) { | ||
10 | + return () => { | ||
11 | + const { columns, actionColumn, dataSource } = props; | ||
12 | + | ||
13 | + return ( | ||
14 | + <table class="file-table"> | ||
15 | + <colgroup> | ||
16 | + {[...columns, actionColumn].map((item) => { | ||
17 | + const { width = 0 } = item; | ||
18 | + return width ? ( | ||
19 | + <col style={'width:' + width + 'px;min-width:' + width + 'px;'} /> | ||
20 | + ) : ( | ||
21 | + <col /> | ||
22 | + ); | ||
23 | + })} | ||
24 | + </colgroup> | ||
25 | + <thead> | ||
26 | + <tr class="file-table-tr"> | ||
27 | + {[...columns, actionColumn].map((item) => { | ||
28 | + const { title = '', align = 'center' } = item; | ||
29 | + return <th class={['file-table-th', align]}>{title}</th>; | ||
30 | + })} | ||
31 | + </tr> | ||
32 | + </thead> | ||
33 | + <tbody> | ||
34 | + {dataSource.map((record = {}) => { | ||
35 | + return ( | ||
36 | + <tr class="file-table-tr"> | ||
37 | + {[...columns, actionColumn].map((item) => { | ||
38 | + const { dataIndex = '', customRender, align = 'center' } = item; | ||
39 | + if (customRender && isFunction(customRender)) { | ||
40 | + return ( | ||
41 | + <td class={['file-table-td', align]}> | ||
42 | + {customRender({ text: record[dataIndex], record })} | ||
43 | + </td> | ||
44 | + ); | ||
45 | + } else { | ||
46 | + return <td class={['file-table-td', align]}>{record[dataIndex]}</td>; | ||
47 | + } | ||
48 | + })} | ||
49 | + </tr> | ||
50 | + ); | ||
51 | + })} | ||
52 | + </tbody> | ||
53 | + </table> | ||
54 | + ); | ||
55 | + }; | ||
56 | + }, | ||
57 | +}); |
src/components/Upload/src/UploadModal.vue
@@ -23,24 +23,25 @@ | @@ -23,24 +23,25 @@ | ||
23 | {{ getUploadBtnText }} | 23 | {{ getUploadBtnText }} |
24 | </a-button> | 24 | </a-button> |
25 | </template> | 25 | </template> |
26 | - | ||
27 | - <BasicTable @register="registerTable" :dataSource="fileListRef"> | ||
28 | - <template #toolbar> | ||
29 | - <Upload :accept="getStringAccept" :multiple="multiple" :before-upload="beforeUpload"> | ||
30 | - <a-button type="primary"> 选择文件 </a-button> | ||
31 | - </Upload> | ||
32 | - </template> | ||
33 | - <template #tableTitle> | ||
34 | - <Alert :message="getHelpText" type="info" banner></Alert> | ||
35 | - </template> | ||
36 | - </BasicTable> | 26 | + <div class="upload-modal-toolbar"> |
27 | + <Alert :message="getHelpText" type="info" banner class="upload-modal-toolbar__text"></Alert> | ||
28 | + <Upload | ||
29 | + :accept="getStringAccept" | ||
30 | + :multiple="multiple" | ||
31 | + :before-upload="beforeUpload" | ||
32 | + class="upload-modal-toolbar__btn" | ||
33 | + > | ||
34 | + <a-button type="primary"> 选择文件 </a-button> | ||
35 | + </Upload> | ||
36 | + </div> | ||
37 | + <FileList :dataSource="fileListRef" :columns="columns" :actionColumn="actionColumn" /> | ||
37 | </BasicModal> | 38 | </BasicModal> |
38 | </template> | 39 | </template> |
39 | <script lang="ts"> | 40 | <script lang="ts"> |
40 | import { defineComponent, reactive, ref, toRefs, unref, computed } from 'vue'; | 41 | import { defineComponent, reactive, ref, toRefs, unref, computed } from 'vue'; |
41 | import { Upload, Alert } from 'ant-design-vue'; | 42 | import { Upload, Alert } from 'ant-design-vue'; |
42 | import { BasicModal, useModalInner } from '/@/components/Modal'; | 43 | import { BasicModal, useModalInner } from '/@/components/Modal'; |
43 | - import { BasicTable, useTable } from '/@/components/Table'; | 44 | + // import { BasicTable, useTable } from '/@/components/Table'; |
44 | // hooks | 45 | // hooks |
45 | import { useUploadType } from './useUpload'; | 46 | import { useUploadType } from './useUpload'; |
46 | import { useMessage } from '/@/hooks/web/useMessage'; | 47 | import { useMessage } from '/@/hooks/web/useMessage'; |
@@ -55,9 +56,9 @@ | @@ -55,9 +56,9 @@ | ||
55 | import { uploadApi } from '/@/api/sys/upload'; | 56 | import { uploadApi } from '/@/api/sys/upload'; |
56 | import { isFunction } from '/@/utils/is'; | 57 | import { isFunction } from '/@/utils/is'; |
57 | import { warn } from '/@/utils/log'; | 58 | import { warn } from '/@/utils/log'; |
58 | - | 59 | + import FileList from './FileList'; |
59 | export default defineComponent({ | 60 | export default defineComponent({ |
60 | - components: { BasicModal, Upload, BasicTable, Alert }, | 61 | + components: { BasicModal, Upload, Alert, FileList }, |
61 | props: basicProps, | 62 | props: basicProps, |
62 | setup(props, { emit }) { | 63 | setup(props, { emit }) { |
63 | // 是否正在上传 | 64 | // 是否正在上传 |
@@ -257,23 +258,25 @@ | @@ -257,23 +258,25 @@ | ||
257 | } | 258 | } |
258 | } | 259 | } |
259 | 260 | ||
260 | - const [registerTable] = useTable({ | 261 | + // const [registerTable] = useTable({ |
262 | + // columns: createTableColumns(), | ||
263 | + // actionColumn: createActionColumn(handleRemove, handlePreview), | ||
264 | + // pagination: false, | ||
265 | + // inset: true, | ||
266 | + // scroll: { | ||
267 | + // y: 3000, | ||
268 | + // }, | ||
269 | + // }); | ||
270 | + return { | ||
261 | columns: createTableColumns(), | 271 | columns: createTableColumns(), |
262 | actionColumn: createActionColumn(handleRemove, handlePreview), | 272 | actionColumn: createActionColumn(handleRemove, handlePreview), |
263 | - pagination: false, | ||
264 | - inset: true, | ||
265 | - scroll: { | ||
266 | - y: 3000, | ||
267 | - }, | ||
268 | - }); | ||
269 | - return { | ||
270 | register, | 273 | register, |
271 | closeModal, | 274 | closeModal, |
272 | getHelpText, | 275 | getHelpText, |
273 | getStringAccept, | 276 | getStringAccept, |
274 | getOkButtonProps, | 277 | getOkButtonProps, |
275 | beforeUpload, | 278 | beforeUpload, |
276 | - registerTable, | 279 | + // registerTable, |
277 | fileListRef, | 280 | fileListRef, |
278 | state, | 281 | state, |
279 | isUploadingRef, | 282 | isUploadingRef, |
@@ -295,5 +298,17 @@ | @@ -295,5 +298,17 @@ | ||
295 | .ant-table-wrapper .ant-spin-nested-loading { | 298 | .ant-table-wrapper .ant-spin-nested-loading { |
296 | padding: 0; | 299 | padding: 0; |
297 | } | 300 | } |
301 | + | ||
302 | + &-toolbar { | ||
303 | + display: flex; | ||
304 | + align-items: center; | ||
305 | + margin-bottom: 8px; | ||
306 | + | ||
307 | + &__btn { | ||
308 | + margin-left: 8px; | ||
309 | + text-align: right; | ||
310 | + flex: 1; | ||
311 | + } | ||
312 | + } | ||
298 | } | 313 | } |
299 | </style> | 314 | </style> |
src/components/Upload/src/UploadPreviewModal.vue
@@ -7,13 +7,15 @@ | @@ -7,13 +7,15 @@ | ||
7 | @register="register" | 7 | @register="register" |
8 | :showOkBtn="false" | 8 | :showOkBtn="false" |
9 | > | 9 | > |
10 | - <BasicTable @register="registerTable" :dataSource="fileListRef" /> | 10 | + <FileList :dataSource="fileListRef" :columns="columns" :actionColumn="actionColumn" /> |
11 | </BasicModal> | 11 | </BasicModal> |
12 | </template> | 12 | </template> |
13 | <script lang="ts"> | 13 | <script lang="ts"> |
14 | import { defineComponent, watch, ref, unref } from 'vue'; | 14 | import { defineComponent, watch, ref, unref } from 'vue'; |
15 | 15 | ||
16 | - import { BasicTable, useTable } from '/@/components/Table'; | 16 | + // import { BasicTable, useTable } from '/@/components/Table'; |
17 | + import FileList from './FileList'; | ||
18 | + | ||
17 | import { BasicModal, useModalInner } from '/@/components/Modal'; | 19 | import { BasicModal, useModalInner } from '/@/components/Modal'; |
18 | import { previewProps } from './props'; | 20 | import { previewProps } from './props'; |
19 | import { PreviewFileItem } from './types'; | 21 | import { PreviewFileItem } from './types'; |
@@ -22,7 +24,7 @@ | @@ -22,7 +24,7 @@ | ||
22 | 24 | ||
23 | import { createPreviewColumns, createPreviewActionColumn } from './data'; | 25 | import { createPreviewColumns, createPreviewActionColumn } from './data'; |
24 | export default defineComponent({ | 26 | export default defineComponent({ |
25 | - components: { BasicModal, BasicTable }, | 27 | + components: { BasicModal, FileList }, |
26 | props: previewProps, | 28 | props: previewProps, |
27 | setup(props, { emit }) { | 29 | setup(props, { emit }) { |
28 | const [register, { closeModal }] = useModalInner(); | 30 | const [register, { closeModal }] = useModalInner(); |
@@ -71,17 +73,12 @@ | @@ -71,17 +73,12 @@ | ||
71 | downloadByUrl({ url }); | 73 | downloadByUrl({ url }); |
72 | } | 74 | } |
73 | 75 | ||
74 | - const [registerTable] = useTable({ | ||
75 | - columns: createPreviewColumns(), | ||
76 | - pagination: false, | ||
77 | - actionColumn: createPreviewActionColumn({ handleRemove, handlePreview, handleDownload }), | ||
78 | - }); | ||
79 | - | ||
80 | return { | 76 | return { |
81 | register, | 77 | register, |
82 | closeModal, | 78 | closeModal, |
83 | fileListRef, | 79 | fileListRef, |
84 | - registerTable, | 80 | + columns: createPreviewColumns(), |
81 | + actionColumn: createPreviewActionColumn({ handleRemove, handlePreview, handleDownload }), | ||
85 | }; | 82 | }; |
86 | }, | 83 | }, |
87 | }); | 84 | }); |
src/components/Upload/src/data.tsx
@@ -12,7 +12,7 @@ export function createTableColumns(): BasicColumn[] { | @@ -12,7 +12,7 @@ export function createTableColumns(): BasicColumn[] { | ||
12 | width: 100, | 12 | width: 100, |
13 | customRender: ({ record }) => { | 13 | customRender: ({ record }) => { |
14 | const { thumbUrl, type } = (record as FileItem) || {}; | 14 | const { thumbUrl, type } = (record as FileItem) || {}; |
15 | - return <span>{thumbUrl ? <img style={{ maxWidth: '60px' }} src={thumbUrl} /> : type}</span>; | 15 | + return <span>{thumbUrl ? <img style={{ maxWidth: '100%' }} src={thumbUrl} /> : type}</span>; |
16 | }, | 16 | }, |
17 | }, | 17 | }, |
18 | { | 18 | { |
src/components/Upload/src/props.ts
1 | import type { PropType } from 'vue'; | 1 | import type { PropType } from 'vue'; |
2 | +import { FileBasicColumn } from './types'; | ||
2 | 3 | ||
3 | export const basicProps = { | 4 | export const basicProps = { |
4 | helpText: { | 5 | helpText: { |
@@ -57,3 +58,18 @@ export const previewProps = { | @@ -57,3 +58,18 @@ export const previewProps = { | ||
57 | default: () => [], | 58 | default: () => [], |
58 | }, | 59 | }, |
59 | }; | 60 | }; |
61 | + | ||
62 | +export const fileListProps = { | ||
63 | + columns: { | ||
64 | + type: [Array] as PropType<FileBasicColumn[]>, | ||
65 | + default: null, | ||
66 | + }, | ||
67 | + actionColumn: { | ||
68 | + type: Object as PropType<FileBasicColumn>, | ||
69 | + default: null, | ||
70 | + }, | ||
71 | + dataSource: { | ||
72 | + type: Array as PropType<any[]>, | ||
73 | + default: null, | ||
74 | + }, | ||
75 | +}; |
src/components/Upload/src/types.ts
@@ -23,3 +23,33 @@ export interface PreviewFileItem { | @@ -23,3 +23,33 @@ export interface PreviewFileItem { | ||
23 | name: string; | 23 | name: string; |
24 | type: string; | 24 | type: string; |
25 | } | 25 | } |
26 | + | ||
27 | +export interface FileBasicColumn { | ||
28 | + /** | ||
29 | + * Renderer of the table cell. The return value should be a VNode, or an object for colSpan/rowSpan config | ||
30 | + * @type Function | ScopedSlot | ||
31 | + */ | ||
32 | + customRender?: Function; | ||
33 | + /** | ||
34 | + * Title of this column | ||
35 | + * @type any (string | slot) | ||
36 | + */ | ||
37 | + title: string; | ||
38 | + | ||
39 | + /** | ||
40 | + * Width of this column | ||
41 | + * @type string | number | ||
42 | + */ | ||
43 | + width?: number; | ||
44 | + /** | ||
45 | + * Display field of the data record, could be set like a.b.c | ||
46 | + * @type string | ||
47 | + */ | ||
48 | + dataIndex: string; | ||
49 | + /** | ||
50 | + * specify how content is aligned | ||
51 | + * @default 'left' | ||
52 | + * @type string | ||
53 | + */ | ||
54 | + align?: 'left' | 'right' | 'center'; | ||
55 | +} |