From 344870fb79e647b87aa79b9433eef8237c901e10 Mon Sep 17 00:00:00 2001 From: Mika Salmela Date: Tue, 3 Dec 2013 14:00:23 +0200 Subject: Better proxy API for surface Part 2, item change. More is on the way. Change-Id: Ic41f3a90b5a47502b741391ace990117ef2eaf80 Reviewed-by: Miikka Heikkinen --- .../engine/surface3dcontroller.cpp | 66 +++++++++++++++--- .../engine/surface3dcontroller_p.h | 9 ++- src/datavisualization/engine/surface3drenderer.cpp | 78 ++++++++++++++++------ src/datavisualization/engine/surface3drenderer_p.h | 3 +- 4 files changed, 123 insertions(+), 33 deletions(-) (limited to 'src/datavisualization/engine') diff --git a/src/datavisualization/engine/surface3dcontroller.cpp b/src/datavisualization/engine/surface3dcontroller.cpp index b1586a78..a9c5f508 100644 --- a/src/datavisualization/engine/surface3dcontroller.cpp +++ b/src/datavisualization/engine/surface3dcontroller.cpp @@ -37,8 +37,6 @@ Surface3DController::Surface3DController(QRect rect) m_renderer(0), m_selectedPoint(invalidSelectionPosition()), m_selectedSeries(0), - m_rowsChangeStartId(0), - m_rowsChangeCount(0), m_flatShadingSupported(true) { // Setting a null axis creates a new default axis according to orientation and graph type. @@ -84,8 +82,15 @@ void Surface3DController::synchDataToRenderer() } if (m_changeTracker.rowsChanged) { - m_renderer->updateRows(m_rowsChangeStartId, m_rowsChangeCount); + m_renderer->updateRows(m_changedRows); m_changeTracker.rowsChanged = false; + m_changedRows.clear(); + } + + if (m_changeTracker.itemChanged) { + m_renderer->updateItem(m_changedItems); + m_changeTracker.itemChanged = false; + m_changedItems.clear(); } if (m_changeTracker.selectedPointChanged) { @@ -320,16 +325,57 @@ void Surface3DController::handleFlatShadingSupportedChange(bool supported) void Surface3DController::handleRowsChanged(int startIndex, int count) { QSurfaceDataProxy *sender = static_cast(QObject::sender()); + if (m_changedRows.size() == 0) + m_changedRows.reserve(sender->rowCount()); + if (static_cast(m_seriesList.at(0)) == sender->series()) { // Change is for the visible series, put the change to queue - m_rowsChangeStartId = startIndex; - m_rowsChangeCount = count; - m_changeTracker.rowsChanged = true; + int oldChangeCount = m_changedRows.size(); + for (int i = 0; i < count; i++) { + bool newItem = true; + int candidate = startIndex + i; + for (int i = 0; i < oldChangeCount; i++) { + if (m_changedRows.at(i) == candidate) { + newItem = false; + break; + } + } + if (newItem) + m_changedRows.append(candidate); + } + if (m_changedRows.size()) { + m_changeTracker.rowsChanged = true; - adjustValueAxisRange(); - // Clear selection unless still valid - setSelectedPoint(m_selectedPoint, m_selectedSeries); - emitNeedRender(); + adjustValueAxisRange(); + // Clear selection unless still valid + setSelectedPoint(m_selectedPoint, m_selectedSeries); + emitNeedRender(); + } + } +} + +void Surface3DController::handleItemChanged(int rowIndex, int columnIndex) +{ + QSurfaceDataProxy *sender = static_cast(QObject::sender()); + if (static_cast(m_seriesList.at(0)) == sender->series()) { + // Change is for the visible series, put the change to queue + bool newItem = true; + QPoint candidate(columnIndex, rowIndex); + foreach (QPoint item, m_changedItems) { + if (item == candidate) { + newItem = false; + break; + } + } + if (newItem) { + m_changedItems.append(candidate); + m_changeTracker.itemChanged = true; + + adjustValueAxisRange(); + // Clear selection unless still valid + setSelectedPoint(m_selectedPoint, m_selectedSeries); + emitNeedRender(); + } } } diff --git a/src/datavisualization/engine/surface3dcontroller_p.h b/src/datavisualization/engine/surface3dcontroller_p.h index b9bd60a1..c7496c18 100644 --- a/src/datavisualization/engine/surface3dcontroller_p.h +++ b/src/datavisualization/engine/surface3dcontroller_p.h @@ -45,13 +45,15 @@ struct Surface3DChangeBitField { bool surfaceGridChanged : 1; bool selectedPointChanged : 1; bool rowsChanged : 1; + bool itemChanged : 1; Surface3DChangeBitField() : gradientColorChanged(false), // Set to false, as it is initially set in theme smoothStatusChanged(true), surfaceGridChanged(true), selectedPointChanged(true), - rowsChanged(true) + rowsChanged(false), + itemChanged(false) { } }; @@ -67,9 +69,9 @@ private: QPoint m_selectedPoint; QSurface3DSeries *m_selectedSeries; // Points to the series for which the point is selected in // single series selection cases. - int m_rowsChangeStartId; - int m_rowsChangeCount; bool m_flatShadingSupported; + QVector m_changedItems; + QVector m_changedRows; public: explicit Surface3DController(QRect rect); @@ -100,6 +102,7 @@ public: public slots: void handleArrayReset(); void handleRowsChanged(int startIndex, int count); + void handleItemChanged(int rowIndex, int columnIndex); // Renderer callback handlers void handlePointClicked(const QPoint &position, QSurface3DSeries *series); diff --git a/src/datavisualization/engine/surface3drenderer.cpp b/src/datavisualization/engine/surface3drenderer.cpp index 4942c4ae..81da15da 100644 --- a/src/datavisualization/engine/surface3drenderer.cpp +++ b/src/datavisualization/engine/surface3drenderer.cpp @@ -285,14 +285,8 @@ void Surface3DRenderer::updateSeries(const QList &seriesLis } } -void Surface3DRenderer::updateRows(int startIndex, int count) +void Surface3DRenderer::updateRows(const QVector &rows) { - // TODO: Properly support non-straight rows and columns (QTRD-2643) - if (startIndex > m_sampleSpace.height()) { - // No changes on visible area - return; - } - // Surface only supports single series for now, so we are only interested in the first series const QSurfaceDataArray *array = 0; if (m_visibleSeriesList.size()) { @@ -306,22 +300,68 @@ void Surface3DRenderer::updateRows(int startIndex, int count) if (array && array->size() >= 2 && array->at(0)->size() >= 2 && m_sampleSpace.width() >= 2 && m_sampleSpace.height() >= 2) { - int endRow = startIndex + count; - if (endRow > m_sampleSpace.height()) - endRow = m_sampleSpace.height(); + bool updateBuffers = false; + int sampleSpaceTop = m_sampleSpace.y() + m_sampleSpace.height(); + foreach (int row, rows) { + if (row >= m_sampleSpace.y() && row <= sampleSpaceTop) { + updateBuffers = true; + for (int j = 0; j < m_sampleSpace.width(); j++) + (*(m_dataArray.at(row - m_sampleSpace.y())))[j] = + array->at(row)->at(j + m_sampleSpace.x()); + + if (m_cachedFlatShading) { + m_surfaceObj->updateCoarseRow(m_dataArray, row - m_sampleSpace.y(), m_heightNormalizer, + m_axisCacheY.min()); + } else { + m_surfaceObj->updateSmoothRow(m_dataArray, row - m_sampleSpace.y(), m_heightNormalizer, + m_axisCacheY.min()); + } + } + } + if (updateBuffers) + m_surfaceObj->uploadBuffers(); + } + + updateSelectedPoint(m_selectedPoint, m_selectedSeries); +} - for (int i = startIndex; i < endRow; i++) { - for (int j = 0; j < m_sampleSpace.width(); j++) - (*(m_dataArray.at(i)))[j] = array->at(i + m_sampleSpace.y())->at(j + m_sampleSpace.x()); +void Surface3DRenderer::updateItem(const QVector &points) +{ + // TODO: Properly support non-straight rows and columns (QTRD-2643) + + // Surface only supports single series for now, so we are only interested in the first series + const QSurfaceDataArray *array = 0; + if (m_visibleSeriesList.size()) { + QSurface3DSeries *firstSeries = static_cast(m_visibleSeriesList.at(0).series()); + if (m_cachedSurfaceGridOn || m_cachedSurfaceVisible) { + QSurfaceDataProxy *dataProxy = firstSeries->dataProxy(); + if (dataProxy) + array = dataProxy->array(); } + } - if (!m_cachedFlatShading) { - m_surfaceObj->updateSmoothRows(m_dataArray, startIndex, endRow, m_heightNormalizer, - m_axisCacheY.min()); - } else { - m_surfaceObj->updateCoarseRows(m_dataArray, startIndex, endRow, m_heightNormalizer, - m_axisCacheY.min()); + if (array && array->size() >= 2 && array->at(0)->size() >= 2 && + m_sampleSpace.width() >= 2 && m_sampleSpace.height() >= 2) { + int sampleSpaceTop = m_sampleSpace.y() + m_sampleSpace.height(); + int sampleSpaceRight = m_sampleSpace.x() + m_sampleSpace.width(); + bool updateBuffers = false; + foreach (QPoint item, points) { + if (item.y() <= sampleSpaceTop && item.y() >= m_sampleSpace.y() && + item.x() <= sampleSpaceRight && item.x() >= m_sampleSpace.x()) { + updateBuffers = true; + int x = item.x() - m_sampleSpace.x(); + int y = item.y() - m_sampleSpace.y(); + (*(m_dataArray.at(y)))[x] = array->at(item.y())->at(item.x()); + + if (m_cachedFlatShading) { + m_surfaceObj->updateCoarseItem(m_dataArray, y, x, m_heightNormalizer, m_axisCacheY.min()); + } else { + m_surfaceObj->updateSmoothItem(m_dataArray, y, x, m_heightNormalizer, m_axisCacheY.min()); + } + } } + if (updateBuffers) + m_surfaceObj->uploadBuffers(); } updateSelectedPoint(m_selectedPoint, m_selectedSeries); diff --git a/src/datavisualization/engine/surface3drenderer_p.h b/src/datavisualization/engine/surface3drenderer_p.h index 476ef78e..37adb0b9 100644 --- a/src/datavisualization/engine/surface3drenderer_p.h +++ b/src/datavisualization/engine/surface3drenderer_p.h @@ -135,7 +135,8 @@ public: void updateData(); void updateSeries(const QList &seriesList, bool updateVisibility); - void updateRows(int startIndex, int count); + void updateRows(const QVector &rows); + void updateItem(const QVector &points); void updateScene(Q3DScene *scene); bool updateFlatStatus(bool enable); void updateSurfaceGridStatus(bool enable); -- cgit v1.2.3