Commit graph

15 commits

Author SHA1 Message Date
Berthold Stoeger
790d2b2ddb statistics: convert QuartileMarkers to QSGNodes
Slowly converting the QGraphicsScene items to QSGNodes to
avoid full replot of the scene.

This adds a new abstraction for line-nodes. Since the render()
function here is fundamentally different from the pixmap-nodes
we had so far, this has to be made virtual.

Also, move the quartile markers to their own source file,
since the StatsView source file is quite huge already.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-20 08:47:18 +01:00
Berthold Stoeger
e1c0cace95 statistics: add notion of Z-value to chart items
The chart items were drawn in order of creation. To control this,
add a notion of Z-value. In contrast to QGraphicsScene, make
this a small integer value.

To controll order of drawing, a plain QSGNode is created for
every possible Z-Value and items are added to these nodes.
Thus, items are rendered by Z-value and if the Z-value is equal
by order of creation.

Likewise split the list of chart-items into Z-values, so that
items can be quickly unregistered: The items that will be
removed individually will usuall be part of Z-levels with only
few items (e.g. legend, infobox). Z-levels with many items
(notably the series) will always be fully rebuilt.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-20 08:47:18 +01:00
Berthold Stoeger
785d5189f6 statistics: turn infobox into a QSGNode
A small step in converting from QGraphicsScene to QQuickItem.
This is the second item to be converted (after the legend)
and for now items are drawn in order of creation, which means
that the infobox is on top of the legend. This will have
to be made deterministic in follow-up commits.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-20 08:47:18 +01:00
Berthold Stoeger
1a869833d8 statistics: implement moving of legend
Catch mouse move events and move the legend accordingly.
Currently, this is the only item that can be dragged and
therefore there is no need of doing some kind of fancy
interface. Simply keep a pointer to the legend if it is
dragged.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-20 08:47:18 +01:00
Berthold Stoeger
2b961414d7 statistics: draw legend as a QSGNode
In order not to waste CPU by constantly rerendering the chart,
we must use these weird OpenGL QSGNode things. The interface
is appallingly low-level and unfriendly.

As a first test, try to convert the legend. Create a wrapper
class that represents a rectangular item with a texture
and that will certainly need some (lots of) optimization.

Make sure that all low-level QSG-objects are only accessed
in the rendering thread. This means that the wrapper has
to maintain a notion of "dirtiness" of the state. I.e.
which part of the QSG-objects have to be modified.

From the low-level wrapper derive a class that draws a rounded
rectangle for every resize. The child class of that must then
paint on the rectangle after every resize.

That looks all not very fortunate, but it displays a
legend and will make it possible to move the legend
without and drawing operations, only shifting around
an OpenGL surface.

The render thread goes through all chart-items and
rerenders them if dirty. Currently, on deletion
of these items, this list is not reset. I.e. currently
it is not supported to remove individual items.
Only the full scene can be cleared!

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-20 08:47:18 +01:00
Robert C. Helling
25cfd852b9 Add back central line for linear regression
Signed-off-by: Robert C. Helling <helling@atdotde.de>
2021-01-14 20:51:23 +01:00
Robert C. Helling
d6712bc5ac Plot proper confidence regions
I was coninced that that rather than doing an order of
magnitude estimate of the confidence region it's better
to have the correct concave shapes that indicate the
95% confidence level for the regression line.

It also turned out that the previous expression was
missing a factor of 1/sqrt(n).

Signed-off-by: Robert C. Helling <helling@atdotde.de>
2021-01-14 20:51:23 +01:00
Robert C. Helling
d83c9b5246 Indicate goodness of fit of regression line
The goodness of fit of a regression line is the percentage
of the variance of the y values that is explained by the
dependence on the x values.

Set the alpha value of the regression line to this goodness
of fit.

Further, set the width of the regression line to a standard
deviation of the values from the regression line valies.

Signed-off-by: Robert C. Helling <helling@atdotde.de>
2021-01-14 20:51:23 +01:00
Berthold Stoeger
e7907c494f statistics: convert chart to QQuickItem
It turns out that the wrong base class was used for the chart.
QQuickWidget can only be used on desktop, not in a mobile UI.

Therefore, turn this into a QQuickItem and move the container
QQuickWidget into desktop-only code.

Currently, this code is insane: The chart is rendered onto a
QGraphicsScene (as it was before), which is then rendered into
a QImage, which is transformed into a QSGTexture, which is then
projected onto the device. This is performed on every mouse
move event, since these events in general change the position
of the info-box.

The plan is to slowly convert elements such as the info-box into
QQuickItems. Browsing the QtQuick documentation, this will
not be much fun.

Also note that the rendering currently tears, flickers and has
antialiasing artifacts, most likely owing to integer (QImage)
to floating point (QGraphicsScene, QQuickItem) conversion
problems. The data flow is
QGraphicsScene (float) -> QImage (int) -> QQuickItem (float).

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-10 15:16:52 -08:00
Berthold Stoeger
405e6b6b69 statistics: fix chart features: regression line and median/mean
The coordinates of these were calculated when creating the feature.
This is wrong, because the min/max values of the axes can change
on resize to get "nice" number. Therefore, recalculate after resizing.
This means that the general "LineMarker" class has to be split into
two classes, one for regression lines and one for median/mean
markers.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-06 12:31:22 -08:00
Berthold Stoeger
ab324ed769 statistics: paint custom grid
With removal of QtCharts' axes, the grid was lost. Readd it.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-06 12:31:22 -08:00
Berthold Stoeger
4ab9f1c6b0 statistics: replace QtCharts' axes
Replace by custom implementation, with the ultimate goal to
remove the QtCharts module. This doesn't yet display axis
titles or a grid.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-01-06 12:31:22 -08:00
Berthold Stoeger
90129aa26f statistics: render title
Since we want to get rid of QtCharts, we have to render our own
title. Simply keep around a QGraphicsSimpleTextItem and put in
the center of the chart. Define the borders to the scene as
constants.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-01-06 12:31:22 -08:00
Berthold Stoeger
bea289e314 statistics: clip regression line
A steep regression line would shoot out of the chart. Therefore,
clip to the y = minY and y = maxY lines.

QtGraphicsScene has its own clipping routines, but they are
very general, so let's do this trivial case by hand.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-01-03 13:56:05 -08:00
Berthold Stoeger
995100a540 statistics: implement StatsView
The StatsView shows the chart described by the StatsState structure.
It is based on a QML ChartView. This should make it possible to
easily port to mobile. It does not include any of the UI around
the chart, viz. the variable and chart selection, etc.

The code checking for the statistical significance of the regression
line was written by Willem.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
Signed-off-by: willemferguson <willemferguson@zoology.up.ac.za>
2021-01-02 11:04:03 -08:00