初步完成
This commit is contained in:
@@ -57,6 +57,14 @@ const bindElementEvents = (element: HTMLElement, type: ElementType, path: string
|
||||
|
||||
if (!dragStore.isDragging) {
|
||||
element.classList.add('fauto-hover')
|
||||
} else {
|
||||
// 拖拽时移动到不同元素,进入目标选择阶段
|
||||
// 检查是否是不同的元素(不是源元素或其父级)
|
||||
const sourcePath = dragStore.confirmedSource?.path || dragStore.dragSource?.path
|
||||
if (sourcePath && path !== sourcePath && !path.startsWith(sourcePath)) {
|
||||
dragStore.enterTargetPhase(element)
|
||||
updateSelectedHighlight()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -93,8 +101,8 @@ const bindElementEvents = (element: HTMLElement, type: ElementType, path: string
|
||||
// 如果已经有拖拽源,不处理
|
||||
if (dragStore.isDragging) return
|
||||
|
||||
// 开始画布内元素拖拽
|
||||
dragStore.startDragFromCanvas(path, type)
|
||||
// 开始画布内元素拖拽,传入元素引用以立即构建层级列表
|
||||
dragStore.startDragFromCanvas(path, type, element)
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
@@ -228,7 +236,8 @@ const clearDragHighlight = () => {
|
||||
* 全局鼠标移动处理(拖拽时更新方向)
|
||||
*/
|
||||
const handleGlobalMouseMove = (e: MouseEvent) => {
|
||||
if (dragStore.isDragging && dragStore.selectedNode) {
|
||||
// 只在目标选择阶段才更新方向
|
||||
if (dragStore.isDragging && dragStore.dragPhase === 'target' && dragStore.selectedNode) {
|
||||
dragStore.updateDirectionFromMouse(e.clientX, e.clientY)
|
||||
}
|
||||
}
|
||||
@@ -237,7 +246,8 @@ const handleGlobalMouseMove = (e: MouseEvent) => {
|
||||
* 全局鼠标松开处理
|
||||
*/
|
||||
const handleGlobalMouseUp = async () => {
|
||||
if (dragStore.isDragging && dragStore.selectedNode && dragStore.hoverDirection) {
|
||||
// 只在目标选择阶段才执行拖放
|
||||
if (dragStore.isDragging && dragStore.dragPhase === 'target' && dragStore.selectedNode && dragStore.hoverDirection) {
|
||||
// 获取当前页面路径(从vueFileStore)
|
||||
const pagePath = vueFileStore.selectedFilePath
|
||||
|
||||
|
||||
@@ -58,6 +58,16 @@ export const useDragStore = defineStore('drag', () => {
|
||||
// 拖拽源
|
||||
const dragSource = ref<DragSource | null>(null)
|
||||
|
||||
// 拖拽阶段: 'source' = 源选择阶段, 'target' = 目标选择阶段
|
||||
const dragPhase = ref<'source' | 'target'>('source')
|
||||
|
||||
// 已确定的源元素信息(当进入目标选择阶段时保存)
|
||||
const confirmedSource = ref<{
|
||||
path: string
|
||||
type: ElementType
|
||||
element: HTMLElement
|
||||
} | null>(null)
|
||||
|
||||
// ========== 层级选择状态 ==========
|
||||
|
||||
// 当前悬停位置的所有层级节点(从深到浅排序)
|
||||
@@ -103,15 +113,57 @@ export const useDragStore = defineStore('drag', () => {
|
||||
|
||||
/**
|
||||
* 开始拖拽(从画布内元素)
|
||||
* @param path 元素路径
|
||||
* @param elementType 元素类型
|
||||
* @param element 元素DOM引用(用于立即构建层级列表)
|
||||
*/
|
||||
const startDragFromCanvas = (path: string, elementType: ElementType) => {
|
||||
const startDragFromCanvas = (path: string, elementType: ElementType, element?: HTMLElement) => {
|
||||
isDragging.value = true
|
||||
dragPhase.value = 'source' // 进入源选择阶段
|
||||
confirmedSource.value = null // 清除之前的确定源
|
||||
dragSource.value = {
|
||||
type: 'canvas-element',
|
||||
path,
|
||||
elementType
|
||||
}
|
||||
console.log('[DragStore] 开始拖拽画布元素:', path)
|
||||
|
||||
// 立即构建层级列表,让用户可以在原地通过上下键切换源元素层级
|
||||
if (element) {
|
||||
updateHierarchy(element)
|
||||
}
|
||||
|
||||
console.log('[DragStore] 开始拖拽画布元素 (源选择阶段):', path)
|
||||
}
|
||||
|
||||
/**
|
||||
* 进入目标选择阶段
|
||||
* 当鼠标移动到不同元素时调用
|
||||
*/
|
||||
const enterTargetPhase = (targetElement: HTMLElement) => {
|
||||
if (dragPhase.value === 'source' && selectedNode.value) {
|
||||
// 保存当前选中的源元素
|
||||
confirmedSource.value = {
|
||||
path: selectedNode.value.path,
|
||||
type: selectedNode.value.type,
|
||||
element: selectedNode.value.element
|
||||
}
|
||||
|
||||
// 更新 dragSource 中的路径和类型
|
||||
if (dragSource.value) {
|
||||
dragSource.value.path = selectedNode.value.path
|
||||
dragSource.value.elementType = selectedNode.value.type
|
||||
}
|
||||
|
||||
console.log('[DragStore] 确定源元素:', confirmedSource.value.path)
|
||||
}
|
||||
|
||||
// 进入目标选择阶段
|
||||
dragPhase.value = 'target'
|
||||
|
||||
// 更新层级列表为目标元素的层级
|
||||
updateHierarchy(targetElement)
|
||||
|
||||
console.log('[DragStore] 进入目标选择阶段')
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -215,6 +267,8 @@ export const useDragStore = defineStore('drag', () => {
|
||||
hierarchyNodes.value = []
|
||||
selectedHierarchyIndex.value = 0
|
||||
hoverDirection.value = null
|
||||
dragPhase.value = 'source'
|
||||
confirmedSource.value = null
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -252,12 +306,11 @@ export const useDragStore = defineStore('drag', () => {
|
||||
* 是否为跨类型拖放(源和目标类型不同)
|
||||
*/
|
||||
const isCrossTypeDrop = computed(() => {
|
||||
if (!dragSource.value || !selectedNode.value) return false
|
||||
// 只有在目标选择阶段才考虑跨类型
|
||||
if (dragPhase.value !== 'target') return false
|
||||
if (!confirmedSource.value || !selectedNode.value) return false
|
||||
|
||||
// 只有画布内元素拖放才考虑跨类型
|
||||
if (dragSource.value.type !== 'canvas-element') return false
|
||||
|
||||
const sourceType = dragSource.value.elementType
|
||||
const sourceType = confirmedSource.value.type
|
||||
const targetType = selectedNode.value.type
|
||||
|
||||
// er 拖到 ec 或 ec 拖到 er 都是跨类型
|
||||
@@ -427,6 +480,8 @@ export const useDragStore = defineStore('drag', () => {
|
||||
// 状态
|
||||
isDragging,
|
||||
dragSource,
|
||||
dragPhase,
|
||||
confirmedSource,
|
||||
hierarchyNodes,
|
||||
selectedHierarchyIndex,
|
||||
selectedNode,
|
||||
@@ -439,6 +494,7 @@ export const useDragStore = defineStore('drag', () => {
|
||||
// 方法
|
||||
startDragFromComponentList,
|
||||
startDragFromCanvas,
|
||||
enterTargetPhase,
|
||||
updateHierarchy,
|
||||
clearHierarchy,
|
||||
selectParentLevel,
|
||||
|
||||
@@ -9,16 +9,18 @@
|
||||
<div class="design-component">右侧标题</div>
|
||||
</el-col>
|
||||
</el-row>
|
||||
<el-row :gutter="10">
|
||||
|
||||
<el-col :span="12">
|
||||
<div class="design-component">右侧列2</div>
|
||||
</el-col>
|
||||
</el-row>
|
||||
<el-col :span="12">
|
||||
<div class="design-component">右侧列1</div>
|
||||
</el-col>
|
||||
|
||||
<el-row :gutter="10">
|
||||
<el-col :span="12">
|
||||
<div class="design-component">右侧列2</div>
|
||||
</el-col>
|
||||
|
||||
</el-row>
|
||||
</el-col>
|
||||
<el-col :span="12">
|
||||
<div class="design-component">右侧列1</div>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</template>
|
||||
|
||||
|
||||
Reference in New Issue
Block a user