So I created an iterator and a region3. Every time someone is inside the region, it prints their name multiple times. I tested with 2 people, but every time someone else goes in after the first person did, it doesn’t print their name anymore. I don’t know if the solution is very obvious… I tried using coroutines but that just would run a single time. (Even when adding coroutine.yield() )
for i, v in pairs(region_p) do
if v.Parent:FindFirstChild("Humanoid") and v.Name == "Head" then
local player = game.Players:GetPlayerFromCharacter(v.Parent)
print(player.Name)
--DrRe:FireClient(player, value)
end
end
You’d have to wrap it in a loop to check for players every x amount of time. You can also check multiple regions at one time with coroutines which allow multiple threads to be ran in a single script at a single time.
while true do
local regionParts = workspace:FindPartsInRegion3(--[[args]])
for i,v in pairs(regionParts) do
-- if statements checking for humanoid and head
end
wait(0.1) -- sets how long to wait before checks.
end
If you want to check multiple regions at one time, you would have to use coroutines
local regions = {RegionA, RegionB, RegionC}
for i,region in pairs(regions) do
coroutine.wrap(function() -- best to use wrap as it returns any errors when called
while true do
local regionParts = workspace:FindPartsInRegion3(region) -- your region as declared in the for pairs loop above
for i,v in pairs(regionparts) do
-- add those if statements from above
end
wait(0.1) -- wait 0.1 seconds between each loop
end
end)() -- it is crucial to have these extra parentheses as it is what calls or "initiates" the coroutine. You could also use the coroutine as a variable and it will work in a similar way.
--[[local myCoroutine = coroutine.wrap(function()
print('Cool coroutine function.')
end) <-- ensure the extra brackets aren't there when using the coroutine as a variable.
myCoroutine() <-- Call the coroutine similarly to how you would call a function.
]]
end
Ex: A player goes into the region. It repeatedly prints his/her name, until someone else comes into the region. Now instead of printing both names, it only prints the player that went after the first person that went into the region.
I need it so both names get printed, but somehow it prints the player that goes in after.
Just ignore the stuff that you don’t know or isn’t relevant to this topic…
for i, v in pairs(workspace:GetDescendants()) do
if v:FindFirstChild("_Water") then
local value = v:FindFirstChild("_Water")
local function water_find()
while true do
wait(0.1)
local region_v = Region3.new(v.Position - v.Size/2, v.Position + v.Size/2)
--local region_p = workspace:FindPartsInRegion3WithIgnoreList(region_v, ignorelist)
for _, v in pairs(workspace:FindPartsInRegion3(region_v)) do
if v.Parent:FindFirstChild("Humanoid") and v.Name == "Head" then
local player = game.Players:GetPlayerFromCharacter(v.Parent)
print(player.Name)
DrRe:FireClient(player, value)
end
end
end
end
local rep = coroutine.create(water_find)
coroutine.resume(rep)
end
end
Don’t create a new Region3 inside of the while true do loop. Otherwise the code seems to look alright, it’s just the order in which you are doing things.
for i,v in pairs(workspace:GetDescendants()) do
local value = v:FindFirstChild('_Water')
if value then -- just shortens it a tiny bit
local region_v = Region3.new(v.Position - v.Size/2, v.Position + v.Size/2) -- create the region here, not inside of the while loop.
local rep = coroutine.wrap(function() -- use wrap, it will output the errors. coroutine.create won't, similar to a pcall IIRC. You can also wrap in a variable like this.
while true do
wait(0.1)
for _, v in pairs(workspace:FindPartsInRegion3(region_v)) do
if v.Parent:FindFirstChild("Humanoid") and v.Name == "Head" then
local player = game.Players:GetPlayerFromCharacter(v.Parent)
print(player.Name)
DrRe:FireClient(player, value)
end
end
end
end
end)
rep() -- you don't have to resume it. Just call it as you would call a function.
end
end
I mean try commenting out the loop, then print it outside of that loop. Add it inside of the while true do loop though.
It should print an array/table.
while true do
wait(0.1)
print(workspace:FindPartsInRegion3(region_v))
--[[for _, v in pairs(workspace:FindPartsInRegion3(region_v)) do
if v.Parent:FindFirstChild("Humanoid") and v.Name == "Head" then
local player = game.Players:GetPlayerFromCharacter(v.Parent)
print(player.Name)
DrRe:FireClient(player, value)
end]]
end
end
Oddly enough, when both of the players collided with the region, the output inserts a table, but none of the player’s name got pasted. Also, since the water (region) is colliding with the baseplate, it prints that out, too. (And, it prints out another object I’ve added in the workspace that isn’t colliding or near the region)
Output:
[1] = Baseplate,
[2] = Acid
Edit: I forgot, if the object has _Water in it, it can only be printed (or that’s what I assumed)
I think I may have found the issue. If this fixes it, it was just your constructors for your Region3. I ended up not copying your game but let me know if this helps any or at least prints anything when the user enters the part.
for i, v in pairs(workspace:GetDescendants()) do
if v:FindFirstChild("_Water") then
local value = v:FindFirstChild("_Water")
--// Construct the bounds for the Region3 //--
local bounds_1 = Vector3.new(
v.Position.X + (v.Size.X / 2),
v.Position.Y + (v.Size.Y / 2),
v.Position.Z + (v.Size.Z / 2)
)
local bounds_2 = Vector3.new(
v.Position.X - (v.Size.X / 2),
v.Position.Y - (v.Size.Y / 2),
v.Position.Z - (v.Size.Z / 2)
)
--// Find the minimum and maximum Vector3 for the Region3 //--
local bounds_min = Vector3.new(
math.min(bounds_1.X, bounds_2.X),
math.min(bounds_1.Y, bounds_2.Y),
math.min(bounds_1.Z, bounds_2.Z)
)
local bounds_max = Vector3.new(
math.max(bounds_1.X, bounds_2.X),
math.max(bounds_1.Y, bounds_2.Y),
math.max(bounds_1.Z, bounds_2.Z)
)
local region_v = Region3.new(bounds_min, bounds_max)
while true do
print(workspace:FindPartsInRegion3(region_v))
wait(1)
end
end
end