I need help with creating a lobby spawner

Well basically what I want to create is :

1- players spawn in the lobby and game starts when two players are in the game (Text that says "There must be 2 players to start, invite your friends).

2- when there are two players, wait for 10 seconds
the players are then teleported into

3- chosen teams in the game area ( the script for the random chosen team is already done)

4-intermission timer for 5 secs with a red wall that blocks the players from going through ( already done )

5-game timer for 10 secs and the red wall disappears so the players can fight ( done)

6-the players are teleported back to the lobby and the script loops ( without the wait for 2 players )

So what i have trouble making is the 1,2 and 6. Basically the wait for 2 players and teleporting from lobby to the game and vice versa. Lastly, where the loop should be placed…

local roundLength = 5
local intermissionLength = 10
local InRound = game.ReplicatedStorage.InRound
local Status = game.ReplicatedStorage.Status


local Teams = game:GetService("Teams"):GetChildren()
local TeamsService = game:GetService("Teams")
local ReplicatedStorage = game:GetService("ReplicatedStorage")

local balanceTeamsEvent = Instance.new("BindableEvent")
balanceTeamsEvent.Name = "BalanceTeamsEvent"
balanceTeamsEvent.Parent = ReplicatedStorage
local player1Spawn = game.Workspace.Player1Spawn
local player2Spawn = game.Workspace.Player2Spawn

game.Players.PlayerAdded:Connect(function(player)

	for i, player in pairs(game.Players:GetPlayers())do
		if player then
			if player.Team == nil then
				local Team = Teams[math.random(1, #Teams)]

				player.Team = Team

			end
		end
	end
end)

local function roundTimer()
	
	while wait() do
		for i = intermissionLength, 1, -1 do
			InRound.Value = false
			wait(1)
			Status.Value = "Intermission: ".. i .." seconds left!"
			
			
			local wall = game.Workspace.RedWall
			wall.Transparency = 0.2
			wall.CanCollide = true
			wall.Anchored = true
			
		end
		
		local wall = game.Workspace.RedWall
		
	for i = roundLength, 1, -1 do
			InRound.Value = true
			wait(1)
			Status.Value = "Game: ".. i .." seconds left!"
			
			wall.Transparency = 1
			wall.CanCollide = false
			wall.Anchored = true
			end
		end
	end

spawn(roundTimer)```
1 Like

Snipping this, nothing to see here.

2 Likes

Hey. Thanks for your reply, i tried the script but I have an issue, I’ll show you below
= 11:45:37.047 ServerScriptService.MainFrame:29: attempt to get length of a Instance value - Server - MainFrame:29
Additionally, I shall show you my explorer tab and updated script so you can tell me if this is alright.
In replicated storage, InRound is a BoolValue and Status is a StringValue…

local players = game:GetService("Players")
local teamsService = game:GetService("Teams")
local teams = game:GetService("Teams"):GetChildren()
local replicatedStorage = game:GetService("ReplicatedStorage")
local inRound = replicatedStorage.InRound
local status = replicatedStorage.Status
local balanceTeamsEvent = Instance.new("BindableEvent")
balanceTeamsEvent.Name = "BalanceTeamsEvent"
balanceTeamsEvent.Parent = replicatedStorage
local player1Spawn = game.Workspace.Player1Spawn
local player2Spawn = game.Workspace.Player2Spawn
local wall = game.Workspace.RedWall
local roundLength = 5
local intermissionLength = 10
local lobby = game.Workspace.LobbySpawn
local MainAreaSpawn = game.Workspace.MainAreaSpawn

players.PlayerAdded:Connect(function(player)
	if player then
		if player.Team == nil then
			local team = teams[math.random(1, #teams)]
			player.Team = team
		end
	end
end)

local function doRound()
	local players = game:GetService("Players")
	if #players <= 1 then
		status.Value = "Waiting: 2 or more players are required to start!"
		repeat
			task.wait()
			players = game:GetService("Players")
		until #players >= 2
	end
	if inRound.Value then --round in progress
		return
	else --round not in progress
		inRound.Value = true --start round
		local roundPlayers = players:GetPlayers() --get round players
		for i, player in pairs(roundPlayers) do
			local character = player.Character
			local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to lobby
			hmr.CFrame = lobby.CFrame --change this to lobby spawn
		end
		wall.Transparency = 0.2
		wall.CanCollide = true
		wall.Anchored = true
		for i = intermissionLength, 0, -1 do
			task.wait(1)
			status.Value = "Intermission: ".. i .." seconds left!"
		end
		for i, player in pairs(roundPlayers) do
			local character = player.Character
			local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to main area
			hmr.CFrame = MainAreaSpawn.CFrame --change this to main area spawn
		end
		wall.Transparency = 1
		wall.CanCollide = false
		wall.Anchored = true
		for i = roundLength, 0, -1 do
			task.wait(1)
			status.Value = "Game: ".. i .." seconds left!"
		end
		status.Value = "Game: 0 seconds left, the game has ended!"
		task.wait(5)
		inRound.Value = false
	end
end

task.spawn(function()
	while task.wait() do
		doRound()
	end
end)
2 Likes

Ignore this, nothing to see here.

1 Like

I tried the edit, but the timer doesn’t work anymore…

1 Like

Snipping, since no longer relevant.

1 Like

Oh yes, sorry that was stupid of me. Nonetheless when I start the game, it shows me “Label” over my head which is where I had the timer gui

1 Like

Also, would it be possible to make it so that the players are spawned first into the lobby and then prompted with “2 players needed” THEN teleported into the game area where they are divided randomly into two teams (AKA two spawns) then intermission, then game timer and finally when the game is over they are teleported back to the lobby and the scripts starts again (sorry for the mess)

1 Like

Snipping again, nothing to see here.

1 Like

12:08:15.962 ServerScriptService.MainFrame:32: attempt to index nil with 'WaitForChild' - Server - MainFrame:32

1 Like

I sent a picture of the Explorer above

1 Like

Snipping, please ignore this post.

1 Like
local players = game:GetService("Players")
local teamsService = game:GetService("Teams")
local teams = game:GetService("Teams"):GetChildren()
local replicatedStorage = game:GetService("ReplicatedStorage")
local inRound = replicatedStorage:WaitForChild("InRound")
local statusMsg = replicatedStorage:WaitForChild("Status")
local balanceTeamsEvent = Instance.new("BindableEvent")
balanceTeamsEvent.Name = "BalanceTeamsEvent"
balanceTeamsEvent.Parent = replicatedStorage
local player1Spawn = game.Workspace:WaitForChild("Player1Spawn")
local player2Spawn = game.Workspace:WaitForChild("Player2Spawn")
local wall = game.Workspace:WaitForChild("RedWall")
local roundLength = 5
local intermissionLength = 10

players.PlayerAdded:Connect(function(player)
	if player then
		if player.Team == nil then
			local team = teams[math.random(1, #teams)]
			player.Team = team
		end
	end
end)

local function doRound()
	inRound.Value = true --start round
	local roundPlayers = players:GetPlayers() --get round players
	for i, player in pairs(roundPlayers) do
		local character = workspace:FindFirstChild(player.Name)
		local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to lobby
		hmr.CFrame = player1Spawn.CFrame --change this to lobby spawn
	end
	if #roundPlayers <= 1 then
		statusMsg.Value = "Waiting: 2 or more players are required to start!"
		repeat
			task.wait()
			roundPlayers = players:GetPlayers()
		until #roundPlayers >= 2
	end
	wall.Transparency = 0.2
	wall.CanCollide = true
	wall.Anchored = true
	for i = intermissionLength, 0, -1 do
		task.wait(1)
		statusMsg.Value = "Intermission: ".. i .." seconds left!"
	end
	for i, player in pairs(roundPlayers) do
		local character = workspace:FindFirstChild(player.Name)
		local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to main area
		hmr.CFrame = player2Spawn.CFrame --change this to main area spawn
	end
	wall.Transparency = 1
	wall.CanCollide = false
	wall.Anchored = true
	for i = roundLength, 0, -1 do
		task.wait(1)
		statusMsg.Value = "Game: ".. i .." seconds left!"
	end
	statusMsg.Value = "Game: 0 seconds left, the game has ended!"
	task.wait(5)
	inRound.Value = false
end

task.spawn(function()
	while task.wait() do
		if inRound.Value then
		else
			doRound()
		end
	end
end)
2 Likes

1 Like

This is how the overall script looks with the explorer.

local players = game:GetService("Players")
local teamsService = game:GetService("Teams")
local teams = game:GetService("Teams"):GetChildren()
local replicatedStorage = game:GetService("ReplicatedStorage")
local inRound = replicatedStorage:WaitForChild("InRound")
local statusMsg = replicatedStorage:WaitForChild("Status")
local balanceTeamsEvent = Instance.new("BindableEvent")
balanceTeamsEvent.Name = "BalanceTeamsEvent"
balanceTeamsEvent.Parent = replicatedStorage
local player1Spawn = game.Workspace:WaitForChild("Player1Spawn")
local player2Spawn = game.Workspace:WaitForChild("Player2Spawn")
local wall = game.Workspace:WaitForChild("RedWall")
local roundLength = 5
local intermissionLength = 10

players.PlayerAdded:Connect(function(player)
	if player then
		if player.Team == nil then
			local team = teams[math.random(1, #teams)]
			player.Team = team
		end
	end
end)

local function doRound()
	inRound.Value = true --start round
	local roundPlayers = players:GetPlayers() --get round players
	for i, player in pairs(roundPlayers) do
		local character = workspace:FindFirstChild(player.Name)
		local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to lobby
		hmr.CFrame = player1Spawn.CFrame --change this to lobby spawn
	end
	if #roundPlayers <= 1 then
		statusMsg.Value = "Waiting: 2 or more players are required to start!"
		repeat
			task.wait()
			roundPlayers = players:GetPlayers()
		until #roundPlayers >= 2
	end
	wall.Transparency = 0.2
	wall.CanCollide = true
	wall.Anchored = true
	for i = intermissionLength, 0, -1 do
		task.wait(1)
		statusMsg.Value = "Intermission: ".. i .." seconds left!"
	end
	for i, player in pairs(roundPlayers) do
		local character = workspace:FindFirstChild(player.Name)
		local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to main area
		hmr.CFrame = player2Spawn.CFrame --change this to main area spawn
	end
	wall.Transparency = 1
	wall.CanCollide = false
	wall.Anchored = true
	for i = roundLength, 0, -1 do
		task.wait(1)
		statusMsg.Value = "Game: ".. i .." seconds left!"
	end
	statusMsg.Value = "Game: 0 seconds left, the game has ended!"
	task.wait(5)
	inRound.Value = false
end

task.spawn(function()
	while task.wait() do
		if inRound.Value then
		else
			doRound()
		end
	end
end)
1 Like
local players = game:GetService("Players")
local teamsService = game:GetService("Teams")
local teams = game:GetService("Teams"):GetChildren()
local replicatedStorage = game:GetService("ReplicatedStorage")
local inRound = replicatedStorage:WaitForChild("InRound")
local statusMsg = replicatedStorage:WaitForChild("Status")
local balanceTeamsEvent = Instance.new("BindableEvent")
balanceTeamsEvent.Name = "BalanceTeamsEvent"
balanceTeamsEvent.Parent = replicatedStorage
local player1Spawn = game.Workspace:WaitForChild("Player1Spawn")
local player2Spawn = game.Workspace:WaitForChild("Player2Spawn")
local wall = game.Workspace:WaitForChild("RedWall")
local loadLength = 5
local clearLength = 5
local roundLength = 5
local intermissionLength = 10

players.PlayerAdded:Connect(function(player)
	if player then
		if player.Team == nil then
			local team = teams[math.random(1, #teams)]
			player.Team = team
		end
	end
end)

local function doRound()
	inRound.Value = true --start round
	for i = loadLength, 0, -1 do
		statusMsg.Value = "Loading: ".. i .." seconds left!"
	end
	local roundPlayers = players:GetChildren() --get round players
	for i, v in pairs(roundPlayers) do
		local character = v.Character
		local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to lobby
		hmr.CFrame = player1Spawn.CFrame --change this to lobby spawn
	end
	if #roundPlayers <= 1 then
		statusMsg.Value = "Waiting: 2 or more players are required to start!"
		repeat
			task.wait()
			roundPlayers = players:GetChildren()
		until #roundPlayers >= 2
	end
	wall.Transparency = 0.2
	wall.CanCollide = true
	wall.Anchored = true
	for i = intermissionLength, 0, -1 do
		task.wait(1)
		statusMsg.Value = "Intermission: ".. i .." seconds left!"
	end
	for i, v in pairs(roundPlayers) do
		local character = v.Character
		local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to main area
		hmr.CFrame = player2Spawn.CFrame --change this to main area spawn
	end
	wall.Transparency = 1
	wall.CanCollide = false
	wall.Anchored = true
	for i = roundLength, 0, -1 do
		task.wait(1)
		statusMsg.Value = "Game: ".. i .." seconds left!"
	end
	statusMsg.Value = "Game: 0 seconds left, the game has ended!"
	for i = clearLength, 0, -1 do
		statusMsg.Value = "Clearing: ".. i .. " seconds left!"
	end
	inRound.Value = false
end

task.spawn(function()
	while task.wait() do
		if inRound.Value then
		else
			doRound()
		end
	end
end)

I’ve added a loading delay before the first round starts. Hopefully that should allow for everything to load in correctly.

1 Like

Theres an error at line 37 :

local hmr = character:WaitForChild("HumanoidRootPart") --teleport players to lobby

12:29:00.947 ServerScriptService.MainFrame:36: attempt to index nil with ‘WaitForChild’ - Server - MainFrame:36

1 Like

1 Like

I dont understand what the problem is in that line, I copied letter for letter what you wrote and it still says it attempts to index NIL with WaitForChild… at line 37

1 Like

Snipping this post again, nothing to see.

1 Like