Why don't my functions run at the same time?

Achieve

I am simply trying to make it so all of my functions run at the same time.

Issues

The issue is that no matter what, the functions seem to run after each-other rather than with each other.
Here’s 1 Gif of it
Here’s a 2nd Gif of it

Solutions

I’ve tried rescripting the Power function, changing issues and so on.
I’ve tried using a coroutine.wrap, that just times itself out which breaks itself.

IMPORTANT NOTE

The script runs perfectly fine, the only issue is that all the functions aren’t running at the same time.
The Toggle is the receiver to see if the Power’s value is true or false.
Yes, all the screens are the exact same but that’s because I didn’t want to put different images for each function while testing my new system.

local Power = script.Parent.Power
Power.Changed:Connect(function(Toggle)
	if Toggle == true then
		repeat
			TVTop() --Activates the TVTop Function
			TV() --Activates the TV Function
			Screen1() --Activates the Screen1 Function
			Screen2() --Activates the Screen2 Function
			Side1() --Activates the Side1 Function
			Side2() --Activates the Side2 Function
			Side3() --Activates the Side3 Function
			Side4() --Activates the Side4 Function
		until Toggle == false --This does not need to be changed to Power.Value. The toggle checks the BoolValue's Enabled State.
	end
end)

Thank you for any help you can give.

2 Likes

Roblox Lua is single-threaded so you will never be able to run code in true parallel. What you can instead try doing is running each one in a separate coroutine.

Instead have all your functions in a table. Kind of like this

local functions = {
    TV = function()
        -- ...
    end,
    -- And so on for the other ones
}

Then in the repeat until loop you can do

for _, f in pairs(functions) do
    coroutine.wrap(f)()
end

So that you don’t need to wait for one function call to finish to proceed with the next. By the way, == true/== false is redundant since Toggle is already a boolean, so all you are doing is comparing it to a boolean only to get another boolean out of that comparison. Just do if Toggle then or if not Toggle then.

4 Likes

So when you were talking about the function tables, did you mean like this?

local PowerFunctions = {
	TVTop = TVTop(), --[[Activates the TVTop Function]]	
	TV = TV(), --[[Activates the TV Function]]
	Screen1 = Screen1(), --[[Activates the Screen1 Function]]
	Screen2 = Screen2(), --[[Activates the Screen2 Function]]
	Side1 = Side1(), --[[Activates the Side1 Function]]
	Side2 = Side2(), --[[Activates the Side2 Function]]
	Side3 = Side3(), --[[Activates the Side3 Function]]
	Side4 = Side4() --[[Activates the Side4 Function]]
	}
local Power = script.Parent.Power
Power.Changed:Connect(function(Toggle)
	if Toggle then
		repeat
			for I,F in pairs (PowerFunctions) do
				coroutine.wrap(F)()
			end
		until not Toggle
	end
end)

Side Note: I originally did that for the Power Toggle but everyone kept stating that oH yOu nEeD tO cHaNgE tHaT!:expressionless:

No, you remove the parentheses.

local PowerFunctions = {
	TVTop = TVTop, --[[Activates the TVTop Function]]	
	TV = TV, --[[Activates the TV Function]]
	Screen1 = Screen1, --[[Activates the Screen1 Function]]
	Screen2 = Screen2, --[[Activates the Screen2 Function]]
	Side1 = Side1, --[[Activates the Side1 Function]]
	Side2 = Side2, --[[Activates the Side2 Function]]
	Side3 = Side3, --[[Activates the Side3 Function]]
	Side4 = Side4 --[[Activates the Side4 Function]]
}

So, I did what you advised and it does work… however I end up timing out the script, just as what has happened in the past. It loops constantly until it inevitably timeout.
image

This generally happens if you add stuff to the table while traversing it. Are you by any chance adding any key-value pairs?

Elaborate please…

A function

local function TV() --Jumbotron
	local ID = game.Workspace.Equipment.Screens.TV
	local AssetLink = "http://www.roblox.com/asset/?id="
	ID.Image = AssetLink.."4824725178" 
	wait(0.5)
	ID.Image = AssetLink.."4824724623" 
	wait(0.5)
	ID.Image = AssetLink.."4824725178" 
	wait(0.5)
	ID.Image = AssetLink.."4824724623" 
	wait(0.5)
	ID.Image = AssetLink.."4824725178" 
	wait(0.5)
	ID.Image = AssetLink.."4824724623" 
	wait(0.5)
	ID.Image = AssetLink.."4824725178" 
	wait(0.5)
	ID.Image = AssetLink.."4824724623" 
	wait(0.5)
end

SIDE NOTE: I did add a wait to the repeat but I worry hat if someone has only one image, that the wait will conflict with the function.

local Power = script.Parent.Power
Power.Changed:Connect(function(Toggle)
	if Toggle then
		repeat
			for I,F in pairs (PowerFunctions) do
				coroutine.wrap(F)()
			end
			wait(5)
		until not Toggle
	end
end)

Edit

Just as I suspected, I lowered the wait(5) to wait(0.05).
The issue with me making them all one value is that not everyone will need their wait value to be one value.
https://gyazo.com/aaffa9b8caac6120ac43e58de88718bc

It’d probably be worth reassessing your system if the screens are just the exact same, because now you’re also dealing with code redundancy. For example, you could set what the current image across all screens should be from one function and then from another, update all the screens at once in a loop.

I’m not making the assumption that you have arbitrary image settings here though. If you do, then it would really be worth revisiting how you’re doing this so you can stray away from hard coding this logic.

Please Elaborate,
I don’t know exactly what I could do to make this work properly nor to reassess it.
Also, I do need all the functions that are here so I have a conundrum…

Have you looked-up spawn() or preferably the “fastspawn” technique?
Simply separate scripts can also be used to “run at the same time” (not really, as stated earlier.)
In reading the various groups, I’ve noticed a tendency for people to almost have the opposite
understanding of what coroutines are. If you want to use coroutines here to have all screen updates
on the same thread, you should be going frame-by-frame, and then you’ll have to manage that too,
which may be a bit more advanced.

1 Like

Yes, as I stated… I looked into every single way possible… I’ve found a solution, thank you for trying to help though.

Okay so I ended up making a script Value through a variable and in each function, I made it so the function repeats until the value is nil.