MAK Data Logger API Documentation for HLA
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
stateObserver Example

A logger plug-in which monitors the state of the logger and displays it in the GUI. This is a working example which is integrated into the actual logger. The output of the state observer can be see by turning on the Object Statistics view remote control GUI.

The Qt Toolkit is required to build this plug-in.

The state observer view component:

stateObView.h

stateObView.cxx

stateObView.h

/******************************************************************************
** Copyright (c) 1992-2025 MAK Technologies, Inc
** All rights reserved.
******************************************************************************/
#pragma once
#include "stateObserver.h"
class QWidget;
namespace MAKLogger
{
class DtLgrAppGui;
class DtLgrGuiModel;
class DtProgressiveLineGraph;
class DtStateObjectViewWidget;
class DtStateObserverController;
class DT_DLL_STATEOBSERVER DtStateObserverView : public DtLgrGuiComponent
{
Q_OBJECT
public:
DtStateObserverView(DtLgrAppGui*,DtStateObserverController*);
virtual ~DtStateObserverView();
void setTotalObjectCount(int count);
void setRemovedObjectCount(int count);
void setUnknownObjectCount(int count);
void setEntityCount(int count);
void setAggregateCount(int count);
void setEnvironmentalProcessCount(int count);
virtual QWidget* initialize(QWidget* parent);
virtual void activate();
virtual void deactivate();
virtual bool canCloseFile() const;
void startView();
void stopView();
void clearView();
virtual double updateTime();
virtual void update();
virtual MAKLogger::DtLgrZoomableWidget* zoomComponent();
public slots:
void fileOpenChanged(QString fileName);
void connectionStatusChanged(bool connected);
protected:
DtLgrAppGui* myGui;
DtLgrGuiModel* myModel;
DtStateObserverController* myController;
DtStateObjectViewWidget* myWidget;
bool myActiveState;
int myCurrentUpdateCount;
DtAbsoluteTime myLastGraphTime;
// Update at 1/10 the default redraw rate.
const static int theRequestUpdateRate = 10;
enum GraphIds
{
Graph_TotalObjectCount = 1,
Graph_RemovedObjectCount,
Graph_UnknownObjectCount,
Graph_EntityCount,
Graph_AggregateCount,
Graph_EnvironmentalProcessCount
};
};
}

stateObView.cxx

/******************************************************************************
** Copyright (c) 1992-2025 MAK Technologies, Inc
** All rights reserved.
******************************************************************************/
#include "stateObView.h"
#include <commonWidgets/qtExtendedDrawing.h>
namespace MAKLogger{
DtStateObserverController* controller)
: DtLgrGuiComponent(QObject::tr("Object Statistics"))
, myGui(gui)
, myModel(0)
, myController(controller)
, myGraph(0)
, myWidget(0)
, myActiveState(false)
, myCurrentUpdateCount(0)
, myLastGraphTime(0.0)
{
QIcon viewSet = QIcon("../data/images/icon_stats.png");
setIconSet(viewSet);
QKeySequence seq("Shift+O");
setKeySequence(seq);
}
DtStateObserverView::~DtStateObserverView()
{
}
void DtStateObserverView::setEntityCount(int count)
{
if(!myActiveState)
{
return;
}
myWidget->myEntityCountLabel->setText(QString::number(count));
double percent;
if(myModel->displayTime().lastTime() == myModel->displayTime().firstTime())
{
percent = 0.0;
}
else
{
percent = myModel->displayTime().percentOfTimeFirstLast(
myModel->displayTime().currentTime()) / 100.0;
}
myGraph->insertValue(Graph_EntityCount,percent,count);
myGraph->forceUpdate(true);
}
void DtStateObserverView::setAggregateCount(int count)
{
if(!myActiveState)
{
return;
}
myWidget->myAggregateCountLabel->setText(QString::number(count));
double percent;
if(myModel->displayTime().lastTime() == myModel->displayTime().firstTime())
{
percent = 0.0;
}
else
{
percent = myModel->displayTime().percentOfTimeFirstLast(
myModel->displayTime().currentTime()) / 100.0;
}
myGraph->insertValue(Graph_AggregateCount,percent,count);
myGraph->forceUpdate(true);
}
void DtStateObserverView::setEnvironmentalProcessCount(int count)
{
if(!myActiveState)
{
return;
}
myWidget->myEnvProcCountLabel->setText(QString::number(count));
double percent;
if(myModel->displayTime().lastTime() == myModel->displayTime().firstTime())
{
percent = 0.0;
}
else
{
percent = myModel->displayTime().percentOfTimeFirstLast(
myModel->displayTime().currentTime()) / 100.0;
}
myGraph->insertValue(Graph_EnvironmentalProcessCount,percent,count);
myGraph->forceUpdate(true);
}
void DtStateObserverView::setUnknownObjectCount(int count)
{
if(!myActiveState)
{
return;
}
myWidget->myUnknownCountLabel->setText(QString::number(count));
double percent;
if(myModel->displayTime().lastTime() == myModel->displayTime().firstTime())
{
percent = 0.0;
}
else
{
percent = myModel->displayTime().percentOfTimeFirstLast(
myModel->displayTime().currentTime()) / 100.0;
}
myGraph->insertValue(Graph_UnknownObjectCount,percent,count);
myGraph->forceUpdate(true);
}
void DtStateObserverView::setTotalObjectCount(int count)
{
if(!myActiveState)
{
return;
}
myWidget->myTotalCountLabel->setText(QString::number(count));
double percent;
if(myModel->displayTime().lastTime() == myModel->displayTime().firstTime())
{
percent = 0.0;
}
else
{
percent = myModel->displayTime().percentOfTimeFirstLast(
myModel->displayTime().currentTime()) / 100.0;
}
myGraph->insertValue(Graph_TotalObjectCount,percent,count);
myGraph->forceUpdate(true);
}
void DtStateObserverView::setRemovedObjectCount(int count)
{
if(!myActiveState)
{
return;
}
myWidget->myRemovedCountLabel->setText(QString::number(count));
double percent;
if(myModel->displayTime().lastTime() == myModel->displayTime().firstTime())
{
percent = 0.0;
}
else
{
percent = myModel->displayTime().percentOfTimeFirstLast(
myModel->displayTime().currentTime()) / 100.0;
}
myGraph->insertValue(Graph_RemovedObjectCount,percent,count);
myGraph->forceUpdate(true);
}
void DtStateObserverView::activate()
{
myController->connectToLogger();
QObject::connect(myModel->eventHandler(),SIGNAL(postUpdateSignal(DtLgrGuiModel&)),
(DtLgrGuiComponent*)this,SLOT(update()));
myActiveState = true;
startView();
}
// This method is called when the component is hidden.
void DtStateObserverView::deactivate()
{
myController->disconnectFromLogger();
QObject::disconnect(myModel->eventHandler(),SIGNAL(postUpdateSignal(DtLgrGuiModel&)),
(DtLgrGuiComponent*)this,SLOT(update()));
myActiveState = false;
stopView();
}
void DtStateObserverView::startView()
{
if(myWidget && myWidget->isVisible())
{
clearView();
}
}
void DtStateObserverView::stopView()
{
clearView();
}
void DtStateObserverView::clearView()
{
myGraph->resetAllValues(0);
myGraph->forceUpdate(true);
myLastGraphTime = 0.0;
setEntityCount(0);
setAggregateCount(0);
setEnvironmentalProcessCount(0);
setTotalObjectCount(0);
setRemovedObjectCount(0);
setUnknownObjectCount(0);
}
// \brief Returns the desired times between updates in seconds. If updateTime
// returns 1.0 the component will be updated every second, if it is 0.1 the
// component will be updated ten times a second or 10hz.
// Return -1 if update should not be called.
double DtStateObserverView::updateTime()
{
//Lets update and main window refresh rate.
return -1;//.1;
}
// \brief Called repeatedly by the host application in the GUI thread. The time
// between calls is controlled by updateTime.
void DtStateObserverView::update()
{
if(myWidget && myWidget->isVisible())
{
++myCurrentUpdateCount;
if(myCurrentUpdateCount >= theRequestUpdateRate)
{
myController->requestUpdate();
myCurrentUpdateCount = 0;
if(myGraph->updateNeeded())
{
myGraph->forceUpdate(true);
}
}
DtRelativeTime duration = myModel->displayTime().lastTime() - myModel->displayTime().firstTime();
if(duration > 0)
{
double offsetPercentage = (myLastGraphTime.seconds() - myModel->displayTime().lastTime().seconds())/duration.seconds();
if(offsetPercentage != 0)
{
myGraph->offsetPercentages(offsetPercentage);
myGraph->forceUpdate(true);
}
}
myLastGraphTime = myModel->displayTime().lastTime();
}
myController->update();
}
// \brief Create the widget.
QWidget* DtStateObserverView::initialize(QWidget* parent)
{
if(!myWidget)
{
myModel = myGui->model();
myWidget = new DtStateObjectViewWidget(parent);
myWidget->setMinimumHeight(75);
QVBoxLayout* layout = new QVBoxLayout();
layout->setMargin(0);
layout->setSpacing(0);
myWidget->myGraphFrame->setLayout(layout);
myGraph = new MAKLogger::DtProgressiveLineGraph(0,0, true,
myWidget->myGraphFrame);
myGraph->setMargins(20,0);
myGraph->setModel(myModel);
layout->addWidget(myGraph);
QPalette pal = myWidget->palette();
pal.setColor(QPalette::Background,QColor(0,64,0));
myWidget->setPalette(pal);
myWidget->setAutoFillBackground(true);
pal.setColor(QPalette::Foreground,Qt::white);
myWidget->myTotalLabel->setPalette(pal);
myWidget->myTotalCountLabel->setPalette(pal);
myWidget->myRemovedLabel->setPalette(pal);
myWidget->myRemovedCountLabel->setPalette(pal);
myWidget->myUnknownLabel->setPalette(pal);
myWidget->myUnknownCountLabel->setPalette(pal);
myWidget->myEntityLabel->setPalette(pal);
myWidget->myEntityCountLabel->setPalette(pal);
myWidget->myAggregateLabel->setPalette(pal);
myWidget->myAggregateCountLabel->setPalette(pal);
myWidget->myEnvProcLabel->setPalette(pal);
myWidget->myEnvProcCountLabel->setPalette(pal);
pal.setColor(QPalette::Foreground,Qt::darkGreen);
myGraph->setPalette(pal);
myGraph->addSet(Graph_TotalObjectCount,QPen(Qt::yellow),0);
pal = myWidget->myTotalCountLabel->palette();
pal.setColor(QPalette::Foreground,Qt::yellow);
myWidget->myTotalCountLabel->setPalette(pal);
myGraph->addSet(Graph_RemovedObjectCount,QPen(Qt::red),0);
pal = myWidget->myRemovedCountLabel->palette();
pal.setColor(QPalette::Foreground,Qt::red);
myWidget->myRemovedCountLabel->setPalette(pal);
myGraph->addSet(Graph_UnknownObjectCount,QPen(Qt::green),0);
pal = myWidget->myUnknownCountLabel->palette();
pal.setColor(QPalette::Foreground,Qt::green);
myWidget->myUnknownCountLabel->setPalette(pal);
myGraph->addSet(Graph_EntityCount,QPen(QColor(128,128,255)),0);
pal = myWidget->myEntityCountLabel->palette();
pal.setColor(QPalette::Foreground,QColor(128,128,255));
myWidget->myEntityCountLabel->setPalette(pal);
myGraph->addSet(Graph_AggregateCount,QPen(Qt::magenta),0);
pal = myWidget->myAggregateCountLabel->palette();
pal.setColor(QPalette::Foreground,Qt::magenta);
myWidget->myAggregateCountLabel->setPalette(pal);
myGraph->addSet(Graph_EnvironmentalProcessCount,QPen(Qt::white),0);
pal = myWidget->myEnvProcCountLabel->palette();
pal.setColor(QPalette::Foreground,Qt::white);
myWidget->myEnvProcCountLabel->setPalette(pal);
connect(myModel->eventHandler(),SIGNAL(filenameChanged(QString)), SLOT(fileOpenChanged(QString)));
connect(myModel->eventHandler(),SIGNAL(connectStatusChanged(bool)), SLOT(connectionStatusChanged(bool)));
}
return myWidget;
}
DtLgrZoomableWidget* DtStateObserverView::zoomComponent()
{
return myGraph;
}
bool DtStateObserverView::canCloseFile() const
{
// A fairly easy way to reset values when a file is closed.
myGraph->resetAllValues(0);
myGraph->forceUpdate(true);
return true;
}
void DtStateObserverView::fileOpenChanged(QString fileName)
{
if (myActiveState && fileName.isEmpty())
{
myGraph->resetAllValues(0);
myGraph->forceUpdate(true);
}
}
void DtStateObserverView::connectionStatusChanged(bool connected)
{
if (myActiveState)
{
if (connected)
{
startView();
}
else
{
stopView();
}
}
}
}

Document ID: Generated on Thu Dec 18 15:35:09 EST 2025 from SVN revision 282494
Copyright © 2024 MAK Technologies. All Rights Reserved (www.mak.com)