yxk-20260527-巡视整改提升台账,问题清单树形结构改造

点击某一行就能展开或者收起树
This commit is contained in:
ye1023
2026-05-28 10:46:50 +08:00
parent adc514fa6b
commit b08ca3eab1
2 changed files with 132 additions and 63 deletions
@@ -5,6 +5,11 @@ import { render } from '/@/utils/common/renderUtils';
import { getWeekMonthQuarterYear } from '/@/utils';
//列表数据
export const columns: BasicColumn[] = [
{
title: '问题名称',
align: 'left',
dataIndex: 'problemName'
},
{
title: '类型',
align: 'center',
@@ -13,42 +18,6 @@ export const columns: BasicColumn[] = [
return render.renderDict(text, 'super_dq_ins_type');
},
},
{
title: '密级',
align: 'center',
dataIndex: 'secretLevel_dictText'
},
{
title: '年份',
align: 'center',
dataIndex: 'year_dictText'
},
{
title: '父节点ID',
align: 'center',
dataIndex: 'pid'
},
{
title: '是否有子节点',
align: 'center',
dataIndex: 'hasChild'
},
{
title: '问题名称',
align: 'left',
dataIndex: 'problemName'
},
{
title: '问题编码/分类字典值',
align: 'center',
dataIndex: 'problemCode'
},
{
title: '排序',
align: 'center',
dataIndex: 'sortNo'
},
{
title: '巡视建议',
align: 'center',
@@ -64,6 +33,38 @@ export const columns: BasicColumn[] = [
align: 'center',
dataIndex: 'questionResDept_dictText'
},
{
title: '年份',
align: 'center',
dataIndex: 'year_dictText'
},
{
title: '密级',
align: 'center',
dataIndex: 'secretLevel_dictText'
},
{
title: '父节点ID',
align: 'center',
dataIndex: 'pid'
},
{
title: '是否有子节点',
align: 'center',
dataIndex: 'hasChild'
},
{
title: '问题编码/分类字典值',
align: 'center',
dataIndex: 'problemCode'
},
{
title: '排序',
align: 'center',
dataIndex: 'sortNo'
},
];
// 高级查询数据
@@ -4,21 +4,22 @@
<div class="jeecg-basic-table-form-container">
<a-form @keyup.enter.native="searchQuery" :model="queryParam" :label-col="labelCol" :wrapper-col="wrapperCol">
<a-row :gutter="24">
<a-col :lg="6">
<a-form-item name="problemName">
<template #label><span title="问题名称">问题名称</span></template>
<JInput v-model:value="queryParam.problemName"/>
</a-form-item>
</a-col>
<a-col :lg="4" :md="6" :sm="8">
<a-form-item label="年份" name="year">
<JDictSelectTag v-model:value="queryParam.year" dictCode="super_year" placeholder="请选择年份" allow-clear @change="searchQuery" />
</a-form-item>
</a-col>
<a-col :lg="6">
<a-form-item name="problemName">
<template #label><span title="问题名称">问题名称</span></template>
<JInput v-model:value="queryParam.problemName"/>
</a-form-item>
</a-col>
<a-col :xl="6" :lg="7" :md="8" :sm="24">
<span style="float: left; overflow: hidden" class="table-page-search-submitButtons">
<a-col :lg="6">
<a-button type="primary" preIcon="ant-design:search-outlined" @click="searchQuery">查询</a-button>
<a-button type="primary" preIcon="ant-design:reload-outlined" @click="searchReset" style="margin-left: 8px">重置</a-button>
<a @click="toggleSearchStatus = !toggleSearchStatus" style="margin-left: 8px">
{{ toggleSearchStatus ? '收起' : '展开' }}
<Icon :icon="toggleSearchStatus ? 'ant-design:up-outlined' : 'ant-design:down-outlined'" />
</a>
</a-col>
</span>
</a-col>
@@ -91,6 +92,14 @@
canResize:false,
useSearchForm: false,
isTreeTable: true,
customRow: (record) => {
return {
onClick: (event) => handleRowClick(record, event),
style: {
cursor: hasExpandableChildren(record) ? 'pointer' : 'default',
},
};
},
actionColumn: {
width: 120,
fixed: 'right',
@@ -120,6 +129,19 @@
xs: 24,
sm: 20,
});
const ROW_CLICK_IGNORE_SELECTOR = [
'a',
'button',
'input',
'textarea',
'select',
'.ant-btn',
'.ant-checkbox-wrapper',
'.ant-dropdown-trigger',
'.ant-table-row-expand-icon',
'.ant-table-selection-column',
'.ant-table-cell-fix-right',
].join(',');
// 高级查询配置
const superQueryConfig = reactive(superQuerySchema);
@@ -288,14 +310,61 @@
}
}
/**
* 行点击展开前先过滤按钮、复选框、展开图标等交互区,避免和原有操作互相触发。
*/
async function handleRowClick(record, event) {
if (!hasExpandableChildren(record) || isInteractiveClick(event)) {
return;
}
if (expandedRowKeys.value.includes(record.id)) {
collapseTreeNode(record);
} else {
await handleExpand(true, record);
}
}
/**
* 判断当前节点是否具备展开能力;loading 占位行和叶子节点不参与行点击切换。
*/
function hasExpandableChildren(record) {
return !!record && !record.isLoading && (record.hasChild == '1' || (record.children && record.children.length > 0));
}
function isInteractiveClick(event) {
const target = event?.target;
return !!target?.closest && !!target.closest(ROW_CLICK_IGNORE_SELECTOR);
}
/**
* 收起当前节点时同步清理已展开子孙节点,避免再次展开时残留旧展开状态。
*/
function collapseTreeNode(record) {
const removeKeys = new Set([record.id]);
collectChildKeys(record.children, removeKeys);
expandedRowKeys.value = expandedRowKeys.value.filter((key) => !removeKeys.has(key));
}
function collectChildKeys(children, keys) {
if (!children || children.length === 0) {
return;
}
children.forEach((child) => {
keys.add(child.id);
collectChildKeys(child.children, keys);
});
}
/**
*树节点展开合并
*/
async function handleExpand(expanded, record) {
// 判断是否是展开状态,展开状态(expanded)并且存在子集(children)并且未加载过(isLoading)的就去查询子节点数据
if (expanded) {
expandedRowKeys.value.push(record.id);
if (record.children.length > 0 && !!record.children[0].isLoading) {
if (!expandedRowKeys.value.includes(record.id)) {
expandedRowKeys.value.push(record.id);
}
if (record.hasChild == '1' && (!record.children || record.children.length === 0 || !!record.children[0].isLoading)) {
let result = await getChildList({ pid: record.id});
result = result.records ? result.records : result;
if (result && result.length > 0) {
@@ -306,10 +375,7 @@
}
}
} else {
let keyIndex = expandedRowKeys.value.indexOf(record.id);
if (keyIndex >= 0) {
expandedRowKeys.value.splice(keyIndex, 1);
}
collapseTreeNode(record);
}
}
@@ -318,7 +384,9 @@
*/
async function expandTreeNode(key) {
let record = findTableDataRecord(key);
expandedRowKeys.value.push(key);
if (!expandedRowKeys.value.includes(key)) {
expandedRowKeys.value.push(key);
}
let result = await getChildList({ pid: key });
if (result && result.length > 0) {
record.children = getDataByResult(result);