mirror of https://github.com/qt/qtdatavis3d.git
Scatter data changing optimization.
No longer reset the entire render item array if single item changes, significantly speeding up this operation. Task-number: QTRD-2190 Change-Id: Ia3de833b761dc6f24acff581ad79668f51c3e9c5 Reviewed-by: Titta Heikkala <titta.heikkala@digia.com> Reviewed-by: Mika Salmela <mika.salmela@digia.com>
This commit is contained in:
parent
44b410f080
commit
13d1117087
|
|
@ -342,7 +342,7 @@ void Bars3DRenderer::updateRows(const QVector<Bars3DController::ChangeRow> &rows
|
|||
}
|
||||
}
|
||||
|
||||
void Bars3DRenderer::updateItems(const QVector<Bars3DController::ChangeItem> &points)
|
||||
void Bars3DRenderer::updateItems(const QVector<Bars3DController::ChangeItem> &items)
|
||||
{
|
||||
int minRow = m_axisCacheZ.min();
|
||||
int maxRow = m_axisCacheZ.max();
|
||||
|
|
@ -352,7 +352,7 @@ void Bars3DRenderer::updateItems(const QVector<Bars3DController::ChangeItem> &po
|
|||
const QBar3DSeries *prevSeries = 0;
|
||||
const QBarDataArray *dataArray = 0;
|
||||
|
||||
foreach (Bars3DController::ChangeItem item, points) {
|
||||
foreach (Bars3DController::ChangeItem item, items) {
|
||||
const int row = item.point.x();
|
||||
const int col = item.point.y();
|
||||
if (row < minRow || row > maxRow || col < minCol || col > maxCol)
|
||||
|
|
|
|||
|
|
@ -118,7 +118,7 @@ public:
|
|||
void updateSeries(const QList<QAbstract3DSeries *> &seriesList);
|
||||
SeriesRenderCache *createNewCache(QAbstract3DSeries *series);
|
||||
void updateRows(const QVector<Bars3DController::ChangeRow> &rows);
|
||||
void updateItems(const QVector<Bars3DController::ChangeItem> &points);
|
||||
void updateItems(const QVector<Bars3DController::ChangeItem> &items);
|
||||
void updateScene(Q3DScene *scene);
|
||||
void render(GLuint defaultFboHandle = 0);
|
||||
|
||||
|
|
|
|||
|
|
@ -71,6 +71,12 @@ void Scatter3DController::synchDataToRenderer()
|
|||
Abstract3DController::synchDataToRenderer();
|
||||
|
||||
// Notify changes to renderer
|
||||
if (m_changeTracker.itemChanged) {
|
||||
m_renderer->updateItems(m_changedItems);
|
||||
m_changeTracker.itemChanged = false;
|
||||
m_changedItems.clear();
|
||||
}
|
||||
|
||||
if (m_changeTracker.selectedItemChanged) {
|
||||
m_renderer->updateSelectedItem(m_selectedItem, m_selectedItemSeries);
|
||||
m_changeTracker.selectedItemChanged = false;
|
||||
|
|
@ -144,17 +150,35 @@ void Scatter3DController::handleItemsAdded(int startIndex, int count)
|
|||
|
||||
void Scatter3DController::handleItemsChanged(int startIndex, int count)
|
||||
{
|
||||
Q_UNUSED(startIndex)
|
||||
Q_UNUSED(count)
|
||||
QScatter3DSeries *series = static_cast<QScatterDataProxy *>(sender())->series();
|
||||
if (series->isVisible()) {
|
||||
adjustAxisRanges();
|
||||
m_isDataDirty = true;
|
||||
series->d_ptr->markItemLabelDirty();
|
||||
int oldChangeCount = m_changedItems.size();
|
||||
if (!oldChangeCount)
|
||||
m_changedItems.reserve(count);
|
||||
|
||||
for (int i = 0; i < count; i++) {
|
||||
bool newItem = true;
|
||||
int candidate = startIndex + i;
|
||||
for (int j = 0; j < oldChangeCount; j++) {
|
||||
const ChangeItem &oldChangeItem = m_changedItems.at(j);
|
||||
if (oldChangeItem.index == candidate && series == oldChangeItem.series) {
|
||||
newItem = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (newItem) {
|
||||
ChangeItem newChangeItem = {series, candidate};
|
||||
m_changedItems.append(newChangeItem);
|
||||
if (series == m_selectedItemSeries && m_selectedItem == candidate)
|
||||
series->d_ptr->markItemLabelDirty();
|
||||
}
|
||||
}
|
||||
|
||||
if (count) {
|
||||
m_changeTracker.itemChanged = true;
|
||||
if (series->isVisible())
|
||||
adjustAxisRanges();
|
||||
emitNeedRender();
|
||||
}
|
||||
if (!m_changedSeriesList.contains(series))
|
||||
m_changedSeriesList.append(series);
|
||||
emitNeedRender();
|
||||
}
|
||||
|
||||
void Scatter3DController::handleItemsRemoved(int startIndex, int count)
|
||||
|
|
|
|||
|
|
@ -40,9 +40,11 @@ class QScatter3DSeries;
|
|||
|
||||
struct Scatter3DChangeBitField {
|
||||
bool selectedItemChanged : 1;
|
||||
bool itemChanged : 1;
|
||||
|
||||
Scatter3DChangeBitField() :
|
||||
selectedItemChanged(true)
|
||||
selectedItemChanged(true),
|
||||
itemChanged(false)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
|
@ -51,8 +53,14 @@ class QT_DATAVISUALIZATION_EXPORT Scatter3DController : public Abstract3DControl
|
|||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
struct ChangeItem {
|
||||
QScatter3DSeries *series;
|
||||
int index;
|
||||
};
|
||||
private:
|
||||
Scatter3DChangeBitField m_changeTracker;
|
||||
QVector<ChangeItem> m_changedItems;
|
||||
|
||||
// Rendering
|
||||
Scatter3DRenderer *m_renderer;
|
||||
|
|
|
|||
|
|
@ -165,12 +165,6 @@ void Scatter3DRenderer::initializeOpenGL()
|
|||
void Scatter3DRenderer::updateData()
|
||||
{
|
||||
calculateSceneScalingFactors();
|
||||
float minX = float(m_axisCacheX.min());
|
||||
float maxX = float(m_axisCacheX.max());
|
||||
float minY = float(m_axisCacheY.min());
|
||||
float maxY = float(m_axisCacheY.max());
|
||||
float minZ = float(m_axisCacheZ.min());
|
||||
float maxZ = float(m_axisCacheZ.max());
|
||||
int totalDataSize = 0;
|
||||
|
||||
foreach (SeriesRenderCache *baseCache, m_renderCacheList) {
|
||||
|
|
@ -185,23 +179,8 @@ void Scatter3DRenderer::updateData()
|
|||
if (dataSize != renderArray.size())
|
||||
renderArray.resize(dataSize);
|
||||
|
||||
for (int i = 0; i < dataSize; i++) {
|
||||
QVector3D dotPos = dataArray.at(i).position();
|
||||
ScatterRenderItem &renderItem = renderArray[i];
|
||||
if ((dotPos.x() >= minX && dotPos.x() <= maxX )
|
||||
&& (dotPos.y() >= minY && dotPos.y() <= maxY)
|
||||
&& (dotPos.z() >= minZ && dotPos.z() <= maxZ)) {
|
||||
renderItem.setPosition(dotPos);
|
||||
renderItem.setVisible(true);
|
||||
if (!dataArray.at(i).rotation().isIdentity())
|
||||
renderItem.setRotation(dataArray.at(i).rotation().normalized());
|
||||
else
|
||||
renderItem.setRotation(identityQuaternion);
|
||||
calculateTranslation(renderItem);
|
||||
} else {
|
||||
renderItem.setVisible(false);
|
||||
}
|
||||
}
|
||||
for (int i = 0; i < dataSize; i++)
|
||||
updateRenderItem(dataArray.at(i), renderArray[i]);
|
||||
cache->setDataDirty(false);
|
||||
}
|
||||
}
|
||||
|
|
@ -272,6 +251,30 @@ SeriesRenderCache *Scatter3DRenderer::createNewCache(QAbstract3DSeries *series)
|
|||
return new ScatterSeriesRenderCache(series, this);
|
||||
}
|
||||
|
||||
void Scatter3DRenderer::updateItems(const QVector<Scatter3DController::ChangeItem> &items)
|
||||
{
|
||||
ScatterSeriesRenderCache *cache = 0;
|
||||
const QScatter3DSeries *prevSeries = 0;
|
||||
const QScatterDataArray *dataArray = 0;
|
||||
|
||||
foreach (Scatter3DController::ChangeItem item, items) {
|
||||
QScatter3DSeries *currentSeries = item.series;
|
||||
if (currentSeries != prevSeries) {
|
||||
cache = static_cast<ScatterSeriesRenderCache *>(m_renderCacheList.value(currentSeries));
|
||||
prevSeries = currentSeries;
|
||||
dataArray = item.series->dataProxy()->array();
|
||||
// Invisible series render caches are not updated, but instead just marked dirty, so that
|
||||
// they can be completely recalculated when they are turned visible.
|
||||
if (!cache->isVisible() && !cache->dataDirty())
|
||||
cache->setDataDirty(true);
|
||||
}
|
||||
if (cache->isVisible()) {
|
||||
const int index = item.index;
|
||||
updateRenderItem(dataArray->at(index), cache->renderArray()[index]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Scatter3DRenderer::updateScene(Q3DScene *scene)
|
||||
{
|
||||
scene->activeCamera()->d_ptr->setMinYRotation(-90.0f);
|
||||
|
|
@ -1802,6 +1805,24 @@ void Scatter3DRenderer::selectionColorToSeriesAndIndex(const QVector4D &color,
|
|||
series = 0;
|
||||
}
|
||||
|
||||
void Scatter3DRenderer::updateRenderItem(const QScatterDataItem &dataItem, ScatterRenderItem &renderItem)
|
||||
{
|
||||
QVector3D dotPos = dataItem.position();
|
||||
if ((dotPos.x() >= m_axisCacheX.min() && dotPos.x() <= m_axisCacheX.max() )
|
||||
&& (dotPos.y() >= m_axisCacheY.min() && dotPos.y() <= m_axisCacheY.max())
|
||||
&& (dotPos.z() >= m_axisCacheZ.min() && dotPos.z() <= m_axisCacheZ.max())) {
|
||||
renderItem.setPosition(dotPos);
|
||||
renderItem.setVisible(true);
|
||||
if (!dataItem.rotation().isIdentity())
|
||||
renderItem.setRotation(dataItem.rotation().normalized());
|
||||
else
|
||||
renderItem.setRotation(identityQuaternion);
|
||||
calculateTranslation(renderItem);
|
||||
} else {
|
||||
renderItem.setVisible(false);
|
||||
}
|
||||
}
|
||||
|
||||
QVector3D Scatter3DRenderer::convertPositionToTranslation(const QVector3D &position) {
|
||||
float xTrans = m_axisCacheX.positionAt(position.x());
|
||||
float yTrans = m_axisCacheY.positionAt(position.y());
|
||||
|
|
|
|||
|
|
@ -105,6 +105,7 @@ public:
|
|||
void updateData();
|
||||
void updateSeries(const QList<QAbstract3DSeries *> &seriesList);
|
||||
SeriesRenderCache *createNewCache(QAbstract3DSeries *series);
|
||||
void updateItems(const QVector<Scatter3DController::ChangeItem> &items);
|
||||
void updateScene(Q3DScene *scene);
|
||||
|
||||
QVector3D convertPositionToTranslation(const QVector3D &position);
|
||||
|
|
@ -154,6 +155,7 @@ public slots:
|
|||
private:
|
||||
void selectionColorToSeriesAndIndex(const QVector4D &color, int &index,
|
||||
QAbstract3DSeries *&series);
|
||||
inline void updateRenderItem(const QScatterDataItem &dataItem, ScatterRenderItem &renderItem);
|
||||
};
|
||||
|
||||
QT_END_NAMESPACE_DATAVISUALIZATION
|
||||
|
|
|
|||
|
|
@ -123,6 +123,9 @@ int main(int argc, char **argv)
|
|||
QPushButton *massiveDataTestButton = new QPushButton(widget);
|
||||
massiveDataTestButton->setText(QStringLiteral("Massive data test"));
|
||||
|
||||
QPushButton *testItemChangesButton = new QPushButton(widget);
|
||||
testItemChangesButton->setText(QStringLiteral("Test Item changing"));
|
||||
|
||||
QLinearGradient grBtoY(0, 0, 100, 0);
|
||||
grBtoY.setColorAt(1.0, Qt::black);
|
||||
grBtoY.setColorAt(0.67, Qt::blue);
|
||||
|
|
@ -137,6 +140,12 @@ int main(int argc, char **argv)
|
|||
gradientBtoYPB->setIcon(QIcon(pm));
|
||||
gradientBtoYPB->setIconSize(QSize(100, 24));
|
||||
|
||||
QLabel *fpsLabel = new QLabel(QStringLiteral(""));
|
||||
|
||||
QCheckBox *fpsCheckBox = new QCheckBox(widget);
|
||||
fpsCheckBox->setText(QStringLiteral("Measure Fps"));
|
||||
fpsCheckBox->setChecked(false);
|
||||
|
||||
QCheckBox *backgroundCheckBox = new QCheckBox(widget);
|
||||
backgroundCheckBox->setText(QStringLiteral("Show background"));
|
||||
backgroundCheckBox->setChecked(true);
|
||||
|
|
@ -232,9 +241,12 @@ int main(int argc, char **argv)
|
|||
vLayout->addWidget(toggleSeriesVisibilityButton, 0, Qt::AlignTop);
|
||||
vLayout->addWidget(changeSeriesNameButton, 0, Qt::AlignTop);
|
||||
vLayout->addWidget(startTimerButton, 0, Qt::AlignTop);
|
||||
vLayout->addWidget(massiveDataTestButton, 1, Qt::AlignTop);
|
||||
vLayout->addWidget(massiveDataTestButton, 0, Qt::AlignTop);
|
||||
vLayout->addWidget(testItemChangesButton, 1, Qt::AlignTop);
|
||||
|
||||
vLayout2->addWidget(gradientBtoYPB, 0, Qt::AlignTop);
|
||||
vLayout2->addWidget(fpsLabel, 0, Qt::AlignTop);
|
||||
vLayout2->addWidget(fpsCheckBox, 0, Qt::AlignTop);
|
||||
vLayout2->addWidget(backgroundCheckBox);
|
||||
vLayout2->addWidget(gridCheckBox);
|
||||
vLayout2->addWidget(new QLabel(QStringLiteral("Adjust shadow quality")));
|
||||
|
|
@ -302,6 +314,8 @@ int main(int argc, char **argv)
|
|||
&ScatterDataModifier::startStopTimer);
|
||||
QObject::connect(massiveDataTestButton, &QPushButton::clicked, modifier,
|
||||
&ScatterDataModifier::massiveDataTest);
|
||||
QObject::connect(testItemChangesButton, &QPushButton::clicked, modifier,
|
||||
&ScatterDataModifier::testItemChanges);
|
||||
QObject::connect(gradientBtoYPB, &QPushButton::clicked, modifier,
|
||||
&ScatterDataModifier::setGradient);
|
||||
QObject::connect(themeButton, &QPushButton::clicked, modifier,
|
||||
|
|
@ -316,6 +330,8 @@ int main(int argc, char **argv)
|
|||
QObject::connect(fontList, &QFontComboBox::currentFontChanged, modifier,
|
||||
&ScatterDataModifier::changeFont);
|
||||
|
||||
QObject::connect(fpsCheckBox, &QCheckBox::stateChanged, modifier,
|
||||
&ScatterDataModifier::setFpsMeasurement);
|
||||
QObject::connect(backgroundCheckBox, &QCheckBox::stateChanged, modifier,
|
||||
&ScatterDataModifier::setBackgroundEnabled);
|
||||
QObject::connect(gridCheckBox, &QCheckBox::stateChanged, modifier,
|
||||
|
|
@ -335,6 +351,8 @@ int main(int argc, char **argv)
|
|||
&ScatterDataModifier::setMaxZ);
|
||||
|
||||
|
||||
modifier->setFpsLabel(fpsLabel);
|
||||
|
||||
modifier->start();
|
||||
|
||||
return app.exec();
|
||||
|
|
|
|||
|
|
@ -134,7 +134,6 @@ void ScatterDataModifier::massiveDataTest()
|
|||
xAxis->setSegmentCount(1);
|
||||
yAxis->setSegmentCount(1);
|
||||
zAxis->setSegmentCount(1);
|
||||
m_chart->setMeasureFps(true);
|
||||
m_chart->setAxisX(xAxis);
|
||||
m_chart->setAxisY(yAxis);
|
||||
m_chart->setAxisZ(zAxis);
|
||||
|
|
@ -231,6 +230,187 @@ void ScatterDataModifier::massiveTestAppendAndScroll()
|
|||
m_chart->axisZ()->setRange(min, max);
|
||||
}
|
||||
|
||||
void ScatterDataModifier::setFpsMeasurement(bool enable)
|
||||
{
|
||||
m_chart->setMeasureFps(enable);
|
||||
}
|
||||
|
||||
void ScatterDataModifier::testItemChanges()
|
||||
{
|
||||
static int counter = 0;
|
||||
const int rowCount = 12;
|
||||
const int colCount = 10;
|
||||
static QScatter3DSeries *series0 = 0;
|
||||
static QScatter3DSeries *series1 = 0;
|
||||
static QScatter3DSeries *series2 = 0;
|
||||
|
||||
switch (counter) {
|
||||
case 0: {
|
||||
qDebug() << __FUNCTION__ << counter << "Setup test";
|
||||
foreach (QScatter3DSeries *series, m_chart->seriesList())
|
||||
m_chart->removeSeries(series);
|
||||
foreach (QValue3DAxis *axis, m_chart->axes())
|
||||
m_chart->releaseAxis(axis);
|
||||
delete series0;
|
||||
delete series1;
|
||||
delete series2;
|
||||
series0 = new QScatter3DSeries;
|
||||
series1 = new QScatter3DSeries;
|
||||
series2 = new QScatter3DSeries;
|
||||
populateFlatSeries(series0, rowCount, colCount, 10.0f);
|
||||
populateFlatSeries(series1, rowCount, colCount, 30.0f);
|
||||
populateFlatSeries(series2, rowCount, colCount, 50.0f);
|
||||
m_chart->axisX()->setRange(3.0f, 6.0f);
|
||||
m_chart->axisY()->setRange(0.0f, 100.0f);
|
||||
m_chart->axisZ()->setRange(4.0f, 8.0f);
|
||||
m_chart->addSeries(series0);
|
||||
m_chart->addSeries(series1);
|
||||
m_chart->addSeries(series2);
|
||||
}
|
||||
break;
|
||||
case 1: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change single item, unselected";
|
||||
int itemIndex = 3 * colCount + 5;
|
||||
QScatterDataItem item = *series0->dataProxy()->itemAt(itemIndex);
|
||||
item.setY(75.0f);
|
||||
series0->dataProxy()->setItem(itemIndex, item);
|
||||
}
|
||||
break;
|
||||
case 2: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change single item, selected";
|
||||
int itemIndex = 4 * colCount + 4;
|
||||
series1->setSelectedItem(itemIndex);
|
||||
QScatterDataItem item = *series1->dataProxy()->itemAt(itemIndex);
|
||||
item.setY(75.0f);
|
||||
series1->dataProxy()->setItem(itemIndex, item);
|
||||
}
|
||||
break;
|
||||
case 3: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change item outside visible area";
|
||||
int itemIndex = 2;
|
||||
QScatterDataItem item = *series1->dataProxy()->itemAt(itemIndex);
|
||||
item.setY(75.0f);
|
||||
series1->dataProxy()->setItem(itemIndex, item);
|
||||
}
|
||||
break;
|
||||
case 4: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change single item from two series, unselected";
|
||||
int itemIndex = 4 * colCount + 6;
|
||||
QScatterDataItem item0 = *series0->dataProxy()->itemAt(itemIndex);
|
||||
QScatterDataItem item1 = *series1->dataProxy()->itemAt(itemIndex);
|
||||
item0.setY(65.0f);
|
||||
item1.setY(85.0f);
|
||||
series0->dataProxy()->setItem(itemIndex, item0);
|
||||
series1->dataProxy()->setItem(itemIndex, item1);
|
||||
}
|
||||
break;
|
||||
case 5: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change single item from two series, one selected";
|
||||
int itemIndex0 = 5 * colCount + 5;
|
||||
int itemIndex1 = 4 * colCount + 4;
|
||||
QScatterDataItem item0 = *series0->dataProxy()->itemAt(itemIndex0);
|
||||
QScatterDataItem item1 = *series1->dataProxy()->itemAt(itemIndex1);
|
||||
item0.setY(65.0f);
|
||||
item1.setY(85.0f);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
series1->dataProxy()->setItem(itemIndex1, item1);
|
||||
}
|
||||
break;
|
||||
case 6: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change single item from two series, one outside range";
|
||||
int itemIndex0 = 6 * colCount + 6;
|
||||
int itemIndex1 = 9 * colCount + 2;
|
||||
QScatterDataItem item0 = *series0->dataProxy()->itemAt(itemIndex0);
|
||||
QScatterDataItem item1 = *series1->dataProxy()->itemAt(itemIndex1);
|
||||
item0.setY(65.0f);
|
||||
item1.setY(85.0f);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
series1->dataProxy()->setItem(itemIndex1, item1);
|
||||
}
|
||||
break;
|
||||
case 7: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change single item from two series, both outside range";
|
||||
int itemIndex0 = 1 * colCount + 3;
|
||||
int itemIndex1 = 9 * colCount + 2;
|
||||
QScatterDataItem item0 = *series0->dataProxy()->itemAt(itemIndex0);
|
||||
QScatterDataItem item1 = *series1->dataProxy()->itemAt(itemIndex1);
|
||||
item0.setY(65.0f);
|
||||
item1.setY(85.0f);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
series1->dataProxy()->setItem(itemIndex1, item1);
|
||||
}
|
||||
break;
|
||||
case 8: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change item to same value as previously";
|
||||
int itemIndex0 = 5 * colCount + 7;
|
||||
int itemIndex1 = 4 * colCount + 7;
|
||||
QScatterDataItem item0 = *series0->dataProxy()->itemAt(itemIndex0);
|
||||
QScatterDataItem item1 = *series1->dataProxy()->itemAt(itemIndex1);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
series1->dataProxy()->setItem(itemIndex1, item1);
|
||||
}
|
||||
break;
|
||||
case 9: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change 3 items on each series";
|
||||
int itemIndex0 = 5 * colCount + 6;
|
||||
int itemIndex1 = 4 * colCount + 6;
|
||||
QScatterDataItem item00 = *series0->dataProxy()->itemAt(itemIndex0);
|
||||
QScatterDataItem item01 = *series0->dataProxy()->itemAt(itemIndex0 + 1);
|
||||
QScatterDataItem item02 = *series0->dataProxy()->itemAt(itemIndex0 + 2);
|
||||
QScatterDataItem item10 = *series1->dataProxy()->itemAt(itemIndex1);
|
||||
QScatterDataItem item11 = *series1->dataProxy()->itemAt(itemIndex1 + 1);
|
||||
QScatterDataItem item12 = *series1->dataProxy()->itemAt(itemIndex1 + 2);
|
||||
item00.setY(65.0f);
|
||||
item01.setY(70.0f);
|
||||
item02.setY(75.0f);
|
||||
item10.setY(80.0f);
|
||||
item11.setY(85.0f);
|
||||
item12.setY(90.0f);
|
||||
series0->dataProxy()->setItem(itemIndex0, item00);
|
||||
series0->dataProxy()->setItem(itemIndex0 + 1, item01);
|
||||
series0->dataProxy()->setItem(itemIndex0 + 2, item02);
|
||||
series1->dataProxy()->setItem(itemIndex1, item10);
|
||||
series1->dataProxy()->setItem(itemIndex1 + 1, item11);
|
||||
series1->dataProxy()->setItem(itemIndex1 + 2, item12);
|
||||
}
|
||||
break;
|
||||
case 10: {
|
||||
qDebug() << __FUNCTION__ << counter << "Level the field single item at a time";
|
||||
QScatterDataItem item;
|
||||
for (int i = 0; i < rowCount; i++) {
|
||||
for (int j = 0; j < colCount; j++) {
|
||||
int itemIndex = i * colCount + j;
|
||||
QScatterDataItem item0 = *series0->dataProxy()->itemAt(itemIndex);
|
||||
QScatterDataItem item1 = *series1->dataProxy()->itemAt(itemIndex);
|
||||
QScatterDataItem item2 = *series2->dataProxy()->itemAt(itemIndex);
|
||||
item0.setY(10.0f);
|
||||
item1.setY(15.0f);
|
||||
item2.setY(20.0f);
|
||||
series0->dataProxy()->setItem(itemIndex, item0);
|
||||
series1->dataProxy()->setItem(itemIndex, item1);
|
||||
series2->dataProxy()->setItem(itemIndex, item2);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 11: {
|
||||
qDebug() << __FUNCTION__ << counter << "Change same items multiple times";
|
||||
int itemIndex0 = 6 * colCount + 6;
|
||||
QScatterDataItem item0 = *series0->dataProxy()->itemAt(itemIndex0);
|
||||
item0.setY(90.0f);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
series0->dataProxy()->setItem(itemIndex0, item0);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
qDebug() << __FUNCTION__ << "Resetting test";
|
||||
counter = -1;
|
||||
}
|
||||
counter++;
|
||||
}
|
||||
|
||||
void ScatterDataModifier::addData()
|
||||
{
|
||||
// Add labels
|
||||
|
|
@ -673,7 +853,8 @@ void ScatterDataModifier::handleAxisZChanged(QValue3DAxis *axis)
|
|||
|
||||
void ScatterDataModifier::handleFpsChange(qreal fps)
|
||||
{
|
||||
qDebug() << "FPS:" << fps;
|
||||
static const QString fpsPrefix(QStringLiteral("FPS: "));
|
||||
m_fpsLabel->setText(fpsPrefix + QString::number(qRound(fps)));
|
||||
}
|
||||
|
||||
void ScatterDataModifier::changeShadowQuality(int quality)
|
||||
|
|
@ -757,3 +938,15 @@ QScatter3DSeries *ScatterDataModifier::createAndAddSeries()
|
|||
|
||||
return series;
|
||||
}
|
||||
|
||||
void ScatterDataModifier::populateFlatSeries(QScatter3DSeries *series, int rows, int columns,
|
||||
float value)
|
||||
{
|
||||
QScatterDataArray *dataArray = new QScatterDataArray;
|
||||
dataArray->resize(rows * columns);
|
||||
for (int i = 0; i < rows; i++) {
|
||||
for (int j = 0; j < columns; j++)
|
||||
(*dataArray)[i * columns + j].setPosition(QVector3D(float(i), value, float(j)));
|
||||
}
|
||||
series->dataProxy()->resetArray(dataArray);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -25,6 +25,7 @@
|
|||
#include <QFont>
|
||||
#include <QDebug>
|
||||
#include <QTimer>
|
||||
#include <QLabel>
|
||||
|
||||
using namespace QtDataVisualization;
|
||||
|
||||
|
|
@ -55,6 +56,9 @@ public:
|
|||
void massiveDataTest();
|
||||
void massiveTestScroll();
|
||||
void massiveTestAppendAndScroll();
|
||||
void setFpsMeasurement(bool enable);
|
||||
void setFpsLabel(QLabel *fpsLabel) { m_fpsLabel = fpsLabel; }
|
||||
void testItemChanges();
|
||||
|
||||
public slots:
|
||||
void changeShadowQuality(int quality);
|
||||
|
|
@ -91,6 +95,7 @@ signals:
|
|||
private:
|
||||
QVector3D randVector();
|
||||
QScatter3DSeries *createAndAddSeries();
|
||||
void populateFlatSeries(QScatter3DSeries *series, int rows, int columns, float value);
|
||||
|
||||
Q3DScatter *m_chart;
|
||||
int m_fontSize;
|
||||
|
|
@ -99,6 +104,7 @@ private:
|
|||
int m_selectedItem;
|
||||
QScatter3DSeries *m_targetSeries;
|
||||
QScatterDataArray m_massiveTestCacheArray;
|
||||
QLabel *m_fpsLabel;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
Loading…
Reference in New Issue