mirror of
https://github.com/kuaifan/dootask.git
synced 2025-12-15 21:32:49 +00:00
perf: 优化项目面板
This commit is contained in:
parent
85a20168dc
commit
a572ba0523
@ -96,7 +96,11 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div v-if="tabTypeActive === 'column'" class="project-column">
|
<div
|
||||||
|
v-if="tabTypeActive === 'column'"
|
||||||
|
ref="projectColumn"
|
||||||
|
class="project-column"
|
||||||
|
@scroll="handleColumnScroll">
|
||||||
<Draggable
|
<Draggable
|
||||||
:list="columnList"
|
:list="columnList"
|
||||||
:animation="150"
|
:animation="150"
|
||||||
@ -105,7 +109,12 @@
|
|||||||
tag="ul"
|
tag="ul"
|
||||||
draggable=".column-item"
|
draggable=".column-item"
|
||||||
@sort="sortUpdate(true)">
|
@sort="sortUpdate(true)">
|
||||||
<li v-for="column in columnList" class="column-item">
|
<li
|
||||||
|
v-for="column in columnList"
|
||||||
|
:ref="`column_${column.id}`"
|
||||||
|
:key="column.id"
|
||||||
|
:data-id="column.id"
|
||||||
|
class="column-item">
|
||||||
<div
|
<div
|
||||||
:class="['column-head', column.color ? 'custom-color' : '']"
|
:class="['column-head', column.color ? 'custom-color' : '']"
|
||||||
:style="column.color ? {backgroundColor: column.color} : {}">
|
:style="column.color ? {backgroundColor: column.color} : {}">
|
||||||
@ -142,7 +151,10 @@
|
|||||||
<Icon class="last" type="md-add" @click="addTopShow(column.id, true)" />
|
<Icon class="last" type="md-add" @click="addTopShow(column.id, true)" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<Scrollbar class="column-task">
|
<Scrollbar
|
||||||
|
class="column-task"
|
||||||
|
class-name="task-scrollbar"
|
||||||
|
@on-scroll="handleTaskScroll">
|
||||||
<div v-if="!!columnTopShow[column.id]" class="task-item additem">
|
<div v-if="!!columnTopShow[column.id]" class="task-item additem">
|
||||||
<TaskAddSimple
|
<TaskAddSimple
|
||||||
:column-id="column.id"
|
:column-id="column.id"
|
||||||
@ -164,9 +176,11 @@
|
|||||||
@remove="sortUpdate">
|
@remove="sortUpdate">
|
||||||
<div
|
<div
|
||||||
v-for="item in column.tasks"
|
v-for="item in column.tasks"
|
||||||
|
:data-id="item.id"
|
||||||
:class="['task-item task-draggable', item.complete_at ? 'complete' : '', taskIsHidden(item) ? 'hidden' : '']"
|
:class="['task-item task-draggable', item.complete_at ? 'complete' : '', taskIsHidden(item) ? 'hidden' : '']"
|
||||||
:style="item.color ? {backgroundColor: item.color} : {}"
|
:style="taskItemStyle(item)"
|
||||||
@click="openTask(item)">
|
@click="openTask(item)">
|
||||||
|
<template v-if="taskItemVisible(item)">
|
||||||
<div :class="['task-head', item.desc ? 'has-desc' : '']">
|
<div :class="['task-head', item.desc ? 'has-desc' : '']">
|
||||||
<div class="task-title">
|
<div class="task-title">
|
||||||
<!--工作流状态-->
|
<!--工作流状态-->
|
||||||
@ -207,6 +221,7 @@
|
|||||||
</div>
|
</div>
|
||||||
<em v-if="item.p_name" class="priority-color" :style="{backgroundColor:item.p_color}"></em>
|
<em v-if="item.p_name" class="priority-color" :style="{backgroundColor:item.p_color}"></em>
|
||||||
</template>
|
</template>
|
||||||
|
</template>
|
||||||
</div>
|
</div>
|
||||||
<div class="task-item additem">
|
<div class="task-item additem">
|
||||||
<TaskAddSimple
|
<TaskAddSimple
|
||||||
@ -607,6 +622,9 @@ export default {
|
|||||||
|
|
||||||
flowInfo: {},
|
flowInfo: {},
|
||||||
flowList: [],
|
flowList: [],
|
||||||
|
|
||||||
|
columnVisibility: {},
|
||||||
|
taskVisibility: {},
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -969,6 +987,7 @@ export default {
|
|||||||
handler(val) {
|
handler(val) {
|
||||||
if (val > 0) {
|
if (val > 0) {
|
||||||
this.getFlowData();
|
this.getFlowData();
|
||||||
|
this.$nextTick(this.handleColumnScroll);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
immediate: true,
|
immediate: true,
|
||||||
@ -1623,6 +1642,93 @@ export default {
|
|||||||
formArchived(value) {
|
formArchived(value) {
|
||||||
this.settingData = { ...this.settingData, archive_method: value };
|
this.settingData = { ...this.settingData, archive_method: value };
|
||||||
},
|
},
|
||||||
|
|
||||||
|
taskItemVisible({id, column_id}) {
|
||||||
|
return this.columnVisibility[column_id] && this.taskVisibility[id]?.visible
|
||||||
|
},
|
||||||
|
|
||||||
|
taskItemStyle({id, column_id, color}) {
|
||||||
|
const style = {}
|
||||||
|
if (color) {
|
||||||
|
style.backgroundColor = color;
|
||||||
|
}
|
||||||
|
if (!this.taskItemVisible({id, column_id})) {
|
||||||
|
style.height = (this.taskVisibility[id]?.height || 146) + 'px';
|
||||||
|
}
|
||||||
|
return style;
|
||||||
|
},
|
||||||
|
|
||||||
|
handleColumnScroll() {
|
||||||
|
this.columnList.forEach(({id}) => {
|
||||||
|
const ref = this.$refs[`column_${id}`];
|
||||||
|
ref && this.checkColumnVisibility(ref[0])
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
checkColumnVisibility(columnContainer = null) {
|
||||||
|
if (!columnContainer) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
const columnId = parseInt(columnContainer.getAttribute('data-id'))
|
||||||
|
if (!columnId) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
const mainContainer = this.$refs.projectColumn;
|
||||||
|
if (!mainContainer) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取容器的边界信息
|
||||||
|
const mainRect = mainContainer.getBoundingClientRect();
|
||||||
|
const columnRect = columnContainer.getBoundingClientRect();
|
||||||
|
|
||||||
|
// 检查元素是否在容器的可视区域内
|
||||||
|
const visible = (
|
||||||
|
columnRect.left < mainRect.right &&
|
||||||
|
columnRect.right > mainRect.left &&
|
||||||
|
columnRect.top < mainRect.bottom &&
|
||||||
|
columnRect.bottom > mainRect.top
|
||||||
|
)
|
||||||
|
if (visible) {
|
||||||
|
this.handleTaskScroll({
|
||||||
|
target: columnContainer.querySelector('.task-scrollbar')
|
||||||
|
})
|
||||||
|
}
|
||||||
|
this.$set(this.columnVisibility, columnId, visible)
|
||||||
|
},
|
||||||
|
|
||||||
|
async handleTaskScroll({target}) {
|
||||||
|
if (!target) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
const targetItem = target.querySelectorAll('.task-item');
|
||||||
|
if (!targetItem.length) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
const targetRect = target.getBoundingClientRect();
|
||||||
|
for (const item of targetItem) {
|
||||||
|
const taskId = parseInt(item.getAttribute('data-id'));
|
||||||
|
if (!taskId) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
const taskRect = item.getBoundingClientRect();
|
||||||
|
const originalVisible = this.taskVisibility[taskId]?.visible || false;
|
||||||
|
const currentVisible = (
|
||||||
|
taskRect.top >= targetRect.top - taskRect.height &&
|
||||||
|
taskRect.bottom <= targetRect.bottom + taskRect.height
|
||||||
|
);
|
||||||
|
if (currentVisible === originalVisible) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
this.$set(this.taskVisibility, taskId, {
|
||||||
|
visible: currentVisible,
|
||||||
|
height: taskRect.height
|
||||||
|
});
|
||||||
|
if (currentVisible) {
|
||||||
|
await this.$nextTick();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@ -403,6 +403,7 @@
|
|||||||
border: 1px solid $primary-color;
|
border: 1px solid $primary-color;
|
||||||
margin-right: 4px;
|
margin-right: 4px;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
|
overflow: hidden;
|
||||||
&.start {
|
&.start {
|
||||||
background-color: rgba($flow-status-start-color, 0.1);
|
background-color: rgba($flow-status-start-color, 0.1);
|
||||||
border-color: rgba($flow-status-start-color, 0.1);
|
border-color: rgba($flow-status-start-color, 0.1);
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user