Files
FLESH/Source/FLESHEditor/Private/FLESHGraph/FLESHGraph.cpp
2025-04-23 01:18:06 +08:00

231 lines
5.9 KiB
C++

#include "FLESHGraph/FLESHGraph.h"
#include "FLESHGraph/FLESHGraphNode.h"
#include "Logging/LogMacros.h"
// Define log category
DEFINE_LOG_CATEGORY_STATIC(LogFLESHGraph, Log, All);
UFLESHGraph::UFLESHGraph()
{
// Initialize default values
RootNode = nullptr;
}
void UFLESHGraph::Initialize()
{
// Clear graph
ClearGraph();
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH graph initialized"));
}
UFLESHGraphNode* UFLESHGraph::AddNode(TSubclassOf<UFLESHGraphNode> NodeClass, const FVector2D& Position)
{
// Check if node class is valid
if (!NodeClass)
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Invalid node class"));
return nullptr;
}
// Create new node
UFLESHGraphNode* NewNode = NewObject<UFLESHGraphNode>(this, NodeClass);
if (!NewNode)
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Failed to create node"));
return nullptr;
}
// Set node position
NewNode->SetNodePosition(Position);
// Add to node list
Nodes.Add(NewNode);
// If it's the first node, set as root node
if (Nodes.Num() == 1)
{
RootNode = NewNode;
}
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Added new node: %s"), *NewNode->GetNodeTitle());
return NewNode;
}
bool UFLESHGraph::RemoveNode(UFLESHGraphNode* Node)
{
// Check if node is valid
if (!Node)
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Trying to remove invalid node"));
return false;
}
// Disconnect from other nodes
TArray<UFLESHGraphNode*> InputNodes = Node->GetInputNodes();
TArray<UFLESHGraphNode*> OutputNodes = Node->GetOutputNodes();
for (UFLESHGraphNode* InputNode : InputNodes)
{
DisconnectNodes(InputNode, Node);
}
for (UFLESHGraphNode* OutputNode : OutputNodes)
{
DisconnectNodes(Node, OutputNode);
}
// If it's the root node, reset root node
if (Node == RootNode)
{
RootNode = nullptr;
// If there are other nodes, choose the first one as the new root node
if (Nodes.Num() > 1)
{
for (UFLESHGraphNode* OtherNode : Nodes)
{
if (OtherNode != Node)
{
RootNode = OtherNode;
break;
}
}
}
}
// Remove from node list
bool bRemoved = Nodes.Remove(Node) > 0;
if (bRemoved)
{
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Removed node: %s"), *Node->GetNodeTitle());
}
else
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Node is not in graph: %s"), *Node->GetNodeTitle());
}
return bRemoved;
}
bool UFLESHGraph::ConnectNodes(UFLESHGraphNode* SourceNode, UFLESHGraphNode* TargetNode)
{
// Check if nodes are valid
if (!SourceNode || !TargetNode)
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Trying to connect invalid nodes"));
return false;
}
// Add connection
bool bSourceAdded = SourceNode->AddOutputNode(TargetNode);
bool bTargetAdded = TargetNode->AddInputNode(SourceNode);
if (bSourceAdded && bTargetAdded)
{
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Connected nodes: %s -> %s"),
*SourceNode->GetNodeTitle(), *TargetNode->GetNodeTitle());
return true;
}
else
{
// If adding failed, rollback changes
if (bSourceAdded)
{
SourceNode->RemoveOutputNode(TargetNode);
}
if (bTargetAdded)
{
TargetNode->RemoveInputNode(SourceNode);
}
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Connecting nodes failed: %s -> %s"),
*SourceNode->GetNodeTitle(), *TargetNode->GetNodeTitle());
return false;
}
}
bool UFLESHGraph::DisconnectNodes(UFLESHGraphNode* SourceNode, UFLESHGraphNode* TargetNode)
{
// Check if nodes are valid
if (!SourceNode || !TargetNode)
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Trying to disconnect invalid nodes"));
return false;
}
// Remove connection
bool bSourceRemoved = SourceNode->RemoveOutputNode(TargetNode);
bool bTargetRemoved = TargetNode->RemoveInputNode(SourceNode);
if (bSourceRemoved && bTargetRemoved)
{
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Disconnected nodes: %s -> %s"),
*SourceNode->GetNodeTitle(), *TargetNode->GetNodeTitle());
return true;
}
else
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Disconnecting nodes failed: %s -> %s"),
*SourceNode->GetNodeTitle(), *TargetNode->GetNodeTitle());
return false;
}
}
TArray<UFLESHGraphNode*> UFLESHGraph::GetAllNodes() const
{
return Nodes;
}
UFLESHGraphNode* UFLESHGraph::GetRootNode() const
{
return RootNode;
}
void UFLESHGraph::SetRootNode(UFLESHGraphNode* InRootNode)
{
// Check if node is in graph
if (InRootNode && Nodes.Contains(InRootNode))
{
RootNode = InRootNode;
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Set new root node: %s"), *RootNode->GetNodeTitle());
}
else if (!InRootNode)
{
RootNode = nullptr;
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Clear root node"));
}
else
{
UE_LOG(LogFLESHGraph, Warning, TEXT("FLESH: Trying to set node not in graph as root node"));
}
}
void UFLESHGraph::ClearGraph()
{
// Clear node list
Nodes.Empty();
// Clear root node
RootNode = nullptr;
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Cleared graph"));
}
bool UFLESHGraph::SaveGraph()
{
// TODO: implement graph saving feature
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Graph saving feature not implemented"));
return false;
}
bool UFLESHGraph::LoadGraph()
{
// TODO: implement graph loading feature
UE_LOG(LogFLESHGraph, Log, TEXT("FLESH: Graph loading feature not implemented"));
return false;
}