Help with detecting when two or more players are near to each other. AKA Proximity Players

So, I was thinking about making a “voice chat system”.

I was planning to make a system that detects when two or more players are near each other, and when they are, a BOT on disc creates a voice chat, and move the users into it.
When they walk away the voice chat gets deleted.

First of all, is this against Roblox’s ToS?
If not, how can I detect when the two or more players are nearby?

I thought about making Region3, but the problem is that when two players are facing each other, but they are in different regions, they won’t get moved in the same chat.

Here’s a screen of what I am talking about:

Thanks in advance!

2 Likes

Use Magnitude to find the distance between 2 vectors.

1 Like

You could use magnitude for checking their distance and raycasting to check for walls. You should also look into the tos because this is most likely against the rules.

2 Likes

Creating a bot that works like that would be difficult

1 Like

Here is an example that uses Magnitude:

-- ServerScript inside of StarterCharacterScripts

local character = script.Parent
local root = character.HumanoidRootPart
local player = game.Players:GetPlayerFromCharacter(character)

local minDistance = 10 -- minimum distance (studs) from another player

local function GetClosestPlayers()
    local closestPlayers = {}

    for _, plr in pairs(game.Players:GetPlayers()) do
        if plr ~= player then
            if plr.Character then
                local targetPos = plr.Character.HumanoidRootPart.Position
                local magnitude = (root.Position - targetPos).Magnitude

                if magnitude <= minDistance then
                    table.insert(closestPlayers, plr)
                end
            end
        end
    end

    return closestPlayers
end

--[[ the rest of your code. Calling the "GetClosestPlayers" function will
return a table of all the players within range. ]]

I have not tested this code example, so there might be a few bugs/typos.

2 Likes

Hey there,
Well, first of all, no. Atleast I don’t think so anyways. Your only real issue may just be the quintillions of HTTP requests you’re sending to your HTTP webserver every few seconds or however long your cooldown will be.
Since you have to have a Discord bot hooked up to a webserver which can both send and receive requests to Discord and/or your Roblox game will be difficult. You would also have to hook up something to create/delete voice channels based on if servers are active or not. You would also need to identify the player without issue, and you need to have some way of getting the ID of the Roblox user’s Discord account (allowing you to move them into different voice channels, of course).
Assuming that you have all of the technical mumbo-jumbo on the Discord side of things down, you would need to shoot an HTTP request with an array of users with distances correlated to each player’s distance from eachother. This shouldn’t be that difficult, assuming that you know how to call these requests without being that costly.
You could have something set up like this:

local HTTPService = game:GetService("HttpService")
local Players = game:GetService("Players")

local List = Players:GetPlayers()

--[[
    These two functions basically replace the use of
    Players:GetPlayers() every cooldown, since it's a costly operation
    ESPECIALLY with many players.
]]--
Players.PlayerRemoving:Connect(function(Player)
    table.remove(List, table.find(List, Player))
end)
Players.PlayerAdded:Connect(function(Player)
    table.insert(List, Player)
end)

local function Find(Player)
    local Character = Player.Character
    return Character and Character:FindFirstChild("HumanoidRootPart")
end
while true do
    local Distances = {}
    for _, Player in pairs(List) do
        local Root = Find(Player)
        if Root then
            local Table = {}
            for _, _Player in pairs(List) do
                if _Player ~= Player then
                    local _Root = Find(_Player)
                    if _Root then
                        Table[_Player.Name] = (Root.Position - _Root.Position).Magnitude
                    end
                end
            end
            Distances[Player.Name] = Table
        end
    end

    local Encoded = HTTPService:JSONEncode(Distances)
    -- Send this over with other data that you need

    wait(.5) -- 0.5 is a good amount for the request sending.
end

This is of course an example I made, so you can change this if needed. This is what your ROBLOX code should look like, though.
Make sure you aren’t abusing Roblox’s HTTPService system too much, or you might exhaust the queue, which then makes your code error or other stuff. This should be the general basis of your code though.

4 Likes