Hi Jaco,
A small observation first: in line 20 and 38 you use the method toUTC() in a way that has no effect. It doesn't change the current object, but returns a changed datetime, so you should write time1 = time1.toUTC();
instead.
Now, here's the code how it works with using the method where toMSecsSinceEpoch is used to generate the times:
demoName = "Time Demo";
QCPBars* bars = new QCPBars(customPlot->xAxis, customPlot->yAxis);
customPlot->addPlottable(bars);
QVector<double> ticks, y0;
ticks << 1 << 2;
QVector<QString> labels;
labels << "Point 1" << "Point 2";
double runtime_dbl;
// Datapoint 1 - 00:00:48
QDateTime time1 = QDateTime::fromString("00:00:48 01.01.1970","hh:mm:ss dd.MM.yyyy");
time1.setTimeSpec(Qt::UTC);
runtime_dbl = time1.toMSecsSinceEpoch()/1000.0;
y0 << runtime_dbl;
qDebug() << runtime_dbl << QDateTime::fromMSecsSinceEpoch(runtime_dbl*1000).toString("hh:mm:ss dd.MM.yyyy");
// Datapoint 1 - 00:05:36
QDateTime time2 = QDateTime::fromString("00:05:36 01.01.1970","hh:mm:ss dd.MM.yyyy");
time2.setTimeSpec(Qt::UTC);
runtime_dbl = time2.toMSecsSinceEpoch()/1000.0;
y0 << runtime_dbl;
qDebug() << runtime_dbl << QDateTime::fromMSecsSinceEpoch(runtime_dbl*1000).toString("hh:mm:ss dd.MM.yyyy");
// Setup X-Axis
customPlot->xAxis->setTickVectorLabels(labels);
customPlot->xAxis->setAutoTicks(false);
customPlot->xAxis->setAutoTickLabels(false);
customPlot->xAxis->setTickLabelRotation(-60);
customPlot->xAxis->setSubTickCount(0);
customPlot->xAxis->setTickLength(0, 4);
customPlot->xAxis->grid()->setVisible(true);
customPlot->xAxis->setRange(0, ticks.count()+1);
customPlot->xAxis->setTickVector(ticks);
// Setup Y-Axis
customPlot->yAxis->setRange(0, runtime_dbl+1);
customPlot->yAxis->setTickLabelType(QCPAxis::ltDateTime);
customPlot->yAxis->setDateTimeSpec(Qt::UTC);
customPlot->yAxis->setDateTimeFormat("hh:mm:ss dd.MM.yyyy");
bars->setData(ticks, y0);
We completely stay in UTC time. This is necessary because the bars plottable anchors the base of the bar at value 0, which only in UTC is 00:00:00. If interpreted in local time, the bars will have their base at your local timezone offset and eventually generate upside down bars. To completely stay in UTC we also need to use QCPAxis::setDateTimeSpec(Qt::UTC)
in line 41 which is new in QCP 1.1.0.
Now there's another pitfall that's worth mentioning: Passing just a time like "00:05:36" to QDateTime::fromString
defaults to the date 01.01.1900. This is not the UTC 0, which is 01.01.1970. So If we had left the date unspecified in lines 14 and 21, we would have ended up with gigantic negative bars from 1970 (the UTC 0) down to 1900. Obviously, if only viewing hh:mm:ss
, this results in seemngly random tick labels. That's why I let it also print day month and year in the above example, to figure this out.
Okay, now how to do it with the explicitly constructed runtime_dbl
from hour, minute and second values:
demoName = "Time Demo";
QCPBars* bars = new QCPBars(customPlot->xAxis, customPlot->yAxis);
customPlot->addPlottable(bars);
QVector<double> ticks, y0;
ticks << 1 << 2;
QVector<QString> labels;
labels << "Point 1" << "Point 2";
double runtime_dbl;
int runtime = 0;
// Datapoint 1 - 00:00:48
QDateTime time1 = QDateTime::fromString("00:00:48","hh:mm:ss");
runtime += time1.time().hour() * 3600;
runtime += time1.time().minute() * 60;
runtime += time1.time().second();
runtime_dbl = (double) runtime;
y0 << runtime_dbl;
qDebug() << runtime_dbl << QDateTime::fromMSecsSinceEpoch(runtime_dbl*1000).toString("hh:mm:ss dd.MM.yyyy");
// Datapoint 1 - 00:05:36
runtime = 0;
QDateTime time2 = QDateTime::fromString("00:05:36","hh:mm:ss");
runtime += time2.time().hour() * 3600;
runtime += time2.time().minute() * 60;
runtime += time2.time().second();
runtime_dbl = (double) runtime;
y0 << runtime_dbl;
qDebug() << runtime_dbl << QDateTime::fromMSecsSinceEpoch(runtime_dbl*1000).toString("hh:mm:ss dd.MM.yyyy");
// Setup X-Axis
customPlot->xAxis->setTickVectorLabels(labels);
customPlot->xAxis->setAutoTicks(false);
customPlot->xAxis->setAutoTickLabels(false);
customPlot->xAxis->setTickLabelRotation(-60);
customPlot->xAxis->setSubTickCount(0);
customPlot->xAxis->setTickLength(0, 4);
customPlot->xAxis->grid()->setVisible(true);
customPlot->xAxis->setRange(0, ticks.count()+1);
customPlot->xAxis->setTickVector(ticks);
// Setup Y-Axis
customPlot->yAxis->setRange(0, runtime_dbl+1);
customPlot->yAxis->setTickLabelType(QCPAxis::ltDateTime);
customPlot->yAxis->setDateTimeSpec(Qt::UTC);
customPlot->yAxis->setDateTimeFormat("hh:mm:ss dd.MM.yyyy");
bars->setData(ticks, y0);
There's not much difference, apart from the fact that now we can get away with not specifying the date explicitly in the QDateTime::fromString
method. This is because we use only the time part of the datetime object and construct our runtime_dbl
from that, effectively starting from the correct UTC 0.
The fact that the bars plottable always places its bar base at value 0 is unfortunate and will be changed in a future release. In your case, as shown above, this behaviour is okay if we set the axis timespec to be UTC, where the value 0 actually is time 00:00:00. I hope switching to QCustomPlot 1.1.0 is an option for you, because before that I'm afraid the bars plottable will always place its base at the local time offset.