I am not clear on the rules on which events can be “implemented” directly in blueprints and which events need to be bind to a custom event first and then can only be implemented from that custom event:
If you look at this: We have 2 events. Calendar.NewDayBegan and Button_0.OnClicked
Both are declared the same way ( DECLARE_DYNAMIC_MULTICAST_DELEGATE + BlueprintAssignable) and broadcasted from c++. Both are implemented the same way: Click on the Calendar or Button in the variable view, click on the event “bind”. But the Calendar does not work, the Button does work.
The only way to get the Calendar event to work is to bind it like displayed.
But why does it work for the one type and not for the other? And is there a way to make the Calendar.NewDayBegan work like the Button_0.OnClicked ?
I was trying to figure out this same question today, and couldn’t find the reason in the documentation. Was happy to find this post but then sad to see it never got answered (8 years ago).
For anyone else who arrives here via search: I discovered through testing that the simpler pre-bound events only work if the target reference is pre-set.
E.g. if your reference to the object dispatching the events was wired up in the details panel in your map, then the events would come through, but if your reference is populated by looking for the object in BeginPlay then the events will not come through.
(My guess would be that under the hood, sometime before BeginPlay, it loops over all such events and attempts to bind them. Missing that boat means they never get bound. I haven’t checked the source to confirm this though.)
If you do need to bind an event using the Bind Event node it’s a good idea to hook a Create Event node into it, instead of a red event node. This then allows you to either match that to a red event node that lives elsewhere on your graph (no wire!) or link it to a function you’ve made.
“Events” are just a fancy name for “Virtual functions that don’t return anything and can run at the top level of the game loop.” This is why events can use things like Delay, which requires simple continuation support, which is hard to implement when there’s a call stack involved.
This means that the built-in “events” can be virtual functions that the engine can call as appropriate, without having to “bind” the event. The engine simply calls the function on the class, no binding needed.
The most obvious instance of this is Tick(), which obviously doesn’t go through dynamic binding for most actors – there’s a whole subsystem for how to tick things with as little overhead as possible, which revolves around calling the Tick() virtual function without any manual event binding. (Making that all work together with blueprint overrides and still supporting Delay adds a fair bit of extra glue code compared to native ticking, btw, so in blueprint it’s more overhead than C++.)