Prevent Exploiters With Remote Events

You basically will handle the touch events on the server and the addition of their currency, then fire the remote with the client that has touched the coin. Use a LocalScript to handle the OnClientEvent that will be received when the remote is fired. The local script will just change the transparency of the coin that was sent inside of the parameters of the event.

ServerScript Example:

local Event = -- Define Event
local CoinFolder = workspace:FindFirstChild("Coins")

for i, v in ipairs(CoinFolder:GetChildren()) do
    if v:IsA("BasePart") then -- Checks to see if the child is a valid base part
       v.Touched:Connect(function(Hit)
           local Player = game:GetService("Players"):GetPlayerFromCharacter(Hit.Parent)
           -- Do leaderstats and coin visibility and other things
           Event:FireClient(Player,v) -- Send the player to be fired, and v which is the coin object
       end)
    end
end

LocalScript Example:

local Event = -- Define Event

Event.OnClientEvent:Connect(function( CoinObject ) -- CoinObject is the coin part that was supplied
  CoinObject.Transparency = 1
end)
2 Likes

@desinied basically meant for you to use a server-script to change your money value when the coin has been touched. However, in the same function, you can use FireClient to change the transparency of the coin.

I’m gonna use @desinied’s idea to express what I mean in the script ( credits go to him )

local coinFolder = workspace:FindFirstChild("Coins")

for _,v in pairs(coinFolder:GetChildren()) do
    if v:IsA("BasePart") then
        v.Touched:connect(function(hit)
            -- Do the coin value change
            -- get player using function
            test:FireClient(player v)
        end)
    end
end

Edit: ah @desinied got to it before me. gg hahahhaha

1 Like

Yes, I know that, but I mean: How does it check if the player already collected the coin? Because if it’s local the serverscript doesn’t detect that, right?

If what you mean is that the coin can still be collected after transparency is changed then you can just do :Destroy() on the coin, that way it’ll destroy it for the client and other players will still see it?

I’m not so sure if that’s what you mean though. Elaborate if you can.

I actually mean to check if it’s already collected. So if the coin already has been collected, you need to wait until it’s visible again and then you can collect it.

If they are created on the server, you could use .Touched and FireClient to remove the coin on the client’s screen and then add them to a table to prevent them from collecting it again

Ah okay so try using a variable in the localscript which checks if the coin is touched or not. You can simply do coinTouched = false or coinTouched = true and then add a wait() for it to set back into it’s normal transparency so it can be touched again.

edit: make sure you set the variables and everything into the localscript so that other players have the same effect as well. If you add a variable and the debounce to the serverscript then it’ll affect every player instead of just the client.

Yes, but then 1. it would be for all coins. 2. How would I do that? Because then it needs to check in the localscript and how would the serverscript know when that variable is true or false?

Have a table where the keys are players and the value is the list of coins that player has collected and each time a player collects a coin check if the coin is already collected if not add thet coin to the collected table

or have a table where the keys are the coins and the values are the list of players

  1. Do the coinTouched variable in a local script.
  2. Use something like this:
local Coin = --define coin
Coin.Touched:Connect(function()
      CoinTouched = true
end)

if Coin.Tocuhed == true then
Coin.CanCollide = false
Coin.Transparency = 1
end

At this point just try adding the coins into a table using table.insert(coinTable, coins) and then using a for loop to get each coin that was touched and then set it from there.

edit: the method I probably told u at first was better though cause you make it check for the coin touched in the first place so it’ll only be for the coin touched. And the server doesn’t need to know because the part won’t be touchable if the parts CanCollide is false. Another thing you can do is just get a StringValue but that’ll be very easy to exploit and get past.

The .Touched event still fires even if the CanCollide property is set to false

I’m sorry, but I’m now kinda confused.

Oh actually? My bad wasn’t aware hahaha

For some reason I thought it did due to a recent test I did but I was probably wrong, thanks for the clearup though mate

what are you confused with? Explain in details what you’re trying to achieve etc.

I’m confused with the tables and how I would do that, sorry, I’m not very known with tables.

Basically what you do is for every coin have a key in a table thats the coin for example the table structure will look like this:

{
  [workspace.Coins.Coin1] = {},
  [workspace.Coins.Coin2] = {},
  [workspace.Coins.Coin3] = {}
}

And the value will be the list of players, for example

{
  [workspace.Coins.Coin1] = {
    game.Players.IggyDev,
    game.Players.LukaGaming_07
  }
}

and check it like this

if not table.find(CoinTable[coin], player) then
  -- give the coin
  table.insert(CoinTable[coin], player)
end

(replace coin with the coin object and player with the player object)
What the if statement is doing is

  1. Go to the coin key in the CoinTable table
  2. Is the player already in that list?
  3. No? Give the player the coin and add the player to the list
2 Likes

Using table.insert You can insert parts and such into that table using arrays I believe. using a for loop into that table or the number amount of the table you can basically get every single item inside that table. It’s useful because it’ll make it easier for you to get

edit: it’ll also stop u from manually having to add stuff because it’ll do it all for u

Thanks to everyone who responded, now I know how!

You should automatically add the coins to the table