@lx-frontend/wrap-element-ui 1.0.1-beta.6 → 1.0.1-beta.7
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/package.json +1 -1
- package/src/components/EditableTable/bizHooks/index.ts +17 -0
- package/src/components/EditableTable/{useColumnHeaderOperation.ts → bizHooks/useColumnHeaderOperation.ts} +6 -6
- package/src/components/EditableTable/{useDefaultOperation.ts → bizHooks/useDefaultOperation.ts} +1 -1
- package/src/components/EditableTable/{useDragSort.ts → bizHooks/useDragSort.ts} +1 -1
- package/src/components/EditableTable/{usePagination.ts → bizHooks/usePagination.ts} +1 -1
- package/src/components/EditableTable/{useRowBgColor.ts → bizHooks/useRowBgColor.ts} +7 -7
- package/src/components/EditableTable/{useViewSetting.ts → bizHooks/useViewSetting.ts} +64 -65
- package/src/components/EditableTable/{viewColorSelect.vue → features/bizColorSelect.vue} +3 -3
- package/src/components/EditableTable/features/bizEditCell.vue +44 -0
- package/src/components/EditableTable/features/bizTableHeaderPopover.vue +202 -0
- package/src/components/EditableTable/features/bizViewSettingDialog.vue +137 -0
- package/src/components/EditableTable/index.less +13 -4
- package/src/components/EditableTable/index.vue +76 -331
- package/src/components/EditableTable/{types.ts → types/index.ts} +116 -116
- /package/src/components/EditableTable/{useCellHover.ts → bizHooks/useCellHover.ts} +0 -0
package/package.json
CHANGED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import usePagination from './usePagination';
|
|
2
|
+
import useCellHover from './useCellHover';
|
|
3
|
+
import useViewSetting from './useViewSetting';
|
|
4
|
+
import useRowBgColor from './useRowBgColor';
|
|
5
|
+
import useDefaultOperation from './useDefaultOperation';
|
|
6
|
+
import useColumnHeaderOperation from './useColumnHeaderOperation';
|
|
7
|
+
import useDragSort from './useDragSort';
|
|
8
|
+
|
|
9
|
+
export {
|
|
10
|
+
usePagination,
|
|
11
|
+
useCellHover,
|
|
12
|
+
useViewSetting,
|
|
13
|
+
useRowBgColor,
|
|
14
|
+
useDefaultOperation,
|
|
15
|
+
useColumnHeaderOperation,
|
|
16
|
+
useDragSort
|
|
17
|
+
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { computed, ref, watch, nextTick, Ref } from "vue"
|
|
2
|
-
import { IColumnConfig, IEmits, IProps } from '
|
|
2
|
+
import { IColumnConfig, IEmits, IProps } from '../types';
|
|
3
3
|
|
|
4
4
|
interface IUseColumnHeaderOperationParams {
|
|
5
5
|
props: IProps
|
|
@@ -20,7 +20,7 @@ export default function useColumnHeaderOperation({ props, tableDomRef, sortFilte
|
|
|
20
20
|
const sortingColumn = ref<IColumnConfig | null>(null);
|
|
21
21
|
|
|
22
22
|
// 临时的排序配置
|
|
23
|
-
const tempSortType = ref<'ascending' | 'descending' |
|
|
23
|
+
const tempSortType = ref<'ascending' | 'descending' | ''>('');
|
|
24
24
|
const tempSortingColumn = ref<IColumnConfig | null>(null);
|
|
25
25
|
|
|
26
26
|
// 生效中的过滤配置 和 临时过滤配置
|
|
@@ -90,12 +90,12 @@ export default function useColumnHeaderOperation({ props, tableDomRef, sortFilte
|
|
|
90
90
|
summaryList.value.includes(column.prop);
|
|
91
91
|
}
|
|
92
92
|
|
|
93
|
-
const handleHeaderPopoverShow = (column) => {
|
|
93
|
+
const handleHeaderPopoverShow = (column: IColumnConfig) => {
|
|
94
94
|
// 关闭其他的排序和筛选弹窗(理论上不写也能关闭其他,但是就是有些列会出现两个弹窗同时出现的情况)
|
|
95
95
|
closeSortAndFilterPopover(column.prop);
|
|
96
96
|
tempFilteredValue.value = { ...filteredValue.value };
|
|
97
97
|
tempSearchValue.value = { ...searchValue.value };
|
|
98
|
-
tempSortType.value = sortType.value;
|
|
98
|
+
tempSortType.value = sortType.value || '';
|
|
99
99
|
tempSortingColumn.value = sortingColumn.value ? { ...sortingColumn.value } as IColumnConfig : null;
|
|
100
100
|
// 临时合计项设置成实际的合计项
|
|
101
101
|
tempSummaryList.value = [...summaryList.value];
|
|
@@ -104,7 +104,7 @@ export default function useColumnHeaderOperation({ props, tableDomRef, sortFilte
|
|
|
104
104
|
const closeSortAndFilterPopover = (exceptProp?: string) => {
|
|
105
105
|
sortFilterPopoverRef.value?.forEach((item: any) => {
|
|
106
106
|
if (!exceptProp || exceptProp !== item.$el.dataset.prop) {
|
|
107
|
-
item.
|
|
107
|
+
item.close();
|
|
108
108
|
}
|
|
109
109
|
});
|
|
110
110
|
}
|
|
@@ -170,7 +170,7 @@ export default function useColumnHeaderOperation({ props, tableDomRef, sortFilte
|
|
|
170
170
|
|
|
171
171
|
summaryList.value = [...tempSummaryList.value];
|
|
172
172
|
sortingColumn.value = tempSortingColumn.value ? { ...tempSortingColumn.value } : null;
|
|
173
|
-
sortType.value = tempSortType.value;
|
|
173
|
+
sortType.value = tempSortType.value || null;
|
|
174
174
|
|
|
175
175
|
if (sortingColumn.value) { // 确认时提交排序
|
|
176
176
|
if (props.localSort) {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { onBeforeUnmount, onMounted, ref, Ref } from 'vue';
|
|
2
|
-
import { IColumnConfig, IDraggingData, IEmits, IProps } from "
|
|
2
|
+
import { IColumnConfig, IDraggingData, IEmits, IProps } from "../types"
|
|
3
3
|
import throttle from "lodash/throttle"
|
|
4
4
|
|
|
5
5
|
interface IUseDragSortParams {
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { IColorList, IEmits } from
|
|
1
|
+
import { IColorList, IEmits } from '../types';
|
|
2
2
|
|
|
3
3
|
interface IUseRowBgColorParams {
|
|
4
4
|
colorList: IColorList;
|
|
@@ -12,18 +12,18 @@ export default function useRowBgColor({ colorList, emit }: IUseRowBgColorParams)
|
|
|
12
12
|
return true;
|
|
13
13
|
}
|
|
14
14
|
return colorList.find(c => +c.id === +id)?.default;
|
|
15
|
-
}
|
|
15
|
+
};
|
|
16
16
|
|
|
17
17
|
const getColorById = (id: number, type: 'bg' | 'sample' = 'bg') => {
|
|
18
18
|
return colorList.find(c => +c.id === +id)?.[`${type}Color`] || '';
|
|
19
|
-
}
|
|
19
|
+
};
|
|
20
20
|
|
|
21
21
|
const setRowStyle = (scope) => {
|
|
22
22
|
const row = scope.row;
|
|
23
23
|
return {
|
|
24
24
|
backgroundColor: row.colorId ? getColorById(row.colorId) : ''
|
|
25
|
-
}
|
|
26
|
-
}
|
|
25
|
+
};
|
|
26
|
+
};
|
|
27
27
|
|
|
28
28
|
const handleColorChange = async (colorId: number, scope) => {
|
|
29
29
|
const { row, $index: rowIndex, store } = scope;
|
|
@@ -33,12 +33,12 @@ export default function useRowBgColor({ colorList, emit }: IUseRowBgColorParams)
|
|
|
33
33
|
newList.splice(rowIndex, 1, curRow);
|
|
34
34
|
store.states.data = newList;
|
|
35
35
|
emit('row-bg-change', { colorId, row, rowIndex });
|
|
36
|
-
}
|
|
36
|
+
};
|
|
37
37
|
|
|
38
38
|
return {
|
|
39
39
|
isDefaultColor,
|
|
40
40
|
getColorById,
|
|
41
41
|
setRowStyle,
|
|
42
42
|
handleColorChange,
|
|
43
|
-
}
|
|
43
|
+
};
|
|
44
44
|
}
|
|
@@ -1,33 +1,74 @@
|
|
|
1
|
-
import { ref,
|
|
2
|
-
import { IColumnConfig, IProps } from "
|
|
1
|
+
import { ref, watch, Ref, computed, nextTick } from "vue"
|
|
2
|
+
import { IColumnConfig, IProps } from "../types"
|
|
3
3
|
|
|
4
4
|
interface IViewSettingParams {
|
|
5
|
-
tableDomRef: any
|
|
6
5
|
showingColumns: Ref<string[]>
|
|
7
|
-
actualColumns:
|
|
6
|
+
actualColumns: Ref<IColumnConfig[]>
|
|
7
|
+
viewSettingDragSortOptions: Ref<IColumnConfig[]>
|
|
8
8
|
props: IProps
|
|
9
|
+
emit: {
|
|
10
|
+
(e: 'update:leftFixedColumnCount', val: number): void
|
|
11
|
+
(e: 'update:showingColumns', val: string[]): void
|
|
12
|
+
(e: 'update:viewSettingDragSortOptions', val: IColumnConfig[]): void
|
|
13
|
+
(e: 'tableDoLayout'): void
|
|
14
|
+
}
|
|
9
15
|
}
|
|
10
16
|
|
|
11
|
-
export default function useViewSetting({
|
|
12
|
-
|
|
17
|
+
export default function useViewSetting({
|
|
18
|
+
showingColumns,
|
|
19
|
+
actualColumns,
|
|
20
|
+
props,
|
|
21
|
+
viewSettingDragSortOptions,
|
|
22
|
+
emit
|
|
23
|
+
}: IViewSettingParams) {
|
|
13
24
|
const columnsToBeShown = ref<string[]>([]); // 显示设置弹窗中勾选的列
|
|
14
25
|
const viewSettingVisible = ref(false);
|
|
15
26
|
const leftFixedColumnCount = ref(0);
|
|
16
27
|
const tempLeftFixedColumnCount = ref(0);
|
|
17
28
|
|
|
29
|
+
const updateShowingColumns = (val: string[]) => emit('update:showingColumns', val);
|
|
30
|
+
|
|
18
31
|
const storageKey = computed(() => `@lx-frontend/wrap-element-ui/table_setting_cloumns/${props.settingStorgeKey || (location.pathname === '/' ? location.hash : location.pathname)}`);
|
|
19
32
|
|
|
20
|
-
const saveSettingToStorge = () =>
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
33
|
+
const saveSettingToStorge = async() => {
|
|
34
|
+
await nextTick()
|
|
35
|
+
localStorage.setItem(storageKey.value, JSON.stringify({
|
|
36
|
+
showingColumns: showingColumns.value,
|
|
37
|
+
leftFixedColumnCount: leftFixedColumnCount.value
|
|
38
|
+
}))
|
|
39
|
+
};
|
|
40
|
+
|
|
41
|
+
const handleViewSettingShow = () => {
|
|
42
|
+
emit('update:viewSettingDragSortOptions', [...actualColumns.value]);
|
|
43
|
+
tempLeftFixedColumnCount.value = leftFixedColumnCount.value;
|
|
44
|
+
viewSettingVisible.value = true;
|
|
45
|
+
columnsToBeShown.value = [...showingColumns.value];
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
const handleViewSettingClose = () => {
|
|
49
|
+
viewSettingVisible.value = false;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
const handleViewSettingConfirm = async () => {
|
|
53
|
+
viewSettingVisible.value = false;
|
|
54
|
+
updateShowingColumns(viewSettingDragSortOptions.value.map(c => c.prop));
|
|
55
|
+
leftFixedColumnCount.value = tempLeftFixedColumnCount.value;
|
|
56
|
+
await saveSettingToStorge()
|
|
57
|
+
emit('tableDoLayout')
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
const handleInputTempLeftFixedColumnCount = (value: string) => {
|
|
61
|
+
const _value = Number(value)
|
|
62
|
+
if (isNaN(_value)) return
|
|
63
|
+
tempLeftFixedColumnCount.value = Math.max(0, Math.min(columnsToBeShown.value.length, Math.floor(_value)))
|
|
64
|
+
}
|
|
24
65
|
|
|
25
66
|
watch(
|
|
26
67
|
() => props.columnConfig,
|
|
27
|
-
(val) => {
|
|
28
|
-
const _keys = new Set(
|
|
68
|
+
async(val) => {
|
|
69
|
+
const _keys = new Set(val.map(c => (c.prop)));
|
|
29
70
|
const _cache = localStorage.getItem(storageKey.value);
|
|
30
|
-
const setColumns = () => (
|
|
71
|
+
const setColumns = () => updateShowingColumns(val.filter(v => !v.defaultHide).map(c => c.prop));
|
|
31
72
|
if (!_cache) {
|
|
32
73
|
setColumns();
|
|
33
74
|
leftFixedColumnCount.value = props.leftFixedCount as number;
|
|
@@ -38,7 +79,7 @@ export default function useViewSetting({ tableDomRef, showingColumns, actualColu
|
|
|
38
79
|
if (!cache.showingColumns || !Array.isArray(cache.showingColumns)) {
|
|
39
80
|
setColumns();
|
|
40
81
|
} else {
|
|
41
|
-
|
|
82
|
+
updateShowingColumns(cache.showingColumns.filter(key => _keys.has(key)))
|
|
42
83
|
}
|
|
43
84
|
const _leftFixedColumnCount = Number(cache?.leftFixedColumnCount)
|
|
44
85
|
leftFixedColumnCount.value = isNaN(_leftFixedColumnCount) ? (props.leftFixedCount as number) : _leftFixedColumnCount;
|
|
@@ -54,59 +95,17 @@ export default function useViewSetting({ tableDomRef, showingColumns, actualColu
|
|
|
54
95
|
{ immediate: true }
|
|
55
96
|
)
|
|
56
97
|
|
|
57
|
-
watch(
|
|
58
|
-
|
|
59
|
-
(
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
{ immediate: true }
|
|
65
|
-
)
|
|
98
|
+
watch(columnsToBeShown, (val) => {
|
|
99
|
+
const _map = new Map<string, IColumnConfig>()
|
|
100
|
+
props.columnConfig.forEach(c => _map.set(c.prop, c))
|
|
101
|
+
// 展示时保留顺序
|
|
102
|
+
emit('update:viewSettingDragSortOptions', val.map(prop => _map.get(prop)!))
|
|
103
|
+
if (tempLeftFixedColumnCount.value > val.length) tempLeftFixedColumnCount.value = val.length
|
|
104
|
+
}, { immediate: true })
|
|
66
105
|
|
|
67
|
-
watch(
|
|
68
|
-
() => showingColumns.value,
|
|
69
|
-
(val) => {
|
|
70
|
-
// 只要正在显示的列发生变化,dialog中的显示项也要同步变化,反之不然
|
|
71
|
-
columnsToBeShown.value = [...val];
|
|
72
|
-
},
|
|
73
|
-
{ immediate: true }
|
|
74
|
-
)
|
|
75
|
-
|
|
76
|
-
onMounted(() => {
|
|
77
|
-
leftFixedColumnCount.value = props.leftFixedCount as number;
|
|
78
|
-
})
|
|
79
|
-
|
|
80
|
-
const handleViewSettingShow = () => {
|
|
81
|
-
viewSettingDragSortOptions.value = actualColumns.value
|
|
82
|
-
.filter(c => columnsToBeShown.value.includes(c.prop));
|
|
83
|
-
tempLeftFixedColumnCount.value = leftFixedColumnCount.value;
|
|
84
|
-
viewSettingVisible.value = true;
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
const handleViewSettingClose = () => {
|
|
88
|
-
viewSettingVisible.value = false;
|
|
89
|
-
// 恢复显示的列
|
|
90
|
-
showingColumns.value = actualColumns.value.map(c => c.prop);
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
const handleViewSettingConfirm = async () => {
|
|
94
|
-
viewSettingVisible.value = false;
|
|
95
|
-
showingColumns.value = viewSettingDragSortOptions.value.map(c => c.prop);
|
|
96
|
-
leftFixedColumnCount.value = tempLeftFixedColumnCount.value;
|
|
97
|
-
saveSettingToStorge()
|
|
98
|
-
await nextTick();
|
|
99
|
-
tableDomRef.value?.doLayout();
|
|
100
|
-
}
|
|
101
|
-
|
|
102
|
-
const handleInputTempLeftFixedColumnCount = (value: string) => {
|
|
103
|
-
const _value = Number(value)
|
|
104
|
-
if (isNaN(_value)) return
|
|
105
|
-
tempLeftFixedColumnCount.value = Math.max(0, Math.min(columnsToBeShown.value.length, Math.floor(_value)))
|
|
106
|
-
}
|
|
106
|
+
watch(leftFixedColumnCount, (val) => emit('update:leftFixedColumnCount', val), { immediate: true });
|
|
107
107
|
|
|
108
108
|
return {
|
|
109
|
-
viewSettingDragSortOptions,
|
|
110
109
|
columnsToBeShown,
|
|
111
110
|
viewSettingVisible,
|
|
112
111
|
leftFixedColumnCount,
|
|
@@ -114,6 +113,6 @@ export default function useViewSetting({ tableDomRef, showingColumns, actualColu
|
|
|
114
113
|
handleInputTempLeftFixedColumnCount,
|
|
115
114
|
handleViewSettingShow,
|
|
116
115
|
handleViewSettingClose,
|
|
117
|
-
handleViewSettingConfirm
|
|
116
|
+
handleViewSettingConfirm,
|
|
118
117
|
}
|
|
119
118
|
}
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
<!-- 行颜色选择组件 -->
|
|
1
2
|
<template>
|
|
2
3
|
<div>
|
|
3
4
|
<el-popover
|
|
@@ -13,7 +14,6 @@
|
|
|
13
14
|
class="color-list__item"
|
|
14
15
|
:style="{ backgroundColor: color.sampleColor }"
|
|
15
16
|
@click="() => {
|
|
16
|
-
|
|
17
17
|
visible = false
|
|
18
18
|
handleColorChange(color.id, scope)
|
|
19
19
|
}"
|
|
@@ -39,8 +39,8 @@
|
|
|
39
39
|
|
|
40
40
|
<script setup lang="ts">
|
|
41
41
|
import { ref } from 'vue';
|
|
42
|
-
import { IColorList, IEmits, ITableDataItem } from '
|
|
43
|
-
import useRowBgColor from '
|
|
42
|
+
import { IColorList, IEmits, ITableDataItem } from '../types';
|
|
43
|
+
import { useRowBgColor } from '../bizHooks';
|
|
44
44
|
|
|
45
45
|
const props = defineProps<{
|
|
46
46
|
colorList: IColorList,
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<div>
|
|
3
|
+
<el-input
|
|
4
|
+
v-if="column.editType === 'input'"
|
|
5
|
+
clearable
|
|
6
|
+
:value="value"
|
|
7
|
+
@input="val => emit('input', val)"
|
|
8
|
+
/>
|
|
9
|
+
|
|
10
|
+
<el-select
|
|
11
|
+
v-if="column.editType === 'select'"
|
|
12
|
+
:value="value"
|
|
13
|
+
@input="val => emit('input', val)"
|
|
14
|
+
>
|
|
15
|
+
<el-option
|
|
16
|
+
v-for="item in column.selectOptions"
|
|
17
|
+
:key="item.label"
|
|
18
|
+
:label="item.label"
|
|
19
|
+
:value="item.value"
|
|
20
|
+
/>
|
|
21
|
+
</el-select>
|
|
22
|
+
|
|
23
|
+
<el-date-picker
|
|
24
|
+
v-if="column.editType === 'date'"
|
|
25
|
+
type="date"
|
|
26
|
+
placeholder="选择日期"
|
|
27
|
+
:value="value"
|
|
28
|
+
@input="val => emit('input', val)"
|
|
29
|
+
/>
|
|
30
|
+
</div>
|
|
31
|
+
</template>
|
|
32
|
+
|
|
33
|
+
<script setup lang="ts">
|
|
34
|
+
import { IColumnConfig } from '../types'
|
|
35
|
+
|
|
36
|
+
defineProps<{
|
|
37
|
+
column: IColumnConfig;
|
|
38
|
+
value: any;
|
|
39
|
+
}>()
|
|
40
|
+
|
|
41
|
+
const emit = defineEmits<{
|
|
42
|
+
(e: 'input', value: any): void;
|
|
43
|
+
}>()
|
|
44
|
+
</script>
|
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<el-popover
|
|
3
|
+
ref="popoverRef"
|
|
4
|
+
placement="bottom"
|
|
5
|
+
trigger="click"
|
|
6
|
+
popper-class="editable-table__sort-filter"
|
|
7
|
+
:data-prop="column.prop"
|
|
8
|
+
@show="() => emit('popover-show')"
|
|
9
|
+
>
|
|
10
|
+
<template slot="reference">
|
|
11
|
+
<!-- 筛选中,或排序中,高亮 -->
|
|
12
|
+
<span :class="['editable-table__sort-reference', headActive && 'editable-table__sort-reference--active']">
|
|
13
|
+
{{ column.label }}
|
|
14
|
+
<div :class="['editable-table__sort-icon', headActive && 'editable-table__sort-icon--active']" />
|
|
15
|
+
</span>
|
|
16
|
+
</template>
|
|
17
|
+
<div class="sort-filter">
|
|
18
|
+
<div class="sort-filter__column-title">
|
|
19
|
+
{{ column.label }}
|
|
20
|
+
</div>
|
|
21
|
+
<div
|
|
22
|
+
v-if="column.isColumnSortable"
|
|
23
|
+
class="sort-filter__sort"
|
|
24
|
+
>
|
|
25
|
+
<div class="sort-filter__sort-title">
|
|
26
|
+
排序
|
|
27
|
+
</div>
|
|
28
|
+
<div class="sort-filter__sort-btns">
|
|
29
|
+
<el-button
|
|
30
|
+
:class="['sort-filter__sort-btn', tempSortingColumn?.prop === column.prop && tempSortType === 'ascending' && 'sort-filter__sort-btn--active']"
|
|
31
|
+
@click="() => emit('update:sort', 'ascending')"
|
|
32
|
+
>
|
|
33
|
+
升序
|
|
34
|
+
</el-button>
|
|
35
|
+
<el-button
|
|
36
|
+
:class="['sort-filter__sort-btn', tempSortingColumn?.prop === column.prop && tempSortType === 'descending' && 'sort-filter__sort-btn--active']"
|
|
37
|
+
@click="() => emit('update:sort', 'descending')"
|
|
38
|
+
>
|
|
39
|
+
降序
|
|
40
|
+
</el-button>
|
|
41
|
+
</div>
|
|
42
|
+
</div>
|
|
43
|
+
<div
|
|
44
|
+
v-if="column.search && !Array.isArray(column.search)"
|
|
45
|
+
class="sort-filter__search"
|
|
46
|
+
>
|
|
47
|
+
<div class="sort-filter__search-title">
|
|
48
|
+
搜索
|
|
49
|
+
</div>
|
|
50
|
+
<el-input
|
|
51
|
+
class="sort-filter__search-input"
|
|
52
|
+
placeholder="请输入内容"
|
|
53
|
+
:value="tempSearchValue[column.prop]"
|
|
54
|
+
@input="val => emit('update:tempSearchValue', column.prop, val)"
|
|
55
|
+
/>
|
|
56
|
+
</div>
|
|
57
|
+
|
|
58
|
+
<div
|
|
59
|
+
v-if="column.search && Array.isArray(column.search)"
|
|
60
|
+
class="sort-filter__search"
|
|
61
|
+
style="display: flex;flex-direction: column;gap: 12px;"
|
|
62
|
+
>
|
|
63
|
+
<div
|
|
64
|
+
v-for="item in column.search"
|
|
65
|
+
:key="item.prop"
|
|
66
|
+
>
|
|
67
|
+
<div class="sort-filter__search-title">
|
|
68
|
+
{{ item.label }}
|
|
69
|
+
</div>
|
|
70
|
+
<el-input
|
|
71
|
+
class="sort-filter__search-input"
|
|
72
|
+
placeholder="请输入内容"
|
|
73
|
+
:value="tempSearchValue[item.prop]"
|
|
74
|
+
@input="val => emit('update:tempSearchValue', item.prop, val)"
|
|
75
|
+
/>
|
|
76
|
+
</div>
|
|
77
|
+
</div>
|
|
78
|
+
|
|
79
|
+
<div
|
|
80
|
+
v-if="column.filters && ((Array.isArray(column.filters) ? column.filters : column.filters.options).length > 0)"
|
|
81
|
+
class="sort-filter__filter"
|
|
82
|
+
>
|
|
83
|
+
<div class="sort-filter__filter-title">
|
|
84
|
+
筛选
|
|
85
|
+
</div>
|
|
86
|
+
<el-checkbox-group
|
|
87
|
+
v-if="column.filters && (Array.isArray(column.filters) || column.filters.type === 'checkbox')"
|
|
88
|
+
class="sort-filter__filter-checkbox-group"
|
|
89
|
+
:value="tempFilteredValue[column.prop]"
|
|
90
|
+
@input="val => emit('update:tempFilteredValue', column.prop, val)"
|
|
91
|
+
>
|
|
92
|
+
<el-checkbox
|
|
93
|
+
v-for="item in (Array.isArray(column.filters) ? column.filters : column.filters.options)"
|
|
94
|
+
:key="item.value"
|
|
95
|
+
:label="item.value"
|
|
96
|
+
class="sort-filter__filter-checkbox"
|
|
97
|
+
>
|
|
98
|
+
<slot
|
|
99
|
+
name="filter-item"
|
|
100
|
+
v-bind="item"
|
|
101
|
+
>
|
|
102
|
+
{{ item.text }}
|
|
103
|
+
</slot>
|
|
104
|
+
</el-checkbox>
|
|
105
|
+
</el-checkbox-group>
|
|
106
|
+
|
|
107
|
+
<el-radio-group
|
|
108
|
+
v-if="column.filters && !Array.isArray(column.filters) && column.filters.type === 'radio'"
|
|
109
|
+
style="display: flex;flex-direction: column;gap: 6px;"
|
|
110
|
+
:value="tempFilteredValue[column.prop]"
|
|
111
|
+
@input="val => emit('update:tempFilteredValue', column.prop, val)"
|
|
112
|
+
>
|
|
113
|
+
<el-radio
|
|
114
|
+
v-for="item in column.filters.options"
|
|
115
|
+
:key="item.value"
|
|
116
|
+
:label="item.value"
|
|
117
|
+
>
|
|
118
|
+
<slot
|
|
119
|
+
name="filter-item"
|
|
120
|
+
v-bind="item"
|
|
121
|
+
>
|
|
122
|
+
{{ item.text }}
|
|
123
|
+
</slot>
|
|
124
|
+
</el-radio>
|
|
125
|
+
</el-radio-group>
|
|
126
|
+
</div>
|
|
127
|
+
<div
|
|
128
|
+
v-if="column.summary"
|
|
129
|
+
class="sort-filter__filter"
|
|
130
|
+
>
|
|
131
|
+
<div class="sort-filter__filter-title">
|
|
132
|
+
统计
|
|
133
|
+
</div>
|
|
134
|
+
<el-checkbox-group
|
|
135
|
+
class="sort-filter__filter-checkbox-group"
|
|
136
|
+
:value="tempSummaryList"
|
|
137
|
+
@input="val => emit('update:tempSummaryList', val)"
|
|
138
|
+
>
|
|
139
|
+
<el-checkbox
|
|
140
|
+
:label="column.prop"
|
|
141
|
+
class="sort-filter__filter-checkbox"
|
|
142
|
+
>
|
|
143
|
+
<slot
|
|
144
|
+
name="summay-item"
|
|
145
|
+
v-bind="column"
|
|
146
|
+
>
|
|
147
|
+
{{ column.label }}
|
|
148
|
+
</slot>
|
|
149
|
+
</el-checkbox>
|
|
150
|
+
</el-checkbox-group>
|
|
151
|
+
</div>
|
|
152
|
+
<div class="sort-filter__footer">
|
|
153
|
+
<el-button
|
|
154
|
+
class="sort-filter__reset-btn"
|
|
155
|
+
@click="() => emit('reset')"
|
|
156
|
+
>
|
|
157
|
+
重置
|
|
158
|
+
</el-button>
|
|
159
|
+
<el-button
|
|
160
|
+
class="sort-filter__confirm-btn"
|
|
161
|
+
type="primary"
|
|
162
|
+
@click="() => emit('confirm')"
|
|
163
|
+
>
|
|
164
|
+
确定
|
|
165
|
+
</el-button>
|
|
166
|
+
</div>
|
|
167
|
+
</div>
|
|
168
|
+
</el-popover>
|
|
169
|
+
</template>
|
|
170
|
+
|
|
171
|
+
<script setup lang="ts">
|
|
172
|
+
import { ref } from 'vue'
|
|
173
|
+
import { IColumnConfig } from '../types'
|
|
174
|
+
|
|
175
|
+
defineProps<{
|
|
176
|
+
headActive: boolean
|
|
177
|
+
column: IColumnConfig
|
|
178
|
+
tempSummaryList: string[]
|
|
179
|
+
tempSortingColumn: IColumnConfig | null
|
|
180
|
+
tempSortType: 'ascending' | 'descending' | ''
|
|
181
|
+
tempSearchValue: Record<string, string>
|
|
182
|
+
tempFilteredValue: Record<string, string | number | number[] | string[]>
|
|
183
|
+
}>()
|
|
184
|
+
|
|
185
|
+
const emit = defineEmits<{
|
|
186
|
+
(e: 'update:tempSearchValue', key: string, value: string): void
|
|
187
|
+
(e: 'update:tempFilteredValue', key: string, value: string): void
|
|
188
|
+
(e: 'update:tempSummaryList', value: string[]): void
|
|
189
|
+
(e: 'update:sort', type: 'ascending' | 'descending'): void
|
|
190
|
+
(e: 'popover-show'): void
|
|
191
|
+
(e: 'reset'): void
|
|
192
|
+
(e: 'confirm'): void
|
|
193
|
+
}>()
|
|
194
|
+
|
|
195
|
+
const popoverRef = ref(null as any)
|
|
196
|
+
|
|
197
|
+
defineExpose({
|
|
198
|
+
close: () => {
|
|
199
|
+
popoverRef.value?.doClose()
|
|
200
|
+
}
|
|
201
|
+
})
|
|
202
|
+
</script>
|