UIDragDetector dragging and snap to nearest frame

Hello! I am working on an inventory system and I want to use a UIDragDetector and it is working fine but I want the object I am dragging to snap to the nearest frame in a collection. Here is an example:
(the two red dots should snap together and the mouse is over the element being dragged)
image

and this is my code that doesn’t work:

local drag:UIDragDetector = guiObj.UIDragDetector
drag:AddConstraintFunction(1, function(proposedPos:UDim2, proposedRot)
	local posX = proposedPos.X.Offset
	local posY = proposedPos.Y.Offset
	for i,v in script.Parent.Inventory.Inventory:GetChildren() do
		if not v:IsA("Frame") then continue end
		local dist = (v.AbsolutePosition - guiObj.AbsolutePosition).Magnitude
		if dist < 25 then
           -- This makes the frame teleport away and my guess is due to reletivity
			posX = v.AbsolutePosition.X
			posY = v.AbsolutePosition.Y
			break
		end
	end
	
	return UDim2.fromOffset(posX, posY), proposedRot
end)

my drag detector settings:
image

Thanks for your help! (If anything needs more clarification or explaination don’t hesitate to ask)

Your current code is almost there, but it’s likely snapping incorrectly because AbsolutePosition is in screen coordinates while UDim2.fromOffset works in local GUI space. When you set posX = v.AbsolutePosition.X, you’re snapping it to screen space, which breaks the
layout.

Try converting the AbsolutePosition to local space first,

local localPos = guiObj.Parent:AbsoluteToLocal(v.AbsolutePosition)
posX = localPos.X
posY = localPos.Y

Then use UDim2.fromOffset(posX, posY) as you already are.

Let me know if your guiObj.Parent is not the immediate parent of the dragged object. It needs to be the GUI that controls its position for the snapping to align properly.

AbsoluteToLocal is not a valid member of Frame "Players.funfoxrr.PlayerGui.ScreenGui.InventoryGroup.InventoryContainer.Items"
The object is cloned and then set to the parent of a frame, is that a valid function…?

No, it is not. It as an AI solution, lol

1 Like
  1. Ideally, both GUIs have identical anchor points, as these influence the interpretation of absolute position. You can calculate the translation otherwise.

  2. Ideally, the dragging GUI object is a child of no other GUI object, as its position becomes relative. You can calculate the translation otherwise.

image

ex is the object I want to snap to
1__Test is the draggable object

They both have the same anchor point and I have no idea how I would calculate the relitivity from the ex object to the 1__Test object

if dist < 25 then
	-- horray!
	local localPos = UDim2.new(0, v.AbsolutePosition.X, 0, v.AbsolutePosition.Y) - UDim2.new(0, guiObj.Parent.AbsolutePosition.X, 0, guiObj.Parent.AbsolutePosition.Y)
	posX = localPos.X.Offset
	posY = localPos.Y.Offset
	print(posX, posY)
	break
end

for some reason I played around a bit and this seemed to work! Thanks for your help guys