Files
lingji-work-fe/src/hooks/useTableSelectionWithPagination.ts

95 lines
2.7 KiB
TypeScript
Raw Normal View History

2025-07-15 17:45:16 +08:00
import { ref, computed } from 'vue';
interface UseTableSelectionWithPaginationOptions {
rowKey?: string; // 主键字段名,默认 'id'
pageInfo?: {
page?: number;
page_size?: number;
total?: number;
};
onPageChange?: (page: number) => void;
onPageSizeChange?: (size: number) => void;
onSelectChange?: () => void;
2025-07-15 17:45:16 +08:00
}
const DEFAULT_PAGE_INFO = {
page: 1,
2025-07-15 17:46:09 +08:00
page_size: 20,
2025-07-15 17:45:16 +08:00
total: 0,
};
export function useTableSelectionWithPagination(options: UseTableSelectionWithPaginationOptions = {}) {
const rowKey = options.rowKey || 'id';
const selectedRowKeys = ref<Array<string | number>>([]);
const selectedRows = ref<any[]>([]);
const pageInfo = ref(merge({}, DEFAULT_PAGE_INFO, options.pageInfo));
const dataSource = ref<any[]>([]);
// 单行选择
const handleSelect = (selectedKeys: (string | number)[], rowKeyValue: string | number, record: any) => {
const select = selectedKeys.includes(rowKeyValue);
selectedRowKeys.value = selectedKeys;
if (select) {
if (!selectedRows.value.some((v) => v[rowKey] === record[rowKey])) {
selectedRows.value.push(record);
}
} else {
selectedRows.value = selectedRows.value.filter((v) => v[rowKey] !== record[rowKey]);
}
options.onSelectChange?.();
2025-07-15 17:45:16 +08:00
};
// 全选/取消全选
const handleSelectAll = (checked: boolean) => {
const currentPageRows = dataSource.value;
const currentPageKeys = currentPageRows.map((v) => v[rowKey]);
if (checked) {
selectedRowKeys.value = Array.from(new Set([...selectedRowKeys.value, ...currentPageKeys]));
const allRows = [...selectedRows.value, ...currentPageRows];
const map = new Map();
allRows.forEach((row) => map.set(row[rowKey], row));
selectedRows.value = Array.from(map.values());
} else {
selectedRowKeys.value = selectedRowKeys.value.filter((key) => !currentPageKeys.includes(key));
selectedRows.value = selectedRows.value.filter((row) => !currentPageKeys.includes(row[rowKey]));
}
options.onSelectChange?.();
2025-07-15 17:45:16 +08:00
};
const onPageChange = (page: number) => {
pageInfo.value.page = page;
options.onPageChange?.(page);
};
const onPageSizeChange = (size: number) => {
pageInfo.value.page_size = size;
pageInfo.value.page = 1;
options.onPageSizeChange?.(size);
};
2025-07-21 12:01:32 +08:00
const resetPageInfo = () => {
pageInfo.value = cloneDeep(DEFAULT_PAGE_INFO)
}
2025-07-15 17:45:16 +08:00
const rowSelection = computed(() => ({
type: 'checkbox',
showCheckedAll: true,
}));
return {
selectedRowKeys,
selectedRows,
dataSource,
pageInfo,
onPageChange,
onPageSizeChange,
rowSelection,
handleSelect,
handleSelectAll,
2025-07-21 12:01:32 +08:00
resetPageInfo
2025-07-15 17:45:16 +08:00
};
}