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

Help with DataStores?

Asked by 9 years ago

I'm trying to make an inventory save when a player leaves.

local ds = game:GetService("DataStoreService"):GetDataStore("tools")

game.Players.PlayerAdded:connect(function(player)
    local key = "user_" .. player.userId
    ds:UpdateAsync(key, function(old)
        old = game.Players.LocalPlayer.Backpack:GetChildren()
        if old:IsA("Tool") then
        local new = old or nil
        local tool = old:Clone()
        tool.Parent = game.Players.LocalPlayer.Backpack
        return new
        end
    end)

end)

Please help!

1 answer

Log in to vote
0
Answered by 9 years ago

Data Stores cannot save instances themselves (A tool is an instance) So, to save a player's backpack I put tools in the "ServerStorage" like so: http://gyazo.com/3746b89ded1f686afb71ad8c97a935dc

local ds = game:GetService("DataStoreService"):GetDataStore("tools")
local defaultTools = {game.ServerStorage.Pistol,game.ServerStorage.Sword} --The values in this are instances of tools. That can be cloned.
game.Players.PlayerAdded:connect(function(ply)
    local key = "user_"..ply.userId
    local playerTools = ds:GetAsync(key)
    if playerTools == nil then --If the value is nil then use the default tools
        for i,t in ipairs(defaultTools) do
            local newClone = t:Clone() --Because the values in the defaultTools are instances they can be cloned
            newClone.Parent = ply.Backpack
        end
    else
        for i,pt in ipairs(playerTools) do --Loop through the tool names
            for i2,st in ipairs(game.ServerStorage:GetChildren()) do --Loop through the tools in ServerStorage
                if st.Name == pt then --If the tool name is equal to the saved string value
                    local newClone = st:Clone()
                    newClone.Parent = ply.Backpack
                    break --No point looping through the rest of the children if it's already been found, breaks out of the "GetChildren" loop.
                end
            end
        end
    end
end)
game.Players.PlayerRemoving:connect(function(ply)
    local key = "user_"..ply.userId
    local playerTools = {}
    for i,b in ipairs(ply.Backpack:GetChildren()) do
        table.insert(playerTools,b.Name) --Inserting the tool's name
    end
    ds:UpdateAsync(key,function(old)
        return playerTools --Saves a table of the names of the tools that are in the player's backpack
    end)
end)

When the player joins the game (when the "PlayerAdded" event is called) then the "GetAsync" is called to retrieve the player's saved backpack. If they haven't saved then the value will be nil. So, I created a table (defaultTools) that stores the Instances of Tools in the ServerStorage. This is looped through and adds to the player's backpack. However, if the retrieved backpack is not nil then the stored values are names of tools. This is looped through, then looping through the children in ServerStorage and checking if the values are the same then if so, adding a clone of the Tool instance (in ServerStorage) to the player's backpack.

Then, when the player leaves ("PlayerRemoving") I looped through the player's backpack adding the tool's name to a table which is then saved using "UpdateAsync".

Hope this helps. I have tested and it works for myself.

Ad

Answer this question