using Godot; public partial class DragMover : Node { [Export] public Node2D Parent; // The node that will move [Export] public Area2D DragArea; // Click detection [Export] public Area2D CheckArea; // Overlap validation [Export] public Area2D ShootArea; // This gets disabled while dragging private bool _dragging; private Vector2 _dragOffset; private Vector2 _originalPosition; private bool _canMove = true; public override void _Ready() { if (Parent == null || DragArea == null || CheckArea == null) { GD.PushError("DragMover exports are not assigned."); return; } DragArea.InputEvent += OnDragAreaInputEvent; _originalPosition = Parent.GlobalPosition; } private void OnDragAreaInputEvent(Node viewport, InputEvent @event, long shapeIdx) { if (!_canMove) return; if (@event is not InputEventMouseButton mb) return; if (mb.ButtonIndex != MouseButton.Left) return; if (mb.Pressed) { _dragging = true; ShootArea.Monitoring = false; _originalPosition = Parent.GlobalPosition; _dragOffset = Parent.GlobalPosition - Parent.GetGlobalMousePosition(); } else { _dragging = false; ShootArea.Monitoring = true; // Check overlaps when released if (CheckArea.HasOverlappingAreas() || CheckArea.HasOverlappingBodies()) { Parent.GlobalPosition = _originalPosition; } else { MovementDelay(); } } } public override void _Process(double delta) { if (!_dragging) return; Parent.GlobalPosition = Parent.GetGlobalMousePosition() + _dragOffset; } private async void MovementDelay() { ShootArea.Monitoring = false; _canMove = false; Parent.SetModulate(Color.FromHtml("ffffff20")); await ToSignal(GetTree().CreateTimer(4), SceneTreeTimer.SignalName.Timeout); Parent.SetModulate(Color.FromHtml("ffffffff")); ShootArea.Monitoring = true; _canMove = true; } }