What I have is a survivals system in my game, what I want to do is when the user gets lets say 100 survivals, I give them a badge, how would I do that?
I know that but i’m talking about awarding them the badge when they have a certain score on the leaderboard
leaderstats.Score.Changed:Connect(function()
if leaderstats.Score.Value >= 10 then
BadgeService:AwardBadge(userId, badgeId)
end
end)
That only checks the default value of the score in the leaderboard and not the players
Yes, so what you do is go into the folder inside the player called leaderstats.
Normally when leaderstats are created they are like this:
local badgeService = game:GetService("BadgeService")
local badgeId = 0
game.Players.PlayerAdded:Connect(function(player)
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
leaderstats.Parent = player
local scoreVal = Instance.new("NumberValue")
scoreVal.Name = "Score"
scoreVal.Parent = leaderstats
scoreVal.Changed:Connect(function()
if scoreVal.Value >= 10 and not badgeService:UserOwnsBadgeAsync(player.UserId, badgeId) then
badgeService:AwardBadge(player.UserId, badgeId)
end
end)
end)
As you can see, I added the changed event from my last post that checks if the score is high enough to get a badge.
But does the part where it actually checks if the score changed checks if the players score changed check everytime the score actually changes, checks only once, or checks all the time, the reason I ask this is because the script which gives the player survivals is the same script that makes the game work so i dont want a part in the middle to completely stop the script (if it for example is like a while true loop the checks all the time)
The ‘Changed’ event is fired every time a value is, well… changed. This means that it will only check if the player has enough score for a badge when their score is actually updated.
In short, no. It won’t completely stop the script and it will run asynchronously.
but is there a way to make it a completely other script that checks the players score because i dont want to risk breaking the main script
If you don’t want it to break the main script, you can wrap it in a pcall like so:
xpcall(function()
scoreVal.Changed:Connect(function()
if scoreVal.Value >= 10 and not badgeService:UserOwnsBadgeAsync(player.UserId, badgeId)
then
badgeService:AwardBadge(player.UserId, badgeId)
end
end)
end, warn)
This will prevent any errors from breaking your script, but also warn them to the dev console if they do happen.
Also, if you want to put them in a seperate script you can do:
player:WaitForChild("leaderstats").Score.Changed:Connect()
So how would i define the player?
I can’t have it when the player joins or the character is added since i want to check it all the time and not when they just spawn
Also thats one of the only ways i know how to define the actual player through a server script since im not too good at scripting
Well not nessesarily all the time but when the players score changed
If you want it to check just when the character spawns you can do:
game.Players.PlayerAdded:Connect(function(player)
player.CharacterAdded:Connect(function(character)
if player:WaitForChild("leaderstats").Score.Value >= 10 and not badgeService:UserOwnsBadgeAsync(player.UserId, badgeId) then
badgeService:AwardBadge(player.UserId, badgeId)
end
end)
end)
thats what i said i didnt want it to do
i want it to check every time their score changed which i know is the changed event but idk how to define the player itself
The code I sent a few posts ago does it when the score changes, thus we use the ‘Changed’ event
xpcall(function()
scoreVal.Changed:Connect(function()
if scoreVal.Value >= 10 and not badgeService:UserOwnsBadgeAsync(player.UserId, badgeId)
then
badgeService:AwardBadge(player.UserId, badgeId)
end
end)
end, warn)
i know how to check when their score changed and how to give them the badge but my question is how to define the player themselves everytime their score changed instead of defineing them everytime they spawn
Okay to make it clearer here is the full code:
local badgeService = game:GetService("BadgeService")
local badgeId = 0
game.Players.PlayerAdded:Connect(function(player)
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
leaderstats.Parent = player
local scoreVal = Instance.new("NumberValue")
scoreVal.Name = "Score"
scoreVal.Parent = leaderstats
scoreVal.Changed:Connect(xpcall(function()
if scoreVal.Value >= 10 and not badgeService:UserOwnsBadgeAsync(player.UserId, badgeId) then
badgeService:AwardBadge(player.UserId, badgeId)
end
end), warn)
end)
The player is defined on the game.Players.PlayerAdded event, as it is passed into the function connected to it.
The part below is what im confused about
local badgeService = game:GetService("BadgeService")
local badgeId = 0
game.Players.PlayerAdded:Connect(function(player)
--I dont need to create the leaderboard since the main script already does it
local scoreVal = player.leaderstats.scoreVal
--would i have to put a while true loop here to make the script check everytime when the score changes or does it always check if the score changes even without a while loop
scoreVal.Changed:Connect(xpcall(function() --im confused as to if this only happens once of all the time
if scoreVal.Value >= 10 and not badgeService:UserOwnsBadgeAsync(player.UserId, badgeId) then
badgeService:AwardBadge(player.UserId, badgeId)
end
end))
end)`