How do I make this function not run infinitely?

So I was told

In this topic:

For my script.

How can I make the loop not run infinitely?

no,this doesn’t do anything, and Disconnect doesn’t take any arguments,this is an example of Disconnect:

local con ; con = game.PlayerRemoving:Connect(function()
   con:Disconnect() -- Disconnecting the function
end)
Players.PlayerRemoving:Connect(function(player)
--do stuff
end)

The reason we use :Disconnect() is because we don’t want these connections that came from using :Connect() to use up our memory, and because we don’t need that connection anymore.


This is an example to use disconnect:

local Brick = script.Parent

TouchConnection = Brick.Touched:Connect(function()
    TouchConnection:Disconnect()
end)

To make something disconnectable you have to make the connection a variable:

Not like this

Brick.Touched:Connect(function()

Like this

local TouchConnection = Brick.Touched:Connect(funcction() -- Notice the variable, "TouchConnection"

Oh. Well, how do I make this function in the script not run infinitely?

-- datastores
local levelingDataStore = game:GetService("DataStoreService"):GetDataStore("LevelingSystemTest#102")

-- functions
game.Players.PlayerAdded:Connect(function(plr)
	pcall(function()
		local levelsFolder = Instance.new("Folder", plr)
		levelsFolder.Name = "Levels"
		local level = Instance.new("IntValue", levelsFolder)
		level.Name = "Level"
		local xp = Instance.new("IntValue", levelsFolder)
		xp.Name = "XP"
		local xprequire = Instance.new("IntValue", levelsFolder)
		xprequire.Name = "XP_REQUIREMENT"
		local xpadd = Instance.new("IntValue", levelsFolder)
		xpadd.Name = "XP_ADD"
		
		local levelingData = nil
		levelingData = levelingDataStore:GetAsync(plr.UserId)
		
		if levelingData ~= nil then
			for i, v in pairs(levelsFolder:GetChildren()) do
				v.Value = levelingData[v.Name]
			end
			print("Success")
		elseif levelingData == nil then
			levelsFolder.XP_REQUIREMENT.Value = 900
			levelsFolder.XP_ADD.Value = 200
			levelsFolder.Level = 1
			print("Success")
		end
		gainXP(plr)
		print("Function success")
	end)
end)

function saveData(plr)
	pcall(function()
		local levelingFolder = plr:WaitForChild("Levels")
		if levelingFolder then
			local levelingData = {}
			for i,v in pairs(levelingFolder:GetChildren()) do
				levelingData[v.Name] = v.Value
			end
			levelingDataStore:SetAsync(plr.UserId, levelingData)
			print("Success")
		end
	end)
end

game.Players.PlayerRemoving:Connect(saveData)
game.Players.PlayerRemoving:Disconnect(gainXP)

function gainXP(plr)
	local lvls = plr.Levels
	
	local xpNeeded = lvls.XP_REQUIREMENT.Value
	local lvl = lvls.Level
	local xp = lvls.XP
	local xpToAdd = lvls.XP_ADD.Value
	
	if xpNeeded ~= nil then
	
	print(xpNeeded)
	print(xpToAdd)
	
	while wait(5) do
		
		xp.Value = xp.Value + xpToAdd
		print("XP Success")
		
		if xp.Value >= xpNeeded then
			lvl.Value = lvl.Value + 1
			xp.Value = 0
			
			xpToAdd = 200 + (lvl.Value * 1)
			xpNeeded = 900 + (lvl.Value * 50)
			
			print(xpToAdd)			
			print(xpNeeded)
			print("Success")
			
			saveData(plr)
		end
	end
	end
end

Please define the function called gainXP() before any other function that calls it. Otherwise your script will not work properly.

Your while loop will not run forever. It will stop once the player leaves and the player object is destroyed among all its descendants, including xp number/int value. The function will just error when trying to index xp.Value.

xp.Value = xp.Value + xpToAdd

To avoid this hacky way to break the loop, modify it slighty:

while plr do
    wait(5)
    --code
end

There, happy ending for the function!

Also, there is no need/point on doing this…

game.Players.PlayerRemoving:Disconnect(gainXP)

… since gainXP was never connected to that event. If you want it to be fired when a player leaves the game, use :Connect(gainXP) instead, just like you did with saveData the previous line.

1 Like

while wait technically isn’t a function.

I’ll guess that this is a datastore script, so the while wait is unnecessary. But to break the loop simply use break

I’m not sure why you’re using a loop in this function, but if it is necessary you can use break somewhere in the loop when you want it to stop.