3
0

LoggingWindowTreeItems.cpp 30 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959
  1. /*
  2. * Copyright (c) Contributors to the Open 3D Engine Project.
  3. * For complete copyright and license terms please see the LICENSE at the root of this distribution.
  4. *
  5. * SPDX-License-Identifier: Apache-2.0 OR MIT
  6. *
  7. */
  8. #include <AzFramework/StringFunc/StringFunc.h>
  9. #include <AzToolsFramework/API/EditorAssetSystemAPI.h>
  10. #include <GraphCanvas/Components/Nodes/NodeTitleBus.h>
  11. #include <GraphCanvas/Components/Slots/SlotBus.h>
  12. #include <GraphCanvas/Components/StyleBus.h>
  13. #include <GraphCanvas/Utils/GraphUtils.h>
  14. #include <Editor/View/Widgets/LoggingPanel/LoggingWindowTreeItems.h>
  15. #include <Editor/GraphCanvas/GraphCanvasEditorNotificationBusId.h>
  16. #include <Editor/Include/ScriptCanvas/GraphCanvas/NodeDescriptorBus.h>
  17. #include <Editor/View/Widgets/LoggingPanel/LoggingDataAggregator.h>
  18. #include <Editor/View/Widgets/AssetGraphSceneDataBus.h>
  19. #include <Editor/View/Widgets/NodePalette/NodePaletteModel.h>
  20. #include <ScriptCanvas/Bus/RequestBus.h>
  21. #include <ScriptCanvas/Core/ExecutionNotificationsBus.h>
  22. #include <ScriptCanvas/Execution/ExecutionState.h>
  23. #include <ScriptCanvas/Execution/ExecutionStateDeclarations.h>
  24. #include <ScriptCanvas/Execution/RuntimeComponent.h>
  25. #include <ScriptCanvas/GraphCanvas/MappingBus.h>
  26. #include <Editor/GraphCanvas/GraphCanvasEditorNotificationBusId.h>
  27. namespace ScriptCanvasEditor
  28. {
  29. /////////////////////
  30. // DebugLogTreeItem
  31. /////////////////////
  32. bool DebugLogTreeItem::MatchesFilter(const DebugLogFilter& treeFilter)
  33. {
  34. DebugLogTreeItem* parent = static_cast<DebugLogTreeItem*>(GetParent());
  35. while (parent)
  36. {
  37. // We don't want to match against the root, since it always matches.
  38. // So only check things that have a valid parent.
  39. DebugLogTreeItem* nextParent = static_cast<DebugLogTreeItem*>(parent->GetParent());
  40. if (nextParent != nullptr && parent->OnMatchesFilter(treeFilter))
  41. {
  42. return true;
  43. }
  44. parent = static_cast<DebugLogTreeItem*>(parent->GetParent());
  45. }
  46. DebugLogTreeItem* currentItem = this;
  47. AZStd::unordered_set< DebugLogTreeItem* > children;
  48. while (currentItem)
  49. {
  50. if (currentItem->OnMatchesFilter(treeFilter))
  51. {
  52. return true;
  53. }
  54. for (int i = 0; i < currentItem->GetChildCount(); ++i)
  55. {
  56. children.insert(static_cast<DebugLogTreeItem*>(currentItem->FindChildByRow(i)));
  57. }
  58. if (!children.empty())
  59. {
  60. currentItem = (*children.begin());
  61. children.erase(children.begin());
  62. }
  63. else
  64. {
  65. currentItem = nullptr;
  66. }
  67. }
  68. return false;
  69. }
  70. const ScriptCanvas::Endpoint& DebugLogTreeItem::GetIncitingEndpoint() const
  71. {
  72. return m_incitingEndpoint;
  73. }
  74. bool DebugLogTreeItem::IsTriggeredBy(const ScriptCanvas::Endpoint& endpoint) const
  75. {
  76. return m_incitingEndpoint == endpoint;
  77. }
  78. Qt::ItemFlags DebugLogTreeItem::Flags([[maybe_unused]] const QModelIndex& index) const
  79. {
  80. return Qt::ItemFlag::ItemIsEnabled | Qt::ItemFlag::ItemIsSelectable;
  81. }
  82. int DebugLogTreeItem::GetColumnCount() const
  83. {
  84. return Column::Count;
  85. }
  86. void DebugLogTreeItem::SetIncitingEndpoint(const ScriptCanvas::Endpoint& endpoint)
  87. {
  88. m_incitingEndpoint = endpoint;
  89. }
  90. /////////////////////
  91. // DebugLogRootItem
  92. /////////////////////
  93. DebugLogRootItem::DebugLogRootItem()
  94. : m_updatePolicy(UpdatePolicy::Batched)
  95. {
  96. m_additionTimer.setSingleShot(true);
  97. m_additionTimer.setInterval(1000);
  98. QObject::connect(&m_additionTimer, &QTimer::timeout, [this]() { this->RedoLayout(); });
  99. }
  100. DebugLogRootItem::~DebugLogRootItem()
  101. {
  102. }
  103. ExecutionLogTreeItem* DebugLogRootItem::CreateExecutionItem(
  104. const LoggingDataId& loggingDataId,
  105. const ScriptCanvas::NodeTypeIdentifier& nodeType,
  106. const ScriptCanvas::GraphInfo& graphInfo,
  107. const ScriptCanvas::NamedNodeId& nodeId)
  108. {
  109. ExecutionLogTreeItem* treeItem = nullptr;
  110. if (m_updatePolicy == UpdatePolicy::Batched)
  111. {
  112. if (!m_additionTimer.isActive())
  113. {
  114. m_additionTimer.start();
  115. }
  116. }
  117. if (m_updatePolicy == UpdatePolicy::SingleTime)
  118. {
  119. treeItem = CreateChildNodeWithoutAddSignal<ExecutionLogTreeItem>(loggingDataId, nodeType, graphInfo, nodeId);
  120. }
  121. else
  122. {
  123. treeItem = CreateChildNode<ExecutionLogTreeItem>(loggingDataId, nodeType, graphInfo, nodeId);
  124. }
  125. return treeItem;
  126. }
  127. QVariant DebugLogRootItem::Data([[maybe_unused]] const QModelIndex& index, [[maybe_unused]] int role) const
  128. {
  129. return QVariant();
  130. }
  131. void DebugLogRootItem::ResetData()
  132. {
  133. SignalLayoutAboutToBeChanged();
  134. ClearChildren();
  135. SignalLayoutChanged();
  136. }
  137. void DebugLogRootItem::SetUpdatePolicy(UpdatePolicy updatePolicy)
  138. {
  139. if (m_updatePolicy != updatePolicy)
  140. {
  141. m_updatePolicy = updatePolicy;
  142. m_additionTimer.stop();
  143. }
  144. }
  145. DebugLogRootItem::UpdatePolicy DebugLogRootItem::GetUpdatePolicy() const
  146. {
  147. return m_updatePolicy;
  148. }
  149. void DebugLogRootItem::RedoLayout()
  150. {
  151. m_additionTimer.stop();
  152. SignalLayoutAboutToBeChanged();
  153. SignalLayoutChanged();
  154. }
  155. /////////////////////////
  156. // ExecutionLogTreeItem
  157. /////////////////////////
  158. ExecutionLogTreeItem::ExecutionLogTreeItem
  159. ( const LoggingDataId& loggingDataId
  160. , const ScriptCanvas::NodeTypeIdentifier& nodeType
  161. , const ScriptCanvas::GraphInfo& graphInfo
  162. , const ScriptCanvas::NamedNodeId& nodeId)
  163. : m_loggingDataId(loggingDataId)
  164. , m_nodeType(nodeType)
  165. , m_graphInfo(graphInfo)
  166. , m_scriptCanvasAssetNodeId(nodeId)
  167. , m_iconPixmap(nullptr)
  168. {
  169. m_paletteConfiguration.m_iconPalette = "NodePaletteTypeIcon";
  170. m_paletteConfiguration.SetColorPalette("MethodNodeTitlePalette");
  171. AZ::NamedEntityId entityName;
  172. LoggingDataRequestBus::EventResult(entityName, m_loggingDataId, &LoggingDataRequests::FindNamedEntityId, m_graphInfo.m_runtimeEntity);
  173. m_sourceEntityName = entityName.ToString().c_str();
  174. m_displayName = nodeId.m_name.c_str();
  175. ScrapeBehaviorContextData();
  176. ScrapeGraphCanvasData();
  177. m_inputName = "---";
  178. m_outputName = "---";
  179. // GeneralAssetNotificationBus::Handler::BusConnect(GetAssetId());
  180. }
  181. QVariant ExecutionLogTreeItem::Data(const QModelIndex& index, int role) const
  182. {
  183. switch (index.column())
  184. {
  185. case Column::NodeName:
  186. {
  187. if (role == Qt::DisplayRole
  188. || role == Qt::ToolTipRole)
  189. {
  190. return m_displayName;
  191. }
  192. else if (role == Qt::DecorationRole)
  193. {
  194. if (m_iconPixmap != nullptr)
  195. {
  196. return (*m_iconPixmap);
  197. }
  198. }
  199. }
  200. break;
  201. case Column::Input:
  202. {
  203. if (role == Qt::DisplayRole
  204. || role == Qt::ToolTipRole)
  205. {
  206. return m_inputName;
  207. }
  208. }
  209. break;
  210. case Column::Output:
  211. {
  212. if (role == Qt::DisplayRole
  213. || role == Qt::ToolTipRole)
  214. {
  215. return m_outputName;
  216. }
  217. }
  218. break;
  219. case Column::TimeStep:
  220. {
  221. if (role == Qt::DisplayRole
  222. || role == Qt::ToolTipRole)
  223. {
  224. return m_timeString;
  225. }
  226. }
  227. break;
  228. case Column::ScriptName:
  229. {
  230. if (role == Qt::DisplayRole)
  231. {
  232. return m_graphName;
  233. }
  234. else if (role == Qt::ToolTipRole)
  235. {
  236. return m_relativeGraphPath;
  237. }
  238. else if (role == Qt::ForegroundRole)
  239. {
  240. return QColor(42,132,252);
  241. }
  242. else if (role == Qt::FontRole)
  243. {
  244. QFont font;
  245. font.setUnderline(true);
  246. return font;
  247. }
  248. }
  249. break;
  250. case Column::SourceEntity:
  251. {
  252. if (role == Qt::DisplayRole
  253. || role == Qt::ToolTipRole)
  254. {
  255. return m_sourceEntityName;
  256. }
  257. }
  258. break;
  259. default:
  260. break;
  261. }
  262. return QVariant();
  263. }
  264. AZ::EntityId ExecutionLogTreeItem::GetNodeId() const
  265. {
  266. return m_scriptCanvasAssetNodeId;
  267. }
  268. void ExecutionLogTreeItem::RegisterAnnotation(const ScriptCanvas::AnnotateNodeSignal& annotationSignal, bool allowAddSignal)
  269. {
  270. // The QTreeView does have a setFirstColumnSpanned, but it doesn't seem dynamic, nor model driven.
  271. // So I don't want to use it.
  272. if (allowAddSignal)
  273. {
  274. CreateChildNode<NodeAnnotationTreeItem>(annotationSignal.m_annotationLevel, annotationSignal.m_annotation);
  275. }
  276. else
  277. {
  278. CreateChildNodeWithoutAddSignal<NodeAnnotationTreeItem>(annotationSignal.m_annotationLevel, annotationSignal.m_annotation);
  279. }
  280. }
  281. void ExecutionLogTreeItem::RegisterDataInput(const ScriptCanvas::Endpoint& incitingEndpoint, const ScriptCanvas::SlotId& slotId, AZStd::string_view slotName, AZStd::string_view dataString, bool allowAddSignal)
  282. {
  283. if (!HasExecutionInput() && !HasExecutionOutput())
  284. {
  285. ResolveWrapperNode();
  286. }
  287. DataLogTreeItem* dataTreeItem = nullptr;
  288. for (int i = 0; i < GetChildCount(); ++i)
  289. {
  290. DataLogTreeItem* testLogItem = azrtti_cast<DataLogTreeItem*>(FindChildByRow(i));
  291. if (testLogItem && !testLogItem->HasInput())
  292. {
  293. dataTreeItem = testLogItem;
  294. break;
  295. }
  296. }
  297. if (dataTreeItem == nullptr)
  298. {
  299. if (allowAddSignal)
  300. {
  301. dataTreeItem = CreateChildNode<DataLogTreeItem>(GetGraphIdentifier());
  302. }
  303. else
  304. {
  305. dataTreeItem = CreateChildNodeWithoutAddSignal<DataLogTreeItem>(GetGraphIdentifier());
  306. }
  307. }
  308. ScriptCanvas::Endpoint endpoint(m_scriptCanvasAssetNodeId, slotId);
  309. dataTreeItem->RegisterDataInput(incitingEndpoint, endpoint, slotName, dataString);
  310. }
  311. void ExecutionLogTreeItem::RegisterDataOutput(const ScriptCanvas::SlotId& slotId, AZStd::string_view slotName, AZStd::string_view dataString, bool allowAddSignal)
  312. {
  313. if (!HasExecutionInput() && !HasExecutionOutput())
  314. {
  315. ResolveWrapperNode();
  316. }
  317. DataLogTreeItem* dataTreeItem = nullptr;
  318. for (int i = 0; i < GetChildCount(); ++i)
  319. {
  320. DataLogTreeItem* testLogItem = azrtti_cast<DataLogTreeItem*>(FindChildByRow(i));
  321. if (testLogItem && !testLogItem->HasOutput())
  322. {
  323. dataTreeItem = testLogItem;
  324. break;
  325. }
  326. }
  327. if (dataTreeItem == nullptr)
  328. {
  329. if (allowAddSignal)
  330. {
  331. dataTreeItem = CreateChildNode<DataLogTreeItem>(GetGraphIdentifier());
  332. }
  333. else
  334. {
  335. dataTreeItem = CreateChildNodeWithoutAddSignal<DataLogTreeItem>(GetGraphIdentifier());
  336. }
  337. }
  338. ScriptCanvas::Endpoint endpoint(m_scriptCanvasAssetNodeId, slotId);
  339. dataTreeItem->RegisterDataOutput(endpoint, slotName, dataString);
  340. }
  341. void ExecutionLogTreeItem::RegisterExecutionInput(const ScriptCanvas::Endpoint& incitingEndpoint, const ScriptCanvas::SlotId& slotId, AZStd::string_view slotName, AZStd::chrono::milliseconds relativeExecution)
  342. {
  343. m_timeString = QTime::fromMSecsSinceStartOfDay(aznumeric_cast<int>(relativeExecution.count())).toString("mm:ss.zzz");
  344. m_inputSlot = slotId;
  345. m_inputName = slotName.data();
  346. SetIncitingEndpoint(incitingEndpoint);
  347. if (!HasExecutionOutput())
  348. {
  349. ResolveWrapperNode();
  350. }
  351. PopulateInputSlotData();
  352. SignalDataChanged();
  353. }
  354. bool ExecutionLogTreeItem::HasExecutionInput() const
  355. {
  356. return m_inputSlot.IsValid();
  357. }
  358. void ExecutionLogTreeItem::RegisterExecutionOutput(const ScriptCanvas::SlotId& slotId, AZStd::string_view slotName, AZStd::chrono::milliseconds relativeExecution)
  359. {
  360. if (!HasExecutionInput())
  361. {
  362. m_timeString = QTime::fromMSecsSinceStartOfDay(aznumeric_cast<int>(relativeExecution.count())).toString("mm:ss.zzz");
  363. }
  364. m_outputSlot = slotId;
  365. m_outputName = slotName.data();
  366. if (!HasExecutionInput())
  367. {
  368. ResolveWrapperNode();
  369. }
  370. PopulateOutputSlotData();
  371. SignalDataChanged();
  372. }
  373. bool ExecutionLogTreeItem::HasExecutionOutput() const
  374. {
  375. return m_outputSlot.IsValid();
  376. }
  377. void ExecutionLogTreeItem::OnStylesUnloaded()
  378. {
  379. m_iconPixmap = nullptr;
  380. }
  381. void ExecutionLogTreeItem::OnStylesLoaded()
  382. {
  383. GraphCanvas::StyleManagerRequestBus::EventResult(m_iconPixmap, ScriptCanvasEditor::AssetEditorId, &GraphCanvas::StyleManagerRequests::GetConfiguredPaletteIcon, m_paletteConfiguration);
  384. SignalDataChanged();
  385. }
  386. void ExecutionLogTreeItem::OnAssetVisualized()
  387. {
  388. ScrapeGraphCanvasData();
  389. for (int i = 0; i < GetChildCount(); ++i)
  390. {
  391. DataLogTreeItem* dataLogTreeItem = azrtti_cast<DataLogTreeItem*>(FindChildByRow(i));
  392. if (dataLogTreeItem)
  393. {
  394. dataLogTreeItem->ScrapeData();
  395. }
  396. }
  397. }
  398. void ExecutionLogTreeItem::OnAssetUnloaded()
  399. {
  400. EditorGraphNotificationBus::Handler::BusDisconnect();
  401. m_scriptCanvasNodeId.SetInvalid();
  402. m_graphCanvasGraphId.SetInvalid();
  403. m_graphCanvasNodeId.SetInvalid();
  404. for (int i = 0; i < GetChildCount(); ++i)
  405. {
  406. DataLogTreeItem* dataLogTreeItem = azrtti_cast<DataLogTreeItem*>(FindChildByRow(i));
  407. if (dataLogTreeItem)
  408. {
  409. dataLogTreeItem->InvalidateEditorIds();
  410. }
  411. }
  412. }
  413. void ExecutionLogTreeItem::OnGraphCanvasSceneDisplayed()
  414. {
  415. m_graphCanvasGraphId.SetInvalid();
  416. m_graphCanvasNodeId.SetInvalid();
  417. for (int i = 0; i < GetChildCount(); ++i)
  418. {
  419. DataLogTreeItem* dataLogTreeItem = azrtti_cast<DataLogTreeItem*>(FindChildByRow(i));
  420. if (dataLogTreeItem)
  421. {
  422. dataLogTreeItem->InvalidateGraphCanvasIds();
  423. }
  424. }
  425. ScrapeGraphCanvasData();
  426. }
  427. const ScriptCanvas::GraphIdentifier& ExecutionLogTreeItem::GetGraphIdentifier() const
  428. {
  429. return m_graphInfo.m_graphIdentifier;
  430. }
  431. AZ::Data::AssetId ExecutionLogTreeItem::GetAssetId() const
  432. {
  433. return m_graphInfo.m_graphIdentifier.m_assetId;
  434. }
  435. AZ::EntityId ExecutionLogTreeItem::GetScriptCanvasAssetNodeId() const
  436. {
  437. return m_scriptCanvasAssetNodeId;
  438. }
  439. GraphCanvas::NodeId ExecutionLogTreeItem::GetGraphCanvasNodeId() const
  440. {
  441. return m_graphCanvasNodeId;
  442. }
  443. bool ExecutionLogTreeItem::OnMatchesFilter(const DebugLogFilter& treeFilter)
  444. {
  445. bool matches = false;
  446. matches = matches || (m_displayName.lastIndexOf(treeFilter.m_filter) >= 0);
  447. matches = matches || (m_inputName.lastIndexOf(treeFilter.m_filter) >= 0);
  448. matches = matches || (m_outputName.lastIndexOf(treeFilter.m_filter) >= 0);
  449. matches = matches || (m_graphName.lastIndexOf(treeFilter.m_filter) >= 0);
  450. matches = matches || (m_sourceEntityName.lastIndexOf(treeFilter.m_filter) >= 0);
  451. matches = matches || (m_timeString.lastIndexOf(treeFilter.m_filter) >= 0);
  452. return matches;
  453. }
  454. void ExecutionLogTreeItem::ResolveWrapperNode(bool refreshData)
  455. {
  456. if (m_graphCanvasNodeId.IsValid())
  457. {
  458. if (GraphCanvas::GraphUtils::IsWrapperNode(m_graphCanvasNodeId))
  459. {
  460. AZ::EntityId originalNodeId = m_graphCanvasNodeId;
  461. ScriptCanvas::SlotId slotId;
  462. if (HasExecutionInput())
  463. {
  464. slotId = m_inputSlot;
  465. }
  466. if (HasExecutionOutput())
  467. {
  468. slotId = m_outputSlot;
  469. }
  470. GraphCanvas::Endpoint endpoint;
  471. EBusHandlerNodeDescriptorRequestBus::EventResult(endpoint, m_graphCanvasNodeId, &EBusHandlerNodeDescriptorRequests::MapSlotToGraphCanvasEndpoint, slotId);
  472. if (endpoint.IsValid())
  473. {
  474. m_graphCanvasNodeId = endpoint.GetNodeId();
  475. }
  476. if (originalNodeId != m_graphCanvasNodeId && refreshData)
  477. {
  478. ScrapeGraphCanvasData();
  479. }
  480. }
  481. }
  482. }
  483. void ExecutionLogTreeItem::ScrapeBehaviorContextData()
  484. {
  485. if (m_graphName.isEmpty())
  486. {
  487. AZ::Data::AssetInfo assetInfo;
  488. AZ::Data::AssetCatalogRequestBus::BroadcastResult(assetInfo, &AZ::Data::AssetCatalogRequests::GetAssetInfoById, GetAssetId());
  489. AZStd::string fileName;
  490. AzFramework::StringFunc::Path::GetFileName(assetInfo.m_relativePath.c_str(), fileName);
  491. m_relativeGraphPath = assetInfo.m_relativePath.c_str();
  492. m_graphName = fileName.c_str();
  493. if (m_graphName.isEmpty())
  494. {
  495. m_graphName = "Unknown Canvas";
  496. m_relativeGraphPath = GetAssetId().ToString<AZStd::string>().c_str();
  497. }
  498. }
  499. const NodePaletteModelInformation* modelInformation = nullptr;
  500. GeneralRequestBus::BroadcastResult(modelInformation, &GeneralRequests::FindNodePaletteModelInformation, m_nodeType);
  501. if (modelInformation)
  502. {
  503. const CategoryInformation* categoryInformation = nullptr;
  504. GeneralRequestBus::BroadcastResult(categoryInformation, &GeneralRequests::FindNodePaletteCategoryInformation, modelInformation->m_categoryPath);
  505. m_displayName = QString(modelInformation->m_displayName.c_str());
  506. if (categoryInformation && categoryInformation->m_paletteOverride.compare(GraphCanvas::NodePaletteTreeItem::DefaultNodeTitlePalette) != 0)
  507. {
  508. m_paletteConfiguration.SetColorPalette(categoryInformation->m_paletteOverride);
  509. }
  510. else if (!modelInformation->m_titlePaletteOverride.empty())
  511. {
  512. m_paletteConfiguration.SetColorPalette(modelInformation->m_titlePaletteOverride);
  513. }
  514. else
  515. {
  516. m_paletteConfiguration.SetColorPalette(GraphCanvas::NodePaletteTreeItem::DefaultNodeTitlePalette);
  517. }
  518. }
  519. OnStylesLoaded();
  520. SignalDataChanged();
  521. }
  522. void ExecutionLogTreeItem::ScrapeGraphCanvasData()
  523. {
  524. if (!m_graphCanvasGraphId.IsValid())
  525. {
  526. GeneralRequestBus::BroadcastResult(m_graphCanvasGraphId
  527. , &GeneralRequests::FindGraphCanvasGraphIdByAssetId, SourceHandle(nullptr, GetAssetId().m_guid));
  528. if (!EditorGraphNotificationBus::Handler::BusIsConnected())
  529. {
  530. ScriptCanvas::ScriptCanvasId scriptCanvasId;
  531. GeneralRequestBus::BroadcastResult(scriptCanvasId
  532. , &GeneralRequests::FindScriptCanvasIdByAssetId, SourceHandle(nullptr, GetAssetId().m_guid));
  533. EditorGraphNotificationBus::Handler::BusConnect(scriptCanvasId);
  534. }
  535. }
  536. if (m_graphCanvasGraphId.IsValid())
  537. {
  538. if (!m_graphCanvasNodeId.IsValid())
  539. {
  540. AssetGraphSceneBus::BroadcastResult(m_scriptCanvasNodeId
  541. , &AssetGraphScene::FindEditorNodeIdByAssetNodeId
  542. , SourceHandle(nullptr, GetAssetId().m_guid), m_scriptCanvasAssetNodeId);
  543. SceneMemberMappingRequestBus::EventResult(m_graphCanvasNodeId, m_scriptCanvasNodeId, &SceneMemberMappingRequests::GetGraphCanvasEntityId);
  544. }
  545. if (m_graphCanvasNodeId.IsValid())
  546. {
  547. const bool refreshDisplayData = false;
  548. ResolveWrapperNode(refreshDisplayData);
  549. AZStd::string displayName;
  550. GraphCanvas::NodeTitleRequestBus::EventResult(displayName, m_graphCanvasNodeId, &GraphCanvas::NodeTitleRequests::GetTitle);
  551. if (!displayName.empty())
  552. {
  553. m_displayName = displayName.c_str();
  554. }
  555. GraphCanvas::NodeTitleRequestBus::Event(m_graphCanvasNodeId, &GraphCanvas::NodeTitleRequests::ConfigureIconConfiguration, m_paletteConfiguration);
  556. OnStylesLoaded();
  557. PopulateInputSlotData();
  558. PopulateOutputSlotData();
  559. SignalDataChanged();
  560. }
  561. }
  562. }
  563. void ExecutionLogTreeItem::PopulateInputSlotData()
  564. {
  565. if (m_graphCanvasNodeId.IsValid() && HasExecutionInput())
  566. {
  567. GraphCanvas::SlotId slotId;
  568. SlotMappingRequestBus::EventResult(slotId, m_graphCanvasNodeId, &SlotMappingRequests::MapToGraphCanvasId, m_inputSlot);
  569. AZStd::string inputName;
  570. GraphCanvas::SlotRequestBus::EventResult(inputName, slotId, &GraphCanvas::SlotRequests::GetName);
  571. if (!inputName.empty())
  572. {
  573. m_inputName = inputName.c_str();
  574. }
  575. }
  576. }
  577. void ExecutionLogTreeItem::PopulateOutputSlotData()
  578. {
  579. if (m_graphCanvasNodeId.IsValid() && HasExecutionOutput())
  580. {
  581. GraphCanvas::SlotId slotId;
  582. SlotMappingRequestBus::EventResult(slotId, m_graphCanvasNodeId, &SlotMappingRequests::MapToGraphCanvasId, m_outputSlot);
  583. AZStd::string outputName;
  584. GraphCanvas::SlotRequestBus::EventResult(outputName, slotId, &GraphCanvas::SlotRequests::GetName);
  585. if (!outputName.empty())
  586. {
  587. m_outputName = outputName.c_str();
  588. }
  589. }
  590. }
  591. ////////////////////
  592. // DataLogTreeItem
  593. ////////////////////
  594. DataLogTreeItem::DataLogTreeItem(const ScriptCanvas::GraphIdentifier& graphIdentifier)
  595. : m_graphIdentifier(graphIdentifier)
  596. {
  597. m_inputName = "---";
  598. m_outputName = "---";
  599. ScrapeData();
  600. }
  601. QVariant DataLogTreeItem::Data(const QModelIndex& index, int role) const
  602. {
  603. switch (index.column())
  604. {
  605. case Column::Input:
  606. {
  607. if (role == Qt::DisplayRole
  608. || role == Qt::ToolTipRole)
  609. {
  610. if (m_inputData.isEmpty())
  611. {
  612. return m_inputName;
  613. }
  614. return QString("%1 - (%2)").arg(m_inputName, m_inputData);
  615. }
  616. }
  617. break;
  618. case Column::Output:
  619. {
  620. if (role == Qt::DisplayRole
  621. || role == Qt::ToolTipRole)
  622. {
  623. if (m_outputData.isEmpty())
  624. {
  625. return m_outputName;
  626. }
  627. return QString("%1 - (%2)").arg(m_outputName, m_outputData);
  628. }
  629. }
  630. break;
  631. default:
  632. break;
  633. }
  634. return QVariant();
  635. }
  636. void DataLogTreeItem::RegisterDataInput(const ScriptCanvas::Endpoint& incitingEndpoint, const ScriptCanvas::Endpoint& endpoint, AZStd::string_view slotName, AZStd::string_view dataString)
  637. {
  638. SetIncitingEndpoint(incitingEndpoint);
  639. m_assetInputEndpoint = endpoint;
  640. m_inputName = slotName.data();
  641. m_inputData = dataString.data();
  642. ScrapeInputName();
  643. }
  644. bool DataLogTreeItem::HasInput() const
  645. {
  646. return m_assetInputEndpoint.IsValid();
  647. }
  648. void DataLogTreeItem::RegisterDataOutput(const ScriptCanvas::Endpoint& endpoint, AZStd::string_view slotName, AZStd::string_view dataString)
  649. {
  650. m_assetOutputEndpoint = endpoint;
  651. m_outputName = slotName.data();
  652. m_outputData = dataString.data();
  653. ScrapeOutputName();
  654. }
  655. bool DataLogTreeItem::HasOutput() const
  656. {
  657. return m_assetOutputEndpoint.IsValid();
  658. }
  659. bool DataLogTreeItem::OnMatchesFilter(const DebugLogFilter& treeFilter)
  660. {
  661. bool matches = false;
  662. matches = matches || (m_inputName.lastIndexOf(treeFilter.m_filter) >= 0);
  663. matches = matches || (m_inputData.lastIndexOf(treeFilter.m_filter) >= 0);
  664. matches = matches || (m_outputName.lastIndexOf(treeFilter.m_filter) >= 0);
  665. matches = matches || (m_outputData.lastIndexOf(treeFilter.m_filter) >= 0);
  666. return matches;
  667. }
  668. AZ::Data::AssetId DataLogTreeItem::GetAssetId() const
  669. {
  670. return m_graphIdentifier.m_assetId;
  671. }
  672. void DataLogTreeItem::ScrapeData()
  673. {
  674. if (!m_graphCanvasGraphId.IsValid())
  675. {
  676. GeneralRequestBus::BroadcastResult(m_graphCanvasGraphId
  677. , &GeneralRequests::FindGraphCanvasGraphIdByAssetId, SourceHandle(nullptr, m_graphIdentifier.m_assetId.m_guid));
  678. }
  679. ScrapeInputName();
  680. ScrapeOutputName();
  681. }
  682. void DataLogTreeItem::InvalidateEditorIds()
  683. {
  684. InvalidateGraphCanvasIds();
  685. }
  686. void DataLogTreeItem::InvalidateGraphCanvasIds()
  687. {
  688. m_graphCanvasGraphId.SetInvalid();
  689. }
  690. void DataLogTreeItem::ScrapeInputName()
  691. {
  692. if (m_graphCanvasGraphId.IsValid() && m_assetInputEndpoint.IsValid())
  693. {
  694. AZ::EntityId scriptCanvasNodeId;
  695. AssetGraphSceneBus::BroadcastResult(scriptCanvasNodeId, &AssetGraphScene::FindEditorNodeIdByAssetNodeId, SourceHandle(nullptr, GetAssetId().m_guid), m_assetInputEndpoint.GetNodeId());
  696. GraphCanvas::NodeId graphCanvasNodeId;
  697. SceneMemberMappingRequestBus::EventResult(graphCanvasNodeId, scriptCanvasNodeId, &SceneMemberMappingRequests::GetGraphCanvasEntityId);
  698. GraphCanvas::SlotId slotId;
  699. SlotMappingRequestBus::EventResult(slotId, graphCanvasNodeId, &SlotMappingRequests::MapToGraphCanvasId, m_assetInputEndpoint.GetSlotId());
  700. AZStd::string name;
  701. GraphCanvas::SlotRequestBus::EventResult(name, slotId, &GraphCanvas::SlotRequests::GetName);
  702. if (!name.empty())
  703. {
  704. m_inputName = name.c_str();
  705. }
  706. }
  707. }
  708. void DataLogTreeItem::ScrapeOutputName()
  709. {
  710. if (m_graphCanvasGraphId.IsValid() && m_assetOutputEndpoint.IsValid())
  711. {
  712. AZ::EntityId scriptCanvasNodeId;
  713. AssetGraphSceneBus::BroadcastResult(scriptCanvasNodeId, &AssetGraphScene::FindEditorNodeIdByAssetNodeId
  714. , SourceHandle(nullptr, GetAssetId().m_guid), m_assetOutputEndpoint.GetNodeId());
  715. GraphCanvas::NodeId graphCanvasNodeId;
  716. SceneMemberMappingRequestBus::EventResult(graphCanvasNodeId, scriptCanvasNodeId, &SceneMemberMappingRequests::GetGraphCanvasEntityId);
  717. GraphCanvas::SlotId slotId;
  718. SlotMappingRequestBus::EventResult(slotId, graphCanvasNodeId, &SlotMappingRequests::MapToGraphCanvasId, m_assetOutputEndpoint.GetSlotId());
  719. AZStd::string name;
  720. GraphCanvas::SlotRequestBus::EventResult(name, slotId, &GraphCanvas::SlotRequests::GetName);
  721. if (!name.empty())
  722. {
  723. m_outputName = name.c_str();
  724. }
  725. }
  726. }
  727. bool DataLogTreeItem::LessThan(const GraphCanvas::GraphCanvasTreeItem* graphItem) const
  728. {
  729. return !azrtti_istypeof<const NodeAnnotationTreeItem*>(graphItem);
  730. }
  731. ///////////////////////////
  732. // NodeAnnotationTreeItem
  733. ///////////////////////////
  734. NodeAnnotationTreeItem::NodeAnnotationTreeItem()
  735. : m_annotationLevel(ScriptCanvas::AnnotateNodeSignal::AnnotationLevel::Info)
  736. {
  737. }
  738. NodeAnnotationTreeItem::NodeAnnotationTreeItem(ScriptCanvas::AnnotateNodeSignal::AnnotationLevel annotationLevel, const AZStd::string& annotation)
  739. : m_annotationLevel(annotationLevel)
  740. , m_annotation(annotation.c_str())
  741. {
  742. switch (m_annotationLevel)
  743. {
  744. case ScriptCanvas::AnnotateNodeSignal::AnnotationLevel::Info:
  745. m_annotationIcon = QIcon(":/ScriptCanvasEditorResources/Resources/message_icon.png");
  746. break;
  747. case ScriptCanvas::AnnotateNodeSignal::AnnotationLevel::Warning:
  748. m_annotationIcon = QIcon(":/ScriptCanvasEditorResources/Resources/warning_symbol.png");
  749. break;
  750. case ScriptCanvas::AnnotateNodeSignal::AnnotationLevel::Error:
  751. m_annotationIcon = QIcon(":/ScriptCanvasEditorResources/Resources/error_icon.png");
  752. break;
  753. default:
  754. break;
  755. }
  756. }
  757. QVariant NodeAnnotationTreeItem::Data(const QModelIndex& index, int role) const
  758. {
  759. // We are spanned, we we only have a single column
  760. if (index.column() == DebugLogTreeItem::Column::NodeName)
  761. {
  762. switch (role)
  763. {
  764. case Qt::DecorationRole:
  765. {
  766. return m_annotationIcon;
  767. }
  768. case Qt::DisplayRole:
  769. {
  770. return m_annotation;
  771. }
  772. case Qt::ToolTipRole:
  773. {
  774. return m_annotation;
  775. }
  776. default:
  777. break;
  778. }
  779. }
  780. return QVariant();
  781. }
  782. bool NodeAnnotationTreeItem::OnMatchesFilter(const DebugLogFilter& treeFilter)
  783. {
  784. bool matches = false;
  785. matches = matches || (m_annotation.lastIndexOf(treeFilter.m_filter) >= 0);
  786. return matches;
  787. }
  788. }