实现功能:当Area内容区只有一个Panel时,拖动Panel标题栏可以移动Area

This commit is contained in:
zqm
2025-11-04 11:05:12 +08:00
parent 8ec95d63f5
commit 9762ef3b1a
2 changed files with 105 additions and 2 deletions

View File

@@ -37,6 +37,9 @@
@maximize="onMaximize"
@close="onClosePanel(area.id, panel.id)"
@toggleToolbar="onToggleToolbar"
@dragStart="onPanelDragStart(area.id, $event)"
@dragMove="onPanelDragMove(area.id, $event)"
@dragEnd="onPanelDragEnd"
/>
</Area>
@@ -67,6 +70,14 @@ const dockLayoutRef = ref(null)
// 区域ID计数器
let areaIdCounter = 1
// Panel拖拽相关状态
const panelDragState = ref({
isDragging: false,
currentAreaId: null,
startClientPos: { x: 0, y: 0 },
startAreaPos: { x: 0, y: 0 }
})
// 添加新的浮动面板
const addFloatingPanel = () => {
// 获取父容器尺寸以计算居中位置
@@ -169,6 +180,59 @@ const onToggleToolbar = (id) => {
}
}
// Panel拖拽开始
const onPanelDragStart = (areaId, event) => {
const area = floatingAreas.value.find(a => a.id === areaId)
// 只有当Area中只有一个Panel时才允许通过Panel标题栏移动Area
if (area && area.panels.length === 1) {
panelDragState.value.isDragging = true
panelDragState.value.currentAreaId = areaId
panelDragState.value.startClientPos = {
x: event.clientX,
y: event.clientY
}
panelDragState.value.startAreaPos = {
x: area.x,
y: area.y
}
}
}
// Panel拖拽移动
const onPanelDragMove = (areaId, event) => {
if (panelDragState.value.isDragging && panelDragState.value.currentAreaId === areaId) {
const area = floatingAreas.value.find(a => a.id === areaId)
if (area) {
// 计算移动距离
const deltaX = event.clientX - panelDragState.value.startClientPos.x
const deltaY = event.clientY - panelDragState.value.startClientPos.y
// 计算新位置
let newLeft = panelDragState.value.startAreaPos.x + deltaX
let newTop = panelDragState.value.startAreaPos.y + deltaY
// 确保不超出父容器边界
if (dockLayoutRef.value) {
const parentRect = dockLayoutRef.value.getBoundingClientRect()
// 严格边界检查
newLeft = Math.max(0, Math.min(newLeft, parentRect.width - area.width))
newTop = Math.max(0, Math.min(newTop, parentRect.height - area.height))
}
// 更新位置
area.x = newLeft
area.y = newTop
}
}
}
// Panel拖拽结束
const onPanelDragEnd = () => {
panelDragState.value.isDragging = false
panelDragState.value.currentAreaId = null
}
// 暴露方法给父组件
defineExpose({
addFloatingPanel