Drag&Drop inventory issue

Hey all! I’m trying to make a slot based inventory with drag and drop system, but something went wrong.
The problem is when I drag and drop an item for the first time - it works fine, but for the second time all other items except first one are gone. You can see it on the video: https://youtu.be/ihO1cNmMg_c

What causes the problem is my own inventory refreshing as I think. I’ll try to make it clear.
The algorithm:
Player got an array of item structures

BeginPlay → Resize array of structs to 20

Item picked up → Item added to array of structs (Sets an item by first empty index as we got 20 empty slots)

Inventory opened → Loop for each element in array of structs → Add element to ListView(via constructing an object with ItemStructure data)

Item Dragged and Dropped → Swap elements in array of structs → Refresh the inventory(Clear List Items → then the same as when the inventory opened)

On the video I linked you can see that when the items are cleared, it adds new items but starting from index 20. Really hoping for help, can’t figure it out on my own

1 Like

Could you show this bit?

How it constructed in widget


The Init function
Function

I’ve found a node called Regenerate All Entries, tryna get it work with this node

1 Like

Do tell how it goes.


Unrelated note:

Instead of Init, we can:

image
image

Saves you a call, which may be important-ish if you have 10000 calls to make. Works with any type of spawn / create / construct / add component.

Yeah, I know about that function I can remove, will do it later when finish with it. Thanks!

1 Like

Seems like it doesn’t work. Now it doesnt swap in my UI at all, but in the inventory(array of structs) it does like as always. What I did:
Item picked up → Item adds to ListVew
Item dragged and dropped → Regenerate All Entries → Request Refresh(just in case)

UPD: Also did swap of entries, not just structs

I almost solved the problem or found the exact reason of it.
The solution(almost solution) is:
Remove From Parent → Delay 0.001 sec → Add to Viewport

The reason of the problem was that when we clear all entries in the list - it remembers the amount of them and starts from 20(in my case).

So I’m just destroying the ListView and constructing it again

You could instead delay until next frame.

image

Note that Adding to Viewport triggers Construct. Any script there will be re-run. Every time.


But is there a reason why you’re clearing the ENTIRE list view? Why not remove only the undesired elements → regenerate. The list view would then regenerate only the visible widgets. Sounds wasteful and undoes all the performance benefits list views bring. If you’re reconstructing all from scratch, why not pop widgets into a simple Grid Panel instead?

Asking as you may have your reasons.

This node works great, thanks!

The list constructs when player opens up the inventroy. Perhaps there is a way to replace each item when it’s added to the inventory but I don’t know what’s better. I’d try to make it

The list constructs when player opens up the inventroy.

It also fires Construct whenever you Add to Viewport. This will re-layout the parent widget and any children widgets. That’s why it’s not recommended - not for complex widgets, not for widgets that must retain data, and not for widgets that rely on Construct script. Changing Visibility is just so much more efficient, and safer.

Hope you see what I mean.

I, on the other hand, am not sure what you mean. Do you mean to update an existing object with new data so the list view can update instanced widgets? Because that’s the whole point of using a list view. The point is to create the objects once (or add new ones / remove them when needed); not to remove all / respawn all. Utterly defeats the performance benefits unless you can justify it with a lower memory footprint. But that’s grasping at straws.

On the other hand, it may not matter if the inventory is small. However, if the inventory is small, there’s no need for a list view either :person_shrugging:


In short:

  • this should be done only once per game launch / save / load
  • from this point, add new / remove unwanted objects only, and only when needed
  • you’d want to clear the entire list view (which destroys the underlying objects & widgets) when the player actually lost their entire inventory

Hope that makes sense; consider it and good luck!

I get it now. I’ll take a look what I can fix in it and probably text here back later, thanks so much for you answers!!

1 Like

Greetings again! I’ve reworked this system and now items add to the list at the same time as to the inventory, so there is no loop no more. That works better but I have the same issue.

The issue is - the list doesn’t update index of items in itself.

This is how it works:

I think I need to update the list but don’t know how. It works via destructing it and constructing again but I’d like to find a better way to refresh it

Do read their tooltips as these two work quite differently:

image

I’ve read the tooltips but still don’t get it. In theory request refresh should update the indexes of items but it doesn’t.
So in practice Regenerate All Entries makes all items in list empty, and Request Refresh does nothing