Made EGLFS handle multiple surfaces with more grace.

Prevents crashing when some menu or similar is shown, although the
visual result might not be ideal.

Task-number: QTBUG-29729
Change-Id: Ia840b3ec17f5ef30ee58150bd2f807ca5e72cc12
Reviewed-by: Gunnar Sletta <gunnar.sletta@digia.com>
Reviewed-by: Andy Nichols <andy.nichols@digia.com>
This commit is contained in:
Samuel Rødal 2013-02-20 08:17:35 +01:00 committed by The Qt Project
parent 888bfb09da
commit 785edaa09d
4 changed files with 47 additions and 1 deletions

View File

@ -48,6 +48,7 @@ QT_BEGIN_NAMESPACE
QEglFSScreen::QEglFSScreen(EGLDisplay dpy)
: m_dpy(dpy)
, m_surface(0)
, m_cursor(0)
{
#ifdef QEGL_EXTRA_DEBUG
@ -95,4 +96,9 @@ QPlatformCursor *QEglFSScreen::cursor() const
return m_cursor;
}
void QEglFSScreen::setPrimarySurface(EGLSurface surface)
{
m_surface = surface;
}
QT_END_NAMESPACE

View File

@ -69,9 +69,16 @@ public:
QPlatformCursor *cursor() const;
EGLDisplay display() const { return m_dpy; }
EGLSurface primarySurface() const { return m_surface; }
protected:
void setPrimarySurface(EGLSurface surface);
private:
friend class QEglFSWindow;
EGLDisplay m_dpy;
EGLSurface m_surface;
QEglFSCursor *m_cursor;
};

View File

@ -42,6 +42,8 @@
#include "qeglfswindow.h"
#include "qeglfshooks.h"
#include <qpa/qwindowsysteminterface.h>
#include <qpa/qplatformintegration.h>
#include <private/qguiapplication_p.h>
#include <QtPlatformSupport/private/qeglconvenience_p.h>
@ -66,6 +68,11 @@ QEglFSWindow::~QEglFSWindow()
destroy();
}
static inline bool supportsMultipleWindows()
{
return QGuiApplicationPrivate::platformIntegration()->hasCapability(QPlatformIntegration::MultipleWindows);
}
void QEglFSWindow::create()
{
if (m_window)
@ -80,6 +87,9 @@ void QEglFSWindow::create()
return;
}
if (!supportsMultipleWindows() && screen()->primarySurface())
return;
EGLDisplay display = (static_cast<QEglFSScreen *>(window()->screen()->handle()))->display();
QSurfaceFormat platformFormat = QEglFSHooks::hooks()->surfaceFormatFor(window()->requestedFormat());
m_config = QEglFSIntegration::chooseConfig(display, platformFormat);
@ -104,11 +114,14 @@ void QEglFSWindow::resetSurface()
m_window = QEglFSHooks::hooks()->createNativeWindow(QEglFSHooks::hooks()->screenSize(), m_format);
m_surface = eglCreateWindowSurface(display, m_config, m_window, NULL);
if (m_surface == EGL_NO_SURFACE) {
EGLint error = eglGetError();
eglTerminate(display);
qFatal("EGL Error : Could not create the egl surface: error = 0x%x\n", error);
}
screen()->setPrimarySurface(m_surface);
}
void QEglFSWindow::destroy()
@ -116,6 +129,12 @@ void QEglFSWindow::destroy()
if (m_surface) {
EGLDisplay display = static_cast<QEglFSScreen *>(screen())->display();
eglDestroySurface(display, m_surface);
if (!supportsMultipleWindows()) {
// ours must be the primary surface
screen()->setPrimarySurface(0);
}
m_surface = 0;
}
@ -144,9 +163,21 @@ WId QEglFSWindow::winId() const
return m_winid;
}
EGLSurface QEglFSWindow::surface() const
{
if (!supportsMultipleWindows())
return screen()->primarySurface();
return m_surface;
}
QSurfaceFormat QEglFSWindow::format() const
{
return m_format;
}
QEglFSScreen *QEglFSWindow::screen() const
{
return static_cast<QEglFSScreen *>(QPlatformWindow::screen());
}
QT_END_NAMESPACE

View File

@ -59,9 +59,11 @@ public:
void setWindowState(Qt::WindowState state);
WId winId() const;
EGLSurface surface() const { return m_surface; }
EGLSurface surface() const;
QSurfaceFormat format() const;
QEglFSScreen *screen() const;
void create();
void destroy();