diff options
Diffstat (limited to 'tests/auto/gui/qopengl/tst_qopengl.cpp')
-rw-r--r-- | tests/auto/gui/qopengl/tst_qopengl.cpp | 173 |
1 files changed, 160 insertions, 13 deletions
diff --git a/tests/auto/gui/qopengl/tst_qopengl.cpp b/tests/auto/gui/qopengl/tst_qopengl.cpp index 63fe8b9693..972c2a7ea4 100644 --- a/tests/auto/gui/qopengl/tst_qopengl.cpp +++ b/tests/auto/gui/qopengl/tst_qopengl.cpp @@ -43,6 +43,7 @@ #include <QtGui/private/qopenglcontext_p.h> #include <QtGui/QOpenGLFramebufferObject> #include <QtGui/QOpenGLFunctions> +#include <QtGui/QOpenGLVertexArrayObject> #include <QtGui/QOpenGLPaintDevice> #include <QtGui/QPainter> #include <QtGui/QScreen> @@ -51,12 +52,25 @@ #include <QtGui/QGenericMatrix> #include <QtGui/QMatrix4x4> #include <QtGui/private/qopengltextureblitter_p.h> - +#include <QtGui/private/qguiapplication_p.h> +#include <qpa/qplatformintegration.h> +#include <qpa/qplatformnativeinterface.h> #include <QtTest/QtTest> #include <QSignalSpy> +#ifdef USE_GLX +// Must be included last due to the X11 types +#include <QtPlatformHeaders/QGLXNativeContext> +#endif + +#if defined(Q_OS_WIN32) && !defined(QT_OPENGL_ES_2) +#include <QtPlatformHeaders/QWGLNativeContext> +#endif + +Q_DECLARE_METATYPE(QImage::Format) + class tst_QOpenGL : public QObject { Q_OBJECT @@ -85,6 +99,16 @@ private slots: void textureblitterPartOriginTopLeftSourceRectTransform(); void textureblitterFullTargetRectTransform(); void textureblitterPartTargetRectTransform(); + +#ifdef USE_GLX + void glxContextWrap(); +#endif + +#if defined(Q_OS_WIN32) && !defined(QT_OPENGL_ES_2) + void wglContextWrap(); +#endif + + void vaoCreate(); }; struct SharedResourceTracker @@ -448,9 +472,9 @@ void tst_QOpenGL::fboSimpleRendering() QVERIFY(fbo->bind()); - glClearColor(1.0, 0.0, 0.0, 1.0); - glClear(GL_COLOR_BUFFER_BIT); - glFinish(); + ctx.functions()->glClearColor(1.0, 0.0, 0.0, 1.0); + ctx.functions()->glClear(GL_COLOR_BUFFER_BIT); + ctx.functions()->glFinish(); const QImage fb = fbo->toImage().convertToFormat(QImage::Format_RGB32); QCOMPARE(fb.size(), size); @@ -494,9 +518,9 @@ void tst_QOpenGL::fboTextureOwnership() fbo->bind(); QVERIFY(fbo->texture() != 0 && fbo->texture() != texture); - glClearColor(1.0, 0.0, 0.0, 1.0); - glClear(GL_COLOR_BUFFER_BIT); - glFinish(); + ctx.functions()->glClearColor(1.0, 0.0, 0.0, 1.0); + ctx.functions()->glClear(GL_COLOR_BUFFER_BIT); + ctx.functions()->glFinish(); QImage fb = fbo->toImage().convertToFormat(QImage::Format_RGB32); QImage reference(fb.size(), QImage::Format_RGB32); @@ -504,7 +528,7 @@ void tst_QOpenGL::fboTextureOwnership() QFUZZY_COMPARE_IMAGES(fb, reference); - glDeleteTextures(1, &texture); + ctx.functions()->glDeleteTextures(1, &texture); delete fbo; } @@ -591,7 +615,14 @@ void tst_QOpenGL::fboHandleNulledAfterContextDestroyed() void tst_QOpenGL::openGLPaintDevice_data() { - common_data(); + QTest::addColumn<int>("surfaceClass"); + QTest::addColumn<QImage::Format>("imageFormat"); + + QTest::newRow("Using QWindow - RGB32") << int(QSurface::Window) << QImage::Format_RGB32; + QTest::newRow("Using QOffscreenSurface - RGB32") << int(QSurface::Offscreen) << QImage::Format_RGB32; + QTest::newRow("Using QOffscreenSurface - RGBx8888") << int(QSurface::Offscreen) << QImage::Format_RGBX8888; + QTest::newRow("Using QOffscreenSurface - RGB888") << int(QSurface::Offscreen) << QImage::Format_RGB888; + QTest::newRow("Using QOffscreenSurface - RGB16") << int(QSurface::Offscreen) << QImage::Format_RGB16; } void tst_QOpenGL::openGLPaintDevice() @@ -601,6 +632,7 @@ void tst_QOpenGL::openGLPaintDevice() #endif QFETCH(int, surfaceClass); + QFETCH(QImage::Format, imageFormat); QScopedPointer<QSurface> surface(createSurface(surfaceClass)); QOpenGLContext ctx; @@ -613,7 +645,7 @@ void tst_QOpenGL::openGLPaintDevice() const QSize size(128, 128); - QImage image(size, QImage::Format_RGB32); + QImage image(size, imageFormat); QPainter p(&image); p.fillRect(0, 0, image.width() / 2, image.height() / 2, Qt::red); p.fillRect(image.width() / 2, 0, image.width() / 2, image.height() / 2, Qt::green); @@ -632,7 +664,7 @@ void tst_QOpenGL::openGLPaintDevice() p.fillRect(0, image.height() / 2, image.width() / 2, image.height() / 2, Qt::white); p.end(); - QImage actual = fbo.toImage().convertToFormat(QImage::Format_RGB32); + QImage actual = fbo.toImage().convertToFormat(imageFormat); QCOMPARE(image.size(), actual.size()); QCOMPARE(image, actual); @@ -641,7 +673,7 @@ void tst_QOpenGL::openGLPaintDevice() p.drawImage(0, 0, image); p.end(); - actual = fbo.toImage().convertToFormat(QImage::Format_RGB32); + actual = fbo.toImage().convertToFormat(imageFormat); QCOMPARE(image.size(), actual.size()); QCOMPARE(image, actual); @@ -650,7 +682,7 @@ void tst_QOpenGL::openGLPaintDevice() p.fillRect(0, 0, image.width(), image.height(), QBrush(image)); p.end(); - actual = fbo.toImage().convertToFormat(QImage::Format_RGB32); + actual = fbo.toImage().convertToFormat(imageFormat); QCOMPARE(image.size(), actual.size()); QCOMPARE(image, actual); } @@ -970,6 +1002,121 @@ void tst_QOpenGL::textureblitterPartTargetRectTransform() QCOMPARE(targetBottomRight, expectedBottomRight); } +#ifdef USE_GLX +void tst_QOpenGL::glxContextWrap() +{ + QWindow *window = new QWindow; + window->setSurfaceType(QWindow::OpenGLSurface); + window->setGeometry(0, 0, 10, 10); + window->show(); + QTest::qWaitForWindowExposed(window); + + QPlatformNativeInterface *nativeIf = QGuiApplicationPrivate::instance()->platformIntegration()->nativeInterface(); + QVERIFY(nativeIf); + + // Fetch a GLXContext. + QOpenGLContext *ctx0 = new QOpenGLContext; + ctx0->setFormat(window->format()); + QVERIFY(ctx0->create()); + QVariant v = ctx0->nativeHandle(); + QVERIFY(!v.isNull()); + QVERIFY(v.canConvert<QGLXNativeContext>()); + GLXContext context = v.value<QGLXNativeContext>().context(); + QVERIFY(context); + + // Then create another QOpenGLContext wrapping it. + QOpenGLContext *ctx = new QOpenGLContext; + ctx->setNativeHandle(QVariant::fromValue<QGLXNativeContext>(QGLXNativeContext(context))); + QVERIFY(ctx->create()); + QVERIFY(ctx->nativeHandle().value<QGLXNativeContext>().context() == context); + QVERIFY(nativeIf->nativeResourceForContext(QByteArrayLiteral("glxcontext"), ctx) == (void *) context); + + QVERIFY(ctx->makeCurrent(window)); + ctx->doneCurrent(); + + delete ctx; + delete ctx0; + + delete window; +} +#endif // USE_GLX + +#if defined(Q_OS_WIN32) && !defined(QT_OPENGL_ES_2) +void tst_QOpenGL::wglContextWrap() +{ + QScopedPointer<QOpenGLContext> ctx(new QOpenGLContext); + QVERIFY(ctx->create()); + if (ctx->isOpenGLES()) + QSKIP("Not applicable to EGL"); + + QScopedPointer<QWindow> window(new QWindow); + window->setSurfaceType(QWindow::OpenGLSurface); + window->setGeometry(0, 0, 256, 256); + window->show(); + QTest::qWaitForWindowExposed(window.data()); + + QVariant v = ctx->nativeHandle(); + QVERIFY(!v.isNull()); + QVERIFY(v.canConvert<QWGLNativeContext>()); + QWGLNativeContext nativeContext = v.value<QWGLNativeContext>(); + QVERIFY(nativeContext.context()); + + // Now do a makeCurrent() do make sure the pixel format on the native + // window (the HWND we are going to retrieve below) is set. + QVERIFY(ctx->makeCurrent(window.data())); + ctx->doneCurrent(); + + HWND wnd = (HWND) qGuiApp->platformNativeInterface()->nativeResourceForWindow(QByteArrayLiteral("handle"), window.data()); + QVERIFY(wnd); + + QScopedPointer<QOpenGLContext> adopted(new QOpenGLContext); + adopted->setNativeHandle(QVariant::fromValue<QWGLNativeContext>(QWGLNativeContext(nativeContext.context(), wnd))); + QVERIFY(adopted->create()); + + // This tests two things: that a regular, non-adopted QOpenGLContext is + // able to return a QSurfaceFormat containing the real values after + // create(), and that the adopted context got the correct pixel format from + // window and was able to update its format accordingly. + QCOMPARE(adopted->format().version(), ctx->format().version()); + QCOMPARE(adopted->format().profile(), ctx->format().profile()); + QVERIFY(ctx->format().redBufferSize() > 0); + QCOMPARE(adopted->format().redBufferSize(), ctx->format().redBufferSize()); + QVERIFY(ctx->format().greenBufferSize() > 0); + QCOMPARE(adopted->format().greenBufferSize(), ctx->format().greenBufferSize()); + QVERIFY(ctx->format().blueBufferSize() > 0); + QCOMPARE(adopted->format().blueBufferSize(), ctx->format().blueBufferSize()); + QVERIFY(ctx->format().depthBufferSize() > 0); + QCOMPARE(adopted->format().depthBufferSize(), ctx->format().depthBufferSize()); + QVERIFY(ctx->format().stencilBufferSize() > 0); + QCOMPARE(adopted->format().stencilBufferSize(), ctx->format().stencilBufferSize()); + + // This must work since we are using the exact same window. + QVERIFY(adopted->makeCurrent(window.data())); + adopted->doneCurrent(); +} +#endif // Q_OS_WIN32 && !QT_OPENGL_ES_2 + +void tst_QOpenGL::vaoCreate() +{ + QScopedPointer<QSurface> surface(createSurface(QSurface::Window)); + QOpenGLContext *ctx = new QOpenGLContext; + ctx->create(); + ctx->makeCurrent(surface.data()); + + QOpenGLVertexArrayObject vao; + bool success = vao.create(); + if (ctx->isOpenGLES()) { + if (ctx->format().majorVersion() >= 3 || ctx->hasExtension(QByteArrayLiteral("GL_OES_vertex_array_object"))) + QVERIFY(success); + } else { + if (ctx->format().majorVersion() >= 3 || ctx->hasExtension(QByteArrayLiteral("GL_ARB_vertex_array_object"))) + QVERIFY(success); + } + + vao.destroy(); + ctx->doneCurrent(); +} + QTEST_MAIN(tst_QOpenGL) #include "tst_qopengl.moc" |