Hi there, I am working on a shop Gui and my goal is to make it so that the buy button in a template (which the template is cloned for every tool in a folder inside replicatedstorage) displays “OWNED” when bought. The issue that I can’t seem to get around my head is how would I do this with a template that clones for every tool in the folder and then change the text individually of the buy button without changing it for every other clone too.
I’ve left most of the scripts just so you know a bit of background context.
Localscript for cloning the template:
local folder = game.ReplicatedStorage:WaitForChild("Tools")
local frame = script.Parent
local template = frame.shoptemplate
template.Visible = false
for _, tool in pairs(folder:GetChildren()) do
local newTemplate = template:Clone()
local button = newTemplate.Buy
newTemplate.Parent = frame
newTemplate.Visible = true
newTemplate.Name = tool.Name
newTemplate.TextLabel.Text = tool.Name
newTemplate.Buy.Text = "$"..tool.Cost.Value
button.MouseButton1Click:Connect(function()
local result = game.ReplicatedStorage.BuyItem:InvokeServer(tool.Name)
if result == true then
--
else
--
end
end)
end
Serverscript for handling the remote of the buy function:
game.ReplicatedStorage.BuyItem.OnServerInvoke = function(player,toolName)
local tool = game.ReplicatedStorage.Tools:FindFirstChild(toolName)
if tool and not player.StarterGear:FindFirstChild(toolName) then
if tool:FindFirstChild("Cost") then
if tool.Cost.Value <= player.leaderstats.Coins.Value then
player.leaderstats.Coins.Value -= tool.Cost.Value
local newTool = tool:Clone()
newTool.Parent = player.Backpack
local newTool = tool:Clone()
newTool.Parent = player.StarterGear
return true
end
end
end
end
everytime someone either open the gui or buy something update all the buttons if they “own” the item and you can check if they own something by using Player.Backpack:FindFirstChild(tool name here) it would return nil if it doesn’t exist, you can do it like this
--your update script
if player.Backpack:FindFirstChild("BloxyCola") then
button.Text = "OWNED"
end
this is a one time item and resets when you die right? if you want something that saves you will need to use data store and then check if that item is in the datastore, the one i showed above is just to check if a player has an item in their backpack
what do you mean? if you put this script a local script and parent it to the specific item button and change ‘BloxyCola’ to what item name you want then it should work
I mean like, instead of copy pasting that script for every item in the folder, can’t I just for every tool check if it is bought, and then if it one of it’s bought then that cloned template will have the buy button saying that it’s owned?
You could create a little update() function, which would go through each button in your GUI and check if you own it, if so, change the text for that GUI to owned, else, leave it be.
You can achieve this with the same method you’re using.
function update()
for _,shopItem in pairs(frame:GetChildren())do -- search frame for the shop items
if player.Backpack:FindFirstChild(shopItem.Name) then --You've named the frame to match the tools name, so we can do this
shopItem.Buy.Text = "OWNED" -- this will only affect the shopItem you're looking at
else
print("You don't own "..shopItem.Name)
end
end
end
call update whenever the purchase button is clicked, this will go through each frame, check if your player has the item in their backpack and set the text to “OWNED” if they do
If you want to implement sanity checks then you can just run this on the server and return the results to the client.
Hm, the script didn’t seem to work. Am I doing something wrong?
local folder = game.ReplicatedStorage:WaitForChild("Tools")
local frame = script.Parent
local template = frame.shoptemplate
local Players = game:GetService("Players")
local player = Players.LocalPlayer
template.Visible = false
for _, tool in pairs(folder:GetChildren()) do
local newTemplate = template:Clone()
local button = newTemplate.Buy
newTemplate.Parent = frame
newTemplate.Visible = true
newTemplate.Name = tool.Name
newTemplate.TextLabel.Text = tool.Name
newTemplate.Buy.Text = "$"..tool.Cost.Value
local button = script.Parent
if player.Backpack:FindFirstChild("BloxyCola") then
button.Text = "OWNED"
button.MouseButton1Click:Connect(function()
local result = game.ReplicatedStorage.BuyItem:InvokeServer(tool.Name)
if result == true then
--
else
--
end
end)
end
end
local folder = game.ReplicatedStorage:WaitForChild("Tools")
local frame = script.Parent
local template = frame.shoptemplate
local Players = game:GetService("Players")
local player = Players.LocalPlayer
template.Visible = false
for _, tool in pairs(folder:GetChildren()) do
local newTemplate = template:Clone()
local button = newTemplate.Buy
newTemplate.Parent = frame
newTemplate.Visible = true
newTemplate.Name = tool.Name
newTemplate.TextLabel.Text = tool.Name
newTemplate.Buy.Text = "$"..tool.Cost.Value
local button = script.Parent
if player.Backpack:FindFirstChild(tool.Name) then
button.Text = "OWNED"
button.MouseButton1Click:Connect(function()
local result = game.ReplicatedStorage.BuyItem:InvokeServer(tool.Name)
if result == true then
--
else
--
end
end)
end
end
Example of the update function in use, bear in mind it’s not the most efficient
local folder = game.ReplicatedStorage:WaitForChild("Tools")
local frame = script.Parent
local template = frame.shoptemplate
local Players = game:GetService("Players")
local player = Players.LocalPlayer
template.Visible = false
function update()
for _,shopItem in pairs(frame:GetChildren())do -- search frame for the shop items
if player:WaitForChild("Backpack"):FindFirstChild(shopItem.Name) then --You've named the frame to match the tools name, so we can do this
shopItem.Buy.Text = "OWNED" -- this will only affect the shopItem you're looking at
else
print("You don't own "..shopItem.Name)
end
end
end
for _, tool in pairs(folder:GetChildren()) do
local newTemplate = template:Clone()
local button = newTemplate.Buy
newTemplate.Parent = frame
newTemplate.Visible = true
newTemplate.Name = tool.Name
newTemplate.TextLabel.Text = tool.Name
newTemplate.Buy.Text = "$"..tool.Cost.Value
local button = script.Parent
button.MouseButton1Click:Connect(function()
local result = game.ReplicatedStorage.BuyItem:InvokeServer(tool.Name)
if result then
update()
else
print("purchase failed.")
end
end)
end
However, even the update function seems unnecessary, are you sure you can’t just set the text to “OWNED” if result is true?, remember this click function only affects the GUI it’s highlighted over (so, if you bought the bloxy cola only the Cola UI would be affected by that)
But wouldn’t that mean that’s it’s checking if the remote is true, rather than if it was in your inventory? Wouldn’t that mean if you clicked the button, the text would just change to “OWNED” even if you don’t have the item?
(I know you’re confused with what I’m saying, I think what I’m saying is incorrect.)
Yeah, I think I was correct in the comment above. I think what is wrong here is that you’re updating the text if the remote function was true and rather not the inventory. Could you do something like this, but with inventory (not really asking for a script)?