I am making a Plugin and realized that I could use some faster Blueprint prototyping for the end developer if I add auto conversions for various types in my system. After building the project however, the auto cast does not work. I followed the meta categories of the String library. Is this not supported outside of the core modules or am I doing something wrong?
UFUNCTION(BlueprintPure, meta = (DisplayName = "Value (MyObject)", CompactNodeTitle = "->", BlueprintAutocast), Category = "MyObject")
static FString Conv_MissionStringBindingValue(const class UMyObject* MyObjectPtr);
Looking at the engine source and trying to follow what happens with the BlueprintAutocast metadata this seems to be the flow:
All functions with the BlueprintAutocast metadata are added to the FAutocastFunctionMap singelton. This map is refreshed for example when you HotReload from the editor (FAutocastFunctionMap::OnProjectHotReload) or a module changes (FAutocastFunctionMap::OnModulesChanged). The FAutocastFunctionMap::InnerMap maps strings to TWeakObjectPtr<UFunction>. The string keys contain the type information of the first input pin and the return property.
So now we have this map available where is it actually used?
The AutocastFunctionMap is searched for an appropriate entry via FAutocastFunctionMap::Find using the input and return pin type information. The search is done in UEdGraphSchema_K2::SearchForAutocastFunction. It is used to determine whether a connection is possible (UEdGraphSchema_K2::CanCreateConnection) and in UEdGraphSchema_K2::CreateAutomaticConversionNodeAndConnections. This function is called when you try to connect a wire for example from a āfloatā type output pin to a āstringā type input pin. Thanks to the BlueprintAutocast function/system, the function call to UKismetStringLibrary::Conv_FloatToString will be added automagically
In your case this means when you drag a wire from a UMyObject* to a string input, your Conv_MissionStringBindingValue function should be automatically created for you.
Is this what you were expecting to happen with the BlueprintAutocast metadata or were you looking for something different?
Yes, I was expecting that. However, that was not the behaviour. Ill step through the code later to see if its not being imported properly to the autocrats registry.
Iāve used it without problems. As far as I can see, your declaration is the same as mine, so Iām not sure why itās not working for you.
Actually looking at my code, for my versions taking UObject/UClass, the parameter is non-const. Seems unlikely that would be an issue, but something to try. The use of const in Blueprint-facing code is rather inconsistent in my experience.
Seems that removing the constness of the parameter worked. However, now it is just passing in a nullptr despite the fact that in the BP Graph in debug, it has a valid referenceā¦ another problem for another day. Thanks.
Another solution (for people with a similar problem): in my case it worked after setting the functions as public.
I forgot that because I was copying it from Epicās code. Interestingly, theirs worked without being public.
And I found this on EdGraphSchema_K2.cpp:
Resurrecting an old thread here, but itās the top result when trying to work out why BlueprintAutocast functions are not working.
I had an issue where I wanted to convert a custom type to/from a float, and while I could easily make the function work, it would never show up as an automatic cast/conversion when using drag-and-drop.
The problem was that if you are using Unreal Engine 5, all āfloatā variables in Blueprint are actually doubles. So, you will need to use double instead of float in the code for any such autocast functions.
If you use float instead, the function will work as a normal function without issue, but it will never be selected for autocasting to/from a Blueprint float variable.
Example code for an autocast function to convert a custom struct to a Blueprint float:
UCLASS()
class UMyFunctionLib : public UBlueprintFunctionLibrary //Must be UBlueprintFunctionLibrary
{
GENERATED_BODY()
public: //must be public
UFUNCTION(BlueprintPure, meta = (DisplayName = "A To B",CompactNodeTitle = "->", BlueprintAutocast), Category = "MyUtils")
static FStructB Conv_AToB(FStructA In)
{
return ....
}
}