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

My script makes a backup of something in workspace, but i don't want it to. Why?

Asked by
ARTEK22 135
7 years ago
Edited 7 years ago

Hello, i am trying to make a miner job in my game. Im trying to make a stone thingy. You have to mine stone then wait for it to respawn. When i mine it, it respawns. But it just makes a backup of the stone in workspace for no reason. Here is the script:

hits = 0
script.Parent.ClickDetector.MouseClick:connect(function()
    hits = hits + 1
    if hits == 3 then
        script.Parent = workspace -- just parent the script in a safe area because we need to remove it's parent
        game.Workspace.Mine.Stone:Destroy() -- remove the stone
        wait(3)
        local stone = game.ReplicatedStorage.Stone:Clone() -- clone the stone from replicatedstorage
        stone.Parent = game.Workspace.Mine -- set the parent to the mine
        script:Destroy() -- now safely remove the script because we dont need it
    end
end)

Note: I added the comments to avoid some questions.

0
Add a debounce? iamnoamesa 674 — 7y
0
There's already a debounce. "if hits == 3 then" Difined_Person 61 — 7y
0
I'm confused. Does the stone instantly respawns? And do you need to fix that? Difined_Person 61 — 7y
0
Okay. The stone respawns after 3 seconds. And when it respawns i think it does in workspace or just clones itself again into workspace. ARTEK22 135 — 7y
View all comments (4 more)
1
Does this mean you have this script in every stone? You should probably put one script in ServerScriptService to handle all the stone and mineral respawning. It wouldn't be too difficult. GoldenPhysics 474 — 7y
0
Agree with gold. This is done inefficiently. Also, this is not a debounce but you probably wouldn't need one. It makes one due to line 9. Does it make an extra one besides that one? iamnoamesa 674 — 7y
1
If you want to replace the stone after 3 seconds. It's better to make move it to storage then destroying. It takes less scripts. Difined_Person 61 — 7y
0
Confusing. ARTEK22 135 — 7y

1 answer

Log in to vote
1
Answered by 7 years ago

You are correct in thinking that the script you are using is a bit inefficient. Instead of copying the stone and script over and over again, it could just restore the originals! This script will do just that:

local hits = 0
local target = workspace.Mine.Stone
local targetParent = target.Parent
target.ClickDetector.MouseClick:connect(function(player)
    hits = hits + 1
    if hits < 3 then return end
    --Hide stone
    target.Parent = nil
    --TODO Reward 'player' with inventory or money here
    wait(3)
    --Restore stone and allow mining again
    target.Parent = targetParent
    hits = 0
end)

Notes:

  • The script must be placed in ServerScriptService (I am assuming it is a regular Script, not a LocalScript.)
  • Saying if hits < 3 then return end is the same idea as if hits == 3 then, but avoids an extra indentation.
  • You have to fill in the 'TODO Reward' line with whatever is appropriate
  • This system is open to the abuse of one player trying to mine, getting 2 hits/clicks in, and then another player stealing the 3rd hit and claiming the reward. One method of addressing this (if you are even concerned about it) is to keep track of how many clicks/hits each player has performed separately (and resetting them all when anyone finishes mining the rock). Alternatively, script "who-ever hits it the most will get it so long as at least 3 hits have occurred".
  • If the script errors on line 2 in Online mode (though I don't think it will), change it to workspace:WaitForChild("Mine"):WaitForChild("Stone") - this assumes that both Mine and Stone exist.

Now, if you only have one rock in your entire place, this works fine. However, what if you want multiple rocks? Now, I don't know how you have your Mine folder/model set up. Say that you have lots of Stones in there, but also other stuff that shouldn't be mined. Then we can go through each child and attach the event to any of them that are named "Stone". Each one can have its own local variable hits so that they are kept separate.

local ch = workspace.Mine:GetChildren() --Get all the children in Mine
for i = 1, #ch do --Go through each child
    if ch[i].Name == "Stone" then --If the child is what we're looking for:
        local target = ch[i]
        local hits = 0
        target.ClickDetector.MouseClick:connect(function(player)
            hits = hits + 1
            if hits < 3 then return end
            --Hide stone
            target.Parent = nil
            --TODO Reward 'player' with inventory or money here
            wait(3)
            --Restore stone and allow mining again
            target.Parent = targetParent
            hits = 0
        end)
    end
end

Since we declare hits and target inside the for loop, the function that is connected to the MouseClick event will receive those local variables. Each Stone will have its own function that will have its own target/hits variables.

0
The game is singleplayer so you didn't need to add the additional code. But thanks anyways! ARTEK22 135 — 7y
Ad

Answer this question