Commit 8b3a4d37a8addd151b918cf64bce6361376dec9e
1 parent
7a1e94c4
feat: add table setting
Showing
15 changed files
with
399 additions
and
57 deletions
src/components/Form/src/BasicForm.vue
@@ -74,7 +74,7 @@ | @@ -74,7 +74,7 @@ | ||
74 | 74 | ||
75 | const getMergePropsRef = computed( | 75 | const getMergePropsRef = computed( |
76 | (): FormProps => { | 76 | (): FormProps => { |
77 | - return deepMerge(toRaw(props), unref(propsRef)); | 77 | + return deepMerge(props, unref(propsRef)); |
78 | } | 78 | } |
79 | ); | 79 | ); |
80 | // 获取表单基本配置 | 80 | // 获取表单基本配置 |
src/components/Table/src/BasicTable.vue
1 | <template> | 1 | <template> |
2 | <div | 2 | <div |
3 | + ref="wrapRef" | ||
3 | class="basic-table" | 4 | class="basic-table" |
4 | :class="{ | 5 | :class="{ |
5 | 'table-form-container': getBindValues.useSearchForm, | 6 | 'table-form-container': getBindValues.useSearchForm, |
@@ -33,7 +34,7 @@ | @@ -33,7 +34,7 @@ | ||
33 | </div> | 34 | </div> |
34 | </template> | 35 | </template> |
35 | <script lang="ts"> | 36 | <script lang="ts"> |
36 | - import { defineComponent, ref, computed, unref, watch, nextTick } from 'vue'; | 37 | + import { defineComponent, ref, computed, unref, watch, nextTick, toRaw } from 'vue'; |
37 | import { Table } from 'ant-design-vue'; | 38 | import { Table } from 'ant-design-vue'; |
38 | import { basicProps } from './props'; | 39 | import { basicProps } from './props'; |
39 | import type { | 40 | import type { |
@@ -41,7 +42,9 @@ | @@ -41,7 +42,9 @@ | ||
41 | FetchParams, | 42 | FetchParams, |
42 | GetColumnsParams, | 43 | GetColumnsParams, |
43 | TableActionType, | 44 | TableActionType, |
45 | + SizeType, | ||
44 | } from './types/table'; | 46 | } from './types/table'; |
47 | + | ||
45 | import { isFunction, isString } from '/@/utils/is'; | 48 | import { isFunction, isString } from '/@/utils/is'; |
46 | 49 | ||
47 | import renderTitle from './components/renderTitle'; | 50 | import renderTitle from './components/renderTitle'; |
@@ -57,18 +60,20 @@ | @@ -57,18 +60,20 @@ | ||
57 | import { provideTable } from './hooks/useProvinceTable'; | 60 | import { provideTable } from './hooks/useProvinceTable'; |
58 | import { BasicForm, FormProps, useForm } from '/@/components/Form/index'; | 61 | import { BasicForm, FormProps, useForm } from '/@/components/Form/index'; |
59 | import { omit } from 'lodash-es'; | 62 | import { omit } from 'lodash-es'; |
60 | - import './style/index.less'; | ||
61 | import { ROW_KEY } from './const'; | 63 | import { ROW_KEY } from './const'; |
62 | import { PaginationProps } from './types/pagination'; | 64 | import { PaginationProps } from './types/pagination'; |
63 | import { deepMerge } from '/@/utils'; | 65 | import { deepMerge } from '/@/utils'; |
64 | import { TableCustomRecord } from 'ant-design-vue/types/table/table'; | 66 | import { TableCustomRecord } from 'ant-design-vue/types/table/table'; |
65 | import { useEvent } from '/@/hooks/event/useEvent'; | 67 | import { useEvent } from '/@/hooks/event/useEvent'; |
68 | + | ||
69 | + import './style/index.less'; | ||
66 | export default defineComponent({ | 70 | export default defineComponent({ |
67 | props: basicProps, | 71 | props: basicProps, |
68 | components: { Table, BasicForm }, | 72 | components: { Table, BasicForm }, |
69 | emits: ['fetch-success', 'fetch-error', 'selection-change', 'register'], | 73 | emits: ['fetch-success', 'fetch-error', 'selection-change', 'register'], |
70 | setup(props, { attrs, emit, slots }) { | 74 | setup(props, { attrs, emit, slots }) { |
71 | const tableElRef = ref<any>(null); | 75 | const tableElRef = ref<any>(null); |
76 | + const wrapRef = ref<Nullable<HTMLDivElement>>(null); | ||
72 | const innerPropsRef = ref<Partial<BasicTableProps>>(); | 77 | const innerPropsRef = ref<Partial<BasicTableProps>>(); |
73 | const [registerForm, { getFieldsValue }] = useForm(); | 78 | const [registerForm, { getFieldsValue }] = useForm(); |
74 | 79 | ||
@@ -93,6 +98,7 @@ | @@ -93,6 +98,7 @@ | ||
93 | }, | 98 | }, |
94 | emit | 99 | emit |
95 | ); | 100 | ); |
101 | + | ||
96 | const { getScrollRef, redoHeight } = useTableScroll(getMergeProps, tableElRef); | 102 | const { getScrollRef, redoHeight } = useTableScroll(getMergeProps, tableElRef); |
97 | const { | 103 | const { |
98 | getRowSelectionRef, | 104 | getRowSelectionRef, |
@@ -108,16 +114,26 @@ | @@ -108,16 +114,26 @@ | ||
108 | 114 | ||
109 | return unref(getAutoCreateKey) ? ROW_KEY : rowKey; | 115 | return unref(getAutoCreateKey) ? ROW_KEY : rowKey; |
110 | }); | 116 | }); |
117 | + | ||
111 | const getBindValues = computed(() => { | 118 | const getBindValues = computed(() => { |
112 | - const { title, titleHelpMessage, showSummary } = unref(getMergeProps); | 119 | + const { title, titleHelpMessage, showSummary, showTableSetting, tableSetting } = unref( |
120 | + getMergeProps | ||
121 | + ); | ||
122 | + const hideTitle = !slots.tableTitle && !title && !slots.toolbar && !showTableSetting; | ||
113 | const titleData: any = | 123 | const titleData: any = |
114 | - !slots.tableTitle && !isString(title) && !title && !slots.toolbar | 124 | + hideTitle && !isString(title) |
115 | ? {} | 125 | ? {} |
116 | : { | 126 | : { |
117 | - title: | ||
118 | - !slots.tableTitle && !title && !slots.toolbar | ||
119 | - ? null | ||
120 | - : renderTitle.bind(null, title, titleHelpMessage, slots), | 127 | + title: hideTitle |
128 | + ? null | ||
129 | + : renderTitle.bind( | ||
130 | + null, | ||
131 | + title, | ||
132 | + titleHelpMessage, | ||
133 | + slots, | ||
134 | + showTableSetting, | ||
135 | + tableSetting | ||
136 | + ), | ||
121 | }; | 137 | }; |
122 | const pagination = unref(getPaginationRef); | 138 | const pagination = unref(getPaginationRef); |
123 | const rowSelection = unref(getRowSelectionRef); | 139 | const rowSelection = unref(getRowSelectionRef); |
@@ -155,6 +171,7 @@ | @@ -155,6 +171,7 @@ | ||
155 | } | 171 | } |
156 | return propsData; | 172 | return propsData; |
157 | }); | 173 | }); |
174 | + | ||
158 | const getFormProps = computed(() => { | 175 | const getFormProps = computed(() => { |
159 | const { formConfig } = unref(getBindValues); | 176 | const { formConfig } = unref(getBindValues); |
160 | const formProps: FormProps = { | 177 | const formProps: FormProps = { |
@@ -198,6 +215,7 @@ | @@ -198,6 +215,7 @@ | ||
198 | setPagination(pagination); | 215 | setPagination(pagination); |
199 | fetch(); | 216 | fetch(); |
200 | } | 217 | } |
218 | + | ||
201 | watch( | 219 | watch( |
202 | () => unref(getDataSourceRef), | 220 | () => unref(getDataSourceRef), |
203 | () => { | 221 | () => { |
@@ -230,6 +248,10 @@ | @@ -230,6 +248,10 @@ | ||
230 | { immediate: true } | 248 | { immediate: true } |
231 | ); | 249 | ); |
232 | 250 | ||
251 | + function setProps(props: Partial<BasicTableProps>) { | ||
252 | + innerPropsRef.value = deepMerge(unref(innerPropsRef) || {}, props); | ||
253 | + } | ||
254 | + | ||
233 | const tableAction: TableActionType = { | 255 | const tableAction: TableActionType = { |
234 | reload: async (opt?: FetchParams) => { | 256 | reload: async (opt?: FetchParams) => { |
235 | await fetch(opt); | 257 | await fetch(opt); |
@@ -247,11 +269,14 @@ | @@ -247,11 +269,14 @@ | ||
247 | return unref(getPaginationRef); | 269 | return unref(getPaginationRef); |
248 | }, | 270 | }, |
249 | getColumns: (opt?: GetColumnsParams) => { | 271 | getColumns: (opt?: GetColumnsParams) => { |
250 | - const { ignoreIndex } = opt || {}; | ||
251 | - let columns = unref(getColumnsRef); | 272 | + const { ignoreIndex, ignoreAction } = opt || {}; |
273 | + let columns = toRaw(unref(getColumnsRef)); | ||
252 | if (ignoreIndex) { | 274 | if (ignoreIndex) { |
253 | columns = columns.filter((item) => item.flag !== 'INDEX'); | 275 | columns = columns.filter((item) => item.flag !== 'INDEX'); |
254 | } | 276 | } |
277 | + if (ignoreAction) { | ||
278 | + columns = columns.filter((item) => item.flag !== 'ACTION'); | ||
279 | + } | ||
255 | return columns; | 280 | return columns; |
256 | }, | 281 | }, |
257 | getDataSource: () => { | 282 | getDataSource: () => { |
@@ -260,12 +285,16 @@ | @@ -260,12 +285,16 @@ | ||
260 | setLoading: (loading: boolean) => { | 285 | setLoading: (loading: boolean) => { |
261 | loadingRef.value = loading; | 286 | loadingRef.value = loading; |
262 | }, | 287 | }, |
263 | - setProps: (props: Partial<BasicTableProps>) => { | ||
264 | - innerPropsRef.value = deepMerge(unref(innerPropsRef) || {}, props); | 288 | + setProps, |
289 | + getSize: (): SizeType => { | ||
290 | + return unref(getBindValues).size; | ||
265 | }, | 291 | }, |
266 | }; | 292 | }; |
267 | 293 | ||
268 | - provideTable(tableAction); | 294 | + provideTable({ |
295 | + ...tableAction, | ||
296 | + wrapRef, | ||
297 | + }); | ||
269 | 298 | ||
270 | emit('register', tableAction); | 299 | emit('register', tableAction); |
271 | return { | 300 | return { |
@@ -278,6 +307,7 @@ | @@ -278,6 +307,7 @@ | ||
278 | getEmptyDataIsShowTable, | 307 | getEmptyDataIsShowTable, |
279 | handleTableChange, | 308 | handleTableChange, |
280 | getRowClassName, | 309 | getRowClassName, |
310 | + wrapRef, | ||
281 | ...tableAction, | 311 | ...tableAction, |
282 | }; | 312 | }; |
283 | }, | 313 | }, |
src/components/Table/src/components/TableSetting.vue
0 → 100644
1 | +<template> | ||
2 | + <div class="table-settings"> | ||
3 | + <Divider type="vertical" /> | ||
4 | + | ||
5 | + <Tooltip placement="top" v-if="getSetting.redo"> | ||
6 | + <template #title> | ||
7 | + <span>刷新</span> | ||
8 | + </template> | ||
9 | + <RedoOutlined @click="redo" /> | ||
10 | + </Tooltip> | ||
11 | + | ||
12 | + <Tooltip placement="top" v-if="getSetting.size"> | ||
13 | + <template #title> | ||
14 | + <span>密度</span> | ||
15 | + </template> | ||
16 | + <Dropdown placement="bottomCenter" :trigger="['click']"> | ||
17 | + <ColumnHeightOutlined /> | ||
18 | + <template #overlay> | ||
19 | + <Menu @click="handleTitleClick" selectable v-model:selectedKeys="selectedKeysRef"> | ||
20 | + <MenuItem key="default"> | ||
21 | + <span>默认</span> | ||
22 | + </MenuItem> | ||
23 | + <MenuItem key="middle"> | ||
24 | + <span>中等</span> | ||
25 | + </MenuItem> | ||
26 | + <MenuItem key="small"> | ||
27 | + <span>紧凑</span> | ||
28 | + </MenuItem> | ||
29 | + </Menu> | ||
30 | + </template> | ||
31 | + </Dropdown> | ||
32 | + </Tooltip> | ||
33 | + | ||
34 | + <Tooltip placement="top" v-if="getSetting.setting"> | ||
35 | + <template #title> | ||
36 | + <span>列设置</span> | ||
37 | + </template> | ||
38 | + <Popover | ||
39 | + placement="bottomLeft" | ||
40 | + trigger="click" | ||
41 | + overlayClassName="table-settings__cloumn-list" | ||
42 | + > | ||
43 | + <template #content> | ||
44 | + <CheckboxGroup v-model:value="checkedList" @change="onChange"> | ||
45 | + <template v-for="item in plainOptions" :key="item.value"> | ||
46 | + <div class="table-settings__check-item"> | ||
47 | + <Checkbox :value="item.value"> | ||
48 | + {{ item.label }} | ||
49 | + </Checkbox> | ||
50 | + </div> | ||
51 | + </template> | ||
52 | + </CheckboxGroup> | ||
53 | + </template> | ||
54 | + <template #title> | ||
55 | + <div class="table-settings__popover-title"> | ||
56 | + <Checkbox | ||
57 | + :indeterminate="indeterminate" | ||
58 | + v-model:checked="checkAll" | ||
59 | + @change="onCheckAllChange" | ||
60 | + > | ||
61 | + 列展示 | ||
62 | + </Checkbox> | ||
63 | + <a-button size="small" type="link" @click="reset">重置</a-button> | ||
64 | + </div> | ||
65 | + </template> | ||
66 | + <SettingOutlined /> | ||
67 | + </Popover> | ||
68 | + </Tooltip> | ||
69 | + | ||
70 | + <Tooltip placement="top" v-if="getSetting.fullScreen"> | ||
71 | + <template #title> | ||
72 | + <span>全屏</span> | ||
73 | + </template> | ||
74 | + <FullscreenOutlined @click="handleFullScreen" v-if="!isFullscreenRef" /> | ||
75 | + <FullscreenExitOutlined @click="handleFullScreen" v-else /> | ||
76 | + </Tooltip> | ||
77 | + </div> | ||
78 | +</template> | ||
79 | +<script lang="ts"> | ||
80 | + import { defineComponent, ref, reactive, toRefs, PropType, computed } from 'vue'; | ||
81 | + import { injectTable } from '../hooks/useProvinceTable'; | ||
82 | + import { Tooltip, Divider, Dropdown, Menu, Popover, Checkbox } from 'ant-design-vue'; | ||
83 | + import { | ||
84 | + RedoOutlined, | ||
85 | + ColumnHeightOutlined, | ||
86 | + FullscreenOutlined, | ||
87 | + FullscreenExitOutlined, | ||
88 | + SettingOutlined, | ||
89 | + } from '@ant-design/icons-vue'; | ||
90 | + import { useFullscreen } from '/@/hooks/web/useFullScreen'; | ||
91 | + | ||
92 | + import type { SizeType, TableSetting } from '../types/table'; | ||
93 | + | ||
94 | + interface Options { | ||
95 | + label: string; | ||
96 | + value: string; | ||
97 | + } | ||
98 | + interface State { | ||
99 | + indeterminate: boolean; | ||
100 | + checkAll: boolean; | ||
101 | + // defaultColumns: BasicColumn[]; | ||
102 | + // columns: BasicColumn[]; | ||
103 | + checkedList: string[]; | ||
104 | + defaultCheckList: string[]; | ||
105 | + } | ||
106 | + export default defineComponent({ | ||
107 | + name: 'TableSetting', | ||
108 | + components: { | ||
109 | + RedoOutlined, | ||
110 | + ColumnHeightOutlined, | ||
111 | + FullscreenExitOutlined, | ||
112 | + FullscreenOutlined, | ||
113 | + SettingOutlined, | ||
114 | + Popover, | ||
115 | + Tooltip, | ||
116 | + Divider, | ||
117 | + Dropdown, | ||
118 | + Checkbox, | ||
119 | + CheckboxGroup: Checkbox.Group, | ||
120 | + Menu, | ||
121 | + MenuItem: Menu.Item, | ||
122 | + }, | ||
123 | + props: { | ||
124 | + setting: { | ||
125 | + type: Object as PropType<TableSetting>, | ||
126 | + default: {}, | ||
127 | + }, | ||
128 | + }, | ||
129 | + setup(props) { | ||
130 | + const table = injectTable(); | ||
131 | + const { toggleFullscreen, isFullscreenRef } = useFullscreen(table.wrapRef); | ||
132 | + const selectedKeysRef = ref<SizeType[]>([table.getSize()]); | ||
133 | + | ||
134 | + let plainOptions: Options[] = []; | ||
135 | + const state = reactive<State>({ | ||
136 | + indeterminate: false, | ||
137 | + checkAll: true, | ||
138 | + checkedList: [], | ||
139 | + defaultCheckList: [], | ||
140 | + }); | ||
141 | + | ||
142 | + function init() { | ||
143 | + let ret: Options[] = []; | ||
144 | + table.getColumns({ ignoreIndex: true, ignoreAction: true }).forEach((item) => { | ||
145 | + ret.push({ | ||
146 | + label: item.title as string, | ||
147 | + value: (item.dataIndex || item.title) as string, | ||
148 | + }); | ||
149 | + }); | ||
150 | + plainOptions = ret; | ||
151 | + const checkList = table | ||
152 | + .getColumns() | ||
153 | + .map((item) => item.dataIndex || item.title) as string[]; | ||
154 | + state.checkedList = checkList; | ||
155 | + state.defaultCheckList = checkList; | ||
156 | + } | ||
157 | + | ||
158 | + function handleTitleClick({ key }: { key: SizeType }) { | ||
159 | + selectedKeysRef.value = [key]; | ||
160 | + table.setProps({ | ||
161 | + size: key, | ||
162 | + }); | ||
163 | + } | ||
164 | + | ||
165 | + function handleFullScreen() { | ||
166 | + toggleFullscreen(); | ||
167 | + } | ||
168 | + | ||
169 | + function onCheckAllChange(e: ChangeEvent) { | ||
170 | + state.indeterminate = false; | ||
171 | + const checkList = plainOptions.map((item) => item.value); | ||
172 | + if (e.target.checked) { | ||
173 | + state.checkedList = checkList; | ||
174 | + table.setColumns(checkList); | ||
175 | + } else { | ||
176 | + state.checkedList = []; | ||
177 | + table.setColumns([]); | ||
178 | + } | ||
179 | + } | ||
180 | + | ||
181 | + function onChange(checkedList: string[]) { | ||
182 | + state.indeterminate = !!checkedList.length && checkedList.length < plainOptions.length; | ||
183 | + state.checkAll = checkedList.length === plainOptions.length; | ||
184 | + table.setColumns(checkedList); | ||
185 | + } | ||
186 | + | ||
187 | + function reset() { | ||
188 | + if (state.checkAll) return; | ||
189 | + state.checkedList = [...state.defaultCheckList]; | ||
190 | + state.checkAll = true; | ||
191 | + state.indeterminate = false; | ||
192 | + table.setColumns(state.defaultCheckList); | ||
193 | + } | ||
194 | + | ||
195 | + const getSetting = computed( | ||
196 | + (): TableSetting => { | ||
197 | + return { | ||
198 | + redo: true, | ||
199 | + size: true, | ||
200 | + setting: true, | ||
201 | + fullScreen: true, | ||
202 | + ...props.setting, | ||
203 | + }; | ||
204 | + } | ||
205 | + ); | ||
206 | + | ||
207 | + init(); | ||
208 | + return { | ||
209 | + redo: () => table.reload(), | ||
210 | + handleTitleClick, | ||
211 | + selectedKeysRef, | ||
212 | + handleFullScreen, | ||
213 | + isFullscreenRef, | ||
214 | + onCheckAllChange, | ||
215 | + onChange, | ||
216 | + plainOptions, | ||
217 | + reset, | ||
218 | + getSetting, | ||
219 | + ...toRefs(state), | ||
220 | + }; | ||
221 | + }, | ||
222 | + }); | ||
223 | +</script> | ||
224 | +<style lang="less"> | ||
225 | + @import (reference) '../../../../design/index.less'; | ||
226 | + | ||
227 | + .table-settings { | ||
228 | + & > * { | ||
229 | + margin-right: 12px; | ||
230 | + } | ||
231 | + | ||
232 | + svg { | ||
233 | + width: 1.2em; | ||
234 | + height: 1.2em; | ||
235 | + } | ||
236 | + | ||
237 | + &__popover-title { | ||
238 | + display: flex; | ||
239 | + align-items: center; | ||
240 | + justify-content: space-between; | ||
241 | + } | ||
242 | + | ||
243 | + &__check-item { | ||
244 | + width: 100%; | ||
245 | + padding: 4px 16px 4px 16px; | ||
246 | + | ||
247 | + .ant-checkbox-wrapper { | ||
248 | + width: 100%; | ||
249 | + } | ||
250 | + | ||
251 | + &:hover { | ||
252 | + background: fade(@primary-color, 10%); | ||
253 | + } | ||
254 | + } | ||
255 | + | ||
256 | + &__cloumn-list { | ||
257 | + .ant-popover-inner-content { | ||
258 | + max-height: 360px; | ||
259 | + padding-right: 0; | ||
260 | + padding-left: 0; | ||
261 | + overflow: auto; | ||
262 | + } | ||
263 | + | ||
264 | + .ant-checkbox-group { | ||
265 | + width: 100%; | ||
266 | + } | ||
267 | + } | ||
268 | + } | ||
269 | +</style> |
src/components/Table/src/components/renderTitle.tsx
1 | import { Slots } from 'vue'; | 1 | import { Slots } from 'vue'; |
2 | import TableTitle from './TableTitle.vue'; | 2 | import TableTitle from './TableTitle.vue'; |
3 | import { getSlot } from '/@/utils/helper/tsxHelper'; | 3 | import { getSlot } from '/@/utils/helper/tsxHelper'; |
4 | -export default (title: any, titleHelpMessage: string | string[], slots: Slots) => { | 4 | +import TableSettingComp from './TableSetting.vue'; |
5 | + | ||
6 | +import type { TableSetting } from '../types/table'; | ||
7 | + | ||
8 | +export default ( | ||
9 | + title: any, | ||
10 | + titleHelpMessage: string | string[], | ||
11 | + slots: Slots, | ||
12 | + showTableSetting: boolean, | ||
13 | + tableSetting: TableSetting | ||
14 | +) => { | ||
5 | return ( | 15 | return ( |
6 | <> | 16 | <> |
7 | {getSlot(slots, 'tableTitle') || | 17 | {getSlot(slots, 'tableTitle') || |
8 | (title && <TableTitle helpMessage={titleHelpMessage} title={title} />) || ( | 18 | (title && <TableTitle helpMessage={titleHelpMessage} title={title} />) || ( |
9 | <span> </span> | 19 | <span> </span> |
10 | )} | 20 | )} |
11 | - {slots.toolbar && <div class="basic-table-toolbar">{getSlot(slots, 'toolbar')}</div>} | 21 | + { |
22 | + <div class="basic-table-toolbar"> | ||
23 | + {slots.toolbar && getSlot(slots, 'toolbar')} | ||
24 | + {showTableSetting && <TableSettingComp setting={tableSetting} />} | ||
25 | + </div> | ||
26 | + } | ||
12 | </> | 27 | </> |
13 | ); | 28 | ); |
14 | }; | 29 | }; |
src/components/Table/src/hooks/useColumns.ts
@@ -81,28 +81,19 @@ export function useColumns( | @@ -81,28 +81,19 @@ export function useColumns( | ||
81 | } | 81 | } |
82 | if (actionColumn) { | 82 | if (actionColumn) { |
83 | const hasIndex = columns.findIndex((column) => column.flag === 'ACTION'); | 83 | const hasIndex = columns.findIndex((column) => column.flag === 'ACTION'); |
84 | - if (hasIndex === -1) { | ||
85 | - columns.push({ | ||
86 | - fixed: 'right', | ||
87 | - ...actionColumn, | ||
88 | - flag: 'ACTION', | ||
89 | - }); | ||
90 | - } else { | ||
91 | - columns[hasIndex] = { | ||
92 | - ...columns[hasIndex], | ||
93 | - fixed: 'right', | ||
94 | - ...actionColumn, | ||
95 | - flag: 'ACTION', | ||
96 | - }; | ||
97 | - } | 84 | + columns.push({ |
85 | + ...(hasIndex === -1 ? columns[hasIndex] : {}), | ||
86 | + fixed: 'right', | ||
87 | + ...actionColumn, | ||
88 | + flag: 'ACTION', | ||
89 | + }); | ||
98 | } | 90 | } |
99 | return columns; | 91 | return columns; |
100 | }); | 92 | }); |
101 | 93 | ||
102 | function setColumns(columns: BasicColumn[] | string[]) { | 94 | function setColumns(columns: BasicColumn[] | string[]) { |
103 | - if (!isArray(columns)) { | ||
104 | - return; | ||
105 | - } | 95 | + if (!isArray(columns)) return; |
96 | + | ||
106 | if (columns.length <= 0) { | 97 | if (columns.length <= 0) { |
107 | columnsRef.value = []; | 98 | columnsRef.value = []; |
108 | return; | 99 | return; |
src/components/Table/src/hooks/useDataSource.ts
src/components/Table/src/hooks/useProvinceTable.ts
1 | +import type { Ref } from 'vue'; | ||
1 | import { provide, inject } from 'vue'; | 2 | import { provide, inject } from 'vue'; |
2 | import { TableActionType } from '../types/table'; | 3 | import { TableActionType } from '../types/table'; |
3 | 4 | ||
4 | const key = Symbol('table'); | 5 | const key = Symbol('table'); |
5 | 6 | ||
6 | -export function provideTable(instance: TableActionType) { | 7 | +type Instance = TableActionType & { wrapRef: Ref<Nullable<HTMLElement>> }; |
8 | + | ||
9 | +export function provideTable(instance: Instance) { | ||
7 | provide(key, instance); | 10 | provide(key, instance); |
8 | } | 11 | } |
9 | 12 | ||
10 | -export function injectTable(): TableActionType { | ||
11 | - return inject(key) as TableActionType; | 13 | +export function injectTable(): Instance { |
14 | + return inject(key) as Instance; | ||
12 | } | 15 | } |
src/components/Table/src/hooks/useTable.ts
@@ -82,6 +82,9 @@ export function useTable( | @@ -82,6 +82,9 @@ export function useTable( | ||
82 | getPaginationRef: () => { | 82 | getPaginationRef: () => { |
83 | return getTableInstance().getPaginationRef(); | 83 | return getTableInstance().getPaginationRef(); |
84 | }, | 84 | }, |
85 | + getSize: () => { | ||
86 | + return getTableInstance().getSize(); | ||
87 | + }, | ||
85 | } as TableActionType; | 88 | } as TableActionType; |
86 | 89 | ||
87 | return [register, methods]; | 90 | return [register, methods]; |
src/components/Table/src/props.ts
1 | -import { PropType } from 'vue'; | ||
2 | -import { PaginationProps } from './types/pagination'; | ||
3 | -import { BasicColumn, FetchSetting } from './types/table'; | ||
4 | -import { TableCustomRecord, TableRowSelection } from 'ant-design-vue/types/table/table'; | ||
5 | -import { FormProps } from '/@/components/Form/index'; | 1 | +import type { PropType } from 'vue'; |
2 | +import type { PaginationProps } from './types/pagination'; | ||
3 | +import type { BasicColumn, FetchSetting, TableSetting } from './types/table'; | ||
4 | +import type { TableCustomRecord, TableRowSelection } from 'ant-design-vue/types/table/table'; | ||
5 | +import type { FormProps } from '/@/components/Form/index'; | ||
6 | import { FETCH_SETTING } from './const'; | 6 | import { FETCH_SETTING } from './const'; |
7 | 7 | ||
8 | // 注释看 types/table | 8 | // 注释看 types/table |
9 | export const basicProps = { | 9 | export const basicProps = { |
10 | + tableSetting: { | ||
11 | + type: Object as PropType<TableSetting>, | ||
12 | + }, | ||
13 | + showTableSetting: { | ||
14 | + type: Boolean as PropType<boolean>, | ||
15 | + default: false, | ||
16 | + }, | ||
10 | autoCreateKey: { | 17 | autoCreateKey: { |
11 | type: Boolean as PropType<boolean>, | 18 | type: Boolean as PropType<boolean>, |
12 | default: true, | 19 | default: true, |
src/components/Table/src/style/index.less
@@ -27,6 +27,9 @@ | @@ -27,6 +27,9 @@ | ||
27 | } | 27 | } |
28 | 28 | ||
29 | &-toolbar { | 29 | &-toolbar { |
30 | + display: flex; | ||
31 | + align-items: center; | ||
32 | + | ||
30 | > * { | 33 | > * { |
31 | margin-right: 10px; | 34 | margin-right: 10px; |
32 | } | 35 | } |
@@ -132,10 +135,10 @@ | @@ -132,10 +135,10 @@ | ||
132 | border-right: 1px solid @border-color !important; | 135 | border-right: 1px solid @border-color !important; |
133 | } | 136 | } |
134 | 137 | ||
135 | - .ant-table-thead > tr > th, | ||
136 | - .ant-table-tbody > tr > td { | ||
137 | - padding: 9px 8px !important; | ||
138 | - } | 138 | + // .ant-table-thead > tr > th, |
139 | + // .ant-table-tbody > tr > td { | ||
140 | + // padding: 9px 8px !important; | ||
141 | + // } | ||
139 | 142 | ||
140 | .ant-pagination { | 143 | .ant-pagination { |
141 | margin: 10px 0 0 0; | 144 | margin: 10px 0 0 0; |
src/components/Table/src/types/table.ts
@@ -32,7 +32,11 @@ export interface FetchParams { | @@ -32,7 +32,11 @@ export interface FetchParams { | ||
32 | 32 | ||
33 | export interface GetColumnsParams { | 33 | export interface GetColumnsParams { |
34 | ignoreIndex?: boolean; | 34 | ignoreIndex?: boolean; |
35 | + ignoreAction?: boolean; | ||
35 | } | 36 | } |
37 | + | ||
38 | +export type SizeType = 'default' | 'middle' | 'small' | 'large'; | ||
39 | + | ||
36 | export interface TableActionType { | 40 | export interface TableActionType { |
37 | reload: (opt?: FetchParams) => Promise<void>; | 41 | reload: (opt?: FetchParams) => Promise<void>; |
38 | getSelectRows: () => any[]; | 42 | getSelectRows: () => any[]; |
@@ -41,7 +45,7 @@ export interface TableActionType { | @@ -41,7 +45,7 @@ export interface TableActionType { | ||
41 | deleteSelectRowByKey: (key: string) => void; | 45 | deleteSelectRowByKey: (key: string) => void; |
42 | setPagination: (info: Partial<PaginationProps>) => void; | 46 | setPagination: (info: Partial<PaginationProps>) => void; |
43 | setTableData: (values: any[]) => void; | 47 | setTableData: (values: any[]) => void; |
44 | - getColumns: ({ ignoreIndex }?: GetColumnsParams) => BasicColumn[]; | 48 | + getColumns: (opt?: GetColumnsParams) => BasicColumn[]; |
45 | setColumns: (columns: BasicColumn[] | string[]) => void; | 49 | setColumns: (columns: BasicColumn[] | string[]) => void; |
46 | getDataSource: () => any[]; | 50 | getDataSource: () => any[]; |
47 | setLoading: (loading: boolean) => void; | 51 | setLoading: (loading: boolean) => void; |
@@ -49,6 +53,7 @@ export interface TableActionType { | @@ -49,6 +53,7 @@ export interface TableActionType { | ||
49 | redoHeight: () => void; | 53 | redoHeight: () => void; |
50 | setSelectedRowKeys: (rowKeys: string[] | number[]) => void; | 54 | setSelectedRowKeys: (rowKeys: string[] | number[]) => void; |
51 | getPaginationRef: () => PaginationProps | boolean; | 55 | getPaginationRef: () => PaginationProps | boolean; |
56 | + getSize: () => SizeType; | ||
52 | } | 57 | } |
53 | 58 | ||
54 | export interface FetchSetting { | 59 | export interface FetchSetting { |
@@ -61,7 +66,18 @@ export interface FetchSetting { | @@ -61,7 +66,18 @@ export interface FetchSetting { | ||
61 | // 请求结果总数字段 支持 a.b.c | 66 | // 请求结果总数字段 支持 a.b.c |
62 | totalField: string; | 67 | totalField: string; |
63 | } | 68 | } |
69 | + | ||
70 | +export interface TableSetting { | ||
71 | + redo?: boolean; | ||
72 | + size?: boolean; | ||
73 | + setting?: boolean; | ||
74 | + fullScreen?: boolean; | ||
75 | +} | ||
76 | + | ||
64 | export interface BasicTableProps<T = any> { | 77 | export interface BasicTableProps<T = any> { |
78 | + // 显示表格设置 | ||
79 | + showTableSetting?: boolean; | ||
80 | + tableSetting?: TableSetting; | ||
65 | // 斑马纹 | 81 | // 斑马纹 |
66 | striped?: boolean; | 82 | striped?: boolean; |
67 | // 是否自动生成key | 83 | // 是否自动生成key |
@@ -234,7 +250,7 @@ export interface BasicTableProps<T = any> { | @@ -234,7 +250,7 @@ export interface BasicTableProps<T = any> { | ||
234 | * @default 'default' | 250 | * @default 'default' |
235 | * @type string | 251 | * @type string |
236 | */ | 252 | */ |
237 | - size?: 'default' | 'middle' | 'small' | 'large'; | 253 | + size?: SizeType; |
238 | 254 | ||
239 | /** | 255 | /** |
240 | * Table title renderer | 256 | * Table title renderer |
src/hooks/web/useFullScreen.ts
@@ -42,15 +42,17 @@ export function useFullscreen( | @@ -42,15 +42,17 @@ export function useFullscreen( | ||
42 | RFC_METHOD_NAME = 'mozRequestFullScreen'; | 42 | RFC_METHOD_NAME = 'mozRequestFullScreen'; |
43 | EFS_METHOD_NAME = 'mozCancelFullScreen'; | 43 | EFS_METHOD_NAME = 'mozCancelFullScreen'; |
44 | FSE_PROP_NAME = 'mozFullScreenElement'; | 44 | FSE_PROP_NAME = 'mozFullScreenElement'; |
45 | - ON_FSC_PROP_NAME = 'onmozfullscreenchange'; | 45 | + // ON_FSC_PROP_NAME = 'onmozfullscreenchange'; |
46 | } else if (!('requestFullscreen' in DOC_EL)) { | 46 | } else if (!('requestFullscreen' in DOC_EL)) { |
47 | throw new Error('当前浏览器不支持Fullscreen API !'); | 47 | throw new Error('当前浏览器不支持Fullscreen API !'); |
48 | } | 48 | } |
49 | function enterFullscreen(): Promise<void> { | 49 | function enterFullscreen(): Promise<void> { |
50 | + isFullscreenRef.value = true; | ||
50 | return (target.value as any)[RFC_METHOD_NAME](options); | 51 | return (target.value as any)[RFC_METHOD_NAME](options); |
51 | } | 52 | } |
52 | 53 | ||
53 | function exitFullscreen(): Promise<void> { | 54 | function exitFullscreen(): Promise<void> { |
55 | + isFullscreenRef.value = false; | ||
54 | return (document as any)[EFS_METHOD_NAME](); | 56 | return (document as any)[EFS_METHOD_NAME](); |
55 | } | 57 | } |
56 | 58 | ||
@@ -89,6 +91,7 @@ export function useFullscreen( | @@ -89,6 +91,7 @@ export function useFullscreen( | ||
89 | watchFullscreen((isFull: boolean) => { | 91 | watchFullscreen((isFull: boolean) => { |
90 | isFullscreenRef.value = isFull; | 92 | isFullscreenRef.value = isFull; |
91 | }); | 93 | }); |
94 | + | ||
92 | return { | 95 | return { |
93 | watchFullscreen, | 96 | watchFullscreen, |
94 | toggleFullscreen, | 97 | toggleFullscreen, |
src/layouts/default/LayoutBreadcrumb.tsx
@@ -65,7 +65,7 @@ export default defineComponent({ | @@ -65,7 +65,7 @@ export default defineComponent({ | ||
65 | 65 | ||
66 | return () => ( | 66 | return () => ( |
67 | <> | 67 | <> |
68 | - <Breadcrumb class="layout-breadcrumb "> | 68 | + <Breadcrumb class="layout-breadcrumb"> |
69 | {() => ( | 69 | {() => ( |
70 | <> | 70 | <> |
71 | <TransitionGroup name="breadcrumb"> | 71 | <TransitionGroup name="breadcrumb"> |
src/store/modules/menu.ts
@@ -8,16 +8,16 @@ const NAME = 'menu'; | @@ -8,16 +8,16 @@ const NAME = 'menu'; | ||
8 | hotModuleUnregisterModule(NAME); | 8 | hotModuleUnregisterModule(NAME); |
9 | @Module({ namespaced: true, name: NAME, dynamic: true, store }) | 9 | @Module({ namespaced: true, name: NAME, dynamic: true, store }) |
10 | class Menu extends VuexModule { | 10 | class Menu extends VuexModule { |
11 | - // 默认展开 | ||
12 | - private collapsedState: boolean = appStore.getProjectConfig.menuSetting.collapsed; | 11 | + // // 默认展开 |
12 | + // private collapsedState: boolean = appStore.getProjectConfig.menuSetting.collapsed; | ||
13 | 13 | ||
14 | - // 菜单宽度 | ||
15 | - private menuWidthState: number = appStore.getProjectConfig.menuSetting.menuWidth; | 14 | + // // 菜单宽度 |
15 | + // private menuWidthState: number = appStore.getProjectConfig.menuSetting.menuWidth; | ||
16 | 16 | ||
17 | // 是否开始拖拽 | 17 | // 是否开始拖拽 |
18 | - private dragStartState: boolean = false; | 18 | + private dragStartState = false; |
19 | 19 | ||
20 | - private currentTopSplitMenuPathState: string = ''; | 20 | + private currentTopSplitMenuPathState = ''; |
21 | 21 | ||
22 | /** | 22 | /** |
23 | * @description: 获取窗口名称 | 23 | * @description: 获取窗口名称 |
@@ -51,7 +51,7 @@ class Menu extends VuexModule { | @@ -51,7 +51,7 @@ class Menu extends VuexModule { | ||
51 | // 改变菜单展开状态 | 51 | // 改变菜单展开状态 |
52 | @Mutation | 52 | @Mutation |
53 | commitCollapsedState(collapsed: boolean): void { | 53 | commitCollapsedState(collapsed: boolean): void { |
54 | - this.collapsedState = collapsed; | 54 | + // this.collapsedState = collapsed; |
55 | appStore.commitProjectConfigState({ | 55 | appStore.commitProjectConfigState({ |
56 | menuSetting: { | 56 | menuSetting: { |
57 | collapsed: collapsed, | 57 | collapsed: collapsed, |
@@ -61,7 +61,7 @@ class Menu extends VuexModule { | @@ -61,7 +61,7 @@ class Menu extends VuexModule { | ||
61 | 61 | ||
62 | @Mutation | 62 | @Mutation |
63 | commitMenuWidthState(menuWidth: number): void { | 63 | commitMenuWidthState(menuWidth: number): void { |
64 | - this.menuWidthState = menuWidth; | 64 | + // this.menuWidthState = menuWidth; |
65 | appStore.commitProjectConfigState({ | 65 | appStore.commitProjectConfigState({ |
66 | menuSetting: { | 66 | menuSetting: { |
67 | menuWidth: menuWidth, | 67 | menuWidth: menuWidth, |
src/views/demo/table/FormTable.vue