Hello, I am a developer working on a Napoleonic group and I am currently trying to add a exp system and I’ve managed to do that so far but the problem now is that I have to figure out how to add exp when a player kills another player and how to save levels and exp when the player leaves the game. Here’s the scripts I’ve made:
-- [ Aiden_Hatzfeldt ] --
-- Player Variables --
local player = game.Players.LocalPlayer
local level = player:WaitForChild("Level")
local current = level:WaitForChild("Current")
local max = level:WaitForChild("Max")
-- UI Variables --
local gui = script.Parent
local exterior = gui:WaitForChild("Exterior")
local label = exterior:WaitForChild("Level")
local exp = exterior:WaitForChild("Exp")
local bar = exterior:WaitForChild("Bar")
-- Change stats when join --
label.Text = "Level "..level.Value
exp.Text = current.Value.."/"..max.Value.." EXP"
bar.Size = UDim2.new(current.Value/max.Value, 0, 1, 0)
level.Changed:Connect(function(val)
label.Text = "Level "..level.Value
exp.Text = current.Value.."/"..max.Value.." EXP"
bar.Size = UDim2.new(current.Value/max.Value, 0, 1, 0)
end)
current.Changed:Connect(function(val)
exp.Text = current.Value.."/"..max.Value.." EXP"
bar.Size = UDim2.new(current.Value/max.Value, 0, 1, 0)
end)
Thats the main script
-- [ Aiden_Hatzfeldt ] --
game.Players.PlayerAdded:Connect(function(player)
local level = Instance.new("IntValue", player)
level.Name = "Level"
level.Value = 1
local exp = Instance.new("IntValue", level)
exp.Name = "Current"
exp.Value = 0
local maxExp = Instance.new("IntValue", level)
maxExp.Name = "Max"
maxExp.Value = 1000
exp.Changed:Connect(function(val)
if exp.Value >= maxExp.Value then
-- Do stuff
level.Value = level.Value + 1
exp.Value = 0
end
end)
end)
And here is the system itself so if someone could maybe give me a little feedback or changes I can make so it runs better, also please help me with the saving levels and exp, and how to give the player exp when that player kills another player.
2 things:
1- the exp required to level up (maxExp) should be determined by the level, for example: maxExp.Value = level.Value * 100, this way, in level 1 you would need 100 exp to level up, in level two you would need 200 exp and so on
2- instead of setting exp back to 0 when the player levels up, its better if you do exp.Value -= maxExp.Value. so if the player needed 100 exp to level up and got 200 exp, he would keep the excess of exp. this way is possible to level up multiple times if you get a lot of exp
I would change the parent of level, exp, and maxExp to a folder of whatever you want your player’s stats to be, here is also a way to save your player’s data with the new changes.
local DataStoreService = game:GetService("DataStoreService")
local playerData = DataStoreService:GetDataStore("SetToWhatYouWant")
local function onPlayerJoin(player)
local PlayerStats = Instance.new("Folder")
PlayerStats.Name = "PlayerStats"
PlayerStats.Parent = player
--//Stats\\--
local level = Instance.new("IntValue")
level .Name = "level "
level .Parent = PlayerStats
local exp = Instance.new("NumberValue")
exp.Name = "exp"
exp.Parent = PlayerStats
local maxExp = Instance.new("IntValue")
maxExp.Name = "maxExp"
maxExp.Parent = PlayerStats
local playerUserId = "Player_" .. player.UserId
local data = playerData:GetAsync(playerUserId)
if data then
level.Value = data['Level']
exp.Value = data['XP']
else
level.Value = 1
exp.Value = 0
end
end
local function create_table(player)
local player_stats = {}
for _, stat in pairs(player.PlayerStats:GetChildren()) do
player_stats[stat.Name] = stat.Value
end
return player_stats
end
local function onPlayerExit(player)
local player_stats = create_table(player)
local success, err = pcall(function()
local playerUserId = "Player_" .. player.UserId
playerData:SetAsync(playerUserId, player_stats)
end)
if not success then
warn('Could not save data!')
end
end
game.Players.PlayerAdded:Connect(onPlayerJoin)
game.Players.PlayerRemoving:Connect(onPlayerExit)
Then I would make a LevelServer which handles when a player levels up and when a player kills someone.
game.Players.PlayerAdded:Connect(function(player)
local PlayerStats = player:WaitForChild('PlayerStats')
local level = PlayerStats:WaitForChild('level')
local exp = PlayerStats:WaitForChild('exp')
local maxExp = PlayerStats:WaitForChild('maxExp')
player.CharacterAdded:Connect(function(character)
character.Humanoid.Died:Connect(function(died)
local killer = character:FindFirstChild('creater')
if killer ~= nil and killer.Value ~= nil then
exp.Value += 10 --Change if you want players to get more exp per kill!
end
end)
end)
maxExp.Value = level.Value * 100 --Change if you want it to take longer or shorter to level up!
level.Changed:Connect(function(Changed)
if Changed then
maxExp.Value = level.Value * 100 --Change if you want it to take longer or shorter to level up!
end
end)
exp.Changed:Connect(function(Changed)
if exp.Value >= maxExp.Value then
level.Value += 1
exp.Value = 0
maxExp.Value = level.Value * 100 --Change if you want it to take longer or shorter to level up!
end
end)
end)
This way if the player gains 1000 exp when their requirement is 100, they can continue leveling up with the extra exp they have in store unless your intention is to not carry over the extra exp. Also, try using a leaderstats system to store your variables, mainly a folder of sort. Learning Datastore will allow you to learn both leaderstats and how to save stats when the player leaves.
Ok so the first line seems fine, could you share what you are setting PlayerStats to. The second line is because you need to look in PlayerStats, not player so try local PlayerStats = player:WaitForChild('PlayerStats') and then local level = PlayerStats:WaitForChild('level') this should solve both your issues. Also, the local data = playerData:GetAsync(playerUserId) or 0 can just be local data = playerData:GetAsync(playerUserId) because we are checking if there is data already.
Ok so my last problem now is that the script isn’t changing the text for the exp bar, it still says 0/0 EXP as I set its name in properties but script should set the text to however much exp the player have, this worked before but its not anymore and I am not getting anymore errors