Inventory System Unnecessarly Duping Items

Hello! I am trying to make an rng type game where you roll and add items to your inventory. The rolling system works, but when you go to claim it, the item often gives you a different item from the same rarity, or a duplicate.


as you can see, I claim one item from the epic tier and it gives me every item in that tier. But, it only appears to do that if you have been rolling for a while. So it does’nt happen on your first role.

Here is my code:

local function addToInventory(character)
	local characterName = character.Name
	print("Adding to inventory: " .. characterName)  
	if inventory[characterName] then
		inventory[characterName].Quantity = inventory[characterName].Quantity + 1
		inventory[characterName].Label.Text = "X" .. inventory[characterName].Quantity
		print("Updated quantity for: " .. characterName .. " to " .. inventory[characterName].Quantity) 
	else
		print("Cloning template for new item: " .. characterName)  
		local newTemplate = template:Clone()
		newTemplate.Parent = script.Parent.Parent.Inventory.ScrollingFrame
		newTemplate.WorldModel:ClearAllChildren()

		local worldModel = newTemplate:FindFirstChild("WorldModel")
		if not worldModel then
			worldModel = Instance.new("WorldModel")
			worldModel.Parent = newTemplate
		end

		local characterClone = character:Clone()
		characterClone.Parent = worldModel

		local camera = Instance.new("Camera")
		camera.Parent = newTemplate
		newTemplate.CurrentCamera = camera

		local humanoidRootPart = characterClone:FindFirstChild("HumanoidRootPart")
		if humanoidRootPart then
			camera.CFrame = CFrame.new(humanoidRootPart.Position + Vector3.new(4, 2, 0), humanoidRootPart.Position)
		end

		newTemplate.NameLabel.Text = characterName
		newTemplate.QuantityLabel.Text = "x1"
		newTemplate.Visible = true

		inventory[characterName] = {
			Quantity = 1,
			Label = newTemplate.QuantityLabel
		}

		print("Added new item to inventory: " .. characterName)  
	end
end
	

NOTE: The characters are located in folders inside of replicated storage.
image

I can’t seem to find out what the issue is. If you need me to provide more code I can.

Any help is apreciated!

There’s nothing wrong with addToInventory. Please show us every place you’re calling addToInventory

I only call it once

	claimButton.MouseButton1Click:Connect(function()
		local character = getCharacterForRarity(textLabel.Text)
		if character then
			print("Claim button pressed. Adding character to inventory: " .. character.Name)  -- Debug statement
			addToInventory(character)
			claimButton.Visible = false
		else
			print("Error: No character to claim.")  
		end
	end)

My guess is the MouseButton1Click are stacking up. Can I see more of the script around the connection?

I don’t think that is it because in the first video I show, you can see that apon claiming one, you get every single item of that tier.

Nothing else in the script should be interfering but here is the rolling logic.

local function roll()
	if isCooldown then return end
	isCooldown = true

	for i = 1, 6 do
		local randomItem = getRandomItem()
		textLabel.Text = randomItem.name
		textLabel.TextColor3 = randomItem.color
		rarityLabel.Text = randomItem.rarity

		local character = getCharacterForRarity(randomItem.name)
		if character then
			characterLabel.Text = character.Name
			displayCharacterInViewport(character)
		else
			characterLabel.Text = "Unknown"
			viewportFrame:ClearAllChildren()
		end

		local startPositionText = UDim2.new(textLabel.Position.X.Scale, textLabel.Position.X.Offset, textLabel.Position.Y.Scale - 0.05, textLabel.Position.Y.Offset)
		local startPositionRarity = UDim2.new(rarityLabel.Position.X.Scale, rarityLabel.Position.X.Offset, rarityLabel.Position.Y.Scale - 0.05, rarityLabel.Position.Y.Offset)
		local startPositionCharacter = UDim2.new(characterLabel.Position.X.Scale, characterLabel.Position.X.Offset, characterLabel.Position.Y.Scale - 0.05, characterLabel.Position.Y.Offset)

		textLabel.Position = startPositionText
		rarityLabel.Position = startPositionRarity
		characterLabel.Position = startPositionCharacter

		local tweenDownText = createTween(textLabel, {Position = UDim2.new(textLabel.Position.X.Scale, textLabel.Position.X.Offset, textLabel.Position.Y.Scale + 0.05, textLabel.Position.Y.Offset)}, 0.1)
		local tweenDownRarity = createTween(rarityLabel, {Position = UDim2.new(rarityLabel.Position.X.Scale, rarityLabel.Position.X.Offset, rarityLabel.Position.Y.Scale + 0.05, rarityLabel.Position.Y.Offset)}, 0.1)
		local tweenDownCharacter = createTween(characterLabel, {Position = UDim2.new(characterLabel.Position.X.Scale, characterLabel.Position.X.Offset, characterLabel.Position.Y.Scale + 0.05, characterLabel.Position.Y.Offset)}, 0.1)

		tweenDownText:Play()
		tweenDownRarity:Play()
		tweenDownCharacter:Play()
		tweenDownText.Completed:Wait()
		script["Pen Clicks 6 (SFX)"]:Play()
		wait(0.1)
	end

	local selectedItem = getRandomItem()
	textLabel.Text = selectedItem.name
	textLabel.TextColor3 = selectedItem.color
	rarityLabel.Text = selectedItem.rarity

	local character = getCharacterForRarity(selectedItem.name)
	if character then
		characterLabel.Text = character.Name
		displayCharacterInViewport(character)
		claimButton.Visible = true
	else
		characterLabel.Text = "Unknown"
		viewportFrame:ClearAllChildren()
	end
	
	claimButton.MouseButton1Click:Connect(function()
		local character = getCharacterForRarity(textLabel.Text)
		if character then
			print("Claim button pressed. Adding character to inventory: " .. character.Name)  -- Debug statement
			addToInventory(character)
			claimButton.Visible = false
		else
			print("Error: No character to claim.")  
		end
	end)

	local startPositionText = UDim2.new(textLabel.Position.X.Scale, textLabel.Position.X.Offset, textLabel.Position.Y.Scale - 0.05, textLabel.Position.Y.Offset)
	local startPositionRarity = UDim2.new(rarityLabel.Position.X.Scale, rarityLabel.Position.X.Offset, rarityLabel.Position.Y.Scale - 0.05, rarityLabel.Position.Y.Offset)
	local startPositionCharacter = UDim2.new(characterLabel.Position.X.Scale, characterLabel.Position.X.Offset, characterLabel.Position.Y.Scale - 0.05, characterLabel.Position.Y.Offset)

	textLabel.Position = startPositionText
	rarityLabel.Position = startPositionRarity
	characterLabel.Position = startPositionCharacter

	local tweenDownText = createTween(textLabel, {Position = UDim2.new(textLabel.Position.X.Scale, textLabel.Position.X.Offset, textLabel.Position.Y.Scale + 0.05, textLabel.Position.Y.Offset)}, 0.1)

	local tweenDownRarity = createTween(rarityLabel, {Position = UDim2.new(rarityLabel.Position.X.Scale, rarityLabel.Position.X.Offset, rarityLabel.Position.Y.Scale + 0.05, rarityLabel.Position.Y.Offset)}, 0.1)
	local tweenDownCharacter = createTween(characterLabel, {Position = UDim2.new(characterLabel.Position.X.Scale, characterLabel.Position.X.Offset, characterLabel.Position.Y.Scale + 0.05, characterLabel.Position.Y.Offset)}, 0.1)

	tweenDownText:Play()
	tweenDownRarity:Play()
	tweenDownCharacter:Play()
	script["Trigger Click 1"]:Play()
	wait(cooldownTime)

	isCooldown = false
end

No, the connections are definitely stacking up, everytime you run roll() a new connection is made. You need to disconnect this connection when it is claimed.

local connection
connection = claimButton.MouseButton1Click:Connect(function()
		local character = getCharacterForRarity(textLabel.Text)
		if character then
			print("Claim button pressed. Adding character to inventory: " .. character.Name)  -- Debug statement
			addToInventory(character)
			claimButton.Visible = false
connection:Disconnect()
		else
			print("Error: No character to claim.")  
		end
	end)

Sorry for the bad formatting I’m on mobile

Actually, don’t do what I said
Store the connection at the top of your script or somewhere else and check if there is a connection, if there is then disconnect it.

local connection -- variable somewhere at the top of your script

if connection then
connection:Disconnect()
connection = nil
end

connection = claimButton.MouseButton1Click:Connect(function()
		local character = getCharacterForRarity(textLabel.Text)
		if character then
			print("Claim button pressed. Adding character to inventory: " .. character.Name)  -- Debug statement
			addToInventory(character)
			claimButton.Visible = false
		else
			print("Error: No character to claim.")  
		end
	end)

Again, ignore my poor formatting I’m on mobile

1 Like

Try this code to see if it fixes the issue.

local function addToInventory(character)
    local characterName = character.Name
    print("Adding to inventory: " .. characterName)  

    -- Check if the item is already in the inventory
    if inventory[characterName] then
        inventory[characterName].Quantity = inventory[characterName].Quantity + 1
        inventory[characterName].Label.Text = "X" .. inventory[characterName].Quantity
        print("Updated quantity for: " .. characterName .. " to " .. inventory[characterName].Quantity) 
    else
        print("Cloning template for new item: " .. characterName)  
        local newTemplate = template:Clone()
        newTemplate.Parent = script.Parent.Parent.Inventory.ScrollingFrame
        newTemplate.WorldModel:ClearAllChildren()

        local worldModel = newTemplate:FindFirstChild("WorldModel")
        if not worldModel then
            worldModel = Instance.new("WorldModel")
            worldModel.Parent = newTemplate
        end

        local characterClone = character:Clone()
        characterClone.Parent = worldModel

        local camera = Instance.new("Camera")
        camera.Parent = newTemplate
        newTemplate.CurrentCamera = camera

        local humanoidRootPart = characterClone:FindFirstChild("HumanoidRootPart")
        if humanoidRootPart then
            camera.CFrame = CFrame.new(humanoidRootPart.Position + Vector3.new(4, 2, 0), humanoidRootPart.Position)
        end

        newTemplate.NameLabel.Text = characterName
        newTemplate.QuantityLabel.Text = "x1"
        newTemplate.Visible = true

        inventory[characterName] = {
            Quantity = 1,
            Label = newTemplate.QuantityLabel
        }

        print("Added new item to inventory: " .. characterName)  
    end

    -- Additional debugging
    for itemName, itemData in pairs(inventory) do
        print("Inventory Item: " .. itemName .. ", Quantity: " .. itemData.Quantity)
    end
end
1 Like

How would additional debugging fix their issue? And there’s nothing wrong with their function the problem is a new connection is made for the claim button everytime a roll is made.

2 Likes

I see Umm debugging won’t fix but it identifies where multiple connections might be getting created. This should this ensure that only one connection is active for the claim button at any time.

Script:

local claimButtonConnection

local function addToInventory(character)
    local characterName = character.Name
    print("Adding to inventory: " .. characterName)  
    if inventory[characterName] then
        inventory[characterName].Quantity = inventory[characterName].Quantity + 1
        inventory[characterName].Label.Text = "X" .. inventory[characterName].Quantity
        print("Updated quantity for: " .. characterName .. " to " .. inventory[characterName].Quantity) 
    else
        print("Cloning template for new item: " .. characterName)  
        local newTemplate = template:Clone()
        newTemplate.Parent = script.Parent.Parent.Inventory.ScrollingFrame
        newTemplate.WorldModel:ClearAllChildren()

        local worldModel = newTemplate:FindFirstChild("WorldModel")
        if not worldModel then
            worldModel = Instance.new("WorldModel")
            worldModel.Parent = newTemplate
        end

        local characterClone = character:Clone()
        characterClone.Parent = worldModel

        local camera = Instance.new("Camera")
        camera.Parent = newTemplate
        newTemplate.CurrentCamera = camera

        local humanoidRootPart = characterClone:FindFirstChild("HumanoidRootPart")
        if humanoidRootPart then
            camera.CFrame = CFrame.new(humanoidRootPart.Position + Vector3.new(4, 2, 0), humanoidRootPart.Position)
        end

        newTemplate.NameLabel.Text = characterName
        newTemplate.QuantityLabel.Text = "x1"
        newTemplate.Visible = true

        inventory[characterName] = {
            Quantity = 1,
            Label = newTemplate.QuantityLabel
        }

        print("Added new item to inventory: " .. characterName)  
    end

    -- Disconnect existing connection if it exists
    if claimButtonConnection then
        claimButtonConnection:Disconnect()
    end

    -- Create a new connection
    claimButtonConnection = claimButton.MouseButton1Click:Connect(function()
        print("Claim button clicked for: " .. characterName)
        -- Your claim button logic here
    end)
end
1 Like

This fixes part of the issue! Before it would give you multiple towers and the more you rolled the more exponential that amount of towers was. Now it only gives you one tower. But that tower never seems to be correct but rather a tower from the same rarity. So now there is just the question, What could be affecting it so that it chooses a random tower from the same rarity you rolled as aposed to the one you rolled?

I really appreciate your help by the way! I’ve been stuck on this for quite some time now.

I managed to solve the rest of the issue on my own. The issue is there because the roll() function first displays the selected character based on the rarity, but when the Claim button is pressed, it calls the getCharacterForRarity() function again, which gets a new random character of the same rarity. To fix this, I just store the specific character that was rolled so it can be consistently added to the inventory when claimed. Thanks for your assistance!

2 Likes

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.