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

How can I use a dying function to end a while loop?

Asked by 5 years ago

I've been trying on numerous different attempts and I thought this would be the closest I could get to what I wanted the outcome to be. Any help or hints are appreciated =)

01local players       = game:GetService("Players")
02local teams         = game:GetService("Teams")
03local rs            = game:GetService("ReplicatedStorage")
04local showgui       = rs:FindFirstChild("ShowGui")
05local touching      = false
06local user          = nil
07local plr           = nil
08local grabbed       = nil
09 
10script.Parent.Touched:Connect(function(hit)
11    if hit.Parent:FindFirstChild("Humanoid") then
12        plr = workspace[hit.Parent.Name]
13        user = players:GetPlayerFromCharacter(plr)
14        if user ~= nil then
15            if user.Robbing.Value == true then
View all 53 lines...
0
your variable indenting is interesting xd starmaq 1290 — 5y
0
sorry i was just trying something new lol wasn't sure if i was gonna stick with it though AnnaVonWachstein 7 — 5y
0
To accept an answer there should be an "Accept Answer" button below the "Post a comment" box on the answer you wish to accept. chess123mate 5873 — 5y

2 answers

Log in to vote
1
Answered by 5 years ago

It much easier than you think! All you have to do is simply get the Humanoid's health and once it reaches 0 health you could break the loop.

Here is a sample that should help you understand how it works.

01local player = game.Players.LocalPlayer
02local character = player.Character
03if not character or not character.Parent then
04    character = player.CharacterAdded:wait()
05end
06 
07while wait(1) do
08    print("Hello") -- Your Code Here
09    if character.Humanoid.Health == 0 then
10        break
11    end
12end
0
Thanks for the help! I'd give you the "question answered" but I'm not so sure on how to do so. AnnaVonWachstein 7 — 5y
Ad
Log in to vote
0
Answered by 5 years ago
Edited 5 years ago

Your "died" function is trying to listen to an event, ie you're wanting to exit a loop when an event occurs. To do this, you listen to the event but save the connection you've made to a variable so that you can disconnect it when the loop ends. Inside the event listener, you change a boolean variable that you periodically check to see if you should keep running the loop. (This is shown below.)

Notes: * you'll probably want to run that code every time the user touches the brick, so put it in a function (and add debounce - you don't want several 'while' loops running, all giving the player 100s of dollars every second) * (Minor) Use Connect, not connect (which is deprecated) * if user ~= nil then can be shortened to if user then so long as you don't expect user to ever equal false * if touching == true and... can be shortened to if touching and... unless you expect touching to be any random value and only want to do something if it's specifically true * You don't want to be using variables like grabbed to refer to things like a player's CashCollected, since this is a server script that needs to handle many players (if 2+ players try to touch the part at once, one player will be awarded the other player's money as well as his/her own). You should either use a dictionary to track all players's CashCollected objects or make it local to the function(s) that use it (passing it to other functions as needed). For the touching variable, you'll definitely need a dictionary for that one (the key is the player, the value is true or false -- be sure to set it to nil when a player leaves to prevent memory leaks) * Variables should be local to the function they are used in; try to avoid sharing variables between functions (though you always need some and that's okay)

Improved code:

01local players       = game:GetService("Players")
02local teams         = game:GetService("Teams")
03local rs            = game:GetService("ReplicatedStorage")
04local showgui       = rs:FindFirstChild("ShowGui")
05local touching      = {} -- touching[player] = true if the player is touching script.Parent
06local db            = {} -- debounce: ensure the "give money" loop doesn't run more than once simultaneously for any one player
07 
08local function mainLoop(player)
09    if db[player] then return end
10    db[player] = true
11    local hasDied = false
12    local con = player.Character.Humanoid.Died:Connect(function()
13        hasDied = true
14    end)
15    local grabbed = user:WaitForChild("CashCollected")
View all 60 lines...

By the way, I'm unsure if TouchEnded is guaranteed to work (last time I checked it doesn't); you should periodically check the character's position to see if they've left the area (then do touching[player] = false if so). Also, if the player's arm briefly touches script.Parent (in addition to the torso), money will stop being awarded even if the player's torso is still touching it.

[Edit: DAsanicmaster's answer of checking the humanoid's health is definitely superior in this case, but I leave this answer here because everything else I said is still fine and sometimes you need to listen to an event instead of checking a value.]

0
Reading this actually helped give me a bunch of information I was unaware of. And thanks so much for helping clean up my messy coding xp AnnaVonWachstein 7 — 5y

Answer this question