diff options
author | Antti Määttä <antti.maatta@qt.io> | 2017-03-20 14:50:32 +0200 |
---|---|---|
committer | Antti Määttä <antti.maatta@qt.io> | 2017-03-23 13:45:10 +0000 |
commit | d18d6cb1989cf6925015da3860439e50e57bc30d (patch) | |
tree | ce776a7d366ef8b4738e53d0d7541223c670dc70 /tests | |
parent | a2adf9df3b0c31f7f7661a1f705b591c5b259ff8 (diff) |
Fix scene2d mouse event coordinate calculation
Apply the window size and use correct texture coordinates.
Task-number: QTBUG-57253
Change-Id: Ibc5f7ef878baf938b1b3e3b7cfb4eba2cea38ad6
Reviewed-by: Shawn Rutledge <shawn.rutledge@qt.io>
Reviewed-by: Sean Harmer <sean.harmer@kdab.com>
Diffstat (limited to 'tests')
-rw-r--r-- | tests/auto/render/commons/testrenderer.cpp | 1 | ||||
-rw-r--r-- | tests/auto/render/commons/testrenderer.h | 5 | ||||
-rw-r--r-- | tests/auto/render/scene2d/tst_scene2d.cpp | 289 |
3 files changed, 293 insertions, 2 deletions
diff --git a/tests/auto/render/commons/testrenderer.cpp b/tests/auto/render/commons/testrenderer.cpp index f318797ca..5304ff142 100644 --- a/tests/auto/render/commons/testrenderer.cpp +++ b/tests/auto/render/commons/testrenderer.cpp @@ -32,6 +32,7 @@ QT_BEGIN_NAMESPACE TestRenderer::TestRenderer() : m_changes(0) + , m_managers(nullptr) { } diff --git a/tests/auto/render/commons/testrenderer.h b/tests/auto/render/commons/testrenderer.h index ecbec4aa3..74f529fa0 100644 --- a/tests/auto/render/commons/testrenderer.h +++ b/tests/auto/render/commons/testrenderer.h @@ -43,10 +43,10 @@ public: API api() const Q_DECL_OVERRIDE { return AbstractRenderer::OpenGL; } qint64 time() const Q_DECL_OVERRIDE { return 0; } void setTime(qint64 time) Q_DECL_OVERRIDE { Q_UNUSED(time); } - void setNodeManagers(Qt3DRender::Render::NodeManagers *managers) Q_DECL_OVERRIDE { Q_UNUSED(managers); } + void setNodeManagers(Qt3DRender::Render::NodeManagers *m) Q_DECL_OVERRIDE { m_managers = m; } void setServices(Qt3DCore::QServiceLocator *services) Q_DECL_OVERRIDE { Q_UNUSED(services); } void setSurfaceExposed(bool exposed) Q_DECL_OVERRIDE { Q_UNUSED(exposed); } - Qt3DRender::Render::NodeManagers *nodeManagers() const Q_DECL_OVERRIDE { return nullptr; } + Qt3DRender::Render::NodeManagers *nodeManagers() const Q_DECL_OVERRIDE { return m_managers; } Qt3DCore::QServiceLocator *services() const Q_DECL_OVERRIDE { return nullptr; } void initialize() Q_DECL_OVERRIDE {} void shutdown() Q_DECL_OVERRIDE {} @@ -81,6 +81,7 @@ public: protected: Qt3DRender::Render::AbstractRenderer::BackendNodeDirtySet m_changes; + Qt3DRender::Render::NodeManagers *m_managers; }; QT_END_NAMESPACE diff --git a/tests/auto/render/scene2d/tst_scene2d.cpp b/tests/auto/render/scene2d/tst_scene2d.cpp index b53318e7c..d0bd5ca9d 100644 --- a/tests/auto/render/scene2d/tst_scene2d.cpp +++ b/tests/auto/render/scene2d/tst_scene2d.cpp @@ -30,13 +30,69 @@ #include <Qt3DQuickScene2D/qscene2d.h> #include <private/qscene2d_p.h> #include <private/scene2d_p.h> +#include <Qt3DRender/qgeometryrenderer.h> +#include <Qt3DRender/qbuffer.h> +#include <private/trianglesvisitor_p.h> +#include <private/nodemanagers_p.h> +#include <private/managers_p.h> +#include <private/geometryrenderer_p.h> +#include <private/geometryrenderermanager_p.h> +#include <private/buffermanager_p.h> +#include <Qt3DRender/qpicktriangleevent.h> +#include <private/qpickevent_p.h> #include <Qt3DCore/qpropertyupdatedchange.h> #include <qbackendnodetester.h> #include "testrenderer.h" using namespace Qt3DRender::Quick; +using namespace Qt3DRender::Render; using namespace Qt3DRender::Render::Quick; +bool qFuzzyComparePointF(const QPointF& a, const QPointF& b) { + return qFuzzyCompare(a.x(), b.x()) && qFuzzyCompare(a.y(), b.y()); +} + +class TestWindow : public QQuickWindow +{ + Q_OBJECT +public: + TestWindow() + : QQuickWindow() + { + + } + + bool event(QEvent *e) Q_DECL_OVERRIDE + { + if (e->type() >= QEvent::MouseButtonPress && + e->type() <= QEvent::MouseMove) { + QMouseEvent *me = static_cast<QMouseEvent *>(e); + m_eventTypes.push_back(e->type()); + m_mousePoints.push_back(me->localPos()); + } + return QQuickWindow::event(e); + } + + bool verifyEventPos(uint index, QEvent::Type type, const QPointF& pos) + { + if (index >= unsigned(m_eventTypes.size()) || + m_eventTypes[index] != type || + !qFuzzyComparePointF(pos, m_mousePoints[index])) + return false; + return true; + } + + void clear() + { + m_eventTypes.clear(); + m_mousePoints.clear(); + } + +private: + QVector<QEvent::Type> m_eventTypes; + QVector<QPointF> m_mousePoints; +}; + class tst_Scene2D : public Qt3DCore::QBackendNodeTester { Q_OBJECT @@ -154,6 +210,239 @@ private Q_SLOTS: backendScene2d->cleanup(); } + + void testCoordinateCalculation() + { + // GIVEN + QScopedPointer<TestWindow> testWindow(new TestWindow()); + Scene2DSharedObjectPtr sharedObject(new Scene2DSharedObject(nullptr)); + QScopedPointer<Scene2D> scene2d(new Scene2D()); + QScopedPointer<NodeManagers> nodeManagers(new NodeManagers()); + Qt3DRender::QGeometry *geometry = new Qt3DRender::QGeometry(); + Qt3DRender::QGeometryRenderer *geometryRenderer = new Qt3DRender::QGeometryRenderer(); + Qt3DRender::QAttribute *positionAttribute = new Qt3DRender::QAttribute(); + Qt3DRender::QAttribute *texcoordAttribute = new Qt3DRender::QAttribute(); + Qt3DRender::QBuffer *dataBuffer =new Qt3DRender::QBuffer(); + QScopedPointer<Qt3DCore::QEntity> entity(new Qt3DCore::QEntity()); + entity->addComponent(geometryRenderer); + TestRenderer renderer; + renderer.setNodeManagers(nodeManagers.data()); + scene2d->setRenderer(&renderer); + sharedObject->m_quickWindow = testWindow.data(); + scene2d->setSharedObject(sharedObject); + testWindow->setGeometry(0,0,1024,1024); + + QByteArray data; + data.resize(sizeof(float) * 5 * 6); + float *dataPtr = reinterpret_cast<float *>(data.data()); + int i = 0; + dataPtr[i++] = -1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 0; + dataPtr[i++] = 0; + + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 0; + + dataPtr[i++] = 1.0f; + dataPtr[i++] = -1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + + dataPtr[i++] = -1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 0; + dataPtr[i++] = 0; + + dataPtr[i++] = 1.0f; + dataPtr[i++] = -1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 1.0f; + + dataPtr[i++] = -1.0f; + dataPtr[i++] = -1.0f; + dataPtr[i++] = 1.0f; + dataPtr[i++] = 0.0f; + dataPtr[i++] = 1.0f; + + dataBuffer->setData(data); + Buffer *backendBuffer = nodeManagers->bufferManager()->getOrCreateResource(dataBuffer->id()); + backendBuffer->setRenderer(&renderer); + backendBuffer->setManager(nodeManagers->bufferManager()); + simulateInitialization(dataBuffer, backendBuffer); + + positionAttribute->setBuffer(dataBuffer); + positionAttribute->setName(Qt3DRender::QAttribute::defaultPositionAttributeName()); + positionAttribute->setVertexBaseType(Qt3DRender::QAttribute::Float); + positionAttribute->setVertexSize(3); + positionAttribute->setCount(6); + positionAttribute->setByteStride(sizeof(float) * 5); + positionAttribute->setByteOffset(0); + positionAttribute->setAttributeType(Qt3DRender::QAttribute::VertexAttribute); + geometry->addAttribute(positionAttribute); + + texcoordAttribute->setBuffer(dataBuffer); + texcoordAttribute->setName(Qt3DRender::QAttribute::defaultTextureCoordinateAttributeName()); + texcoordAttribute->setVertexBaseType(Qt3DRender::QAttribute::Float); + texcoordAttribute->setVertexSize(2); + texcoordAttribute->setCount(6); + texcoordAttribute->setByteStride(sizeof(float) * 5); + texcoordAttribute->setByteOffset(sizeof(float) * 3); + texcoordAttribute->setAttributeType(Qt3DRender::QAttribute::VertexAttribute); + geometry->addAttribute(texcoordAttribute); + + geometryRenderer->setGeometry(geometry); + geometryRenderer->setPrimitiveType(Qt3DRender::QGeometryRenderer::Triangles); + + Attribute *backendAttribute = nodeManagers->attributeManager()->getOrCreateResource( + positionAttribute->id()); + backendAttribute->setRenderer(&renderer); + simulateInitialization(positionAttribute, backendAttribute); + + Attribute *backendTexcoordAttribute = nodeManagers->attributeManager() + ->getOrCreateResource(texcoordAttribute->id()); + backendTexcoordAttribute->setRenderer(&renderer); + simulateInitialization(texcoordAttribute, backendTexcoordAttribute); + + Geometry *backendGeometry = nodeManagers->geometryManager() + ->getOrCreateResource(geometry->id()); + backendGeometry->setRenderer(&renderer); + simulateInitialization(geometry, backendGeometry); + + GeometryRenderer *backendRenderer = nodeManagers->geometryRendererManager() + ->getOrCreateResource(geometryRenderer->id()); + backendRenderer->setRenderer(&renderer); + backendRenderer->setManager(nodeManagers->geometryRendererManager()); + simulateInitialization(geometryRenderer, backendRenderer); + + Entity *backendEntity = nodeManagers->renderNodesManager()->getOrCreateResource(entity->id()); + backendEntity->setRenderer(&renderer); + backendEntity->setNodeManagers(nodeManagers.data()); + simulateInitialization(entity.data(), backendEntity); + +#define PICK_TRIANGLE(tri, v0, v1, v2, uvw) \ + new Qt3DRender::QPickTriangleEvent(QPointF(), QVector3D(), QVector3D(), 0.0f, \ + tri, v0, v1, v2, Qt3DRender::QPickEvent::LeftButton, Qt::LeftButton, 0, uvw) + + { + // WHEN + QVector3D uvw(1.0, 0.0f, 0.0f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(0, 0, 1, 2, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(0,0))); + testWindow->clear(); + } + + { + // WHEN + QVector3D uvw(0.0, 1.0f, 0.0f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(0, 0, 1, 2, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(1024,0))); + testWindow->clear(); + } + + { + // WHEN + QVector3D uvw(0.0, 0.0f, 1.0f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(0, 0, 1, 2, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(1024,1024))); + testWindow->clear(); + } + + { + // WHEN + QVector3D uvw(1.0, 0.0f, 0.0f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(1, 3, 4, 5, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(0,0))); + testWindow->clear(); + } + + { + // WHEN + QVector3D uvw(0.0, 1.0f, 0.0f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(1, 3, 4, 5, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(1024,1024))); + testWindow->clear(); + } + + { + // WHEN + QVector3D uvw(0.0, 0.0f, 1.0f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(1, 3, 4, 5, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(0,1024))); + testWindow->clear(); + } + + { + // WHEN + QVector3D uvw(0.5f, 0.25f, 0.25f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(0, 0, 1, 2, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(512.0f, 256.0f))); + testWindow->clear(); + } + + { + // WHEN + QVector3D uvw(0.875f, 0.09375f, 0.03125f); + Qt3DRender::QPickEventPtr ev = Qt3DRender::QPickEventPtr(PICK_TRIANGLE(1, 3, 4, 5, uvw)); + Qt3DRender::QPickEventPrivate::get(ev.data())->m_entity = entity->id(); + scene2d->handlePickEvent(QEvent::MouseButtonPress, ev); + + QCoreApplication::processEvents(); + + // THEN + QVERIFY(testWindow->verifyEventPos(0, QEvent::MouseButtonPress, QPointF(96.0f, 128.0f))); + testWindow->clear(); + } + } }; QTEST_MAIN(tst_Scene2D) |