// Copyright Epic Games, Inc. All Rights Reserved. #pragma once #include "CoreMinimal.h" #include "SlateFwd.h" #include "TraceServices/Model/TimingProfiler.h" #include "Widgets/DeclarativeSyntaxSupport.h" #include "Widgets/SCompoundWidget.h" #include "Widgets/SWidget.h" #include "Widgets/Views/SHeaderRow.h" #include "Widgets/Views/STableRow.h" #include "Widgets/Views/STableViewBase.h" #include "Widgets/Views/STreeView.h" // Insights #include "Insights/ViewModels/TimerGroupingAndSorting.h" #include "Insights/ViewModels/TimerNode.h" //////////////////////////////////////////////////////////////////////////////////////////////////// class FMenuBuilder; class FUICommandList; namespace Insights { class FTable; class FTableColumn; class ITableCellValueSorter; class SAggregatorStatus; } // namespace Insights //////////////////////////////////////////////////////////////////////////////////////////////////// /** * A custom widget used to display the timers in a tree view (ex. Callers and Callees). */ class STimerTreeView: public SCompoundWidget { public: /** Default constructor. */ STimerTreeView(); /** Virtual destructor. */ virtual ~STimerTreeView(); SLATE_BEGIN_ARGS(STimerTreeView) {} SLATE_END_ARGS() /** * Construct this widget * @param InArgs - The declaration data for this widget */ void Construct(const FArguments& InArgs, const FText& InViewName); void Reset(); void SetTree(const Trace::FTimingProfilerButterflyNode& Root); virtual FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) override; private: void InitCommandList(); FTimerNodePtr CreateTimerNodeRec(const Trace::FTimingProfilerButterflyNode& Node); void ExpandNodesRec(FTimerNodePtr NodePtr, int32 Depth); //////////////////////////////////////////////////////////////////////////////////////////////////// // Tree View - Context Menu TSharedPtr TreeView_GetMenuContent(); void TreeView_BuildSortByMenu(FMenuBuilder& MenuBuilder); void TreeView_BuildViewColumnMenu(FMenuBuilder& MenuBuilder); bool ContextMenu_CopySelectedToClipboard_CanExecute() const; void ContextMenu_CopySelectedToClipboard_Execute(); //////////////////////////////////////////////////////////////////////////////////////////////////// // Tree View - Columns' Header void InitializeAndShowHeaderColumns(); FText GetColumnHeaderText(const FName ColumnId) const; TSharedRef TreeViewHeaderRow_GenerateColumnMenu(const Insights::FTableColumn& Column); //////////////////////////////////////////////////////////////////////////////////////////////////// // Tree View - Misc void TreeView_Refresh(); /** * Called by STreeView to retrieves the children for the specified parent item. * @param InParent - The parent node to retrieve the children from. * @param OutChildren - List of children for the parent node. */ void TreeView_OnGetChildren(FTimerNodePtr InParent, TArray& OutChildren); /** Called by STreeView when selection has changed. */ void TreeView_OnSelectionChanged(FTimerNodePtr SelectedItem, ESelectInfo::Type SelectInfo); /** Called by STreeView when a tree item is double clicked. */ void TreeView_OnMouseButtonDoubleClick(FTimerNodePtr TreeNode); //////////////////////////////////////////////////////////////////////////////////////////////////// // Tree View - Table Row /** Called by STreeView to generate a table row for the specified item. */ TSharedRef TreeView_OnGenerateRow(FTimerNodePtr TreeNode, const TSharedRef& OwnerTable); bool TableRow_ShouldBeEnabled(FTimerNodePtr NodePtr) const; void TableRow_SetHoveredCell(TSharedPtr TablePtr, TSharedPtr ColumnPtr, FTimerNodePtr NodePtr); EHorizontalAlignment TableRow_GetColumnOutlineHAlignment(const FName ColumnId) const; FText TableRow_GetHighlightText() const; FName TableRow_GetHighlightedNodeName() const; //////////////////////////////////////////////////////////////////////////////////////////////////// // Sorting static const FName GetDefaultColumnBeingSorted(); static const EColumnSortMode::Type GetDefaultColumnSortMode(); void CreateSortings(); void UpdateCurrentSortingByColumn(); void SortTreeNodes(); void SortTreeNodesRec(FTimerNode& Node, const Insights::ITableCellValueSorter& Sorter); EColumnSortMode::Type GetSortModeForColumn(const FName ColumnId) const; void SetSortModeForColumn(const FName& ColumnId, EColumnSortMode::Type SortMode); void OnSortModeChanged(const EColumnSortPriority::Type SortPriority, const FName& ColumnId, const EColumnSortMode::Type SortMode); //////////////////////////////////////////////////////////////////////////////////////////////////// // Sorting actions // SortMode (HeaderMenu) bool HeaderMenu_SortMode_IsChecked(const FName ColumnId, const EColumnSortMode::Type InSortMode); bool HeaderMenu_SortMode_CanExecute(const FName ColumnId, const EColumnSortMode::Type InSortMode) const; void HeaderMenu_SortMode_Execute(const FName ColumnId, const EColumnSortMode::Type InSortMode); // SortMode (ContextMenu) bool ContextMenu_SortMode_IsChecked(const EColumnSortMode::Type InSortMode); bool ContextMenu_SortMode_CanExecute(const EColumnSortMode::Type InSortMode) const; void ContextMenu_SortMode_Execute(const EColumnSortMode::Type InSortMode); // SortByColumn (ContextMenu) bool ContextMenu_SortByColumn_IsChecked(const FName ColumnId); bool ContextMenu_SortByColumn_CanExecute(const FName ColumnId) const; void ContextMenu_SortByColumn_Execute(const FName ColumnId); //////////////////////////////////////////////////////////////////////////////////////////////////// // Column visibility actions // ShowColumn bool CanShowColumn(const FName ColumnId) const; void ShowColumn(const FName ColumnId); // HideColumn bool CanHideColumn(const FName ColumnId) const; void HideColumn(const FName ColumnId); // ToggleColumnVisibility bool IsColumnVisible(const FName ColumnId); bool CanToggleColumnVisibility(const FName ColumnId) const; void ToggleColumnVisibility(const FName ColumnId); // ShowAllColumns (ContextMenu) bool ContextMenu_ShowAllColumns_CanExecute() const; void ContextMenu_ShowAllColumns_Execute(); // ResetColumns (ContextMenu) bool ContextMenu_ResetColumns_CanExecute() const; void ContextMenu_ResetColumns_Execute(); //////////////////////////////////////////////////////////////////////////////////////////////////// private: /** Table view model. */ TSharedPtr Table; /** The view name (ex.: "Callers" or "Callees"). */ FText ViewName; TSharedPtr CommandList; ////////////////////////////////////////////////// // Tree View, Columns /** The tree widget which holds the list of groups and timers corresponding with each group. */ TSharedPtr> TreeView; /** Holds the tree view header row widget which display all columns in the tree view. */ TSharedPtr TreeViewHeaderRow; /** External scrollbar used to synchronize tree view position. */ TSharedPtr ExternalScrollbar; ////////////////////////////////////////////////// // Hovered Column, Hovered Timer Node /** Name of the column currently being hovered by the mouse. */ FName HoveredColumnId; /** A shared pointer to the timer node currently being hovered by the mouse. */ FTimerNodePtr HoveredNodePtr; /** Name of the timer that should be drawn as highlighted. */ FName HighlightedNodeName; ////////////////////////////////////////////////// // Timer Nodes /** The root node(s) of the tree. */ TArray TreeNodes; ////////////////////////////////////////////////// // Sorting /** All available sorters. */ TArray> AvailableSorters; /** Current sorter. It is nullptr if sorting is disabled. */ TSharedPtr CurrentSorter; /** Name of the column currently being sorted. Can be NAME_None if sorting is disabled (CurrentSorting == nullptr) or if a complex sorting is used (CurrentSorting != nullptr). */ FName ColumnBeingSorted; /** How we sort the nodes? Ascending or Descending. */ EColumnSortMode::Type ColumnSortMode; ////////////////////////////////////////////////// double StatsStartTime; double StatsEndTime; uint32 StatsTimerId; TSharedPtr AggregatorStatus; }; ////////////////////////////////////////////////////////////////////////////////////////////////////