面板拖拽问题

This commit is contained in:
zqm
2025-12-29 13:18:13 +08:00
parent 9aad6ebc21
commit bd9faf6ebe
7 changed files with 738 additions and 560 deletions

View File

@@ -106,43 +106,68 @@ const mainAreaResizeBars = ref([])
// 检查主区域内是否有其他Area简化版
const hasAreasInMainContent = ref(false)
/**
* 检查是否应该操作区域而非面板
* 当只有一个面板时,操作区域而不是面板
* @param {string} areaId - Area ID
* @returns {boolean} 是否应该操作区域
*/
const shouldOperateAreaInsteadOfPanel = (areaId) => {
const area = floatingAreas.value.find(a => a.id === areaId);
if (!area) return false;
if (!area) {
console.log(`[DockLayout] 未找到Area: ${areaId}`);
return false;
}
const childrenArray = Array.isArray(area.children) ? area.children : [area.children];
if (childrenArray.length !== 1) return false;
const tabPage = childrenArray[0];
if (tabPage.type !== 'TabPage') return false;
const tabPageChildren = tabPage.children;
const tabPageChildrenArray = Array.isArray(tabPageChildren) ? tabPageChildren : [tabPageChildren];
if (tabPageChildrenArray.length !== 1) return false;
// 检查TabPage的children是否是Panel组件
const childItem = tabPageChildrenArray[0];
if (childItem.type !== 'Panel') return false;
return true;
try {
// 简化逻辑:直接检查区域的面板数量
// 遍历所有子元素统计Panel数量
let panelCount = 0;
const childrenArray = Array.isArray(area.children) ? area.children : [area.children];
for (const child of childrenArray) {
if (child.type === 'TabPage' && child.children) {
const tabChildrenArray = Array.isArray(child.children) ? child.children : [child.children];
for (const tabChild of tabChildrenArray) {
if (tabChild.type === 'Panel') {
panelCount++;
}
}
}
}
// 如果区域中只有一个面板返回true
const result = panelCount === 1;
if (result) {
console.log(`[DockLayout] Area ${areaId} 是单Panel模式应该操作Area而不是Panel`);
}
return result;
} catch (error) {
console.error(`[DockLayout] 检查单Panel模式时出错:`, error);
return false;
}
};
const onCloseFloatingArea = (event) => {
const id = event.areaId;
areaActions.closeFloatingArea(id);
areaActions.closeFloating(id);
const index = floatingAreas.value.findIndex(a => a.id === id);
if (index !== -1) {
floatingAreas.value.splice(index, 1);
}
};
// 保持旧的onUpdatePosition函数以兼容现有事件
const onUpdatePosition = (event) => {
const id = event.areaId;
const position = event;
// 处理不同事件类型的数据结构
const position = event.position || event;
const area = floatingAreas.value.find(a => a.id === id);
if (area) {
area.x = position.left;
area.y = position.top;
area.left = position.left;
area.top = position.top;
}
};
@@ -227,64 +252,79 @@ const handleAreaDragLeave = (event) => {
const onPanelDragStart = (event) => {
const areaId = event.areaId;
if (shouldOperateAreaInsteadOfPanel(areaId)) {
const area = floatingAreas.value.find(a => a.id === areaId);
const startLeft = area ? (area.x || 0) : 0;
const startTop = area ? (area.y || 0) : 0;
eventBus.emit(EVENT_TYPES.AREA_DRAG_START, {
dragId: event.dragId,
areaId: areaId,
event: {
clientX: event.position.x,
clientY: event.position.y
},
element: null,
position: event.position,
clientX: event.position.x,
clientY: event.position.y,
startLeft: startLeft,
startTop: startTop,
timestamp: event.timestamp
});
}
const panelId = event.panelId;
// 触发面板拖拽开始上升事件
eventBus.emit(EVENT_TYPES.PANEL_DRAG_START, {
dragId: event.dragId,
panelId: panelId,
areaId: areaId,
position: event.position,
timestamp: event.timestamp,
layout: {
areas: floatingAreas.value
}
});
console.log(`🚀 面板拖拽开始: panelId=${panelId}, areaId=${areaId}, dragId=${event.dragId}`);
};
const onPanelDragMove = (event) => {
const areaId = event.areaId;
if (shouldOperateAreaInsteadOfPanel(areaId)) {
eventBus.emit(EVENT_TYPES.AREA_DRAG_MOVE, {
dragId: event.dragId,
areaId: areaId,
event: {
clientX: event.position.x,
clientY: event.position.y
},
position: event.position,
clientX: event.position.x,
clientY: event.position.y,
timestamp: event.timestamp
});
}
const panelId = event.panelId;
// 触发面板拖拽移动上升事件
eventBus.emit(EVENT_TYPES.PANEL_DRAG_MOVE, {
dragId: event.dragId,
panelId: panelId,
areaId: areaId,
position: event.position,
timestamp: event.timestamp,
layout: {
areas: floatingAreas.value
}
});
console.log(`📱 面板拖拽移动: panelId=${panelId}, areaId=${areaId}, position=${JSON.stringify(event.position)}`);
};
const onPanelDragEnd = (event) => {
const areaId = event.areaId;
if (shouldOperateAreaInsteadOfPanel(areaId)) {
const area = floatingAreas.value.find(a => a.id === areaId);
const left = area ? (area.x || 0) : 0;
const top = area ? (area.y || 0) : 0;
eventBus.emit(EVENT_TYPES.AREA_DRAG_END, {
dragId: event.dragId,
areaId: areaId,
finalPosition: {
x: left,
y: top
},
left: left,
top: top
});
const panelId = event.panelId;
// 触发面板拖拽结束上升事件
eventBus.emit(EVENT_TYPES.PANEL_DRAG_END, {
dragId: event.dragId,
panelId: panelId,
areaId: areaId,
position: event.position,
timestamp: event.timestamp,
layout: {
areas: floatingAreas.value
}
});
console.log(`✅ 面板拖拽结束: panelId=${panelId}, areaId=${areaId}, finalPosition=${JSON.stringify(event.position)}`);
};
// 监听区域位置更新下降事件
const onAreaPositionUpdate = (event) => {
const id = event.areaId;
const position = event.position;
const area = floatingAreas.value.find(a => a.id === id);
if (area) {
area.left = position.left;
area.top = position.top;
}
};
// 监听区域拖拽状态更新下降事件
const onAreaDragStateUpdate = (event) => {
const id = event.areaId;
const status = event.status;
const area = floatingAreas.value.find(a => a.id === id);
if (area) {
area.isDragging = status === 'active' || status === 'moving';
}
};
@@ -387,10 +427,15 @@ const setupEventListeners = () => {
// Area相关事件
unsubscribeFunctions.push(eventBus.on(EVENT_TYPES.AREA_POSITION_UPDATE, onUpdatePosition, { componentId: 'dock-layout' }));
unsubscribeFunctions.push(eventBus.on(EVENT_TYPES.AREA_FLOATING_UPDATE_POSITION, onUpdatePosition, { componentId: 'dock-layout' }));
unsubscribeFunctions.push(eventBus.on(EVENT_TYPES.AREA_DRAG_OVER, handleAreaDragOver, { componentId: 'dock-layout' }));
unsubscribeFunctions.push(eventBus.on(EVENT_TYPES.AREA_DRAG_LEAVE, handleAreaDragLeave, { componentId: 'dock-layout' }));
unsubscribeFunctions.push(eventBus.on(EVENT_TYPES.AREA_MERGE_REQUEST, handleAreaMergeRequest, { componentId: 'dock-layout' }));
// 添加新的下降事件监听器
unsubscribeFunctions.push(eventBus.on('area.position.update', onAreaPositionUpdate, { componentId: 'dock-layout' }));
unsubscribeFunctions.push(eventBus.on('area.drag.state.update', onAreaDragStateUpdate, { componentId: 'dock-layout' }));
// Tab相关事件
unsubscribeFunctions.push(eventBus.on(EVENT_TYPES.TAB_CHANGE, onTabChange, { componentId: 'dock-layout' }));
unsubscribeFunctions.push(eventBus.on(EVENT_TYPES.TAB_CLOSE, onTabClose, { componentId: 'dock-layout' }));
@@ -533,8 +578,9 @@ const addFloatingPanel = (panel) => {
const newArea = {
id: `area-${Date.now()}`,
x: 100 + Math.random() * 200,
y: 100 + Math.random() * 200,
type: 'floating', // 添加浮动类型标识
left: 100 + Math.random() * 200,
top: 100 + Math.random() * 200,
width: 300,
height: 200,
zIndex: zIndexManager.getFloatingAreaZIndex(`area-${Date.now()}`),
@@ -549,7 +595,13 @@ const addFloatingPanel = (panel) => {
}]
}
}
// 添加到DockLayout的floatingAreas数组中用于渲染
floatingAreas.value.push(newArea)
// 同时注册到AreaHandler的状态管理中确保事件处理能正常进行
areaActions.createFloating(newArea)
return newArea.id
}