diff --git a/AutoRobot/Windows/Robot/Web/src/components/DockPanelContainer.vue b/AutoRobot/Windows/Robot/Web/src/components/DockPanelContainer.vue index 5b74f1f..6372b80 100644 --- a/AutoRobot/Windows/Robot/Web/src/components/DockPanelContainer.vue +++ b/AutoRobot/Windows/Robot/Web/src/components/DockPanelContainer.vue @@ -1,100 +1,112 @@ diff --git a/AutoRobot/Windows/Robot/Web/src/components/LayoutCoordinator.js b/AutoRobot/Windows/Robot/Web/src/components/LayoutCoordinator.js index 646a506..582060a 100644 --- a/AutoRobot/Windows/Robot/Web/src/components/LayoutCoordinator.js +++ b/AutoRobot/Windows/Robot/Web/src/components/LayoutCoordinator.js @@ -252,11 +252,15 @@ export class LayoutCoordinator { influencedBy: { left: [ { position: 'center', property: 'width', influence: true }, - { position: 'right', property: 'width', influence: true } + { position: 'right', property: 'width', influence: true }, + { position: 'top', property: 'width', influence: true }, + { position: 'bottom', property: 'width', influence: true } ], right: [ { position: 'left', property: 'width', influence: true }, - { position: 'center', property: 'width', influence: true } + { position: 'center', property: 'width', influence: true }, + { position: 'top', property: 'width', influence: true }, + { position: 'bottom', property: 'width', influence: true } ], top:[ { position: 'left', property: 'width', influence: true }, @@ -346,56 +350,58 @@ export class LayoutCoordinator { // 计算左侧面板边界 - 考虑被影响列表(influencedBy) if (panelAreas.left && panelAreas.left.panels && panelAreas.left.panels.length > 0) { - // 计算y坐标 - 根据被影响列表,如果包含top区,则y值应该在top区的下边缘 - let leftY = 0; const leftInfluencedBy = influenceData.influencedBy.left || []; - - // 检查是否被top区域影响 - if (leftInfluencedBy.some(item => item.position === 'top' && item.influence)) { - leftY = this.panelBounds.top.height; + let leftY = 0; + // 若被 top.height 影响且顶部区存在有效子面板,则从 top.height 起始 + if ( + leftInfluencedBy.some(item => item.position === 'top' && item.property === 'height' && item.influence) && + panelAreas.top && panelAreas.top.panels && panelAreas.top.panels.length > 0 + ) { + leftY = (this.panelBounds.top?.height ?? panelAreas.top.height ?? 0); } - - // 计算宽度和高度 const leftWidth = panelAreas.left.width || 300; let leftHeight = containerHeight; - - // 考虑顶部和底部面板对高度的影响 - leftHeight -= this.panelBounds.top.height; - leftHeight -= this.panelBounds.bottom.height; - - this.panelBounds.left = { - x: 0, - y: leftY, - width: leftWidth, - height: leftHeight - }; + // 按被影响列表中所有属性为 height 的条目进行扣减,且仅在对应区有有效子面板时生效 + leftInfluencedBy.forEach(item => { + if (item.influence && item.property === 'height') { + const pos = item.position; + const area = panelAreas[pos]; + const hasPanels = area && area.panels && area.panels.length > 0; + if (hasPanels) { + const h = (this.panelBounds[pos]?.height ?? area.height ?? 0); + leftHeight -= h; + } + } + }); + this.panelBounds.left = { x: 0, y: leftY, width: leftWidth, height: leftHeight }; } - + // 计算右侧面板边界 - 考虑被影响列表 if (panelAreas.right && panelAreas.right.panels && panelAreas.right.panels.length > 0) { - // 计算y坐标 - 根据被影响列表,如果包含top区,则y值应该在top区的下边缘 - let rightY = 0; const rightInfluencedBy = influenceData.influencedBy.right || []; - - // 检查是否被top区域影响 - if (rightInfluencedBy.some(item => item.position === 'top' && item.influence)) { - rightY = this.panelBounds.top.height; + let rightY = 0; + // 若被 top.height 影响且顶部区存在有效子面板,则从 top.height 起始 + if ( + rightInfluencedBy.some(item => item.position === 'top' && item.property === 'height' && item.influence) && + panelAreas.top && panelAreas.top.panels && panelAreas.top.panels.length > 0 + ) { + rightY = (this.panelBounds.top?.height ?? panelAreas.top.height ?? 0); } - - // 计算宽度和高度 const rightWidth = panelAreas.right.width || 250; let rightHeight = containerHeight; - - // 考虑顶部和底部面板对高度的影响 - rightHeight -= this.panelBounds.top.height; - rightHeight -= this.panelBounds.bottom.height; - - this.panelBounds.right = { - x: containerWidth - rightWidth, - y: rightY, - width: rightWidth, - height: rightHeight - }; + // 按被影响列表中所有属性为 height 的条目进行扣减,且仅在对应区有有效子面板时生效 + rightInfluencedBy.forEach(item => { + if (item.influence && item.property === 'height') { + const pos = item.position; + const area = panelAreas[pos]; + const hasPanels = area && area.panels && area.panels.length > 0; + if (hasPanels) { + const h = (this.panelBounds[pos]?.height ?? area.height ?? 0); + rightHeight -= h; + } + } + }); + this.panelBounds.right = { x: containerWidth - rightWidth, y: rightY, width: rightWidth, height: rightHeight }; } // 计算中心面板边界 - 中心面板通常被所有其他面板影响 diff --git a/AutoRobot/Windows/Robot/Web/src/components/PanelArea.vue b/AutoRobot/Windows/Robot/Web/src/components/PanelArea.vue index e4d265a..180cae6 100644 --- a/AutoRobot/Windows/Robot/Web/src/components/PanelArea.vue +++ b/AutoRobot/Windows/Robot/Web/src/components/PanelArea.vue @@ -57,6 +57,12 @@ const props = defineProps({ store: { type: Object, required: true + }, + // 绝对定位边界(可选):{ x, y, width, height } + bounds: { + type: Object, + required: false, + default: null } }); @@ -81,11 +87,24 @@ const containerClasses = computed(() => { bottom: 'flex border-t border-gray-300 panel-area-bottom' }; - return `${baseClasses} ${positionClasses[props.position]}`; + const absoluteClass = props.bounds ? ' absolute' : ''; + return `${baseClasses} ${positionClasses[props.position]}${absoluteClass}`; }); // 根据位置计算容器样式 const containerStyle = computed(() => { + // 若提供了绝对定位边界,则使用top/left/width/height + if (props.bounds) { + const { x = 0, y = 0, width = 0, height = 0 } = props.bounds; + return { + position: 'absolute', + top: `${y}px`, + left: `${x}px`, + width: `${width}px`, + height: `${height}px` + }; + } + const isVertical = ['left', 'right'].includes(props.position); const styleProperty = isVertical ? 'width' : 'height';