Yo, anybody mind telling me how I can add little confetti/sparkle effects to my checkpoints when a player walks over em? I already have a local checkpoint noise, but I wanted to add a local effect since I think it would look nice when completing a stage. I’ll post both my checkpoint script in serverscriptservice and my local checkpoint sounds script down below!
Main checkpoint script in ServerScriptService:
local checkpoints = workspace:WaitForChild("Checkpoints")
local Players = game:GetService("Players")
local RunService = game:GetService("RunService")
local DatastoreService = game:GetService("DataStoreService")
local Data = DatastoreService:GetDataStore("1")
local sessionData = {}
function PlayerAdded(player)
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
local stage = Instance.new("NumberValue")
stage.Name = "Stage"
stage.Parent = leaderstats
local success = nil
local playerData = nil
local attempt = 1
repeat
success, playerData = pcall(function() -- here pcall or protected call is just repeat waiting until the data loads for the player
return Data:GetAsync(player.UserId)
end)
attempt += 1
if not success then
warn(playerData)
task.wait(2)
end
until success or attempt == 5 -- it repeats it until it loads
if success then --if it loads then make the table with their data inside
print("Data loaded: "..player.Name)
if not playerData then -- if they have no table then they're a new player so we create the table
print("new player, giving default data")
playerData = {
["Stage"] = 1, --add all your values and stuff inside of the data
}
end
sessionData[player.UserId] = playerData --set the data to a table with the players id and make to make a variable
else
warn("couldnt load data: "..player.Name)
player:Kick("couldnt load your data, rejoin") --if the data couldnt load we kick them so their not just sitting there forever waiting
end
stage.Value = sessionData[player.UserId].Stage --here we get the numbervalue created above and get the value of it and set it to the value inside of the table
stage:GetPropertyChangedSignal("Value"):Connect(function()
sessionData[player.UserId].Stage = stage.Value --update the table value whenever the leaderstat value changes
end)
leaderstats.Parent = player
end
Players.PlayerAdded:Connect(function(player)
PlayerAdded(player)
player.CharacterAdded:Connect(function(char)
local leaderstats = player:WaitForChild("leaderstats")
local stage = leaderstats.Stage
local hum = char:WaitForChild("Humanoid")
task.wait()
char:MoveTo(checkpoints[stage.Value].Position)
hum.Touched:Connect(function(hit)
if hit.Parent == checkpoints then
if tonumber(hit.Name) == stage.Value + 1 then
stage.Value += 1
end
end
end)
end)
end)
function PlayerLeaving(player)
if sessionData[player.UserId] then
local success = nil
local errorMsg = nil
local attempt = 1
repeat
success, errorMsg = pcall(function()
Data:SetAsync(player.UserId, sessionData[player.UserId]) --here is the same as loading data just repeat waits until the data saves
end)
attempt += 1
if not success then
warn(errorMsg)
task.wait(2)
end
until success or attempt == 5
if success then
print("Data saved: "..player.Name)
else
warn("Cant save: "..player.Name)
end
end
end
Players.PlayerRemoving:Connect(PlayerLeaving)
function ServerShutdown()
if RunService:IsStudio() then
return
end
for i, player in ipairs(Players:GetPlayers()) do
task.spawn(function()
PlayerLeaving(player)
end)
end
end
game:BindToClose(ServerShutdown)
Checkpoint sounds local script in StarterPlayerScripts:
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local player = game.Players.LocalPlayer
player:WaitForChild("leaderstats")
local CheckpointsFolder = workspace:WaitForChild("Checkpoints")
local function updateCheckpointColors()
for _, part in ipairs(CheckpointsFolder:GetDescendants()) do
if part:IsA("BasePart") and part.Parent == CheckpointsFolder then
local stageNumber = tonumber(part.Name)
if stageNumber and game.Players.LocalPlayer.leaderstats.Stage.Value >= stageNumber then
part.BrickColor = BrickColor.new("Light reddish violet")
end
end
end
if ReplicatedStorage:FindFirstChild("CheckpointSound") then
ReplicatedStorage.CheckpointSound:Play()
end
end
updateCheckpointColors()
player.leaderstats.Stage.Changed:Connect(updateCheckpointColors)
You can create a particle emitter and parent it to your current checkpoint.
Code:
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local player = game.Players.LocalPlayer
local stage = player:WaitForChild("leaderstats"):WaitForChild("Stage")
local CheckpointsFolder = workspace:WaitForChild("Checkpoints")
local particleEmitter = Instance.new("ParticleEmitter")
particleEmitter.Enabled = false
local function updateCheckpointColors(playerStage)
for _, part in ipairs(CheckpointsFolder:GetChildren()) do
if part:IsA("BasePart") then
local stageNumber = tonumber(part.Name)
if stageNumber and playerStage >= stageNumber then
part.BrickColor = BrickColor.new("Light reddish violet")
end
end
end
if ReplicatedStorage:FindFirstChild("CheckpointSound") then
ReplicatedStorage.CheckpointSound:Play()
end
local currentStage = CheckpointsFolder[playerStage]
particleEmitter.Parent = currentStage
particleEmitter:Emit(20)
end
stage.Changed:Connect(updateCheckpointColors)
updateCheckpointColors(stage.Value)
Is this what you meant for more performant and readable? I just wanna know if I did it right
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local player = game.Players.LocalPlayer
player:WaitForChild("leaderstats")
local CheckpointsFolder = workspace:WaitForChild("Checkpoints")
local function updateCheckpointColors()
for _, part in ipairs(CheckpointsFolder:GetChildren()) do
local stageNumber = tonumber(part.Name)
if stageNumber and game.Players.LocalPlayer.leaderstats.Stage.Value >= stageNumber then
part.BrickColor = BrickColor.new("Light reddish violet")
end
if ReplicatedStorage:FindFirstChild("CheckpointSound") then
end
end
ReplicatedStorage.CheckpointSound:Play()
end
updateCheckpointColors()
player.leaderstats.Stage.Changed:Connect(updateCheckpointColors)
Alright I changed it up some, only error it says now is "unknown global ‘stage’
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local player = game.Players.LocalPlayer
player:WaitForChild("leaderstats")
local CheckpointsFolder = workspace:WaitForChild("Checkpoints")
local particleEmitter = Instance.new("ParticleEmitter")
particleEmitter.Enabled = false
local function updateCheckpointColors()
for _, part in ipairs(CheckpointsFolder:GetChildren()) do
local stageNumber = tonumber(part.Name)
if stageNumber and game.Players.LocalPlayer.leaderstats.Stage.Value >= stageNumber then
part.BrickColor = BrickColor.new("Light reddish violet")
end
if ReplicatedStorage:FindFirstChild("CheckpointSound") then
end
end
ReplicatedStorage.CheckpointSound:Play()
end
local currentStage = CheckpointsFolder[stage]
particleEmitter.Parent = currentStage
particleEmitter:Emit(20)
updateCheckpointColors()
player.leaderstats.Stage.Changed:Connect(updateCheckpointColors)
My bad I was cooking so I just saw this and changed it to your code, now what do I do? Did you want me to remove if part:IsA("BasePart") then local stageNumber = tonumber(part.Name) and put the rest of the code there? Or do I just leave it like it is? Also, I’m fairly new to all this scripting stuff and I appreciate you being patient with me gang.
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local player = game.Players.LocalPlayer
local stage = player:WaitForChild("leaderstats"):WaitForChild("Stage")
local CheckpointsFolder = workspace:WaitForChild("Checkpoints")
local particleEmitter = Instance.new("ParticleEmitter")
particleEmitter.Enabled = false
particleEmitter.Color = ColorSequence.new({
ColorSequenceKeypoint.new(0, Color3.fromRGB(255, 0, 0)),
ColorSequenceKeypoint.new(0.25, Color3.fromRGB(255, 238, 0)),
ColorSequenceKeypoint.new(0.5, Color3.fromRGB(0, 255, 8)),
ColorSequenceKeypoint.new(0.75, Color3.fromRGB(0, 136, 255)),
ColorSequenceKeypoint.new(1, Color3.fromRGB(157, 0, 255)),
})
local function updateCheckpointColors(playerStage)
for _, part in ipairs(CheckpointsFolder:GetChildren()) do
if part:IsA("BasePart") then
local stageNumber = tonumber(part.Name)
if stageNumber and playerStage >= stageNumber then
part.BrickColor = BrickColor.new("Light reddish violet")
end
end
end
if ReplicatedStorage:FindFirstChild("CheckpointSound") then
ReplicatedStorage.CheckpointSound:Play()
end
local currentStage = CheckpointsFolder[playerStage]
particleEmitter.Parent = currentStage
particleEmitter:Emit(20)
end
stage.Changed:Connect(updateCheckpointColors)
updateCheckpointColors(stage.Value)