// Copyright Epic Games, Inc. All Rights Reserved. #pragma once #include "ControlRigBlueprintLegacy.h" #include "EdGraph/EdGraph.h" #include "Graph/ControlRigGraphNode.h" #include "Rigs/RigHierarchy.h" #include "Rigs/RigHierarchyController.h" #include "RigVMModel/RigVMGraph.h" #include "RigVMCore/RigVM.h" #include "EdGraph/RigVMEdGraph.h" #include "ControlRigGraph.generated.h" #define UE_API CONTROLRIGDEVELOPER_API class UControlRigBlueprint; class UControlRigGraphSchema; class UControlRig; class URigVMController; struct FRigCurveContainer; UCLASS(MinimalAPI) class UControlRigGraph : public URigVMEdGraph { GENERATED_BODY() public: UE_API UControlRigGraph(); /** Set up this graph */ UE_API virtual void InitializeFromAsset(FRigVMAssetInterfacePtr InBlueprint) override; UE_API virtual bool HandleModifiedEvent_Internal(ERigVMGraphNotifType InNotifType, URigVMGraph* InGraph, UObject* InSubject) override; #if WITH_EDITOR const TArray>* GetBoneNameList(URigVMPin* InPin = nullptr) const { return GetElementNameList(ERigElementType::Bone); } const TArray>* GetControlNameList(URigVMPin* InPin = nullptr) const { return GetElementNameList(ERigElementType::Control); } const TArray>* GetControlNameListWithoutAnimationChannels(URigVMPin* InPin = nullptr) const { return &ControlNameListWithoutAnimationChannels; } const TArray>* GetNullNameList(URigVMPin* InPin = nullptr) const { return GetElementNameList(ERigElementType::Null); } const TArray>* GetCurveNameList(URigVMPin* InPin = nullptr) const { return GetElementNameList(ERigElementType::Curve); } const TArray>* GetConnectorNameList(URigVMPin* InPin = nullptr) const { return GetElementNameList(ERigElementType::Connector); } const TArray>* GetSocketNameList(URigVMPin* InPin = nullptr) const { return GetElementNameList(ERigElementType::Socket); } UE_API virtual const TArray>* GetNameListForWidget(const FString& InWidgetName) const override; UE_API void CacheNameLists(URigHierarchy* InHierarchy, const FRigVMDrawContainer* DrawContainer, TArray> ShapeLibraries); UE_API const TArray>* GetElementNameList(ERigElementType InElementType = ERigElementType::Bone) const; UE_API const TArray>* GetElementNameList(URigVMPin* InPin = nullptr) const; UE_API const TArray> GetSelectedElementsNameList() const; UE_API const TArray>* GetDrawingNameList(URigVMPin* InPin = nullptr) const; UE_API const TArray>* GetShapeNameList(URigVMPin* InPin = nullptr) const; UE_API FReply HandleGetSelectedClicked(URigVMEdGraph* InEdGraph, URigVMPin* InPin, FString InDefaultValue); UE_API FReply HandleBrowseClicked(URigVMEdGraph* InEdGraph, URigVMPin* InPin, FString InDefaultValue); private: template static bool IncludeElementInNameList(const T* InElement) { return true; } template void CacheNameListForHierarchy(UControlRig* InControlRig, URigHierarchy* InHierarchy, TArray>& OutNameList, bool bFilter = true) { TArray Names; UE::TScopeLock Lock(InHierarchy->ElementsLock); for (auto Element : *InHierarchy) { if(Element->IsA()) { if(!bFilter || IncludeElementInNameList(Cast(Element))) { static const FLinearColor Color(FLinearColor(0.0, 112.f/255.f, 224.f/255.f)); FRigVMStringTag Tag; if(InControlRig) { if(const FRigElementKey* SourceKey = InControlRig->GetElementKeyRedirector().FindReverse(Element->GetKey())) { Tag = FRigVMStringTag(Element->GetKey().Name, Color); Names.Emplace(SourceKey->Name.ToString(), Tag); continue; } // look up the resolved name if(Element->GetType() == ERigElementType::Connector) { if(const FRigElementKeyRedirector::FCachedKeyArray* Cache = InControlRig->GetElementKeyRedirector().Find(Element->GetKey())) { if(!Cache->IsEmpty()) { Tag = FRigVMStringTag((*Cache)[0].GetKey().Name, Color); } } } } Names.Emplace(Element->GetName(), Tag); } } } Names.Sort(); OutNameList.Reset(); OutNameList.Add(MakeShared(FName(NAME_None).ToString())); for (const FRigVMStringWithTag& Name : Names) { OutNameList.Add(MakeShared(Name)); } } template void CacheNameList(const T& ElementList, TArray>& OutNameList) { TArray Names; for (auto Element : ElementList) { Names.Add(Element.Name.ToString()); } Names.Sort(); OutNameList.Reset(); OutNameList.Add(MakeShared(FName(NAME_None).ToString())); for (const FString& Name : Names) { OutNameList.Add(MakeShared(Name)); } } TMap>> ElementNameLists; TArray> ControlNameListWithoutAnimationChannels; TArray> DrawingNameList; TArray> ShapeNameList; int32 LastHierarchyTopologyVersion; static UE_API TArray> EmptyElementNameList; #endif friend class UControlRigGraphNode; friend class SRigVMGraphNode; friend class UControlRigBlueprint; }; template<> inline bool UControlRigGraph::IncludeElementInNameList(const FRigControlElement* InElement) { return !InElement->IsAnimationChannel(); } #undef UE_API