item_granter_device is buggy.

Please select what you are reporting on:

Unreal Editor for Fortnite

What Type of Bug are you experiencing?

Verse

Summary

The Item Granter device is buggy and doesn’t properly grant items.

Steps to Reproduce

using { /Fortnite.com/Devices }
using { /Verse.org/Simulation }
using { /UnrealEngine.com/Temporary/Diagnostics }

# See https://dev.epicgames.com/documentation/en-us/uefn/create-your-own-device-in-verse for how to create a verse device.

# A Verse-authored creative device that can be placed in a level
hello_world_device := class(creative_device):
    @editable ItemGranter: item_granter_device = item_granter_device{}
    @editable ConditionalButton: conditional_button_device = conditional_button_device{}
    # Runs when the device is started in a running game
    OnBegin<override>()<suspends>:void=
        Sleep(10.0)
        for (Player: GetPlayspace().GetPlayers()):
            ItemGranter.GrantItem(Player)
            ItemGranter.GrantItem(Player)
            ItemGranter.GrantItem(Player)
            ItemGranter.GrantItem(Player)
            for (Frame := 0..10):
                Print("Frame {Frame}: {ConditionalButton.GetItemCount(Player, 0)}")
                Sleep(0.0)
            

Expected Result

The prints should be:
LogVerse: : Frame 0: 4
LogVerse: : Frame 1: 4
LogVerse: : Frame 2: 4
LogVerse: : Frame 3: 4
LogVerse: : Frame 4: 4
LogVerse: : Frame 5: 4
LogVerse: : Frame 6: 4
LogVerse: : Frame 7: 4
LogVerse: : Frame 8: 4
LogVerse: : Frame 9: 4
LogVerse: : Frame 10: 4

Observed Result

The prints are:
LogVerse: : Frame 0: 0
LogVerse: : Frame 1: 1
LogVerse: : Frame 2: 1
LogVerse: : Frame 3: 2
LogVerse: : Frame 4: 2
LogVerse: : Frame 5: 3
LogVerse: : Frame 6: 3
LogVerse: : Frame 7: 4
LogVerse: : Frame 8: 4
LogVerse: : Frame 9: 4
LogVerse: : Frame 10: 4

Platform(s)

All

Island Code

0064-6931-6604

Additional Notes

Check my private uploaded map to reproduce it.

The status of UCB-1240 incident has been moved from ‘Awaiting Validation’ to ‘Needs Triage’.

I noticed we only have issues with granters in maps built with newer tools (post 28.10), previously built versions worked fine last time I checked, so we are hesitant to update our maps.

1 Like

The issue i described exists for several major versions.

From my testing the reason that this happen is because only the device trigger, not the result and confirmation, are handled by the primary game thread.
I can’t tell you if this is a server/client interaction or multhreaded processing where the second thread gets handed off teh confirmation and checks back into the main thread, but I can say for sure that only the trigger is confirmed, not the result of the trigger.
The item granters work this way specifically, and there are some other devices that do as well, where all it does is guarantee the trigger not the result.
My theory is this has to do with server-client authorative processes and this “handoff” to an sycn thread, or a requirement of the client machine to confirm.

Previously what would happen is you would have this work on your local test environemnt, but once you had multplayer involved or uploaded to private it would start exhibiting this behavior.

The Item Granter queues requests and awards them asynchronously, so the Grant Item event doesn’t happen immediately, especially when you queue up a bunch of requests at once. This will be why checking the inventory immediately after granting doesn’t work (as the debugging shows, they’re not actually granted till a couple of frames later). ItemGrantedEvent will fire when the item is actually given, so that provides a point where you can check your inventory for an accurate result.

That’s exactly what i described. Will it be fixed or is that intentional behavior?

I would get that it might be something that is desirable for ppl using Creative, so they don’t do some crazy event loops, that freeze their games and aren’t possible to debug with their tools, but i don’t see a reason for it to be like that in Verse.

If it won’t be fixed, i would appreciate a note in the docs.
It should either be marked as Async or get a <suspends> specicifier, but since this would break backwards compatibility, i suggest that it just is mentioned in the API, so ppl won’t need to figure out what is wrong with it.

1 Like