1void VisualScriptEditorPanel::RunGraphSimulation()
3 SYSTEM_LOG <<
"[VisualScriptEditorPanel] RunGraphSimulation() called for graph '"
4 << m_template.Name <<
"'\n";
7 m_simulationTraces.clear();
8 m_executionTokenStack.clear();
10 m_simulationTraces.push_back(
"[SIMULATION] Graph execution simulation started");
11 m_simulationTraces.push_back(
"[SIMULATION] Graph: " + m_template.Name);
12 m_simulationTraces.push_back(
"[SIMULATION] Total nodes: " + std::to_string(m_template.Nodes.size()));
13 m_simulationTraces.push_back(
"[SIMULATION] Total connections: " + std::to_string(m_template.ExecConnections.size()));
14 m_simulationTraces.push_back(
"[SIMULATION] Blackboard entries: " + std::to_string(m_template.Blackboard.size()));
16 m_simulationTraces.push_back(
"");
17 m_simulationTraces.push_back(
"=== EXECUTION TRACE ===");
21 for (
size_t i = 0;
i < m_template.Blackboard.size(); ++
i)
23 blackboard[m_template.Blackboard[
i].Key] = m_template.Blackboard[
i].Default;
28 m_template.EntryPointID : m_template.RootNodeID;
32 m_simulationTraces.push_back(
"[ERROR] No entry point or root node found!");
33 SYSTEM_LOG <<
"[VisualScriptEditorPanel] Simulation FAILED: No entry point\n";
34 m_simulationDone =
true;
38 m_simulationTraces.push_back(
"[START] Entry point: Node #" + std::to_string(
entryPointID));
41 m_executionTokenStack.push_back(ExecutionToken(
entryPointID, 0));
50 ExecutionToken
currentToken = m_executionTokenStack.back();
51 m_executionTokenStack.pop_back();
57 const TaskNodeDefinition*
nodePtr =
nullptr;
58 for (
size_t i = 0;
i < m_template.Nodes.size(); ++
i)
69 m_simulationTraces.push_back(
"[ERROR] Node #" + std::to_string(
currentNodeID) +
" not found in template!");
77 m_simulationTraces.push_back(
"[CYCLE] WARNING: Cycle detected at Node #" + std::to_string(
currentNodeID));
89 m_simulationTraces.push_back(
nodeEntry.str());
96 case TaskNodeType::EntryPoint:
98 m_simulationTraces.push_back(
" ├─ [EVAL] EntryPoint - start of graph");
99 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
103 nextNodeIDs.push_back(m_template.ExecConnections[
i].TargetNodeID);
107 m_simulationTraces.push_back(
" └─ [RESULT] EntryPoint completed");
111 case TaskNodeType::GetBBValue:
113 m_simulationTraces.push_back(
" ├─ [EVAL] GetBBValue node");
114 m_simulationTraces.push_back(
" │ Key: '" +
nodePtr->BBKey +
"'");
118 m_simulationTraces.push_back(
" │ Value: " +
it->second.AsString());
122 m_simulationTraces.push_back(
" │ Value: [NOT FOUND]");
124 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
128 nextNodeIDs.push_back(m_template.ExecConnections[
i].TargetNodeID);
132 m_simulationTraces.push_back(
" └─ [RESULT] Read value from blackboard");
136 case TaskNodeType::SetBBValue:
138 m_simulationTraces.push_back(
" ├─ [EVAL] SetBBValue node");
139 m_simulationTraces.push_back(
" │ Key: '" +
nodePtr->BBKey +
"'");
140 m_simulationTraces.push_back(
" │ Setting value in blackboard (simulated)");
141 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
145 nextNodeIDs.push_back(m_template.ExecConnections[
i].TargetNodeID);
149 m_simulationTraces.push_back(
" └─ [RESULT] Value written to blackboard");
153 case TaskNodeType::MathOp:
155 m_simulationTraces.push_back(
" ├─ [EVAL] MathOp node");
156 m_simulationTraces.push_back(
" │ Operator: '" +
nodePtr->MathOperator +
"'");
158 if (
nodePtr->mathOpRef.leftOperand.mode == MathOpOperand::Mode::Variable)
159 leftOp <<
"Variable: " <<
nodePtr->mathOpRef.leftOperand.variableName;
160 else if (
nodePtr->mathOpRef.leftOperand.mode == MathOpOperand::Mode::Const)
161 leftOp <<
"Const: " <<
nodePtr->mathOpRef.leftOperand.constValue;
164 if (
nodePtr->mathOpRef.rightOperand.mode == MathOpOperand::Mode::Variable)
165 rightOp <<
"Variable: " <<
nodePtr->mathOpRef.rightOperand.variableName;
166 else if (
nodePtr->mathOpRef.rightOperand.mode == MathOpOperand::Mode::Const)
167 rightOp <<
"Const: " <<
nodePtr->mathOpRef.rightOperand.constValue;
170 m_simulationTraces.push_back(
" │ Left: " +
leftOp.str());
171 m_simulationTraces.push_back(
" │ Right: " +
rightOp.str());
172 m_simulationTraces.push_back(
" │ Result: [computed]");
173 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
177 nextNodeIDs.push_back(m_template.ExecConnections[
i].TargetNodeID);
181 m_simulationTraces.push_back(
" └─ [RESULT] Math operation executed");
185 case TaskNodeType::Branch:
187 m_simulationTraces.push_back(
" ├─ [EVAL] Branch node");
188 m_simulationTraces.push_back(
" │ Evaluating condition...");
189 bool conditionResult =
true;
190 m_simulationTraces.push_back(
" │ Condition result: " + std::string(conditionResult ?
"TRUE" :
"FALSE"));
191 const std::string
targetPin = conditionResult ?
"Out" :
"OutElse";
192 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
194 const ExecPinConnection&
conn = m_template.ExecConnections[
i];
202 m_simulationTraces.push_back(
" └─ [RESULT] Branch taken: " +
targetPin);
206 case TaskNodeType::Switch:
208 m_simulationTraces.push_back(
" ├─ [EVAL] Switch node");
209 m_simulationTraces.push_back(
" │ Variable: '" +
nodePtr->switchVariable +
"'");
210 m_simulationTraces.push_back(
" │ Cases: " + std::to_string(
nodePtr->switchCases.size()));
211 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
215 nextNodeIDs.push_back(m_template.ExecConnections[
i].TargetNodeID);
216 m_simulationTraces.push_back(
" │ Case selected: (first available)");
220 m_simulationTraces.push_back(
" └─ [RESULT] Switch case executed");
224 case TaskNodeType::Delay:
226 m_simulationTraces.push_back(
" ├─ [EVAL] Delay node");
227 m_simulationTraces.push_back(
" │ Duration: " + std::to_string(
nodePtr->DelaySeconds) +
" seconds");
228 m_simulationTraces.push_back(
" │ (Delay simulated)");
229 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
233 nextNodeIDs.push_back(m_template.ExecConnections[
i].TargetNodeID);
237 m_simulationTraces.push_back(
" └─ [RESULT] Delay completed");
241 case TaskNodeType::AtomicTask:
243 m_simulationTraces.push_back(
" ├─ [EVAL] AtomicTask node");
244 m_simulationTraces.push_back(
" │ Task type: '" +
nodePtr->AtomicTaskID +
"'");
245 m_simulationTraces.push_back(
" │ (Task execution simulated)");
246 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
248 const ExecPinConnection&
conn = m_template.ExecConnections[
i];
255 m_simulationTraces.push_back(
" └─ [RESULT] Task completed");
259 case TaskNodeType::VSSequence:
261 m_simulationTraces.push_back(
" ├─ [EVAL] Sequence node");
265 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
273 m_simulationTraces.push_back(
" │ Output pins: " + std::to_string(
sequenceOutputs.size()));
274 m_simulationTraces.push_back(
" │ Queueing " + std::to_string(
sequenceOutputs.size()) +
" branches:");
280 const TaskNodeDefinition*
outNodePtr =
nullptr;
281 for (
size_t i = 0;
i < m_template.Nodes.size(); ++
i)
283 if (m_template.Nodes[
i].NodeID ==
outConn.TargetNodeID)
294 m_simulationTraces.push_back(
outTrace.str());
297 m_executionTokenStack.push_back(ExecutionToken(
outConn.TargetNodeID, depth + 1));
300 m_simulationTraces.push_back(
" └─ [RESULT] Queued " + std::to_string(
sequenceOutputs.size()) +
" branch tokens");
304 case TaskNodeType::While:
306 m_simulationTraces.push_back(
" ├─ [EVAL] While loop node");
307 m_simulationTraces.push_back(
" │ Evaluating condition...");
308 m_simulationTraces.push_back(
" │ Condition result: TRUE (Loop continues)");
309 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
311 const ExecPinConnection&
conn = m_template.ExecConnections[
i];
318 m_simulationTraces.push_back(
" └─ [RESULT] Loop iteration");
324 m_simulationTraces.push_back(
" ├─ [EVAL] Node type: " + std::to_string(
static_cast<int>(
nodePtr->Type)));
325 for (
size_t i = 0;
i < m_template.ExecConnections.size(); ++
i)
329 nextNodeIDs.push_back(m_template.ExecConnections[
i].TargetNodeID);
333 m_simulationTraces.push_back(
" └─ [RESULT] Node processed");
343 m_simulationTraces.push_back(
"[EXIT] -> Next: Node #" + std::to_string(
nextNodeIDs[
ni]));
345 m_executionTokenStack.push_back(ExecutionToken(
nextNodeIDs[
ni], depth));
350 m_simulationTraces.push_back(
"[EXIT] -> Branch ends (no next node)");
353 m_simulationTraces.push_back(
"");
358 m_simulationTraces.push_back(
"=== EXECUTION SUMMARY ===");
361 m_simulationTraces.push_back(
"[WARNING] Maximum steps reached (" + std::to_string(
maxSteps) +
") - possible infinite loop");
363 else if (m_executionTokenStack.empty())
365 m_simulationTraces.push_back(
"[SUCCESS] All execution branches completed");
367 m_simulationTraces.push_back(
"Total steps executed: " + std::to_string(
stepCount));
368 m_simulationTraces.push_back(
"Blackboard entries: " + std::to_string(
blackboard.size()));
369 m_simulationTraces.push_back(
"Remaining tokens in stack: " + std::to_string(m_executionTokenStack.size()));
371 m_simulationDone =
true;
373 SYSTEM_LOG <<
"[VisualScriptEditorPanel] Simulation completed: " <<
stepCount <<
" steps\n";
376 m_verificationLogs.push_back(
"");
377 m_verificationLogs.push_back(
"--- SIMULATION EXECUTION TRACE (Token-based) ---");
378 m_verificationLogs.insert(m_verificationLogs.end(),
379 m_simulationTraces.begin(),
380 m_simulationTraces.end());
ComponentTypeID GetComponentTypeID_Static()
constexpr int32_t NODE_INDEX_NONE
Sentinel value for "no node" in node index / ID fields.