I’m currently trying to make a leaderstats system, but there’s currently no way to save the points. I’m confused, and I’ve been trying to make a way to save for what feels like ages.
Please help me
SCRIPT:
local DataStoreService = game:GetService("DataStoreService")
local playerDataStore = DataStoreService:GetDataStore("PlayerData")
game.Players.PlayerRemoving:Connect(function(player)
-- Save the player's leaderstats to the data store
local success, error = pcall(function()
playerDataStore:SetAsync(player.UserId .. "_leaderstats", player.leaderstats)
end)
if not success then
warn("Failed to save player data: " .. error)
end
end)
game.Players.PlayerAdded:Connect(function(player)
-- Load the player's leaderstats from the data store
local success, leaderstats = pcall(function()
return playerDataStore:GetAsync(player.UserId .. "_leaderstats")
end)
if success and leaderstats then
leaderstats.Parent = player
end
end)
Your issue is that you are trying to save an instance, which you cannot do.
You have to pass a table or a value through to save.
--> Services
local Players = game:GetService("Players")
local DataStoreService = game:GetService("DataStoreService")
--> Data Store
local DataStore = DataStoreService:GetDataStore("PlayerData")
--> Functions
local function PlayerAdded(player: Player)
--> Create Players Leaderstats
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
local coins = Instance.new("NumberValue")
coins.Name = "Coins"
coins.Parent = leaderstats
leaderstats.Parent = player
--> Load Players Data
local succ, data = pcall(function()
return DataStore:GetAsync(player.UserId)
end)
if succ and data ~= nil then
coins.Value = data["Coins"]
end
end
--> Save The Players Data
local function PlayerRemoving(player: Player)
--> Get Players Leaderstats
local leaderstats = player:FindFirstChild("leaderstats")
local coins = leaderstats:FindFirstChild("Coins")
local DataTable = {
["Coins"] = coins.Value,
}
--> Save Players Data
pcall(function()
DataStore:SetAsync(player.UserId, DataTable)
end)
end
for _, v in pairs(Players:GetPlayers()) do
PlayerAdded(v)
end
Players.PlayerAdded:Connect(PlayerAdded)
Players.PlayerRemoving:Connect(PlayerRemoving)
You should also look at the documentation for Data Stores
For some reason this script still doesn’t work. I have no Idea if I did something wrong, but I don’t think I did.
I put the script inside of ServerScriptService, and changed the names to Gold instead of Coins. I tried it out, and the leaderstats worked, but the Data Store didn’t.
I also made a backup of your script and tried it out completely unchanged. That also didn’t work. Thank You for trying to help me though!
If Gold is the only value you’d like to save then you can use this:
local DataStoreService = game:GetService("DataStoreService")
local Players = game:GetService("Players")
local RunService = game:GetService("RunService")
local playerDataStore = DataStoreService:GetDataStore("PlayerData")
local function onPlayerAdded(player)
local success, value = xpcall(playerDataStore.GetAsync, warn, playerDataStore, player.UserId.."_leaderstats")
if success then
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
leaderstats.Parent = player
local Gold = Instance.new("IntValue")
Gold.Name = "Gold"
if value then
Gold.Value = value
end
Gold.Parent = leaderstats
end
end
local function onPlayerRemoving(player)
local leaderstats = player:FindFirstChild("leaderstats")
if leaderstats then
xpcall(playerDataStore.SetAsync, warn, playerDataStore, player.UserId.."_leaderstats", leaderstats.Gold.Value)
end
end
if RunService:IsStudio() then
game:BindToClose(function()
task.wait(1)
end)
else
game:BindToClose(function()
local x, y = 0, 0
local spawn = task.spawn
local wait = task.wait
local function onBindToClose(player)
onPlayerRemoving(player)
y += 1
end
for _, player in Players:GetPlayers() do
x += 1
spawn(onBindToClose, player)
end
repeat wait(0) until y == x
end)
end
Players.PlayerAdded:Connect(onPlayerAdded)
Players.PlayerRemoving:Connect(onPlayerRemoving)
But if in the future you’d like to save more values you’ll need to do this instead:
local DataStoreService = game:GetService("DataStoreService")
local Players = game:GetService("Players")
local RunService = game:GetService("RunService")
local playerDataStore = DataStoreService:GetDataStore("PlayerData")
local function onPlayerAdded(player)
local success, data = xpcall(playerDataStore.GetAsync, warn, playerDataStore, player.UserId.."_leaderstats")
if success then
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
leaderstats.Parent = player
local Gold = Instance.new("IntValue")
Gold.Name = "Gold"
local Example = Instance.new("IntValue")
Example.Name = "Example"
if data then
Gold.Value = data.Gold
Example.Value = data.Example
end
Gold.Parent = leaderstats
Example.Parent = leaderstats
end
end
local function onPlayerRemoving(player)
local leaderstats = player:FindFirstChild("leaderstats")
if leaderstats then
xpcall(playerDataStore.SetAsync, warn, playerDataStore, player.UserId.."_leaderstats", {
Gold = leaderstats.Gold.Value,
Example = leaderstats.Example.Value
})
end
end
if RunService:IsStudio() then
game:BindToClose(function()
task.wait(1)
end)
else
game:BindToClose(function()
local x, y = 0, 0
local spawn = task.spawn
local wait = task.wait
local function onBindToClose(player)
onPlayerRemoving(player)
y += 1
end
for _, player in Players:GetPlayers() do
x += 1
spawn(onBindToClose, player)
end
repeat wait(0) until y == x
end)
end
Players.PlayerAdded:Connect(onPlayerAdded)
Players.PlayerRemoving:Connect(onPlayerRemoving)
Although for both scripts to work you must make sure that:
It’s a server Script
You have Studio access to API services enabled
You’re testing in a place that’s published to Roblox
You change the values while in server mode when play-testing (there should be a green border around the viewport if you have the latest version of Studio installed)
You change the values within server scripts during actual gameplay
I knew this DataStore template script I made would come in handy