how do i make the item to duplicate when its being picked up again

:information_source: Attention Topic was automatically imported from the old Question2Answer platform.
:bust_in_silhouette: Asked By GrumpyIdiot

well i just need the item to be added to another slot every time i pick it up the more i pick items the more it adds in the inventory slots

thats the code i got for items to be added in the inventory

func add_item(item):
	var item_added = false
	for i in range(len(items)):
		if items[i] != null:
			if items[i].name == item.name:
				item_added = true
				emit_signal("items_changed" , [i])
				return true
				break
	if item_added == false:
		for i in range(len(items)):
			if items[i] == null:
				set_item(i, item)
				item_added = true
				emit_signal("items_changed", [i])
				return true 
    ***************************************************************

and thats the item code

 extends Area2D
var item
var inventory = preload("res://colourful gui/codes/Inventory.tres")
onready var sprite = $Sprite

func _ready():
	sprite.texture = item.texture


func _on_KinematicBody2D_body_entered(body):
	if inventory.add_item(item):
		queue_free()
  *****************************************************************

and thats the code that drop items

extends StaticBody2D

var base_item = preload("res://colourful gui/codes/baseitem.tscn")
var drop = preload("res://colourful gui/codes/gun.tres")



func _on_Area2D_body_entered(body):
	drop_item(drop)
	
	
func drop_item(drop):
	var base_item_instance = base_item.instance()
	base_item_instance.item = drop
	base_item_instance.position = position
	get_parent().call_deferred("add_child" , base_item_instance)

Edited to format the code. Use the Code Sample button.

Zylann | 2023-07-07 17:08

We have repeat code here for func add_item(item): but not the code for item. Also, if it’s not in item, I would also like to see where add_item(item): is called.

Vadalken | 2023-07-08 10:35

yeah sorry i didn’t realize it, my mouse been acting up lately

thats the items code

extends Area2D
var item
var inventory = preload("res://colourful gui/codes/Inventory.tres")
onready var sprite = $Sprite

func _ready():
	sprite.texture = item.texture

func _on_KinematicBody2D_body_entered(body):
	if inventory.add_item(item):
		queue_free()

GrumpyIdiot | 2023-07-08 15:48

:bust_in_silhouette: Reply From: Vadalken

I am not sure your problem is with the code you have posted. If your code is not working then the problem might be with the set_item() function or with whatever is listening to the items_changed signal.
There could also be a tree structure issue with item drop since it is adding a child to it’s parent.

Staying within the code you have posted the problematic part is the add_item() function. add_item() is supposed to do 3 things:

  1. It checks if the item is already in items (inventory?). This returns true if successful.
  2. If item is not in items then it tries to find an unassigned slot in items to set as item. This returns true if successful.
  3. Return false if both previous steps fail.

If this is correct then here is what should change in the add_item() code:

  1. Add return false at end of the function. There is currently no return value if item is not in items and items is full. This is the only major issue with the function. As in it can cause crashes.
  2. If return is reached in the code, then the rest of the function is not executed. This can be used to simplify your code.
  3. break is written after return and will never be reached. It can be removed.

Example:

func add_item(item):
    for i in range(len(items)):
        if items[i] != null: 
            if items[i].name == item.name:
                emit_signal("items_changed" , [i])
                return true
    for i in range(len(items)):
        if items[i] == null:
            set_item(i, item)
            emit_signal("items_changed", [i])
            return true 
    return false

4 . You should consider using in build array functions. I would usefind() in this case.
Example:

func add_item(item):
    var i = items.find(item)
    if i != -1:
        emit_signal("items_changed" , [i])
        return true
    i = items.find(null)
    if i != -1:
        set_item(i, item)
        emit_signal("items_changed" , [i])
        return true
    return false

The array.find(argument) call returns the first index of the array that matches argument. If argument is not found then find() returns -1.

first of all thank you so much for that!!!

and the code works fine. sure i didnt think of that. i didnt know it would crush of the inventory was full lol

here is the thing. i have one item and i want the player to pick this item and if it appears again i want it to be picked again and appear in a different slot in the inventory. thats what im having an issue with.

so using in build array functions like find() will help me to achieve that or am i just being really dumb here

GrumpyIdiot | 2023-07-08 21:49