Tween With Function Help

Hello! I have many buttons I’m trying to offset to the right. Am I able to use a single function for all animations? I’m very new to using the same function for many different objects. Am I able to tell whatever button is moused over to offset to the right by say 30?

Here’s what I have so far but it only works on one button and tweens to that exact buttons position.

local Tween = game:GetService("TweenService")
local Catagory = script.Parent.Main.Catagory
local weaponButton = Catagory.WeaponsButton
local medicineButton = Catagory.MedicineButton
local toolsButton = Catagory.ToolsButton
local armorButton = Catagory.ArmorButton
weaponButton.Modal = true
local function TweenCatagoryIn()
	local tweening
	tweening = true
	if tweening then
		weaponButton:TweenPosition(
			UDim2.new(0.393, 30,0.388, 0),
			Enum.EasingDirection.In,
			Enum.EasingStyle.Linear,
			0.1,
			true)
		wait(0.1)
		tweening = false
	end
end
local function TweenCatagoryOut()
	local tweening = false
	tweening = true
	if tweening == true then
		weaponButton:TweenPosition(
			UDim2.new(0.393, 0,0.388, 0),
			Enum.EasingDirection.In,
			Enum.EasingStyle.Linear,
			0.1,
			true)
		wait(0.1)
		tweening = false
	end
end
local tweens = game:GetService("TweenService")
local run = game:GetService("RunService")
local mouseIn
weaponButton.MouseEnter:Connect(TweenCatagoryIn)
medicineButton.MouseEnter:Connect(TweenCatagoryIn)
toolsButton.MouseEnter:Connect(TweenCatagoryIn)
armorButton.MouseEnter:Connect(TweenCatagoryIn)
weaponButton.MouseLeave:Connect(TweenCatagoryOut)
medicineButton.MouseLeave:Connect(TweenCatagoryOut)
toolsButton.MouseLeave:Connect(TweenCatagoryOut)
armorButton.MouseLeave:Connect(TweenCatagoryOut)

Instead of manually assigning each event to a function, you can use a for loop to automatically create these events. Here is what your code would look like if you were to use this.

-- I used an array here, but you could also just loop through everything in "Category" if all your buttons are there and nothing else
local buttons = {toolsButton, armorButton, medicineButton}
for _, button in buttons do
	button.MouseEnter:Connect(function()
		-- this tweening variable does nothing. You're making an new variable and setting it to true everytime and then immediately checking if it's true
		local tweening
		tweening = true
		if tweening then
			button:TweenPosition(
				-- edit this UDim2 to have it referenced to the button's position, not a set position
				UDim2.new(0.393, 30,0.388, 0),
				Enum.EasingDirection.In,
				Enum.EasingStyle.Linear,
				0.1,
				true)
			task.wait(0.1) -- use task.wait
			tweening = false
		end
	end)
	-- same stuff here
	button.MouseLeave:Connect(function()
		local tweening = false
		tweening = true
		if tweening == true then
			button:TweenPosition(
				UDim2.new(0.393, 0,0.388, 0),
				Enum.EasingDirection.In,
				Enum.EasingStyle.Linear,
				0.1,
				true)
			task.wait(0.1)
			tweening = false
		end
	end)
end
2 Likes

Taking that a step further, you could forego the booleans and statements by using the ternary operator.

local function main()
    -- ROBLOX has implemented this in the form of a one-line if-else, though if you prefer the and-or makeshift version:
    -- button:TweenPosition((button.Position == UDim2.new(0.393, 0, 0.388, 0)) and UDim2.new(0.393, 30, 0.388, 0) or UDim2.new(0.393, 0, 0.388, 0)
    button:TweenPosition(if button.Position == UDim2.new(0.393, 0, 0.388, 0) then UDim2.new(0.393, 30, 0.388, 0) else UDim2.new(0.393, 0, 0.388, 0)
end

for _, button in buttons do
    button.MouseEnter:Connect(main)
end

That’s really cool! Had no idea you could make events with a loop. Here’s the code with your changes. I’m stuck on how to make the buttons move based on relative position?

local Tween = game:GetService("TweenService")
local Catagory = script.Parent.Main.Catagory
local sounds = script.Parent.Sounds
local buttons = Catagory.Buttons:GetChildren()
for _, button in buttons do
	button.MouseEnter:Connect(function()
		button:TweenPosition(
			UDim2.new(button.Position.X.Scale, button.Position.X.Offset + 15, button.Position.Y.Scale, button.Position.Y.Offset), -- Would it be like this?
			Enum.EasingDirection.In,
			Enum.EasingStyle.Linear,
			0.1,
			true)
		task.wait(0.1) -- use task.wait
	end)
end
for _, button in buttons do
	button.MouseLeave:Connect(function()
		button:TweenPosition(
			UDim2.new(0.393, 0,0.388, 0),
			Enum.EasingDirection.In,
			Enum.EasingStyle.Linear,
			0.1,
			true)	
		task.wait(0.1)
	end)
end

That actually works but now the buttons slowly slide to the left off of the screen if you mouse over them really fast? haha
How do I make them return to their original position? Doing this all in a loop is really hurting my brain lol

You’d need to reference their original position when making the tween to return to their position. As I said before, you should also make a different position for where they should go. This is what my implementation of this would look like for the code you mentioned:

local Catagory = script.Parent.Main.Catagory
local sounds = script.Parent.Sounds
local buttons = Catagory.Buttons:GetChildren()
for _, button in buttons do
	local originalPosition = button.Position
	button.MouseEnter:Connect(function()
		button:TweenPosition(
			UDim2.new(originalPosition.X.Scale, 30, originalPosition.Y.Scale, originalPosition.Y.Offset)
		)
	end)
	button.MouseLeave:Connect(function()
		button:TweenPosition(originalPosition,Enum.EasingDirection.In,Enum.EasingStyle.Linear,0.1,true)
	end)
end

Some other things to mention with your code is that you’re using two different loops when you can just use one loop as I did above. You also don’t need the variable “Tween” since you aren’t using TweenService at all. If you want specific positions for each individual button, like @anon_j1124 mentioned, you could do what he did or put the custom positions in a dictionary to find what position you want. For example, do something like myDictionary = {"ToolsButton" = toolsCustomPosition, "WeaponsButton" = weaponsCustomPosition} and then in the for loop you would get the position by using myDictionary[button.Name]. Another way you could do it on top of that, which is probably easier, is to use attributes in the button’s properties to set a position attribute that tells you its custom position.
Keep in mind that if the buttons have similar position properties, you have an option to replace the references with that shared number for a miniscule performance boost. (You’d have to change that number every time you move around the GUI though, so it might not be worth it unless there are properties you don’t plan to change, like the Y offset).

1 Like

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.