You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
o3de/Code/Tools/Standalone/Source/Driller/Replica/OverallReplicaDetailView.cpp

747 lines
28 KiB
C++

/*
* Copyright (c) Contributors to the Open 3D Engine Project.
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
*
* SPDX-License-Identifier: Apache-2.0 OR MIT
*
*/
#include <AzCore/Serialization/SerializeContext.h>
#include <AzToolsFramework/UI/UICore/QTreeViewStateSaver.hxx>
#include <AzToolsFramework/UI/UICore/QWidgetSavedState.h>
#include "OverallReplicaDetailView.hxx"
#include <Source/Driller/Replica/ui_overallreplicadetailview.h>
#include <Source/Driller/Replica/moc_OverallReplicaDetailView.cpp>
#include "ReplicaChunkUsageDataContainers.h"
#include "ReplicaDataAggregator.hxx"
#include "ReplicaDataEvents.h"
#include "ReplicaUsageDataContainers.h"
#include "Source/Driller/DrillerMainWindowMessages.h"
#include "Source/Driller/DrillerOperationTelemetryEvent.h"
#include "Source/Driller/Replica/ReplicaDataView.hxx"
#include "Source/Driller/Replica/ReplicaDisplayHelpers.h"
#include "Source/Driller/Workspaces/Workspace.h"
namespace Driller
{
////////////////////////
// TreeModelSavedState
////////////////////////
class TreeModelSavedState
: public AZ::UserSettings
{
public:
AZ_RTTI(TreeModelSavedState, "{36103E46-2503-4EEE-BA4B-2650E25A5B26}", AZ::UserSettings);
AZ_CLASS_ALLOCATOR(TreeModelSavedState, AZ::SystemAllocator, 0);
AZStd::vector<AZ::u8> m_treeColumnStorage;
static void Reflect(AZ::ReflectContext* context)
{
AZ::SerializeContext* serialize = azrtti_cast<AZ::SerializeContext*>(context);
if (serialize)
{
serialize->Class<TreeModelSavedState>()
->Field("m_treeColumnStorage", &TreeModelSavedState::m_treeColumnStorage)
->Version(1);
}
}
};
////////////////////////////////
// OverallReplicaTreeViewModel
////////////////////////////////
OverallReplicaTreeViewModel::OverallReplicaTreeViewModel(AbstractOverallReplicaDetailView* overallDetailView)
: BaseOverallTreeViewModel<AZ::u64>(overallDetailView)
{
}
int OverallReplicaTreeViewModel::columnCount(const QModelIndex& parentIndex) const
{
(void)parentIndex;
return CD_COUNT;
}
QVariant OverallReplicaTreeViewModel::data(const QModelIndex& index, int role) const
{
const bool relativeValue = true;
const bool absoluteValue = false;
const BaseDisplayHelper* baseDisplay = static_cast<const BaseDisplayHelper*>(index.internalPointer());
switch (index.column())
{
case CD_DISPLAY_NAME:
return displayNameData(baseDisplay, role);
case CD_REPLICA_ID:
{
if (role == Qt::DisplayRole || role == Qt::UserRole)
{
AZ::u64 replicaId = 0;
const BaseDisplayHelper* currentDisplay = baseDisplay;
while (currentDisplay != nullptr && !azrtti_istypeof<OverallReplicaDetailDisplayHelper>(currentDisplay))
{
currentDisplay = currentDisplay->GetParent();
}
if (currentDisplay)
{
const OverallReplicaDetailDisplayHelper* replicaDisplay = static_cast<const OverallReplicaDetailDisplayHelper*>(currentDisplay);
replicaId = replicaDisplay->GetReplicaId();
}
if (role == Qt::DisplayRole)
{
return FormattingHelper::ReplicaID(replicaId);
}
else
{
return QVariant(replicaId);
}
}
}
break;
case CD_TOTAL_SENT:
return totalSentData(baseDisplay, role);
case CD_AVG_SENT_FRAME:
return avgSentPerFrameData(baseDisplay, role);
case CD_AVG_SENT_SECOND:
return avgSentPerSecondData(baseDisplay, role);
case CD_PARENT_PERCENT_SENT:
return percentOfSentData(baseDisplay, role, relativeValue);
case CD_TOTAL_PERCENT_SENT:
return percentOfSentData(baseDisplay, role, absoluteValue);
case CD_TOTAL_RECEIVED:
return totalReceivedData(baseDisplay, role);
case CD_AVG_RECEIVED_FRAME:
return avgReceivedPerFrameData(baseDisplay, role);
case CD_AVG_RECEIVED_SECOND:
return avgReceivedPerSecondData(baseDisplay, role);
case CD_PARENT_PERCENT_RECEIVED:
return percentOfReceivedData(baseDisplay, role, relativeValue);
case CD_TOTAL_PERCENT_RECEIVED:
return percentOfReceivedData(baseDisplay, role, absoluteValue);
default:
AZ_Warning("OverallReplicaTreeViewModel", false, "Unknown Column");
break;
}
return QVariant();
}
QVariant OverallReplicaTreeViewModel::headerData(int section, Qt::Orientation orientation, int role) const
{
if (role == Qt::DisplayRole)
{
if (orientation == Qt::Horizontal)
{
switch (section)
{
case CD_DISPLAY_NAME:
return QString("Name");
case CD_REPLICA_ID:
return QString("ReplicaId");
case CD_TOTAL_SENT:
return QString("Sent Bytes");
case CD_AVG_SENT_FRAME:
return QString("Sent Bytes/Frame");
case CD_AVG_SENT_SECOND:
return QString("Sent Bytes/Second");
case CD_PARENT_PERCENT_SENT:
return QString("% of Parent Sent");
case CD_TOTAL_PERCENT_SENT:
return QString("% of Total Sent");
case CD_TOTAL_RECEIVED:
return QString("Received Bytes");
case CD_AVG_RECEIVED_FRAME:
return QString("Received Bytes/Frame");
case CD_AVG_RECEIVED_SECOND:
return QString("Received Bytes/Second");
case CD_PARENT_PERCENT_RECEIVED:
return QString("% of Parent Received");
case CD_TOTAL_PERCENT_RECEIVED:
return QString("% of Total Received");
}
}
}
return QVariant();
}
const BaseDisplayHelper* OverallReplicaTreeViewModel::FindDisplayHelperAtRoot(int row) const
{
if (row < 0 || row >= m_tableViewOrdering.size())
{
return nullptr;
}
return m_overallReplicaDetailView->FindReplicaDisplayHelper(m_tableViewOrdering[row]);
}
/////////////////////////////////////////
// OverallReplicaChunkTypeTreeViewModel
/////////////////////////////////////////
OverallReplicaChunkTypeTreeViewModel::OverallReplicaChunkTypeTreeViewModel(AbstractOverallReplicaDetailView* overallDetailView)
: BaseOverallTreeViewModel<AZStd::string>(overallDetailView)
{
}
int OverallReplicaChunkTypeTreeViewModel::columnCount(const QModelIndex& parentIndex) const
{
(void)parentIndex;
return CD_COUNT;
}
QVariant OverallReplicaChunkTypeTreeViewModel::data(const QModelIndex& index, int role) const
{
const bool relativeValue = true;
const bool absoluteValue = false;
const BaseDisplayHelper* baseDisplay = static_cast<const BaseDisplayHelper*>(index.internalPointer());
switch (index.column())
{
case CD_DISPLAY_NAME:
return displayNameData(baseDisplay, role);
case CD_TOTAL_SENT:
return totalSentData(baseDisplay, role);
case CD_AVG_SENT_FRAME:
return avgSentPerFrameData(baseDisplay, role);
case CD_AVG_SENT_SECOND:
return avgSentPerSecondData(baseDisplay, role);
case CD_PARENT_PERCENT_SENT:
return percentOfSentData(baseDisplay, role, relativeValue);
case CD_TOTAL_PERCENT_SENT:
return percentOfSentData(baseDisplay, role, absoluteValue);
case CD_TOTAL_RECEIVED:
return totalReceivedData(baseDisplay, role);
case CD_AVG_RECEIVED_FRAME:
return avgReceivedPerFrameData(baseDisplay, role);
case CD_AVG_RECEIVED_SECOND:
return avgReceivedPerSecondData(baseDisplay, role);
case CD_PARENT_PERCENT_RECEIVED:
return percentOfReceivedData(baseDisplay, role, relativeValue);
case CD_TOTAL_PERCENT_RECEIVED:
return percentOfReceivedData(baseDisplay, role, absoluteValue);
default:
AZ_Warning("OverallReplicaTreeViewModel", false, "Unknown Column");
break;
}
return QVariant();
}
QVariant OverallReplicaChunkTypeTreeViewModel::headerData(int section, Qt::Orientation orientation, int role) const
{
if (role == Qt::DisplayRole)
{
if (orientation == Qt::Horizontal)
{
switch (section)
{
case CD_DISPLAY_NAME:
return QString("Name");
case CD_TOTAL_SENT:
return QString("Sent Bytes");
case CD_AVG_SENT_FRAME:
return QString("Sent Bytes/Frame");
case CD_AVG_SENT_SECOND:
return QString("Sent Bytes/Second");
case CD_PARENT_PERCENT_SENT:
return QString("% of Parent Sent");
case CD_TOTAL_PERCENT_SENT:
return QString("% of Total Sent");
case CD_TOTAL_RECEIVED:
return QString("Received Bytes");
case CD_AVG_RECEIVED_FRAME:
return QString("Received Bytes/Frame");
case CD_AVG_RECEIVED_SECOND:
return QString("Received Bytes/Second");
case CD_PARENT_PERCENT_RECEIVED:
return QString("% of Parent Received");
case CD_TOTAL_PERCENT_RECEIVED:
return QString("% of Total Received");
}
}
}
return QVariant();
}
const BaseDisplayHelper* OverallReplicaChunkTypeTreeViewModel::FindDisplayHelperAtRoot(int row) const
{
if (row < 0 || row >= m_tableViewOrdering.size())
{
return nullptr;
}
return m_overallReplicaDetailView->FindReplicaChunkTypeDisplayHelper(m_tableViewOrdering[row]);
}
/////////////////////////////
// OverallReplicaDetailView
/////////////////////////////
const char* OverallReplicaDetailView::WINDOW_STATE_FORMAT = "OVERALL_REPLICA_DETAIL_VIEW_WINDOW_STATE";
const char* OverallReplicaDetailView::REPLICA_TREE_STATE_FORMAT = "OVERALL_REPLICA_DETAIL_VIEW_TREE_STATE";
const char* OverallReplicaDetailView::REPLICA_CHUNK_TREE_STATE_FORMAT = "OVERALL_REPLICA_CHUNK_DETAIL_VIEW_TREE_STATE";
OverallReplicaDetailView::OverallReplicaDetailView(ReplicaDataView* dataView, const ReplicaDataAggregator& dataAggregator)
: AbstractOverallReplicaDetailView()
, m_lifespanTelemetry("OverallReplicaDetailView")
, m_replicaDataView(dataView)
, m_windowStateCRC(AZ::Crc32(WINDOW_STATE_FORMAT))
, m_replicaTreeStateCRC(AZ::Crc32(REPLICA_TREE_STATE_FORMAT))
, m_replicaChunkTreeStateCRC(AZ::Crc32(REPLICA_CHUNK_TREE_STATE_FORMAT))
, m_dataAggregator(dataAggregator)
, m_overallReplicaModel(this)
, m_replicaFilterProxyModel(this)
, m_overallChunkTypeModel(this)
, m_replicaChunkTypeFilterProxyModel(this)
{
setAttribute(Qt::WA_DeleteOnClose, true);
setWindowFlags(windowFlags() | Qt::WindowMaximizeButtonHint | Qt::WindowMinimizeButtonHint);
m_gui = azcreate(Ui::OverallReplicaDetailView, ());
m_gui->setupUi(this);
show();
raise();
activateWindow();
setFocus();
QString titleName("Overall Replica Usage - %2");
this->setWindowTitle(titleName.arg(m_dataAggregator.GetInspectionFileName()));
// Loading up saved state
AZStd::intrusive_ptr<AzToolsFramework::QWidgetSavedState> windowState = AZ::UserSettings::Find<AzToolsFramework::QWidgetSavedState>(m_windowStateCRC, AZ::UserSettings::CT_GLOBAL);
if (windowState)
{
windowState->RestoreGeometry(this);
}
auto treeState = AZ::UserSettings::Find<TreeModelSavedState>(m_replicaTreeStateCRC, AZ::UserSettings::CT_GLOBAL);
if (treeState)
{
QByteArray treeData((const char*)treeState->m_treeColumnStorage.data(), (int)treeState->m_treeColumnStorage.size());
m_gui->overallReplicaUsage->header()->restoreState(treeData);
}
treeState = AZ::UserSettings::Find<TreeModelSavedState>(m_replicaChunkTreeStateCRC, AZ::UserSettings::CT_GLOBAL);
if (treeState)
{
QByteArray treeData((const char*)treeState->m_treeColumnStorage.data(), (int)treeState->m_treeColumnStorage.size());
m_gui->overallChunkTypeUsage->header()->restoreState(treeData);
}
m_gui->startFrame->setMinimum(0);
m_gui->startFrame->setValue(0);
m_gui->endFrame->setMaximum(static_cast<int>(m_dataAggregator.GetFrameCount()) - 1);
m_gui->endFrame->setValue(static_cast<int>(m_dataAggregator.GetFrameCount() - 1));
m_changeTimer.setInterval(500);
m_changeTimer.setSingleShot(true);
UpdateFrameBoundaries();
ParseData();
SetupTreeView();
UpdateDisplay();
QObject::connect(m_gui->startFrame, SIGNAL(valueChanged(int)), this, SLOT(QueueUpdate(int)));
QObject::connect(m_gui->endFrame, SIGNAL(valueChanged(int)), this, SLOT(QueueUpdate(int)));
QObject::connect(m_gui->framesPerSecond, SIGNAL(valueChanged(int)),this,SLOT(OnFPSChanged(int)));
connect(&m_changeTimer, SIGNAL(timeout()), SLOT(OnDataRangeChanged()));
}
OverallReplicaDetailView::~OverallReplicaDetailView()
{
ClearData();
// Save out whatever data we want to save out.
auto pState = AZ::UserSettings::CreateFind<AzToolsFramework::QWidgetSavedState>(m_windowStateCRC, AZ::UserSettings::CT_GLOBAL);
if (pState)
{
pState->CaptureGeometry(this);
}
auto treeState = AZ::UserSettings::CreateFind<TreeModelSavedState>(m_replicaTreeStateCRC, AZ::UserSettings::CT_GLOBAL);
if (treeState)
{
if (m_gui->overallReplicaUsage && m_gui->overallReplicaUsage->header())
{
QByteArray qba = m_gui->overallReplicaUsage->header()->saveState();
treeState->m_treeColumnStorage.assign((AZ::u8*)qba.begin(), (AZ::u8*)qba.end());
}
}
treeState = AZ::UserSettings::CreateFind<TreeModelSavedState>(m_replicaChunkTreeStateCRC, AZ::UserSettings::CT_GLOBAL);
if (treeState)
{
if (m_gui->overallChunkTypeUsage && m_gui->overallChunkTypeUsage->header())
{
QByteArray qba = m_gui->overallChunkTypeUsage->header()->saveState();
treeState->m_treeColumnStorage.assign((AZ::u8*)qba.begin(), (AZ::u8*)qba.end());
}
}
if (m_replicaDataView)
{
m_replicaDataView->SignalDialogClosed(this);
}
azdestroy(m_gui);
}
int OverallReplicaDetailView::GetFrameRange() const
{
return m_frameRange;
}
int OverallReplicaDetailView::GetFPS() const
{
return m_gui->framesPerSecond->value();
}
void OverallReplicaDetailView::SignalDataViewDestroyed(ReplicaDataView* replicaDataView)
{
if (m_replicaDataView == replicaDataView)
{
m_replicaDataView = nullptr;
}
close();
}
void OverallReplicaDetailView::ApplySettingsFromWorkspace(WorkspaceSettingsProvider*)
{
}
void OverallReplicaDetailView::ActivateWorkspaceSettings(WorkspaceSettingsProvider*)
{
}
void OverallReplicaDetailView::SaveSettingsToWorkspace(WorkspaceSettingsProvider*)
{
}
void OverallReplicaDetailView::ApplyPersistentState()
{
}
void OverallReplicaDetailView::Reflect(AZ::ReflectContext* context)
{
(void)context;
}
void OverallReplicaDetailView::OnFPSChanged(int fps)
{
(void)fps;
UpdateDisplay();
}
void OverallReplicaDetailView::QueueUpdate(int ignoredFrame)
{
(void)ignoredFrame;
m_changeTimer.start();
}
void OverallReplicaDetailView::OnDataRangeChanged()
{
ParseData();
UpdateFrameBoundaries();
UpdateDisplay();
}
OverallReplicaDetailDisplayHelper* OverallReplicaDetailView::CreateReplicaDisplayHelper(const char* replicaName, AZ::u64 replicaId)
{
OverallReplicaDetailDisplayHelper* detailDisplay = nullptr;
ReplicaDisplayHelperMap::iterator displayIter = m_replicaDisplayHelpers.find(replicaId);
if (displayIter == m_replicaDisplayHelpers.end())
{
detailDisplay = aznew OverallReplicaDetailDisplayHelper(replicaName, replicaId);
m_replicaDisplayHelpers.insert(ReplicaDisplayHelperMap::value_type(replicaId, detailDisplay));
m_overallReplicaModel.m_tableViewOrdering.push_back(replicaId);
}
else
{
detailDisplay = displayIter->second;
}
return detailDisplay;
}
OverallReplicaDetailDisplayHelper* OverallReplicaDetailView::FindReplicaDisplayHelper(AZ::u64 replicaId)
{
OverallReplicaDetailDisplayHelper* detailDisplay = nullptr;
ReplicaDisplayHelperMap::iterator displayIter = m_replicaDisplayHelpers.find(replicaId);
if (displayIter != m_replicaDisplayHelpers.end())
{
detailDisplay = displayIter->second;
}
return detailDisplay;
}
ReplicaChunkDetailDisplayHelper* OverallReplicaDetailView::CreateReplicaChunkTypeDisplayHelper(const AZStd::string& chunkTypeName, AZ::u32 chunkIndex)
{
ReplicaChunkDetailDisplayHelper* detailDisplay = nullptr;
ReplicaChunkTypeDisplayHelperMap::iterator displayIter = m_replicaChunkTypeDisplayHelpers.find(chunkTypeName);
if (displayIter == m_replicaChunkTypeDisplayHelpers.end())
{
detailDisplay = aznew ReplicaChunkDetailDisplayHelper(chunkTypeName.c_str(), chunkIndex);
m_replicaChunkTypeDisplayHelpers.insert(ReplicaChunkTypeDisplayHelperMap::value_type(chunkTypeName, detailDisplay));
m_overallChunkTypeModel.m_tableViewOrdering.push_back(chunkTypeName);
}
else
{
detailDisplay = displayIter->second;
}
return detailDisplay;
}
ReplicaChunkDetailDisplayHelper* OverallReplicaDetailView::FindReplicaChunkTypeDisplayHelper(const AZStd::string& chunkTypeName)
{
ReplicaChunkDetailDisplayHelper* detailDisplay = nullptr;
ReplicaChunkTypeDisplayHelperMap::iterator displayIter = m_replicaChunkTypeDisplayHelpers.find(chunkTypeName);
if (displayIter != m_replicaChunkTypeDisplayHelpers.end())
{
detailDisplay = displayIter->second;
}
return detailDisplay;
}
void OverallReplicaDetailView::SaveOnExit()
{
}
void OverallReplicaDetailView::UpdateFrameBoundaries()
{
m_gui->startFrame->setMaximum(m_gui->endFrame->value());
m_gui->endFrame->setMinimum(m_gui->startFrame->value());
m_frameRange = (m_gui->endFrame->value() - m_gui->startFrame->value()) + 1;
if (m_frameRange <= 0)
{
m_frameRange = 1;
}
}
void OverallReplicaDetailView::ParseData()
{
// Not the best approach. But this shouldn't update all that frequently.
ClearData();
FrameNumberType startFrame = static_cast<FrameNumberType>(m_gui->startFrame->value());
FrameNumberType endFrame = static_cast<FrameNumberType>(m_gui->endFrame->value());
EventNumberType startIndex = m_dataAggregator.GetFirstIndexAtFrame(startFrame);
EventNumberType endIndex = m_dataAggregator.GetFirstIndexAtFrame(endFrame) + m_dataAggregator.NumOfEventsAtFrame(endFrame);
const Aggregator::EventListType& events = m_dataAggregator.GetEvents();
for (EventNumberType currentIndex = startIndex; currentIndex < endIndex; ++currentIndex)
{
ReplicaChunkEvent* chunkEvent = static_cast<ReplicaChunkEvent*>(events[currentIndex]);
// Since I process each event twice, I need to do the total aggregation seperately.
if (chunkEvent->GetEventType() == Replica::RET_CHUNK_DATASET_SENT
|| chunkEvent->GetEventType() == Replica::RET_CHUNK_RPC_SENT)
{
m_totalUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
}
else
{
m_totalUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
}
ProcessForReplica(chunkEvent);
ProcessForReplicaChunk(chunkEvent);
}
}
void OverallReplicaDetailView::ProcessForReplica(ReplicaChunkEvent* chunkEvent)
{
const char* replicaName = chunkEvent->GetReplicaName();
AZ::u64 replicaId = chunkEvent->GetReplicaId();
OverallReplicaDetailDisplayHelper* replicaDisplayHelper = CreateReplicaDisplayHelper(replicaName, replicaId);
if (replicaDisplayHelper)
{
if (chunkEvent->GetEventType() == Replica::RET_CHUNK_DATASET_SENT
|| chunkEvent->GetEventType() == Replica::RET_CHUNK_RPC_SENT)
{
replicaDisplayHelper->m_bandwidthUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
}
else if (chunkEvent->GetEventType() == Replica::RET_CHUNK_RPC_RECEIVED
|| chunkEvent->GetEventType() == Replica::RET_CHUNK_DATASET_RECEIVED)
{
replicaDisplayHelper->m_bandwidthUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
}
ReplicaChunkDetailDisplayHelper* chunkDetailDisplayHelper = replicaDisplayHelper->FindReplicaChunk(chunkEvent->GetReplicaChunkIndex());
if (chunkDetailDisplayHelper == nullptr)
{
chunkDetailDisplayHelper = replicaDisplayHelper->CreateReplicaChunkDisplayHelper(chunkEvent->GetChunkTypeName(), chunkEvent->GetReplicaChunkIndex());
}
ProcessForBaseDetailDisplayHelper(chunkEvent, chunkDetailDisplayHelper);
}
}
void OverallReplicaDetailView::ProcessForReplicaChunk(ReplicaChunkEvent* chunkEvent)
{
AZ::u32 chunkId = chunkEvent->GetReplicaChunkIndex();
AZStd::string chunkTypeName = chunkEvent->GetChunkTypeName();
ReplicaChunkDetailDisplayHelper* chunkDisplayHelper = CreateReplicaChunkTypeDisplayHelper(chunkTypeName, chunkId);
if (chunkDisplayHelper)
{
ProcessForBaseDetailDisplayHelper(chunkEvent, chunkDisplayHelper);
}
}
void OverallReplicaDetailView::ProcessForBaseDetailDisplayHelper(ReplicaChunkEvent* chunkEvent, BaseDetailDisplayHelper* detailDisplayHelper)
{
if (chunkEvent->GetEventType() == Replica::RET_CHUNK_DATASET_SENT
|| chunkEvent->GetEventType() == Replica::RET_CHUNK_DATASET_RECEIVED)
{
ReplicaChunkDataSetEvent* dataSetEvent = static_cast<ReplicaChunkDataSetEvent*>(chunkEvent);
detailDisplayHelper->SetupDataSet(dataSetEvent->GetIndex(), dataSetEvent->GetDataSetName());
DataSetDisplayFilter* dataSetDisplayFilter = detailDisplayHelper->GetDataSetDisplayHelper();
DataSetDisplayHelper* dataSetDisplayHelper = detailDisplayHelper->FindDataSet(dataSetEvent->GetIndex());
if (chunkEvent->GetEventType() == Replica::RET_CHUNK_DATASET_SENT)
{
detailDisplayHelper->m_bandwidthUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
dataSetDisplayFilter->m_bandwidthUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
dataSetDisplayHelper->m_bandwidthUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
}
else
{
detailDisplayHelper->m_bandwidthUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
dataSetDisplayFilter->m_bandwidthUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
dataSetDisplayHelper->m_bandwidthUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
}
}
else
{
ReplicaChunkRPCEvent* rpcEvent = static_cast<ReplicaChunkRPCEvent*>(chunkEvent);
detailDisplayHelper->SetupRPC(rpcEvent->GetIndex(), rpcEvent->GetRPCName());
RPCDisplayFilter* rpcDisplayFilter = detailDisplayHelper->GetRPCDisplayHelper();
RPCDisplayHelper* rpcDisplayHelper = detailDisplayHelper->FindRPC(rpcEvent->GetIndex());
if (chunkEvent->GetEventType() == Replica::RET_CHUNK_RPC_SENT)
{
detailDisplayHelper->m_bandwidthUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
rpcDisplayFilter->m_bandwidthUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
rpcDisplayHelper->m_bandwidthUsageAggregator.m_bytesSent += chunkEvent->GetUsageBytes();
}
else
{
detailDisplayHelper->m_bandwidthUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
rpcDisplayFilter->m_bandwidthUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
rpcDisplayHelper->m_bandwidthUsageAggregator.m_bytesReceived += chunkEvent->GetUsageBytes();
}
}
}
void OverallReplicaDetailView::ClearData()
{
for (auto& mapPair : m_replicaDisplayHelpers)
{
delete mapPair.second;
}
m_replicaDisplayHelpers.clear();
m_overallReplicaModel.m_tableViewOrdering.clear();
for (auto& mapPair : m_replicaChunkTypeDisplayHelpers)
{
delete mapPair.second;
}
m_replicaChunkTypeDisplayHelpers.clear();
m_overallChunkTypeModel.m_tableViewOrdering.clear();
m_totalUsageAggregator.m_bytesSent = 0;
m_totalUsageAggregator.m_bytesReceived = 0;
}
void OverallReplicaDetailView::UpdateDisplay()
{
int frameRange = GetFrameRange();
// Sent Total
m_gui->totalBytesSent->setText(QString::number(m_totalUsageAggregator.m_bytesSent));
size_t avgBytesPerFrame = m_totalUsageAggregator.m_bytesSent / frameRange;
m_gui->avgBytesSentFrame->setText(QString::number(avgBytesPerFrame));
m_gui->avgBytesSentSecond->setText(QString::number(avgBytesPerFrame * GetFPS()));
// Received Total
m_gui->totalBytesReceived->setText(QString::number(m_totalUsageAggregator.m_bytesReceived));
avgBytesPerFrame = m_totalUsageAggregator.m_bytesReceived / frameRange;
m_gui->avgBytesReceivedFrame->setText(QString::number(avgBytesPerFrame));
m_gui->avgBytesReceivedSecond->setText(QString::number(avgBytesPerFrame * GetFPS()));
m_overallChunkTypeModel.layoutChanged();
m_overallReplicaModel.layoutChanged();
}
void OverallReplicaDetailView::SetupTreeView()
{
SetupReplicaTreeView();
SetupReplicaChunkTypeTreeView();
}
void OverallReplicaDetailView::SetupReplicaTreeView()
{
m_replicaFilterProxyModel.setSortRole(Qt::UserRole);
m_replicaFilterProxyModel.setSourceModel(&m_overallReplicaModel);
m_gui->overallReplicaUsage->setModel(&m_replicaFilterProxyModel);
}
void OverallReplicaDetailView::SetupReplicaChunkTypeTreeView()
{
m_replicaChunkTypeFilterProxyModel.setSortRole(Qt::UserRole);
m_replicaChunkTypeFilterProxyModel.setSourceModel(&m_overallChunkTypeModel);
m_gui->overallChunkTypeUsage->setModel(&m_replicaChunkTypeFilterProxyModel);
}
};