I am trying to return a reference to a structure which can be called by blueprints. I can get it to compile in c++, but in blueprints, I get an error “Error The direction of Return Value doesn’t match the direction of parameter ReturnValue”.
Thank you for pointing this out to us. I ran some tests and was able to see the results that you described. I have entered a report to have this investigated further (UE-8693).
Yes! That was it. I glossed over my “const” as well. Making non-const removed the error. I guess what would be helpful is to change the error to something like “can’t set value on const reference”.
This still does not explain to me why it is impossible to return such a value as const. If you don’t want to alter the returned value, it should be const
Blueprints don’t actually know what const means, so if this is only being used in Blueprints, the const keyword doesn’t help much. What I did find that worked in this case is instead of using const struct FTestStruct& AMyActor::GetTestStruct() const, use const struct FTestStruct AMyActor::GetTestStruct() const instead. Leaving the & out seems to allow this to work as expected.
While this may work, it shouldn’t be this way. You should be able to return a const reference from a function. If the blueprint system then chooses to copy this into a new non-const/ref structure, so be it, the inefficiencies of BP climb.
The problem lies here:
const bool bOutParam = (Property->HasAnyPropertyFlags(CPF_OutParm | CPF_ReturnParm) && !(Property->HasAnyPropertyFlags(CPF_ReferenceParm)));
if ( ((SourcePin->Direction == EGPD_Input) && bOutParam) || ((SourcePin->Direction == EGPD_Output) && !bOutParam))
{
MessageLog.Error(*FString::Printf(*LOCTEXT("DirectionMismatchParameter_Error", "The direction of @@ doesn't match the direction of parameter %s").ToString(), *Property->GetName()), SourcePin);
}
An an out param (i.e. return value) cannot be a reference, const or not, which is entirely silly.
You are correct that you will receive an error message when trying to have a reference as a return value (as in the original post, for example). This is unfortunately a current limitation of Blueprints.
However, you are still able to pass parameters to a BlueprintCallable function as references, and those should function normally. There is one thing to keep in mind, however. If you write your function declaration like you normally would in C++, the parameter will appear on the node as an output pin instead of as an input pin. For example, the following code will give you a Return Float output pin: