From 75d03fe577b2e61180b7e7e6cb1a61f31ba2b08f Mon Sep 17 00:00:00 2001 From: "Janus C. H. Knudsen" Date: Wed, 8 Oct 2025 19:01:35 +0200 Subject: [PATCH] Improves drag and drop position calculation Refines drag and drop functionality by calculating position relative to the column during drag and snapping to the grid on mouse up, resulting in more precise placement. Addresses an issue where the dragged element's position was not correctly calculated relative to the target column. --- src/managers/DragDropManager.ts | 37 ++++++++++++++++++++++++--------- 1 file changed, 27 insertions(+), 10 deletions(-) diff --git a/src/managers/DragDropManager.ts b/src/managers/DragDropManager.ts index b713971..793e9f0 100644 --- a/src/managers/DragDropManager.ts +++ b/src/managers/DragDropManager.ts @@ -262,12 +262,15 @@ export class DragDropManager { // Continue with normal drag behavior only if drag has started if (this.isDragStarted && this.draggedElement && this.draggedClone) { if (!this.draggedElement.hasAttribute("data-allday")) { - // Calculate raw target position from mouse (no snapping yet) - const positionData = this.calculateDragPosition(currentPosition); + // Calculate raw position from mouse (no snapping) + const column = ColumnDetectionUtils.getColumnBounds(currentPosition); - if (positionData.column) { - this.targetY = positionData.snappedY; // Store raw Y as target - this.targetColumn = positionData.column; + if (column) { + // Calculate raw Y position relative to column (accounting for mouse offset) + const columnRect = column.boundingClientRect; + const eventTopY = currentPosition.y - columnRect.top - this.mouseOffset.y; + this.targetY = Math.max(0, eventTopY); // Store raw Y as target (no snapping) + this.targetColumn = column; // Start animation loop if not already running if (this.dragAnimationId === null) { @@ -314,8 +317,22 @@ export class DragDropManager { if (this.isDragStarted) { const mousePosition: MousePosition = { x: event.clientX, y: event.clientY }; - // Use consolidated position calculation - const positionData = this.calculateDragPosition(mousePosition); + // Snap to grid on mouse up (like ResizeHandleManager) + const column = ColumnDetectionUtils.getColumnBounds(mousePosition); + + if (!column) { + console.warn('No column detected on mouseUp'); + return; + } + + // Get current position and snap it to grid + const currentY = parseFloat(this.draggedClone?.style.top || '0'); + const snappedY = this.calculateSnapPosition(mousePosition.y, column); + + // Update clone to snapped position immediately + if (this.draggedClone) { + this.draggedClone.style.top = `${snappedY}px`; + } // Detect drop target (swp-day-column or swp-day-header) const dropTarget = this.detectDropTarget(mousePosition); @@ -325,8 +342,8 @@ export class DragDropManager { console.log('🎯 DragDropManager: Emitting drag:end', { draggedElement: this.draggedElement.dataset.eventId, - finalColumn: positionData.column, - finalY: positionData.snappedY, + finalColumn: column, + finalY: snappedY, dropTarget: dropTarget, isDragStarted: this.isDragStarted }); @@ -335,7 +352,7 @@ export class DragDropManager { originalElement: this.draggedElement, draggedClone: this.draggedClone, mousePosition, - finalPosition: positionData, + finalPosition: { column, snappedY }, target: dropTarget }; this.eventBus.emit('drag:end', dragEndPayload);