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

Whenever I Run A For Loop It Determines Instance Isn't Nil.. Even When I Know It's Nil .. Help?

Asked by 6 years ago

Before I start..

while wait(0.5) do
    local Playing = game.ServerStorage:WaitForChild("GameState"):WaitForChild("Playing")
    if Playing.Value == true then
        for i, v in pairs(game.Players:GetPlayers()) do
            local WeaponToFind = v.Stats.LoadoutGun.Value
            if v.Backpack:FindFirstChild(WeaponToFind) == nil or v.Character:FindFirstChild(WeaponToFind) == nil then
                local WeaponToGive = game.ReplicatedStorage.Weapons:FindFirstChild(WeaponToFind):Clone()
                WeaponToGive.Parent = v.Backpack
            elseif v.Backpack:FindFirstChild(WeaponToFind) ~= nil or v.Character:FindFirstChild(WeaponToFind) ~= nil then

            end
        end
    end
end

This is in a ServerScript in ServerScriptService game.ServerScriptService.OnStart.WeaponsGive

As the title suggests, I'm having problems with the server finding if a player has a tool in either their backpack or their character. It's supposed to do nothing if it finds the tool, as the loop is constantly repeating, and it's supposed to give the tool if it finds nothing.

However, it always seems to be nil, since the code is giving the tool over and over and over again. Not sure what I'm doing wrong, so I figured maybe I needed a different set of eyes.

Thanks for all and any help!

0
It's a logic error. User#24403 69 — 6y
0
Sorry, I don't understand what that is exactly. xXDoneBeingCoolXx 33 — 6y

1 answer

Log in to vote
1
Answered by 6 years ago
Edited 6 years ago

It's a logic error. If you notice on line 6 (you do the same on line 9)

    if v.Backpack:FindFirstChild(WeaponToFind) == nil or v.Character:FindFirstChild(WeaponToFind) == nil then

What is happening is that the weapon wasn't found in the character so v.Character:FindFirstChild(WeaponToFind) == nil was met, or it was in the character and v.Backpack:FindFirstChild(WeaponToFind) == nil was met. When you use or in a conditional statement, at least one of the conditions have to be truthy (not false or nil), and since Instances are not false or nil, your condition is met.

You want to switch that 'or' to 'and' so that BOTH must be met (no weapon in backpack AND character).

local playing = game.ServerStorage:WaitForChild("GameState"):WaitForChild("Playing")

playing.Changed:Connect(function(isPlaying) -- much better than a while loop
    if isPlaying then -- if the new value is true
        for _, player in ipairs(game.Players:GetPlayers()) do
            local WeaponToFind = player.Stats.LoadoutGun.Value
            if not player.Backpack:FindFirstChild(WeaponToFind) and not v.Character:FindFirstChild(WeaponToFind) then
                local WeaponToGive = game.ReplicatedStorage.Weapons:FindFirstChild(WeaponToFind):Clone()
                WeaponToGive.Parent = player.Backpack
            end
        end
    end
end)

I also used a Changed event rather than a while loop. You only need to check when it changed, not every 0.5 seconds. And you don't need that elseif, and the == nil was not needed, because as I said, not nil would be true, since 'nil' and 'false' is falsey, and :FindFirstChild() returns nil if there isn't a child found.


Hopefully this answered your question, and if it did, then don't forget to hit that "Accept Answer" button. If you have any other questions, then feel free to leave them down in the comments.
0
Thank you SO much for this! xXDoneBeingCoolXx 33 — 6y
Ad

Answer this question