Hello, I am developing a single player game in which the player gets to place models into the Workspace, but I need to make it so every 60s or such the game saves which objects are in the assigned PlayerBuildings folder in Workspace. I found this script, but it only works on parts, does anyone know how I could adapt this code to save models?
Script in Workspace
local playerDataStore = game:GetService("DataStoreService"):GetDataStore("PlayerData")
local function savePlayerData(player)
local playerKey = "player_"..player.UserId
local playerData = {}
for _, part in ipairs(game.Workspace.PlayerBuildings:GetChildren()) do
playerData[part.Name] = {
Position = part.Position,
Rotation = part.Rotation,
Color = part.Color,
Size = part.Size,
Material = part.Material
}
end
local success, err = pcall(function()
playerDataStore:SetAsync(playerKey, playerData)
end)
end
local function loadPlayerData(player)
local playerKey = "player_"..player.UserId
local playerData
local success, err = pcall(function()
playerData = playerDataStore:GetAsync(playerKey)
end)
if playerData then
for partName, partData in ipairs(playerData) do
local newPart = Instance.new("Model")
newPart.Position = partData.Position
newPart.Rotation = partData.Rotation
newPart.Color = partData.Color
newPart.Material = partData.Material
newPart.Size = playerData.Size
end
end
end
game.Players.PlayerAdded:Connect(function(player)
loadPlayerData(player)
player.PlayerGui:WaitForChild("Save").Save.MouseButton1Click:Connect(function()
savePlayerData(player)
end)
end)
Hello, there !
What you’ve to do is basically replacing part’s properties by model’s.
As well, edit the following things: part.Position → model.PrimaryPart.Position part.Rotation → model.PrimaryPart.Orientation part.Color → model.PrimaryPart.Color part.Size → model.GetScale() part.Material → model.PrimaryPart.Material
Do the same for partData
Don’t forget to set a part as the primary part of your model, in other cases, it won’t work.
If you want the color of each part of your model, you’ll need to loop the corresponding step for the number of parts in your model and to store them in an array. This is the method I’d rather use, but I’m not sure it’s the best. Maybe a function exists for this, but I sadly don’t know it yet.
Don’t hesitate if you have other questions or if something is wrong with what I said.
Hoping I could satisfy you.
Have a great day!
It didn’t work, I got an error saying I couldn’t store Dictionary in date store.
My script
local playerDataStore = game:GetService("DataStoreService"):GetDataStore("PlayerData")
local function savePlayerData(player)
local playerKey = "player_"..player.UserId
local playerData = {}
for _, model in ipairs(game.Workspace.PlayerBuildings:GetChildren()) do
playerData[model.Name] = {
Position = model.PrimaryPart.Position,
Rotation = model.PrimaryPart.Rotation,
Color = model.PrimaryPart.Color,
Size = model:GetScale(),
Material = model.PrimaryPart.Material
}
end
local success, err = pcall(function()
playerDataStore:SetAsync(playerKey, playerData)
end)
end
local function loadPlayerData(player)
local playerKey = "player_"..player.UserId
local playerData
local success, err = pcall(function()
playerData = playerDataStore:GetAsync(playerKey)
end)
if playerData then
for modelName, modelData in ipairs(playerData) do
local newmodel = Instance.new("mode")
newmodel.Position = modelData.PrimaryPart.Position
newmodel.Rotation = modelData.PrimaryPart.Rotation
newmodel.Color = modelData.PrimaryPart.Color
newmodel.Material = modelData.PrimaryPart.Material
newmodel.Size = playerData.PrimaryPart:GetScale()
end
end
end
game.Players.PlayerAdded:Connect(function(player)
loadPlayerData(player)
player.PlayerGui:WaitForChild("Save").Save.MouseButton1Click:Connect(function()
savePlayerData(player)
end)
end)
Try encoding the table via HttpService:JSONEncode(tableHere). If you want to get the table the way it was before, you would use game.HttpService:JSONDecode(stringHere)
Also special values like Vector3, Color3, and CFrames don’t have a way to be stored in tables if they are going to be encoded into string format. Only null, String, Number, Arrays, and Dictionaries. I recommend using these two functions when it comes to carrying over these values.
-- Convert Vector3s and Color3s into tables
function preserveSpecialValues(t)
local new = {}
local function a(lt,nt)
for i,v in pairs(lt) do
if type(v) == 'table' then
nt[i] = {}
a(v,nt[i])
else
if typeof(v) == 'Vector3' then
nt[i] = {type='Vector3', params={v.X, v.Y, v.Z}}
elseif typeof(v) == 'Color3' then
nt[i] = {type='Color3', params={v.R, v.G, v.B}}
elseif typeof(v) == 'EnumItem' then
nt[i] = v.Name
end
end
end
end
a(t,new)
return new
end
-- Convert supported tables back into Vector3s and Color3s.
function obtainSpecialValues(t)
local new = {}
local function a(lt,nt)
for i,v in pairs(lt) do
if type(v) == 'table' then
nt[i] = {}
if not v.type then
a(v,nt[i])
else
if v.type == 'Vector3' then
nt[i] = Vector3.new(table.unpack(v.params))
elseif v.type == 'Color3' then
nt[i] = Color3.new(table.unpack(v.params))
end
end
else
nt[i] = v
end
end
end
a(t,new)
return new
end