-
Notifications
You must be signed in to change notification settings - Fork 246
Expand file tree
/
Copy pathanalyzerconsole.cpp
More file actions
198 lines (158 loc) · 7.39 KB
/
analyzerconsole.cpp
File metadata and controls
198 lines (158 loc) · 7.39 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
/******************************************************************************\
* Copyright (c) 2004-2026
*
* Author(s):
* Volker Fischer
*
******************************************************************************
*
* This program is free software; you can redistribute it and/or modify it under
* the terms of the GNU General Public License as published by the Free Software
* Foundation; either version 2 of the License, or (at your option) any later
* version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
* details.
*
* You should have received a copy of the GNU General Public License along with
* this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*
\******************************************************************************/
#include "analyzerconsole.h"
// Analyzer console implementation *********************************************
CAnalyzerConsole::CAnalyzerConsole ( CClient* pNCliP, QWidget* parent ) :
CBaseDlg ( parent, Qt::Window ), // use Qt::Window to get min/max window buttons
pClient ( pNCliP ),
GraphImage ( 1, 1, QImage::Format_RGB32 ),
GraphErrRateCanvasRect ( 0, 0, 600, 450 ), // defines total size of graph
iGridFrameOffset ( 10 ),
iLineWidth ( 2 ),
iMarkerSize ( 10 ),
iXAxisTextHeight ( 22 ),
GraphBackgroundColor ( Qt::white ), // background
GraphFrameColor ( Qt::black ), // frame
GraphGridColor ( Qt::gray ), // grid
LineColor ( Qt::blue ),
LineLimitColor ( Qt::green ),
LineMaxUpLimitColor ( Qt::red )
{
// set the window icon and title text
const QIcon icon = QIcon ( QString::fromUtf8 ( ":/png/main/res/fronticon.png" ) );
setWindowIcon ( icon );
setWindowTitle ( tr ( "Analyzer Console" ) );
// create main layout
QVBoxLayout* pMainLayout = new QVBoxLayout;
// create and add main tab widget
pMainTabWidget = new QTabWidget ( this );
pMainLayout->addWidget ( pMainTabWidget );
setLayout ( pMainLayout );
// error rate gaph tab
pTabWidgetBufErrRate = new QWidget();
QVBoxLayout* pTabErrRateLayout = new QVBoxLayout ( pTabWidgetBufErrRate );
pGraphErrRate = new QLabel ( this );
pTabErrRateLayout->addWidget ( pGraphErrRate );
pMainTabWidget->addTab ( pTabWidgetBufErrRate, tr ( "Error Rate of Each Buffer Size" ) );
// Connections -------------------------------------------------------------
// timers
QObject::connect ( &TimerErrRateUpdate, &QTimer::timeout, this, &CAnalyzerConsole::OnTimerErrRateUpdate );
}
void CAnalyzerConsole::showEvent ( QShowEvent* )
{
// start timer for error rate graph
TimerErrRateUpdate.start ( ERR_RATE_GRAPH_UPDATE_TIME_MS );
}
void CAnalyzerConsole::hideEvent ( QHideEvent* )
{
// if window is closed, stop timer
TimerErrRateUpdate.stop();
}
void CAnalyzerConsole::OnTimerErrRateUpdate()
{
// generate current graph image
DrawFrame();
DrawErrorRateTrace();
// set new image to the label
pGraphErrRate->setPixmap ( QPixmap().fromImage ( GraphImage ) );
}
void CAnalyzerConsole::DrawFrame()
{
// scale image to correct size
GraphImage = GraphImage.scaled ( GraphErrRateCanvasRect.width(), GraphErrRateCanvasRect.height() );
// generate plot grid frame rectangle
GraphGridFrame.setRect ( GraphErrRateCanvasRect.x() + iGridFrameOffset,
GraphErrRateCanvasRect.y() + iGridFrameOffset,
GraphErrRateCanvasRect.width() - 2 * iGridFrameOffset,
GraphErrRateCanvasRect.height() - 2 * iGridFrameOffset - iXAxisTextHeight );
GraphImage.fill ( GraphBackgroundColor.rgb() ); // fill background
// create painter
QPainter GraphPainter ( &GraphImage );
// create actual plot region (grid frame)
GraphPainter.setPen ( GraphFrameColor );
GraphPainter.drawRect ( GraphGridFrame );
}
void CAnalyzerConsole::DrawErrorRateTrace()
{
// create painter
QPainter GraphPainter ( &GraphImage );
// get the network buffer error rates to be displayed
CVector<double> vecButErrorRates;
double dLimit;
double dMaxUpLimit;
pClient->GetBufErrorRates ( vecButErrorRates, dLimit, dMaxUpLimit );
// get the number of data elements
const int iNumBuffers = vecButErrorRates.Size();
// convert the limits in the log domain
const double dLogLimit = log10 ( dLimit );
const double dLogMaxUpLimit = log10 ( dMaxUpLimit );
// use fixed y-axis scale where the limit line is in the middle of the graph
const double dMax = 0;
const double dMin = dLogLimit * 2;
// calculate space between points on the x-axis
const double dXSpace = static_cast<double> ( GraphGridFrame.width() ) / ( iNumBuffers - 1 );
// plot the limit line as dashed line
const double dYValLimitInGraph = CalcYPosInGraph ( dMin, dMax, dLogLimit );
GraphPainter.setPen ( QPen ( QBrush ( LineLimitColor ), iLineWidth, Qt::DashLine ) );
GraphPainter.drawLine ( QPoint ( GraphGridFrame.x(), dYValLimitInGraph ),
QPoint ( GraphGridFrame.x() + GraphGridFrame.width(), dYValLimitInGraph ) );
// plot the maximum upper limit line as a dashed line
const double dYValMaxUpLimitInGraph = CalcYPosInGraph ( dMin, dMax, dLogMaxUpLimit );
GraphPainter.setPen ( QPen ( QBrush ( LineMaxUpLimitColor ), iLineWidth, Qt::DashLine ) );
GraphPainter.drawLine ( QPoint ( GraphGridFrame.x(), dYValMaxUpLimitInGraph ),
QPoint ( GraphGridFrame.x() + GraphGridFrame.width(), dYValMaxUpLimitInGraph ) );
// plot the data
for ( int i = 0; i < iNumBuffers; i++ )
{
// data convert in log domain
// check for special case if error rate is 0 (which would lead to -Inf
// after the log operation)
if ( vecButErrorRates[i] > 0 )
{
vecButErrorRates[i] = log10 ( vecButErrorRates[i] );
}
else
{
// definition: set it to lowest possible axis value
vecButErrorRates[i] = dMin;
}
// calculate the actual point in the graph (in pixels)
const QPoint curPoint ( GraphGridFrame.x() + static_cast<int> ( dXSpace * i ), CalcYPosInGraph ( dMin, dMax, vecButErrorRates[i] ) );
// draw a marker and a solid line which goes from the bottom to the
// marker (similar to Matlab stem() function)
GraphPainter.setPen ( QPen ( QBrush ( LineColor ), iMarkerSize, Qt::SolidLine, Qt::RoundCap ) );
GraphPainter.drawPoint ( curPoint );
GraphPainter.setPen ( QPen ( QBrush ( LineColor ), iLineWidth ) );
GraphPainter.drawLine ( QPoint ( curPoint.x(), GraphGridFrame.y() + GraphGridFrame.height() ), curPoint );
}
}
int CAnalyzerConsole::CalcYPosInGraph ( const double dAxisMin, const double dAxisMax, const double dValue ) const
{
// calculate value range
const double dValRange = dAxisMax - dAxisMin;
// calculate current normalized y-axis value
const double dYValNorm = ( dValue - dAxisMin ) / dValRange;
// consider the graph grid size to calculate the final y-axis value
return GraphGridFrame.y() + static_cast<int> ( static_cast<double> ( GraphGridFrame.height() ) * ( 1 - dYValNorm ) );
}