Hey. So I am making an order board, which has several parts inside of it. It moves decals from the highest to lowest numbered part.
This script works, but I dont think using while true do is efficient.
local next = script.Parent.Parent:FindFirstChild(script.Parent.Name - 1) -- Finds next space --------------------Detects next box for Decal, if false, moves "next"------------------------- while true do -- Loop Script repeat wait() until script.Parent:FindFirstChildOfClass("Decal") ~= nil and -- If current order true and next order nil, continue next:FindFirstChildOfClass("Decal") == nil if next:FindFirstChildOfClass("Decal") == nil then -- If next order nil, move current order forward wait(2) local g = script.Parent:GetChildren() for i = 1 ,#g do if g[i].className == "Decal" then repeat wait() until next:FindFirstChildOfClass("Decal") == nil g[i].Parent = next end end end end
You can use RunService and you can use task.wait() instead of wait() because the task library allows u to communicate directly with the game engine’s task schedular.
Here is a link to Task Library if u want to know more about it!
If you can, try to use and somehow implement GetPropertyChangedSignal() instead of while loops in your code.
I tried to understand and rewrite the function of your code, and here’s what I came up with:
local next = script.Parent.Parent[tostring(tonumber(script.Parent.Name) - 1)] script.Parent.ChildAdded:Connect(function(child) if child.ClassName ~= "Decal" then return end if next:FindFirstChildOfClass("Decal") then return end wait(2) local decals = script.Parent:GetChildren() for _,d in ipairs(decals) do if d:IsA("Decal") then d.Parent = next end end end)
I think its to do with the function script.Parent.ChildAdded:Connect(function(child)
I dont really understand why it wouldnt do anything though. Does the script need to be a Local Script? I dont think using that type would be a good idea though.
I tested and came up with this script that changes the parent of a Decal to the parts in descending order based on name. Feel free to try it out:
local parts = script.Parent:GetChildren() table.foreachi(parts, function(i, v) if not v:IsA("BasePart") then table.remove(parts, i) end end) table.sort(parts, function(a, b) return (tonumber(a.Name) or 0) < (tonumber(b.Name) or 0) end) for i,p in ipairs(parts) do local function onChildAdded(child) if not child:IsA("Decal") then return end local nextPart = parts[i - 1] or parts[#parts] if nextPart:FindFirstChildOfClass(child.ClassName) then return end task.wait(2) child.Parent = nextPart end p.ChildAdded:Connect(onChildAdded) for _,c in ipairs(p:GetChildren()) do onChildAdded(c) end end
If you need something that runs a lot but don’t necessarily need a “while true do” as such, and your code revolves around something that is often changing, you’re potentially better off with Instance.Property.Changed:Connect()
If you absolutely must have a while true do, and you will never ever want to escape it, you can cut down on lines/make it cleaner by making it while wait() do instead. Does the same as putting a wait() in a while true do loop, just a lot less characters.
I don’t think you have to be worried about that, unless you are using an unhealthy amount of remote events and remote functions. Also, you might wanna include a wait of sorts in the while loop.