1 // Copyright (c) 2011-2015 The Bitcoin Core developers
2 // Distributed under the MIT software license, see the accompanying
3 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
5 #include "trafficgraphwidget.h"
6 #include "clientmodel.h"
14 #define DESIRED_SAMPLES 800
19 TrafficGraphWidget::TrafficGraphWidget(QWidget
*parent
) :
30 timer
= new QTimer(this);
31 connect(timer
, SIGNAL(timeout()), SLOT(updateRates()));
34 void TrafficGraphWidget::setClientModel(ClientModel
*model
)
38 nLastBytesIn
= model
->getTotalBytesRecv();
39 nLastBytesOut
= model
->getTotalBytesSent();
43 int TrafficGraphWidget::getGraphRangeMins() const
48 void TrafficGraphWidget::paintPath(QPainterPath
&path
, QQueue
<float> &samples
)
50 int h
= height() - YMARGIN
* 2, w
= width() - XMARGIN
* 2;
51 int sampleCount
= samples
.size(), x
= XMARGIN
+ w
, y
;
53 path
.moveTo(x
, YMARGIN
+ h
);
54 for(int i
= 0; i
< sampleCount
; ++i
) {
55 x
= XMARGIN
+ w
- w
* i
/ DESIRED_SAMPLES
;
56 y
= YMARGIN
+ h
- (int)(h
* samples
.at(i
) / fMax
);
59 path
.lineTo(x
, YMARGIN
+ h
);
63 void TrafficGraphWidget::paintEvent(QPaintEvent
*)
65 QPainter
painter(this);
66 painter
.fillRect(rect(), Qt::black
);
68 if(fMax
<= 0.0f
) return;
70 QColor
axisCol(Qt::gray
);
71 int h
= height() - YMARGIN
* 2;
72 painter
.setPen(axisCol
);
73 painter
.drawLine(XMARGIN
, YMARGIN
+ h
, width() - XMARGIN
, YMARGIN
+ h
);
75 // decide what order of magnitude we are
76 int base
= floor(log10(fMax
));
77 float val
= pow(10.0f
, base
);
79 const QString units
= tr("KB/s");
80 const float yMarginText
= 2.0;
83 painter
.setPen(axisCol
);
84 painter
.drawText(XMARGIN
, YMARGIN
+ h
- h
* val
/ fMax
-yMarginText
, QString("%1 %2").arg(val
).arg(units
));
85 for(float y
= val
; y
< fMax
; y
+= val
) {
86 int yy
= YMARGIN
+ h
- h
* y
/ fMax
;
87 painter
.drawLine(XMARGIN
, yy
, width() - XMARGIN
, yy
);
89 // if we drew 3 or fewer lines, break them up at the next lower order of magnitude
90 if(fMax
/ val
<= 3.0f
) {
91 axisCol
= axisCol
.darker();
92 val
= pow(10.0f
, base
- 1);
93 painter
.setPen(axisCol
);
94 painter
.drawText(XMARGIN
, YMARGIN
+ h
- h
* val
/ fMax
-yMarginText
, QString("%1 %2").arg(val
).arg(units
));
96 for(float y
= val
; y
< fMax
; y
+= val
, count
++) {
97 // don't overwrite lines drawn above
100 int yy
= YMARGIN
+ h
- h
* y
/ fMax
;
101 painter
.drawLine(XMARGIN
, yy
, width() - XMARGIN
, yy
);
105 if(!vSamplesIn
.empty()) {
107 paintPath(p
, vSamplesIn
);
108 painter
.fillPath(p
, QColor(0, 255, 0, 128));
109 painter
.setPen(Qt::green
);
112 if(!vSamplesOut
.empty()) {
114 paintPath(p
, vSamplesOut
);
115 painter
.fillPath(p
, QColor(255, 0, 0, 128));
116 painter
.setPen(Qt::red
);
121 void TrafficGraphWidget::updateRates()
123 if(!clientModel
) return;
125 quint64 bytesIn
= clientModel
->getTotalBytesRecv(),
126 bytesOut
= clientModel
->getTotalBytesSent();
127 float inRate
= (bytesIn
- nLastBytesIn
) / 1024.0f
* 1000 / timer
->interval();
128 float outRate
= (bytesOut
- nLastBytesOut
) / 1024.0f
* 1000 / timer
->interval();
129 vSamplesIn
.push_front(inRate
);
130 vSamplesOut
.push_front(outRate
);
131 nLastBytesIn
= bytesIn
;
132 nLastBytesOut
= bytesOut
;
134 while(vSamplesIn
.size() > DESIRED_SAMPLES
) {
135 vSamplesIn
.pop_back();
137 while(vSamplesOut
.size() > DESIRED_SAMPLES
) {
138 vSamplesOut
.pop_back();
142 Q_FOREACH(float f
, vSamplesIn
) {
143 if(f
> tmax
) tmax
= f
;
145 Q_FOREACH(float f
, vSamplesOut
) {
146 if(f
> tmax
) tmax
= f
;
152 void TrafficGraphWidget::setGraphRangeMins(int mins
)
155 int msecsPerSample
= nMins
* 60 * 1000 / DESIRED_SAMPLES
;
157 timer
->setInterval(msecsPerSample
);
162 void TrafficGraphWidget::clear()
171 nLastBytesIn
= clientModel
->getTotalBytesRecv();
172 nLastBytesOut
= clientModel
->getTotalBytesSent();