增加重算列表
This commit is contained in:
@@ -131,6 +131,8 @@ export const useDockPanelStore = defineStore('dockPanel', () => {
|
||||
center: ref([])
|
||||
}
|
||||
}
|
||||
// 全局:待重算的区域队列(去重)
|
||||
const pendingRecompute = new Set();
|
||||
|
||||
// 根据面板ID获取面板位置
|
||||
function getPanelPositionById(panelId) {
|
||||
@@ -193,57 +195,102 @@ export const useDockPanelStore = defineStore('dockPanel', () => {
|
||||
// 获取全局容器元素(只查询一次DOM)
|
||||
const container = document.querySelector('.dock-panel-container');
|
||||
|
||||
// 辅助:获取区域对象
|
||||
function getAreaByPos(pos) {
|
||||
return pos === 'left' ? leftPanelArea.value
|
||||
: pos === 'right' ? rightPanelArea.value
|
||||
: pos === 'top' ? topPanelArea.value
|
||||
: pos === 'bottom' ? bottomPanelArea.value
|
||||
: pos === 'center' ? centerPanelArea.value
|
||||
: null;
|
||||
}
|
||||
// 辅助:获取受影响的区域列表
|
||||
function impactedBy(position) {
|
||||
const map = panelSizeInfluence.value?.influencedBy || {};
|
||||
return Object.keys(map).filter(pos => {
|
||||
const arr = map[pos] || [];
|
||||
return arr.some(item => item.influence && item.position === position);
|
||||
});
|
||||
}
|
||||
// 队列入列
|
||||
function enqueueRecompute(...positions) {
|
||||
positions.filter(Boolean).forEach(p => pendingRecompute.add(p));
|
||||
}
|
||||
// 处理队列
|
||||
function processRecomputeQueue(externalContainer, sizes = minSizes) {
|
||||
if (!externalContainer) return;
|
||||
let guard = 0;
|
||||
while (pendingRecompute.size > 0 && guard < 20) {
|
||||
guard++;
|
||||
const iterator = pendingRecompute.values();
|
||||
const current = iterator.next().value;
|
||||
pendingRecompute.delete(current);
|
||||
// 先整体更新边界
|
||||
handlePanelSizeInfluence(current, externalContainer);
|
||||
// 更新当前区域的子面板尺寸
|
||||
const currentArea = getAreaByPos(current);
|
||||
if (currentArea) {
|
||||
updatePanelsSize(current, currentArea, externalContainer, sizes);
|
||||
}
|
||||
// 将受影响区域入队并更新其子面板尺寸
|
||||
const impacted = impactedBy(current);
|
||||
impacted.forEach(pos => {
|
||||
const area = getAreaByPos(pos);
|
||||
if (area) {
|
||||
updatePanelsSize(pos, area, externalContainer, sizes);
|
||||
pendingRecompute.add(pos);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
switch (panel.position) {
|
||||
case 'left':
|
||||
const isLeftFirst = leftPanels.value.length === 0
|
||||
leftPanelArea.value.panels.push(panelData)
|
||||
resetPanelsSizeRatios('left')
|
||||
// 使用全局容器元素更新面板尺寸和绝对位置
|
||||
if (container) {
|
||||
updatePanelsSize('left', leftPanelArea.value, container, minSizes);
|
||||
}
|
||||
if (isLeftFirst) {
|
||||
// 触发左侧面板的尺寸影响处理,传入容器引用避免重复查询
|
||||
handlePanelSizeInfluence('left', container)
|
||||
enqueueRecompute('left');
|
||||
processRecomputeQueue(container, minSizes);
|
||||
}
|
||||
break
|
||||
case 'right':
|
||||
const isRightFirst = rightPanels.value.length === 0
|
||||
rightPanelArea.value.panels.push(panelData)
|
||||
resetPanelsSizeRatios('right')
|
||||
// 使用全局容器元素更新面板尺寸和绝对位置
|
||||
if (container) {
|
||||
updatePanelsSize('right', rightPanelArea.value, container, minSizes);
|
||||
}
|
||||
if (isRightFirst) {
|
||||
// 触发右侧面板的尺寸影响处理,传入容器引用避免重复查询
|
||||
handlePanelSizeInfluence('right', container)
|
||||
enqueueRecompute('right');
|
||||
processRecomputeQueue(container, minSizes);
|
||||
}
|
||||
break
|
||||
case 'top':
|
||||
const isTopFirst = topPanels.value.length === 0
|
||||
topPanelArea.value.panels.push(panelData)
|
||||
resetPanelsSizeRatios('top')
|
||||
// 使用全局容器元素更新面板尺寸和绝对位置
|
||||
if (container) {
|
||||
updatePanelsSize('top', topPanelArea.value, container, minSizes);
|
||||
}
|
||||
if (isTopFirst) {
|
||||
// 触发顶部面板的尺寸影响处理,传入容器引用避免重复查询
|
||||
handlePanelSizeInfluence('top', container)
|
||||
enqueueRecompute('top');
|
||||
processRecomputeQueue(container, minSizes);
|
||||
}
|
||||
break
|
||||
case 'bottom':
|
||||
const isBottomFirst = bottomPanels.value.length === 0
|
||||
bottomPanelArea.value.panels.push(panelData)
|
||||
resetPanelsSizeRatios('bottom')
|
||||
// 使用全局容器元素更新面板尺寸和绝对位置
|
||||
if (container) {
|
||||
updatePanelsSize('bottom', bottomPanelArea.value, container, minSizes);
|
||||
}
|
||||
if (isBottomFirst) {
|
||||
// 触发底部面板的尺寸影响处理,传入容器引用避免重复查询
|
||||
handlePanelSizeInfluence('bottom', container)
|
||||
enqueueRecompute('bottom');
|
||||
processRecomputeQueue(container, minSizes);
|
||||
}
|
||||
break
|
||||
case 'center':
|
||||
@@ -363,7 +410,9 @@ export const useDockPanelStore = defineStore('dockPanel', () => {
|
||||
}
|
||||
// 如果面板区域变为空,触发尺寸影响处理以更新其他区域
|
||||
if (panels.length === 0) {
|
||||
handlePanelSizeInfluence(position, container);
|
||||
// 入队并批量重算,直到队列为空
|
||||
enqueueRecompute(position);
|
||||
processRecomputeQueue(container, { panelWidth: 150, panelHeight: 100 });
|
||||
}
|
||||
|
||||
// 处理中心面板的特殊逻辑
|
||||
|
||||
Reference in New Issue
Block a user