Scripting Helpers is winding down operations and is now read-only. More info→
Ad
Log in to vote
2

Best way to handle detecting when in range to a list of objects?

Asked by 7 years ago
Edited 7 years ago

Basically I'm creating a system where when you walk up to certain parts, if your character is within range, a prompt will show up. For the sake of this question you don't have to worry about what the prompt will do, I'm just a bit confused on how I'd handle setting this up.

Info:

The method I have so far is creating a table, containing columns of other tables with information about the part the player needs to be within range of. Like this:

local stones = {
    {
        Name = "Green stone", -- The name
        Range = 5, -- Distance you need to be from stone to activate it
        Object = workspace.GreenStone -- The physical stone to get it's position
    }, 
    -- Same thing goes for the rest below
    {
        Name = "Red stone", 
        Range = 5,
        Object = workspace.RedStone
    },
    {
        Name = "Blue stone",
         Range = 10,
        Object = workspace.BlueStone
    }
}

Now I like this way of storing the objects the player can interact with, but my method for CHECKING if the player is in range of them concerns me a bit.


I'm using magnitude to obviously check the distance between the objects and the player, but the entire process is done within a while loop, iterating the table and comparing the player's current position to each individual objects each iteration. This - I don't like. Here would be an example:

function updateRange(player)
    local torso = player.Character:WaitForChild("Torso")
    for i = 1,#stones do
        local v = stones[i]
        if (v.Object.Position-torso.Position).magnitude < v.Range then -- If the player is in range of the current object the for loop is checking

            print("Player is in range of: ", v.Name) -- Then we'll just say i does this.
        end
    end
end

-- The while loop that updates it
while wait(0.5) do
    updateRange(player) -- We'll just assume player is defined as a player
end

This method seems buggy, impractical, inefficient, and I don't like it. So my question summed up is pretty much:

Is there a better way for this program to allow you to interact with the parts in the table when in range, without the need for a while loop updating the entire process each time?

If anyone could help with this, I'd really appreciate it. Thanks for reading.

1 answer

Log in to vote
0
Answered by 7 years ago

run updateRange() when you move the Torso trought the Changed event and have the property as "Position"

so like:

torso.Changed:connect(function(prop)
if prop=="Position" then
updateRange(player)
end
end)
0
My problem isn't speed, it's efficiency. This would actually be worse. MightyQuestionAsker 297 — 7y
Ad

Answer this question