From 365212fedeef639787a2c183b1ae975b2a9cb9c3 Mon Sep 17 00:00:00 2001 From: Andrew Knight Date: Fri, 14 Nov 2014 11:50:32 +0200 Subject: [PATCH] winrt: Blacklist certain devices from creating a depth/stencil buffer This passes the EGLConfig created in the platform screen to the underlying context, and certain GPUs are blacklisted to be prevented from creating a configuration which does not render properly with Qt Quick. Task-number: QTBUG-42260 Change-Id: I7e1cdc33c2f5662538723c6930fad5f13b151d6f Reviewed-by: Oliver Wolff --- .../platforms/winrt/qwinrteglcontext.cpp | 4 +- .../platforms/winrt/qwinrteglcontext.h | 2 +- .../platforms/winrt/qwinrtintegration.cpp | 2 +- src/plugins/platforms/winrt/qwinrtscreen.cpp | 43 ++++++++++++++++++- src/plugins/platforms/winrt/qwinrtscreen.h | 1 + 5 files changed, 47 insertions(+), 5 deletions(-) diff --git a/src/plugins/platforms/winrt/qwinrteglcontext.cpp b/src/plugins/platforms/winrt/qwinrteglcontext.cpp index 5daeee69c0..64aedb1b33 100644 --- a/src/plugins/platforms/winrt/qwinrteglcontext.cpp +++ b/src/plugins/platforms/winrt/qwinrteglcontext.cpp @@ -35,8 +35,8 @@ QT_BEGIN_NAMESPACE -QWinRTEGLContext::QWinRTEGLContext(const QSurfaceFormat &format, QPlatformOpenGLContext *share, EGLDisplay display, EGLSurface surface) - : QEGLPlatformContext(format, share, display), m_eglSurface(surface) +QWinRTEGLContext::QWinRTEGLContext(const QSurfaceFormat &format, QPlatformOpenGLContext *share, EGLDisplay display, EGLSurface surface, EGLConfig config) + : QEGLPlatformContext(format, share, display, &config), m_eglSurface(surface) { } diff --git a/src/plugins/platforms/winrt/qwinrteglcontext.h b/src/plugins/platforms/winrt/qwinrteglcontext.h index fb1199a79e..142e204fc8 100644 --- a/src/plugins/platforms/winrt/qwinrteglcontext.h +++ b/src/plugins/platforms/winrt/qwinrteglcontext.h @@ -41,7 +41,7 @@ QT_BEGIN_NAMESPACE class QWinRTEGLContext : public QEGLPlatformContext { public: - explicit QWinRTEGLContext(const QSurfaceFormat &format, QPlatformOpenGLContext *share, EGLDisplay display, EGLSurface surface); + explicit QWinRTEGLContext(const QSurfaceFormat &format, QPlatformOpenGLContext *share, EGLDisplay display, EGLSurface surface, EGLConfig config); QFunctionPointer getProcAddress(const QByteArray &procName) Q_DECL_OVERRIDE; diff --git a/src/plugins/platforms/winrt/qwinrtintegration.cpp b/src/plugins/platforms/winrt/qwinrtintegration.cpp index b8ca9fdc66..4fa90b4b68 100644 --- a/src/plugins/platforms/winrt/qwinrtintegration.cpp +++ b/src/plugins/platforms/winrt/qwinrtintegration.cpp @@ -110,7 +110,7 @@ QPlatformBackingStore *QWinRTIntegration::createPlatformBackingStore(QWindow *wi QPlatformOpenGLContext *QWinRTIntegration::createPlatformOpenGLContext(QOpenGLContext *context) const { QWinRTScreen *screen = static_cast(context->screen()->handle()); - return new QWinRTEGLContext(context->format(), context->handle(), screen->eglDisplay(), screen->eglSurface()); + return new QWinRTEGLContext(context->format(), context->handle(), screen->eglDisplay(), screen->eglSurface(), screen->eglConfig()); } QPlatformFontDatabase *QWinRTIntegration::fontDatabase() const diff --git a/src/plugins/platforms/winrt/qwinrtscreen.cpp b/src/plugins/platforms/winrt/qwinrtscreen.cpp index 3933902ae3..681307ddcf 100644 --- a/src/plugins/platforms/winrt/qwinrtscreen.cpp +++ b/src/plugins/platforms/winrt/qwinrtscreen.cpp @@ -33,6 +33,11 @@ #include "qwinrtscreen.h" +#define EGL_EGLEXT_PROTOTYPES +#include +#include +#include + #include "qwinrtbackingstore.h" #include "qwinrtinputcontext.h" #include "qwinrtcursor.h" @@ -452,6 +457,7 @@ public: EGLDisplay eglDisplay; EGLSurface eglSurface; + EGLConfig eglConfig; QHash applicationTokens; QHash windowTokens; @@ -575,7 +581,36 @@ QWinRTScreen::QWinRTScreen() if (!eglInitialize(d->eglDisplay, NULL, NULL)) qCritical("Failed to initialize EGL: 0x%x", eglGetError()); - d->eglSurface = eglCreateWindowSurface(d->eglDisplay, q_configFromGLFormat(d->eglDisplay, d->surfaceFormat), d->coreWindow.Get(), NULL); + // Check that the device properly supports depth/stencil rendering, and disable them if not + ComPtr d3dDevice; + const EGLBoolean ok = eglQuerySurfacePointerANGLE(d->eglDisplay, EGL_NO_SURFACE, EGL_DEVICE_EXT, (void **)d3dDevice.GetAddressOf()); + if (ok && d3dDevice) { + ComPtr dxgiDevice; + hr = d3dDevice.As(&dxgiDevice); + if (SUCCEEDED(hr)) { + ComPtr dxgiAdapter; + hr = dxgiDevice->GetAdapter(&dxgiAdapter); + if (SUCCEEDED(hr)) { + ComPtr dxgiAdapter2; + hr = dxgiAdapter.As(&dxgiAdapter2); + if (SUCCEEDED(hr)) { + DXGI_ADAPTER_DESC2 desc; + hr = dxgiAdapter2->GetDesc2(&desc); + if (SUCCEEDED(hr)) { + // The following GPUs do not render properly with depth/stencil + if ((desc.VendorId == 0x4d4f4351 && desc.DeviceId == 0x32303032)) { // Qualcomm Adreno 225 + d->surfaceFormat.setDepthBufferSize(-1); + d->surfaceFormat.setStencilBufferSize(-1); + } + } + } + } + } + } + + d->eglConfig = q_configFromGLFormat(d->eglDisplay, d->surfaceFormat); + d->surfaceFormat = q_glFormatFromConfig(d->eglDisplay, d->eglConfig, d->surfaceFormat); + d->eglSurface = eglCreateWindowSurface(d->eglDisplay, d->eglConfig, d->coreWindow.Get(), NULL); if (d->eglSurface == EGL_NO_SURFACE) qCritical("Failed to create EGL window surface: 0x%x", eglGetError()); } @@ -706,6 +741,12 @@ EGLSurface QWinRTScreen::eglSurface() const return d->eglSurface; } +EGLConfig QWinRTScreen::eglConfig() const +{ + Q_D(const QWinRTScreen); + return d->eglConfig; +} + QWindow *QWinRTScreen::topWindow() const { Q_D(const QWinRTScreen); diff --git a/src/plugins/platforms/winrt/qwinrtscreen.h b/src/plugins/platforms/winrt/qwinrtscreen.h index e70a998216..c95a2073ed 100644 --- a/src/plugins/platforms/winrt/qwinrtscreen.h +++ b/src/plugins/platforms/winrt/qwinrtscreen.h @@ -109,6 +109,7 @@ public: ABI::Windows::UI::Core::ICoreWindow *coreWindow() const; EGLDisplay eglDisplay() const; // To opengl context EGLSurface eglSurface() const; // To window + EGLConfig eglConfig() const; private: void handleExpose();