summaryrefslogtreecommitdiffstats
path: root/src/charts/scatterchart/scatterchartitem.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/charts/scatterchart/scatterchartitem.cpp')
-rw-r--r--src/charts/scatterchart/scatterchartitem.cpp93
1 files changed, 83 insertions, 10 deletions
diff --git a/src/charts/scatterchart/scatterchartitem.cpp b/src/charts/scatterchart/scatterchartitem.cpp
index 3c9c8cfb..79eedc4d 100644
--- a/src/charts/scatterchart/scatterchartitem.cpp
+++ b/src/charts/scatterchart/scatterchartitem.cpp
@@ -50,17 +50,20 @@ ScatterChartItem::ScatterChartItem(QScatterSeries *series, QGraphicsItem *item)
m_items(this),
m_visible(true),
m_markerShape(QScatterSeries::MarkerShapeRectangle),
+ m_pointsVisible(true),
m_pointLabelsVisible(false),
m_markerSize(series->markerSize()),
m_pointLabelsFormat(series->pointLabelsFormat()),
m_pointLabelsFont(series->pointLabelsFont()),
m_pointLabelsColor(series->pointLabelsColor()),
m_pointLabelsClipping(true),
+ m_lastHoveredPoint(QPointF(qQNaN(), qQNaN())),
m_mousePressed(false)
{
connect(series->d_func(), &QXYSeriesPrivate::seriesUpdated,
this, &ScatterChartItem::handleSeriesUpdated);
connect(series, &QXYSeries::lightMarkerChanged, this, &ScatterChartItem::handleSeriesUpdated);
+ connect(series, &QXYSeries::selectedLightMarkerChanged, this, &ScatterChartItem::handleSeriesUpdated);
connect(series, &QXYSeries::markerSizeChanged, this, &ScatterChartItem::handleSeriesUpdated);
connect(series, &QXYSeries::visibleChanged, this, &ScatterChartItem::handleSeriesUpdated);
connect(series, &QXYSeries::opacityChanged, this, &ScatterChartItem::handleSeriesUpdated);
@@ -82,7 +85,7 @@ ScatterChartItem::ScatterChartItem(QScatterSeries *series, QGraphicsItem *item)
this, &ScatterChartItem::handleSeriesUpdated);
setZValue(ChartPresenter::ScatterSeriesZValue);
- setFlags(QGraphicsItem::ItemClipsChildrenToShape);
+ setFlags(QGraphicsItem::ItemClipsChildrenToShape | QGraphicsItem::ItemIsSelectable);
handleSeriesUpdated();
@@ -281,7 +284,7 @@ void ScatterChartItem::updateGeometry()
if (!m_visible || offGridStatus.at(i)) {
item->setVisible(false);
} else {
- bool drawPoint = true;
+ bool drawPoint = m_pointsVisible;
if (m_pointsConfiguration.contains(i)) {
const auto &conf = m_pointsConfiguration[i];
@@ -298,6 +301,9 @@ void ScatterChartItem::updateGeometry()
}
}
+ if (m_series->isPointSelected(i))
+ drawPoint = m_series->selectedLightMarker().isNull();
+
item->setVisible(drawPoint);
}
}
@@ -307,6 +313,64 @@ void ScatterChartItem::updateGeometry()
}
}
+void ScatterChartItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
+{
+ QPointF matchedP = matchForLightMarker(event->pos());
+ if (!qIsNaN(matchedP.x())) {
+ emit XYChart::pressed(matchedP);
+ m_lastMousePos = event->pos();
+ m_mousePressed = true;
+ } else {
+ event->ignore();
+ }
+
+ QGraphicsItem::mousePressEvent(event);
+}
+
+void ScatterChartItem::hoverMoveEvent(QGraphicsSceneHoverEvent *event)
+{
+ QPointF matchedP = matchForLightMarker(event->pos());
+ if (!qIsNaN(matchedP.x())) {
+ if (matchedP != m_lastHoveredPoint) {
+ if (!qIsNaN(m_lastHoveredPoint.x()))
+ emit XYChart::hovered(m_lastHoveredPoint, false);
+
+ m_lastHoveredPoint = matchedP;
+ emit XYChart::hovered(matchedP, true);
+ }
+ } else if (!qIsNaN(m_lastHoveredPoint.x())) {
+ emit XYChart::hovered(m_lastHoveredPoint, false);
+ m_lastHoveredPoint = QPointF(qQNaN(), qQNaN());
+ }
+
+ QGraphicsItem::hoverMoveEvent(event);
+}
+
+void ScatterChartItem::mouseReleaseEvent(QGraphicsSceneMouseEvent *event)
+{
+ QPointF result;
+ QPointF matchedP = matchForLightMarker(m_lastMousePos);
+ if (!qIsNaN(matchedP.x()) && m_mousePressed) {
+ result = matchedP;
+ emit XYChart::released(result);
+ emit XYChart::clicked(result);
+ }
+
+ m_mousePressed = false;
+ QGraphicsItem::mouseReleaseEvent(event);
+}
+
+void ScatterChartItem::mouseDoubleClickEvent(QGraphicsSceneMouseEvent *event)
+{
+ QPointF matchedP = matchForLightMarker(event->pos());
+ if (!qIsNaN(matchedP.x()))
+ emit XYChart::doubleClicked(matchedP);
+ else
+ emit XYChart::doubleClicked(domain()->calculateDomainPoint(m_lastMousePos));
+
+ QGraphicsItem::mouseDoubleClickEvent(event);
+}
+
void ScatterChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget)
{
Q_UNUSED(option);
@@ -315,8 +379,14 @@ void ScatterChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *
if (m_series->useOpenGL())
return;
- // Draw markers if a marker has been set (set to QImage() to disable)
- if (!m_series->lightMarker().isNull()) {
+ QRectF clipRect = QRectF(QPointF(0, 0), domain()->size());
+
+ painter->save();
+ painter->setClipRect(clipRect);
+
+ // Draw markers if a marker or marker for selected points only has been
+ // set (set to QImage() to disable)
+ if (!m_series->lightMarker().isNull() || !m_series->selectedLightMarker().isNull()) {
const QImage &marker = m_series->lightMarker();
const QImage &selectedMarker = m_series->selectedLightMarker();
qreal markerHalfSize = m_markerSize / 2.0;
@@ -326,7 +396,7 @@ void ScatterChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *
// light markers are independent features. Therefore m_pointsVisible
// is not used here as light markers are drawn if lightMarker is not null.
// However points visibility configuration can be still used here.
- bool drawPoint = true;
+ bool drawPoint = !m_series->lightMarker().isNull();
if (m_pointsConfiguration.contains(i)) {
const auto &conf = m_pointsConfiguration[i];
@@ -350,11 +420,6 @@ void ScatterChartItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *
}
}
- QRectF clipRect = QRectF(QPointF(0, 0), domain()->size());
-
- painter->save();
- painter->setClipRect(clipRect);
-
if (m_series->bestFitLineVisible())
m_series->d_func()->drawBestFitLine(painter, clipRect);
@@ -422,6 +487,7 @@ void ScatterChartItem::handleSeriesUpdated()
m_pointsConfigurationDirty = m_series->pointsConfiguration() != m_pointsConfiguration;
bool recreate = m_visible != m_series->isVisible()
+ || m_pointsVisible != m_series->pointsVisible()
|| m_markerSize != m_series->markerSize()
|| m_markerShape != m_series->markerShape()
|| m_selectedColor != m_series->selectedColor()
@@ -432,6 +498,7 @@ void ScatterChartItem::handleSeriesUpdated()
m_markerShape = m_series->markerShape();
setVisible(m_visible);
setOpacity(m_series->opacity());
+ m_pointsVisible = m_series->pointsVisible();
m_pointLabelsFormat = m_series->pointLabelsFormat();
m_pointLabelsVisible = m_series->pointLabelsVisible();
m_pointLabelsFont = m_series->pointLabelsFont();
@@ -451,6 +518,12 @@ void ScatterChartItem::handleSeriesUpdated()
updateGeometry();
}
+ // Only accept hover events when light/selection markers are in use so we don't unnecessarily
+ // eat the events in the regular case
+ setAcceptHoverEvents(!(m_series->lightMarker().isNull()
+ && (m_series->selectedLightMarker().isNull()
+ || m_series->selectedPoints().isEmpty())));
+
setPen(m_series->pen());
setBrush(m_series->brush());
// Update whole chart in case label clipping changed as labels can be outside series area