diff options
Diffstat (limited to 'src/plugins/platforms/xcb')
40 files changed, 1555 insertions, 181 deletions
diff --git a/src/plugins/platforms/xcb/README b/src/plugins/platforms/xcb/README index 86db96fdbc..ab802ced27 100644 --- a/src/plugins/platforms/xcb/README +++ b/src/plugins/platforms/xcb/README @@ -1,6 +1,6 @@ Required packages: -libxcb1 libxcb1-dev libx11-xcb1 libx11-xcb-dev libxcb-keysyms1 libxcb-keysyms1-dev libxcb-image0 libxcb-image0-dev libxcb-shm0 libxcb-shm0-dev libxcb-icccm1 libxcb-icccm1-dev libxcb-sync0 libxcb-sync0-dev libxcb-render-util0 libxcb-render-util0-dev libxcb-xfixes0-dev +libxcb1 libxcb1-dev libx11-xcb1 libx11-xcb-dev libxcb-keysyms1 libxcb-keysyms1-dev libxcb-image0 libxcb-image0-dev libxcb-shm0 libxcb-shm0-dev libxcb-icccm1 libxcb-icccm1-dev libxcb-sync0 libxcb-sync0-dev libxcb-render-util0 libxcb-render-util0-dev libxcb-xfixes0-dev libxrender-dev On Ubuntu 11.10 icccm1 is replaced by icccm4 and xcb-render-util is not available: -libxcb1 libxcb1-dev libx11-xcb1 libx11-xcb-dev libxcb-keysyms1 libxcb-keysyms1-dev libxcb-image0 libxcb-image0-dev libxcb-shm0 libxcb-shm0-dev libxcb-icccm4 libxcb-icccm4-dev libxcb-sync0 libxcb-sync0-dev libxcb-xfixes0-dev +libxcb1 libxcb1-dev libx11-xcb1 libx11-xcb-dev libxcb-keysyms1 libxcb-keysyms1-dev libxcb-image0 libxcb-image0-dev libxcb-shm0 libxcb-shm0-dev libxcb-icccm4 libxcb-icccm4-dev libxcb-sync0 libxcb-sync0-dev libxcb-xfixes0-dev libxrender-dev The packages for xcb-render-util can be installed manually from http://packages.ubuntu.com/natty/libxcb-render-util0 and http://packages.ubuntu.com/natty/libxcb-render-util0-dev diff --git a/src/plugins/platforms/xcb/main.cpp b/src/plugins/platforms/xcb/main.cpp index 16ef7628a7..5aa3e921f3 100644 --- a/src/plugins/platforms/xcb/main.cpp +++ b/src/plugins/platforms/xcb/main.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qdri2context.cpp b/src/plugins/platforms/xcb/qdri2context.cpp index c16052f021..c596ca139d 100644 --- a/src/plugins/platforms/xcb/qdri2context.cpp +++ b/src/plugins/platforms/xcb/qdri2context.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qdri2context.h b/src/plugins/platforms/xcb/qdri2context.h index 7c4dbb35c2..d0a1b469a9 100644 --- a/src/plugins/platforms/xcb/qdri2context.h +++ b/src/plugins/platforms/xcb/qdri2context.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qglxintegration.cpp b/src/plugins/platforms/xcb/qglxintegration.cpp index 86b7f09166..6ada127beb 100644 --- a/src/plugins/platforms/xcb/qglxintegration.cpp +++ b/src/plugins/platforms/xcb/qglxintegration.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -71,15 +71,28 @@ QGLXContext::QGLXContext(QXcbScreen *screen, const QSurfaceFormat &format, QPlat GLXFBConfig config = qglx_findConfig(DISPLAY_FROM_XCB(screen),screen->screenNumber(),format); - m_context = glXCreateNewContext(DISPLAY_FROM_XCB(screen), config, GLX_RGBA_TYPE, m_shareContext, TRUE); - if (!m_context && m_shareContext) { - // re-try without a shared glx context - m_shareContext = 0; - m_context = glXCreateNewContext(DISPLAY_FROM_XCB(screen), config, GLX_RGBA_TYPE, 0, TRUE); - } + if (config) { + m_context = glXCreateNewContext(DISPLAY_FROM_XCB(screen), config, GLX_RGBA_TYPE, m_shareContext, TRUE); + if (!m_context && m_shareContext) { + // re-try without a shared glx context + m_shareContext = 0; + m_context = glXCreateNewContext(DISPLAY_FROM_XCB(screen), config, GLX_RGBA_TYPE, 0, TRUE); + } - if (m_context) - m_format = qglx_surfaceFormatFromGLXFBConfig(DISPLAY_FROM_XCB(screen), config, m_context); + if (m_context) + m_format = qglx_surfaceFormatFromGLXFBConfig(DISPLAY_FROM_XCB(screen), config, m_context); + } else { + XVisualInfo *visualInfo = qglx_findVisualInfo(DISPLAY_FROM_XCB(m_screen), screen->screenNumber(), format); + if (!visualInfo) + qFatal("Could not initialize GLX"); + m_context = glXCreateContext(DISPLAY_FROM_XCB(screen), visualInfo, m_shareContext, true); + if (!m_context && m_shareContext) { + // re-try without a shared glx context + m_shareContext = 0; + m_context = glXCreateContext(DISPLAY_FROM_XCB(screen), visualInfo, 0, true); + } + XFree(visualInfo); + } } QGLXContext::~QGLXContext() diff --git a/src/plugins/platforms/xcb/qglxintegration.h b/src/plugins/platforms/xcb/qglxintegration.h index 93c4805ec8..dce9193eba 100644 --- a/src/plugins/platforms/xcb/qglxintegration.h +++ b/src/plugins/platforms/xcb/qglxintegration.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbbackingstore.cpp b/src/plugins/platforms/xcb/qxcbbackingstore.cpp index ad8b47c25a..b7369525a5 100644 --- a/src/plugins/platforms/xcb/qxcbbackingstore.cpp +++ b/src/plugins/platforms/xcb/qxcbbackingstore.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -115,8 +115,12 @@ QXcbShmImage::QXcbShmImage(QXcbScreen *screen, const QSize &size, uint depth, QI m_shm_info.shmaddr = m_xcb_image->data = (quint8 *)shmat (m_shm_info.shmid, 0, 0); m_shm_info.shmseg = xcb_generate_id(xcb_connection()); - xcb_generic_error_t *error = xcb_request_check(xcb_connection(), xcb_shm_attach_checked(xcb_connection(), m_shm_info.shmseg, m_shm_info.shmid, false)); - if (error) { + const xcb_query_extension_reply_t *shm_reply = xcb_get_extension_data(xcb_connection(), &xcb_shm_id); + bool shm_present = shm_reply != NULL && shm_reply->present; + xcb_generic_error_t *error = NULL; + if (shm_present) + error = xcb_request_check(xcb_connection(), xcb_shm_attach_checked(xcb_connection(), m_shm_info.shmseg, m_shm_info.shmid, false)); + if (!shm_present || error) { free(error); shmdt(m_shm_info.shmaddr); diff --git a/src/plugins/platforms/xcb/qxcbbackingstore.h b/src/plugins/platforms/xcb/qxcbbackingstore.h index 70fed46563..e02c6eb15b 100644 --- a/src/plugins/platforms/xcb/qxcbbackingstore.h +++ b/src/plugins/platforms/xcb/qxcbbackingstore.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbclipboard.cpp b/src/plugins/platforms/xcb/qxcbclipboard.cpp index 14d802a8bd..bad80568e3 100644 --- a/src/plugins/platforms/xcb/qxcbclipboard.cpp +++ b/src/plugins/platforms/xcb/qxcbclipboard.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbclipboard.h b/src/plugins/platforms/xcb/qxcbclipboard.h index c3b072984e..a43518e80b 100644 --- a/src/plugins/platforms/xcb/qxcbclipboard.h +++ b/src/plugins/platforms/xcb/qxcbclipboard.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbconnection.cpp b/src/plugins/platforms/xcb/qxcbconnection.cpp index ca21b1eb9d..fdc2c76fea 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.cpp +++ b/src/plugins/platforms/xcb/qxcbconnection.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -49,11 +49,13 @@ #include "qxcbclipboard.h" #include "qxcbdrag.h" #include "qxcbwmsupport.h" +#include "qxcbnativeinterface.h" #include <QtAlgorithms> #include <QSocketNotifier> #include <QAbstractEventDispatcher> #include <QTimer> +#include <QByteArray> #include <stdio.h> #include <errno.h> @@ -93,9 +95,10 @@ static int nullErrorHandler(Display *, XErrorEvent *) } #endif -QXcbConnection::QXcbConnection(const char *displayName) +QXcbConnection::QXcbConnection(QXcbNativeInterface *nativeInterface, const char *displayName) : m_connection(0) , m_displayName(displayName ? QByteArray(displayName) : qgetenv("DISPLAY")) + , m_nativeInterface(nativeInterface) #ifdef XCB_USE_XINPUT2_MAEMO , m_xinputData(0) #endif @@ -129,7 +132,7 @@ QXcbConnection::QXcbConnection(const char *displayName) m_connection = xcb_connect(m_displayName.constData(), &m_primaryScreen); #endif //XCB_USE_XLIB - if (!m_connection) + if (!m_connection || xcb_connection_has_error(m_connection)) qFatal("Could not connect to display %s", m_displayName.constData()); m_reader = new QXcbEventReader(this); @@ -493,72 +496,77 @@ void QXcbConnection::handleXcbEvent(xcb_generic_event_t *event) m_callLog.remove(0, i); } #endif - bool handled = true; + bool handled = false; + + if (QPlatformNativeInterface::EventFilter filter = m_nativeInterface->eventFilter(QXcbNativeInterface::GenericEventFilter)) + handled = filter(event, 0); uint response_type = event->response_type & ~0x80; - switch (response_type) { - case XCB_EXPOSE: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_expose_event_t, window, handleExposeEvent); - case XCB_BUTTON_PRESS: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_button_press_event_t, event, handleButtonPressEvent); - case XCB_BUTTON_RELEASE: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_button_release_event_t, event, handleButtonReleaseEvent); - case XCB_MOTION_NOTIFY: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_motion_notify_event_t, event, handleMotionNotifyEvent); - case XCB_CONFIGURE_NOTIFY: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_configure_notify_event_t, event, handleConfigureNotifyEvent); - case XCB_MAP_NOTIFY: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_map_notify_event_t, event, handleMapNotifyEvent); - case XCB_UNMAP_NOTIFY: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_unmap_notify_event_t, event, handleUnmapNotifyEvent); - case XCB_CLIENT_MESSAGE: - handleClientMessageEvent((xcb_client_message_event_t *)event); - case XCB_ENTER_NOTIFY: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_enter_notify_event_t, event, handleEnterNotifyEvent); - case XCB_LEAVE_NOTIFY: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_leave_notify_event_t, event, handleLeaveNotifyEvent); - case XCB_FOCUS_IN: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_focus_in_event_t, event, handleFocusInEvent); - case XCB_FOCUS_OUT: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_focus_out_event_t, event, handleFocusOutEvent); - case XCB_KEY_PRESS: - HANDLE_KEYBOARD_EVENT(xcb_key_press_event_t, handleKeyPressEvent); - case XCB_KEY_RELEASE: - HANDLE_KEYBOARD_EVENT(xcb_key_release_event_t, handleKeyReleaseEvent); - case XCB_MAPPING_NOTIFY: - m_keyboard->handleMappingNotifyEvent((xcb_mapping_notify_event_t *)event); - break; - case XCB_SELECTION_REQUEST: - { - xcb_selection_request_event_t *sr = (xcb_selection_request_event_t *)event; - if (sr->selection == atom(QXcbAtom::XdndSelection)) - m_drag->handleSelectionRequest(sr); - else - m_clipboard->handleSelectionRequest(sr); - break; - } - case XCB_SELECTION_CLEAR: - setTime(((xcb_selection_clear_event_t *)event)->time); - m_clipboard->handleSelectionClearRequest((xcb_selection_clear_event_t *)event); - handled = true; - break; - case XCB_SELECTION_NOTIFY: - setTime(((xcb_selection_notify_event_t *)event)->time); - qDebug() << "XCB_SELECTION_NOTIFY"; - handled = false; - break; - case XCB_PROPERTY_NOTIFY: - HANDLE_PLATFORM_WINDOW_EVENT(xcb_property_notify_event_t, window, handlePropertyNotifyEvent); - break; -#ifdef XCB_USE_XINPUT2_MAEMO - case GenericEvent: - handleGenericEvent((xcb_ge_event_t*)event); - break; -#endif - default: - handled = false; - break; + if (!handled) { + switch (response_type) { + case XCB_EXPOSE: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_expose_event_t, window, handleExposeEvent); + case XCB_BUTTON_PRESS: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_button_press_event_t, event, handleButtonPressEvent); + case XCB_BUTTON_RELEASE: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_button_release_event_t, event, handleButtonReleaseEvent); + case XCB_MOTION_NOTIFY: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_motion_notify_event_t, event, handleMotionNotifyEvent); + case XCB_CONFIGURE_NOTIFY: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_configure_notify_event_t, event, handleConfigureNotifyEvent); + case XCB_MAP_NOTIFY: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_map_notify_event_t, event, handleMapNotifyEvent); + case XCB_UNMAP_NOTIFY: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_unmap_notify_event_t, event, handleUnmapNotifyEvent); + case XCB_CLIENT_MESSAGE: + handleClientMessageEvent((xcb_client_message_event_t *)event); + case XCB_ENTER_NOTIFY: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_enter_notify_event_t, event, handleEnterNotifyEvent); + case XCB_LEAVE_NOTIFY: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_leave_notify_event_t, event, handleLeaveNotifyEvent); + case XCB_FOCUS_IN: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_focus_in_event_t, event, handleFocusInEvent); + case XCB_FOCUS_OUT: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_focus_out_event_t, event, handleFocusOutEvent); + case XCB_KEY_PRESS: + HANDLE_KEYBOARD_EVENT(xcb_key_press_event_t, handleKeyPressEvent); + case XCB_KEY_RELEASE: + HANDLE_KEYBOARD_EVENT(xcb_key_release_event_t, handleKeyReleaseEvent); + case XCB_MAPPING_NOTIFY: + m_keyboard->handleMappingNotifyEvent((xcb_mapping_notify_event_t *)event); + break; + case XCB_SELECTION_REQUEST: + { + xcb_selection_request_event_t *sr = (xcb_selection_request_event_t *)event; + if (sr->selection == atom(QXcbAtom::XdndSelection)) + m_drag->handleSelectionRequest(sr); + else + m_clipboard->handleSelectionRequest(sr); + break; + } + case XCB_SELECTION_CLEAR: + setTime(((xcb_selection_clear_event_t *)event)->time); + m_clipboard->handleSelectionClearRequest((xcb_selection_clear_event_t *)event); + handled = true; + break; + case XCB_SELECTION_NOTIFY: + setTime(((xcb_selection_notify_event_t *)event)->time); + qDebug() << "XCB_SELECTION_NOTIFY"; + handled = false; + break; + case XCB_PROPERTY_NOTIFY: + HANDLE_PLATFORM_WINDOW_EVENT(xcb_property_notify_event_t, window, handlePropertyNotifyEvent); + break; + #ifdef XCB_USE_XINPUT2_MAEMO + case GenericEvent: + handleGenericEvent((xcb_ge_event_t*)event); + break; + #endif + default: + handled = false; + break; + } } if (!handled) { @@ -909,6 +917,9 @@ static const char * xcb_atomnames = { "Abs MT Pressure\0" "Abs MT Tracking ID\0" "Max Contacts\0" +#if XCB_USE_MAEMO_WINDOW_PROPERTIES + "_MEEGOTOUCH_ORIENTATION_ANGLE\0" +#endif }; xcb_atom_t QXcbConnection::atom(QXcbAtom::Atom atom) diff --git a/src/plugins/platforms/xcb/qxcbconnection.h b/src/plugins/platforms/xcb/qxcbconnection.h index c227b4c863..7beb41bdd7 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.h +++ b/src/plugins/platforms/xcb/qxcbconnection.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -66,6 +66,7 @@ class QXcbDrag; class QXcbKeyboard; class QXcbClipboard; class QXcbWMSupport; +class QXcbNativeInterface; typedef QHash<xcb_window_t, QXcbWindow *> WindowMapper; @@ -243,6 +244,10 @@ namespace QXcbAtom { AbsMTTrackingID, MaxContacts, +#if XCB_USE_MAEMO_WINDOW_PROPERTIES + MeegoTouchOrientationAngle, +#endif + NPredefinedAtoms, _QT_SETTINGS_TIMESTAMP = NPredefinedAtoms, @@ -285,7 +290,7 @@ class QXcbConnection : public QObject { Q_OBJECT public: - QXcbConnection(const char *displayName = 0); + QXcbConnection(QXcbNativeInterface *nativeInterface, const char *displayName = 0); ~QXcbConnection(); QXcbConnection *connection() const { return const_cast<QXcbConnection *>(this); } @@ -386,6 +391,7 @@ private: QXcbClipboard *m_clipboard; QXcbDrag *m_drag; QScopedPointer<QXcbWMSupport> m_wmSupport; + QXcbNativeInterface *m_nativeInterface; #if defined(XCB_USE_XLIB) void *m_xlib_display; diff --git a/src/plugins/platforms/xcb/qxcbconnection_maemo.cpp b/src/plugins/platforms/xcb/qxcbconnection_maemo.cpp index 12b3d67b9f..1339df78b4 100644 --- a/src/plugins/platforms/xcb/qxcbconnection_maemo.cpp +++ b/src/plugins/platforms/xcb/qxcbconnection_maemo.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbcursor.cpp b/src/plugins/platforms/xcb/qxcbcursor.cpp index a00fdd4824..ed7c22b1e6 100644 --- a/src/plugins/platforms/xcb/qxcbcursor.cpp +++ b/src/plugins/platforms/xcb/qxcbcursor.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -426,10 +426,12 @@ xcb_cursor_t QXcbCursor::createNonStandardCursor(int cshape) } else if (cshape == Qt::DragCopyCursor || cshape == Qt::DragMoveCursor || cshape == Qt::DragLinkCursor) { QImage image = QGuiApplicationPrivate::instance()->getPixmapCursor(static_cast<Qt::CursorShape>(cshape)).toImage(); - xcb_pixmap_t pm = qt_xcb_XPixmapFromBitmap(m_screen, image); - xcb_pixmap_t pmm = qt_xcb_XPixmapFromBitmap(m_screen, image.createAlphaMask()); - cursor = xcb_generate_id(conn); - xcb_create_cursor(conn, cursor, pm, pmm, 0, 0, 0, 0xFFFF, 0xFFFF, 0xFFFF, 8, 8); + if (!image.isNull()) { + xcb_pixmap_t pm = qt_xcb_XPixmapFromBitmap(m_screen, image); + xcb_pixmap_t pmm = qt_xcb_XPixmapFromBitmap(m_screen, image.createAlphaMask()); + cursor = xcb_generate_id(conn); + xcb_create_cursor(conn, cursor, pm, pmm, 0, 0, 0, 0xFFFF, 0xFFFF, 0xFFFF, 8, 8); + } } return cursor; diff --git a/src/plugins/platforms/xcb/qxcbcursor.h b/src/plugins/platforms/xcb/qxcbcursor.h index f766d7c74e..da243424d5 100644 --- a/src/plugins/platforms/xcb/qxcbcursor.h +++ b/src/plugins/platforms/xcb/qxcbcursor.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbdrag.cpp b/src/plugins/platforms/xcb/qxcbdrag.cpp index 89b1fa7445..a05fc780bc 100644 --- a/src/plugins/platforms/xcb/qxcbdrag.cpp +++ b/src/plugins/platforms/xcb/qxcbdrag.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the QtGui module of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbdrag.h b/src/plugins/platforms/xcb/qxcbdrag.h index 0233cc32b2..e32e630548 100644 --- a/src/plugins/platforms/xcb/qxcbdrag.h +++ b/src/plugins/platforms/xcb/qxcbdrag.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the QtGui module of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbeglsurface.h b/src/plugins/platforms/xcb/qxcbeglsurface.h index c4367cf572..a8594fdf2d 100644 --- a/src/plugins/platforms/xcb/qxcbeglsurface.h +++ b/src/plugins/platforms/xcb/qxcbeglsurface.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbimage.cpp b/src/plugins/platforms/xcb/qxcbimage.cpp index 824805a983..13ff8ab2a5 100644 --- a/src/plugins/platforms/xcb/qxcbimage.cpp +++ b/src/plugins/platforms/xcb/qxcbimage.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbimage.h b/src/plugins/platforms/xcb/qxcbimage.h index 6a06610937..708b9305c2 100644 --- a/src/plugins/platforms/xcb/qxcbimage.h +++ b/src/plugins/platforms/xcb/qxcbimage.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbintegration.cpp b/src/plugins/platforms/xcb/qxcbintegration.cpp index 3cf50cbbd9..40359169ca 100644 --- a/src/plugins/platforms/xcb/qxcbintegration.cpp +++ b/src/plugins/platforms/xcb/qxcbintegration.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -47,6 +47,7 @@ #include "qxcbnativeinterface.h" #include "qxcbclipboard.h" #include "qxcbdrag.h" +#include "qxcbsharedgraphicscache.h" #include <xcb/xcb.h> @@ -90,13 +91,14 @@ QXcbIntegration::QXcbIntegration(const QStringList ¶meters) #ifdef XCB_USE_XLIB XInitThreads(); #endif + m_nativeInterface.reset(new QXcbNativeInterface); - m_connections << new QXcbConnection; + m_connections << new QXcbConnection(m_nativeInterface.data()); for (int i = 0; i < parameters.size() - 1; i += 2) { qDebug() << parameters.at(i) << parameters.at(i+1); QString display = parameters.at(i) + ':' + parameters.at(i+1); - m_connections << new QXcbConnection(display.toAscii().constData()); + m_connections << new QXcbConnection(m_nativeInterface.data(), display.toAscii().constData()); } foreach (QXcbConnection *connection, m_connections) @@ -104,9 +106,12 @@ QXcbIntegration::QXcbIntegration(const QStringList ¶meters) screenAdded(screen); m_fontDatabase.reset(new QGenericUnixFontDatabase()); - m_nativeInterface.reset(new QXcbNativeInterface); m_inputContext.reset(QPlatformInputContextFactory::create()); m_accessibility.reset(new QPlatformAccessibility()); + +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + m_sharedGraphicsCache.reset(new QXcbSharedGraphicsCache); +#endif } QXcbIntegration::~QXcbIntegration() @@ -186,6 +191,10 @@ QPlatformBackingStore *QXcbIntegration::createPlatformBackingStore(QWindow *wind bool QXcbIntegration::hasCapability(QPlatformIntegration::Capability cap) const { switch (cap) { +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + case SharedGraphicsCache: return true; +#endif + case ThreadedPixmaps: return true; case OpenGL: return true; case ThreadedOpenGL: @@ -239,4 +248,24 @@ QPlatformAccessibility *QXcbIntegration::accessibility() const return m_accessibility.data(); } +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) +static bool sharedGraphicsCacheDisabled() +{ + static const char *environmentVariable = "QT_DISABLE_SHARED_CACHE"; + static bool cacheDisabled = !qgetenv(environmentVariable).isEmpty() + && qgetenv(environmentVariable).toInt() != 0; + return cacheDisabled; +} + +QPlatformSharedGraphicsCache *QXcbIntegration::createPlatformSharedGraphicsCache(const char *cacheId) const +{ + Q_UNUSED(cacheId); + + if (sharedGraphicsCacheDisabled()) + return 0; + + return m_sharedGraphicsCache.data(); +} +#endif + QT_END_NAMESPACE diff --git a/src/plugins/platforms/xcb/qxcbintegration.h b/src/plugins/platforms/xcb/qxcbintegration.h index 8a3926dbfb..eefecd509b 100644 --- a/src/plugins/platforms/xcb/qxcbintegration.h +++ b/src/plugins/platforms/xcb/qxcbintegration.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -49,6 +49,7 @@ QT_BEGIN_NAMESPACE class QXcbConnection; class QAbstractEventDispatcher; +class QXcbNativeInterface; class QXcbIntegration : public QPlatformIntegration { @@ -76,16 +77,24 @@ public: QPlatformAccessibility *accessibility() const; +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + QPlatformSharedGraphicsCache *createPlatformSharedGraphicsCache(const char *cacheId) const; +#endif + private: QList<QXcbConnection *> m_connections; QScopedPointer<QPlatformFontDatabase> m_fontDatabase; - QScopedPointer<QPlatformNativeInterface> m_nativeInterface; + QScopedPointer<QXcbNativeInterface> m_nativeInterface; QScopedPointer<QPlatformInputContext> m_inputContext; QAbstractEventDispatcher *m_eventDispatcher; QScopedPointer<QPlatformAccessibility> m_accessibility; + +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + QScopedPointer<QPlatformSharedGraphicsCache> m_sharedGraphicsCache; +#endif }; QT_END_NAMESPACE diff --git a/src/plugins/platforms/xcb/qxcbkeyboard.cpp b/src/plugins/platforms/xcb/qxcbkeyboard.cpp index ef71b78339..8c86d43f17 100644 --- a/src/plugins/platforms/xcb/qxcbkeyboard.cpp +++ b/src/plugins/platforms/xcb/qxcbkeyboard.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbkeyboard.h b/src/plugins/platforms/xcb/qxcbkeyboard.h index 4a62dde11a..e93f9065e8 100644 --- a/src/plugins/platforms/xcb/qxcbkeyboard.h +++ b/src/plugins/platforms/xcb/qxcbkeyboard.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbmime.cpp b/src/plugins/platforms/xcb/qxcbmime.cpp index 5d86a118c7..bcc94baed7 100644 --- a/src/plugins/platforms/xcb/qxcbmime.cpp +++ b/src/plugins/platforms/xcb/qxcbmime.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbmime.h b/src/plugins/platforms/xcb/qxcbmime.h index 02be4c9c5b..e6a7ccc834 100644 --- a/src/plugins/platforms/xcb/qxcbmime.h +++ b/src/plugins/platforms/xcb/qxcbmime.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbnativeinterface.cpp b/src/plugins/platforms/xcb/qxcbnativeinterface.cpp index 52ff30991e..b7403cfdce 100644 --- a/src/plugins/platforms/xcb/qxcbnativeinterface.cpp +++ b/src/plugins/platforms/xcb/qxcbnativeinterface.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -76,6 +76,11 @@ public: Q_GLOBAL_STATIC(QXcbResourceMap, qXcbResourceMap) +QXcbNativeInterface::QXcbNativeInterface() +{ + qFill(m_eventFilters, m_eventFilters + EventFilterCount, EventFilter(0)); +} + void *QXcbNativeInterface::nativeResourceForContext(const QByteArray &resourceString, QOpenGLContext *context) { QByteArray lowerCaseResource = resourceString.toLower(); @@ -118,6 +123,21 @@ void *QXcbNativeInterface::nativeResourceForWindow(const QByteArray &resourceStr return result; } +QPlatformNativeInterface::EventFilter QXcbNativeInterface::setEventFilter(const QByteArray &eventType, QPlatformNativeInterface::EventFilter filter) +{ + int type = -1; + if (eventType == QByteArrayLiteral("xcb_generic_event_t")) + type = GenericEventFilter; + if (type == -1) { + qWarning("%s: Attempt to set invalid event filter type '%s'.", + Q_FUNC_INFO, eventType.constData()); + return 0; + } + const EventFilter oldFilter = m_eventFilters[type]; + m_eventFilters[type] = filter; + return oldFilter; +} + QXcbScreen *QXcbNativeInterface::qPlatformScreenForWindow(QWindow *window) { QXcbScreen *screen; diff --git a/src/plugins/platforms/xcb/qxcbnativeinterface.h b/src/plugins/platforms/xcb/qxcbnativeinterface.h index 517e92bc64..6f6130d3e9 100644 --- a/src/plugins/platforms/xcb/qxcbnativeinterface.h +++ b/src/plugins/platforms/xcb/qxcbnativeinterface.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -61,9 +61,19 @@ public: EglContext }; + enum EventFilterType { + GenericEventFilter, + EventFilterCount + }; + + QXcbNativeInterface(); + void *nativeResourceForContext(const QByteArray &resourceString, QOpenGLContext *context); void *nativeResourceForWindow(const QByteArray &resourceString, QWindow *window); + EventFilter setEventFilter(const QByteArray &eventType, EventFilter filter); + EventFilter eventFilter(EventFilterType type) const { return m_eventFilters[type]; } + void *displayForWindow(QWindow *window); void *eglDisplayForWindow(QWindow *window); void *connectionForWindow(QWindow *window); @@ -73,6 +83,8 @@ public: void *eglContextForContext(QOpenGLContext *context); private: + EventFilter m_eventFilters[EventFilterCount]; + static QXcbScreen *qPlatformScreenForWindow(QWindow *window); }; diff --git a/src/plugins/platforms/xcb/qxcbobject.h b/src/plugins/platforms/xcb/qxcbobject.h index b164f63f76..ccc7ab0e58 100644 --- a/src/plugins/platforms/xcb/qxcbobject.h +++ b/src/plugins/platforms/xcb/qxcbobject.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbscreen.cpp b/src/plugins/platforms/xcb/qxcbscreen.cpp index 8b01b4389f..c93b4863e1 100644 --- a/src/plugins/platforms/xcb/qxcbscreen.cpp +++ b/src/plugins/platforms/xcb/qxcbscreen.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -108,7 +108,11 @@ QXcbScreen::QXcbScreen(QXcbConnection *connection, xcb_screen_t *screen, int num free(reply); - m_syncRequestSupported = m_windowManagerName != QLatin1String("KWin"); + const xcb_query_extension_reply_t *sync_reply = xcb_get_extension_data(xcb_connection(), &xcb_sync_id); + if (!sync_reply || !sync_reply->present) + m_syncRequestSupported = false; + else + m_syncRequestSupported = m_windowManagerName != QLatin1String("KWin"); m_clientLeader = xcb_generate_id(xcb_connection()); Q_XCB_CALL2(xcb_create_window(xcb_connection(), diff --git a/src/plugins/platforms/xcb/qxcbscreen.h b/src/plugins/platforms/xcb/qxcbscreen.h index 1975d56189..870d4d5662 100644 --- a/src/plugins/platforms/xcb/qxcbscreen.h +++ b/src/plugins/platforms/xcb/qxcbscreen.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbsharedbuffermanager.cpp b/src/plugins/platforms/xcb/qxcbsharedbuffermanager.cpp new file mode 100644 index 0000000000..f9e388b662 --- /dev/null +++ b/src/plugins/platforms/xcb/qxcbsharedbuffermanager.cpp @@ -0,0 +1,640 @@ +/**************************************************************************** +** +** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/ +** +** This file is part of the plugins of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** GNU Lesser General Public License Usage +** This file may be used under the terms of the GNU Lesser General Public +** License version 2.1 as published by the Free Software Foundation and +** appearing in the file LICENSE.LGPL included in the packaging of this +** file. Please review the following information to ensure the GNU Lesser +** General Public License version 2.1 requirements will be met: +** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU General +** Public License version 3.0 as published by the Free Software Foundation +** and appearing in the file LICENSE.GPL included in the packaging of this +** file. Please review the following information to ensure the GNU General +** Public License version 3.0 requirements will be met: +** http://www.gnu.org/copyleft/gpl.html. +** +** Other Usage +** Alternatively, this file may be used in accordance with the terms and +** conditions contained in a signed written agreement between you and Nokia. +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + +#include "qxcbsharedbuffermanager.h" + +#include <QtCore/quuid.h> +#include <QtGui/qimage.h> + +#include <stdio.h> + +#if !defined(SHAREDGRAPHICSCACHE_MAX_MEMORY_USED) +# define SHAREDGRAPHICSCACHE_MAX_MEMORY_USED 16 * 1024 * 1024 // 16 MB limit +#endif + +#if !defined(SHAREDGRAPHICSCACHE_MAX_TEXTURES_PER_CACHE) +# define SHAREDGRAPHICSCACHE_MAX_TEXTURES_PER_CACHE 1 +#endif + +#if !defined(SHAREDGRAPHICSCACHE_TEXTURE_SIZE) +# define SHAREDGRAPHICSCACHE_TEXTURE_SIZE 2048 +#endif + +#define SHAREDBUFFERMANAGER_DEBUG 1 + +QT_BEGIN_NAMESPACE + +QXcbSharedBufferManager::QXcbSharedBufferManager() + : m_memoryUsed(0) + , m_mostRecentlyUsed(0) + , m_leastRecentlyUsed(0) +{ +} + +QXcbSharedBufferManager::~QXcbSharedBufferManager() +{ + { + QHash<QByteArray, Buffer *>::const_iterator it = m_buffers.constBegin(); + while (it != m_buffers.constEnd()) { + Buffer *buffer = it.value(); + delete buffer; + ++it; + } + } + + { + QHash<QByteArray, Items *>::const_iterator it = m_items.constBegin(); + while (it != m_items.constEnd()) { + Items *items = it.value(); + QHash<quint32, Item *>::const_iterator itemIt = items->items.constBegin(); + while (itemIt != items->items.constEnd()) { + delete itemIt.value(); + ++itemIt; + } + delete it.value(); + ++it; + } + } +} + +void QXcbSharedBufferManager::getBufferForItem(const QByteArray &cacheId, quint32 itemId, + Buffer **buffer, int *x, int *y) const +{ + Q_ASSERT_X(m_currentCacheId.isEmpty(), Q_FUNC_INFO, + "Call endSharedBufferAction before accessing data"); + + Q_ASSERT(buffer != 0); + Q_ASSERT(x != 0); + Q_ASSERT(y != 0); + + Items *items = itemsForCache(cacheId); + Item *item = items->items.value(itemId); + if (item != 0) { + *buffer = item->buffer; + *x = item->x; + *y = item->y; + } else { + *buffer = 0; + *x = -1; + *y = -1; + } +} + +QPair<QByteArray, int> QXcbSharedBufferManager::serializeBuffer(QSharedMemory *buffer) const +{ + Q_ASSERT_X(m_currentCacheId.isEmpty(), Q_FUNC_INFO, + "Call endSharedBufferAction before accessing data"); + + return qMakePair(buffer->key().toLatin1(), 0); +} + +void QXcbSharedBufferManager::beginSharedBufferAction(const QByteArray &cacheId) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::beginSharedBufferAction() called for %s", cacheId.constData()); +#endif + + Q_ASSERT(m_currentCacheId.isEmpty()); + Q_ASSERT(!cacheId.isEmpty()); + + m_pendingInvalidatedItems.clear(); + m_pendingReadyItems.clear(); + m_pendingMissingItems.clear(); + + m_currentCacheId = cacheId; +} + +void QXcbSharedBufferManager::requestItems(const QSet<quint32> &itemIds) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::requestItems for %d items", itemIds.size()); +#endif + + Q_ASSERT_X(!m_currentCacheId.isEmpty(), Q_FUNC_INFO, + "Call beginSharedBufferAction before requesting items"); + Items *items = itemsForCache(m_currentCacheId); + + QSet<quint32>::const_iterator it = itemIds.constBegin(); + while (it != itemIds.constEnd()) { + if (items->items.contains(*it)) + m_pendingReadyItems[m_currentCacheId].insert(*it); + else + m_pendingMissingItems[m_currentCacheId].insert(*it); + ++it; + } +} + +void QXcbSharedBufferManager::releaseItems(const QSet<quint32> &itemIds) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::releaseItems for %d items", itemIds.size()); +#endif + + Items *items = itemsForCache(m_currentCacheId); + + QSet<quint32>::const_iterator it; + for (it = itemIds.constBegin(); it != itemIds.constEnd(); ++it) { + Item *item = items->items.value(*it); + if (item != 0) + pushItemToBack(items, item); + + m_pendingReadyItems[m_currentCacheId].remove(*it); + m_pendingMissingItems[m_currentCacheId].remove(*it); + } +} + +void QXcbSharedBufferManager::insertItem(quint32 itemId, uchar *data, + int itemWidth, int itemHeight) +{ + Q_ASSERT_X(!m_currentCacheId.isEmpty(), Q_FUNC_INFO, + "Call beginSharedBufferAction before inserting items"); + Items *items = itemsForCache(m_currentCacheId); + + if (!items->items.contains(itemId)) { + Buffer *sharedBuffer = 0; + int x = 0; + int y = 0; + + findAvailableBuffer(itemWidth, itemHeight, &sharedBuffer, &x, &y); + copyIntoBuffer(sharedBuffer, x, y, itemWidth, itemHeight, data); + +// static int counter=0; +// QString fileName = QString::fromLatin1("buffer%1.png").arg(counter++); +// saveBuffer(sharedBuffer, fileName); + + Item *item = new Item; + item->itemId = itemId; + item->buffer = sharedBuffer; + item->x = x; + item->y = y; + + items->items[itemId] = item; + + touchItem(items, item); + } +} + +void QXcbSharedBufferManager::endSharedBufferAction() +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::endSharedBufferAction() called for %s", + m_currentCacheId.constData()); +#endif + + Q_ASSERT(!m_currentCacheId.isEmpty()); + + // Do an extra validation pass on the invalidated items since they may have been re-inserted + // after they were invalidated + if (m_pendingInvalidatedItems.contains(m_currentCacheId)) { + QSet<quint32> &invalidatedItems = m_pendingInvalidatedItems[m_currentCacheId]; + QSet<quint32>::iterator it = invalidatedItems.begin(); + while (it != invalidatedItems.end()) { + Items *items = m_items.value(m_currentCacheId); + + if (items->items.contains(*it)) { + m_pendingReadyItems[m_currentCacheId].insert(*it); + it = invalidatedItems.erase(it); + } else { + ++it; + } + } + } + + m_currentCacheId.clear(); +} + +void QXcbSharedBufferManager::pushItemToBack(Items *items, Item *item) +{ + if (items->leastRecentlyUsed == item) + return; + + if (item->next != 0) + item->next->prev = item->prev; + if (item->prev != 0) + item->prev->next = item->next; + + if (items->mostRecentlyUsed == item) + items->mostRecentlyUsed = item->prev; + + if (items->leastRecentlyUsed != 0) + items->leastRecentlyUsed->prev = item; + + item->prev = 0; + item->next = items->leastRecentlyUsed; + items->leastRecentlyUsed = item; + if (items->mostRecentlyUsed == 0) + items->mostRecentlyUsed = item; +} + +void QXcbSharedBufferManager::touchItem(Items *items, Item *item) +{ + if (items->mostRecentlyUsed == item) + return; + + if (item->next != 0) + item->next->prev = item->prev; + if (item->prev != 0) + item->prev->next = item->next; + + if (items->leastRecentlyUsed == item) + items->leastRecentlyUsed = item->next; + + if (items->mostRecentlyUsed != 0) + items->mostRecentlyUsed->next = item; + + item->next = 0; + item->prev = items->mostRecentlyUsed; + items->mostRecentlyUsed = item; + if (items->leastRecentlyUsed == 0) + items->leastRecentlyUsed = item; +} + +void QXcbSharedBufferManager::deleteItem(Items *items, Item *item) +{ + Q_ASSERT(items != 0); + Q_ASSERT(item != 0); + + if (items->mostRecentlyUsed == item) + items->mostRecentlyUsed = item->prev; + if (items->leastRecentlyUsed == item) + items->leastRecentlyUsed = item->next; + + if (item->next != 0) + item->next->prev = item->prev; + if (item->prev != 0) + item->prev->next = item->next; + + m_pendingInvalidatedItems[items->cacheId].insert(item->itemId); + + { + QHash<quint32, Item *>::iterator it = items->items.find(item->itemId); + while (it != items->items.end() && it.value()->itemId == item->itemId) + it = items->items.erase(it); + } + + delete item; +} + +void QXcbSharedBufferManager::recycleItem(Buffer **sharedBuffer, int *glyphX, int *glyphY) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::recycleItem() called for %s", m_currentCacheId.constData()); +#endif + + Items *items = itemsForCache(m_currentCacheId); + + Item *recycledItem = items->leastRecentlyUsed; + Q_ASSERT(recycledItem != 0); + + *sharedBuffer = recycledItem->buffer; + *glyphX = recycledItem->x; + *glyphY = recycledItem->y; + + deleteItem(items, recycledItem); +} + +void QXcbSharedBufferManager::touchBuffer(Buffer *buffer) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::touchBuffer() called for %s", buffer->cacheId.constData()); +#endif + + if (buffer == m_mostRecentlyUsed) + return; + + if (buffer->next != 0) + buffer->next->prev = buffer->prev; + if (buffer->prev != 0) + buffer->prev->next = buffer->next; + + if (m_leastRecentlyUsed == buffer) + m_leastRecentlyUsed = buffer->next; + + buffer->next = 0; + buffer->prev = m_mostRecentlyUsed; + if (m_mostRecentlyUsed != 0) + m_mostRecentlyUsed->next = buffer; + if (m_leastRecentlyUsed == 0) + m_leastRecentlyUsed = buffer; + m_mostRecentlyUsed = buffer; +} + +void QXcbSharedBufferManager::deleteLeastRecentlyUsed() +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::deleteLeastRecentlyUsed() called"); +#endif + + if (m_leastRecentlyUsed == 0) + return; + + Buffer *old = m_leastRecentlyUsed; + m_leastRecentlyUsed = old->next; + m_leastRecentlyUsed->prev = 0; + + QByteArray cacheId = old->cacheId; + Items *items = itemsForCache(cacheId); + + QHash<quint32, Item *>::iterator it = items->items.begin(); + while (it != items->items.end()) { + Item *item = it.value(); + if (item->buffer == old) { + deleteItem(items, item); + it = items->items.erase(it); + } else { + ++it; + } + } + + m_buffers.remove(cacheId, old); + m_memoryUsed -= old->width * old->height * old->bytesPerPixel; + +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::deleteLeastRecentlyUsed: Memory used: %d / %d (%6.2f %%)", + m_memoryUsed, SHAREDGRAPHICSCACHE_MAX_MEMORY_USED, + 100.0f * float(m_memoryUsed) / float(SHAREDGRAPHICSCACHE_MAX_MEMORY_USED)); +#endif + + delete old; +} + +QXcbSharedBufferManager::Buffer *QXcbSharedBufferManager::createNewBuffer(const QByteArray &cacheId, + int heightRequired) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::createNewBuffer() called for %s", cacheId.constData()); +#endif + + // ### + // if (bufferCount of cacheId == SHAREDGRAPHICACHE_MAX_TEXTURES_PER_CACHE) + // deleteLeastRecentlyUsedBufferForCache(cacheId); + + // ### Take pixel format into account + while (m_memoryUsed + SHAREDGRAPHICSCACHE_TEXTURE_SIZE * heightRequired >= SHAREDGRAPHICSCACHE_MAX_MEMORY_USED) + deleteLeastRecentlyUsed(); + + Buffer *buffer = allocateBuffer(SHAREDGRAPHICSCACHE_TEXTURE_SIZE, heightRequired); + buffer->cacheId = cacheId; + + buffer->currentLineMaxHeight = 0; + m_buffers.insert(cacheId, buffer); + + return buffer; +} + +static inline int qt_next_power_of_two(int v) +{ + v--; + v |= v >> 1; + v |= v >> 2; + v |= v >> 4; + v |= v >> 8; + v |= v >> 16; + ++v; + return v; +} + +QXcbSharedBufferManager::Buffer *QXcbSharedBufferManager::resizeBuffer(Buffer *oldBuffer, const QSize &newSize) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::resizeBuffer() called for %s (current size: %dx%d, new size: %dx%d)", + oldBuffer->cacheId.constData(), oldBuffer->width, oldBuffer->height, + newSize.width(), newSize.height()); +#endif + + // Remove old buffer from lists to avoid deleting it under our feet + if (m_leastRecentlyUsed == oldBuffer) + m_leastRecentlyUsed = oldBuffer->next; + if (m_mostRecentlyUsed == oldBuffer) + m_mostRecentlyUsed = oldBuffer->prev; + + if (oldBuffer->prev != 0) + oldBuffer->prev->next = oldBuffer->next; + if (oldBuffer->next != 0) + oldBuffer->next->prev = oldBuffer->prev; + + m_memoryUsed -= oldBuffer->width * oldBuffer->height * oldBuffer->bytesPerPixel; + m_buffers.remove(oldBuffer->cacheId, oldBuffer); + +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::resizeBuffer: Memory used: %d / %d (%6.2f %%)", + m_memoryUsed, SHAREDGRAPHICSCACHE_MAX_MEMORY_USED, + 100.0f * float(m_memoryUsed) / float(SHAREDGRAPHICSCACHE_MAX_MEMORY_USED)); +#endif + + Buffer *resizedBuffer = createNewBuffer(oldBuffer->cacheId, newSize.height()); + copyIntoBuffer(resizedBuffer, 0, 0, oldBuffer->width, oldBuffer->height, + reinterpret_cast<uchar *>(oldBuffer->buffer->data())); + + resizedBuffer->currentLineMaxHeight = oldBuffer->currentLineMaxHeight; + + Items *items = itemsForCache(oldBuffer->cacheId); + QHash<quint32, Item *>::const_iterator it = items->items.constBegin(); + while (it != items->items.constEnd()) { + Item *item = it.value(); + if (item->buffer == oldBuffer) { + m_pendingReadyItems[oldBuffer->cacheId].insert(item->itemId); + item->buffer = resizedBuffer; + } + ++it; + } + + resizedBuffer->nextX = oldBuffer->nextX; + resizedBuffer->nextY = oldBuffer->nextY; + resizedBuffer->currentLineMaxHeight = oldBuffer->currentLineMaxHeight; + + delete oldBuffer; + return resizedBuffer; +} + +void QXcbSharedBufferManager::findAvailableBuffer(int itemWidth, int itemHeight, + Buffer **sharedBuffer, int *glyphX, int *glyphY) +{ + Q_ASSERT(sharedBuffer != 0); + Q_ASSERT(glyphX != 0); + Q_ASSERT(glyphY != 0); + + QMultiHash<QByteArray, Buffer *>::iterator it = m_buffers.find(m_currentCacheId); + + int bufferCount = 0; + while (it != m_buffers.end() && it.key() == m_currentCacheId) { + Buffer *buffer = it.value(); + + int x = buffer->nextX; + int y = buffer->nextY; + int width = buffer->width; + int height = buffer->height; + + if (x + itemWidth <= width && y + itemHeight <= height) { + // There is space on the current line, put the item there + buffer->currentLineMaxHeight = qMax(buffer->currentLineMaxHeight, itemHeight); + *sharedBuffer = buffer; + *glyphX = x; + *glyphY = y; + + buffer->nextX += itemWidth; + + return; + } else if (itemWidth <= width && y + buffer->currentLineMaxHeight + itemHeight <= height) { + // There is space for a new line, put the item on the new line + buffer->nextX = 0; + buffer->nextY += buffer->currentLineMaxHeight; + buffer->currentLineMaxHeight = 0; + + *sharedBuffer = buffer; + *glyphX = buffer->nextX; + *glyphY = buffer->nextY; + + buffer->nextX += itemWidth; + + return; + } else if (y + buffer->currentLineMaxHeight + itemHeight <= SHAREDGRAPHICSCACHE_TEXTURE_SIZE) { + // There is space if we resize the buffer, so we do that + int newHeight = qt_next_power_of_two(y + buffer->currentLineMaxHeight + itemHeight); + buffer = resizeBuffer(buffer, QSize(width, newHeight)); + + buffer->nextX = 0; + buffer->nextY += buffer->currentLineMaxHeight; + buffer->currentLineMaxHeight = 0; + + *sharedBuffer = buffer; + *glyphX = buffer->nextX; + *glyphY = buffer->nextY; + + buffer->nextX += itemWidth; + return; + } + + bufferCount++; + ++it; + } + + if (bufferCount == SHAREDGRAPHICSCACHE_MAX_TEXTURES_PER_CACHE) { + // There is no space in any buffer, and there is no space for a new buffer + // recycle an old item + recycleItem(sharedBuffer, glyphX, glyphY); + } else { + // Create a new buffer for the item + *sharedBuffer = createNewBuffer(m_currentCacheId, qt_next_power_of_two(itemHeight)); + if (*sharedBuffer == 0) { + Q_ASSERT(false); + return; + } + + *glyphX = (*sharedBuffer)->nextX; + *glyphY = (*sharedBuffer)->nextY; + + (*sharedBuffer)->nextX += itemWidth; + } +} + +QXcbSharedBufferManager::Buffer *QXcbSharedBufferManager::allocateBuffer(int width, int height) +{ + Buffer *buffer = new Buffer; + buffer->nextX = 0; + buffer->nextY = 0; + buffer->width = width; + buffer->height = height; + buffer->bytesPerPixel = 1; // ### Use pixel format here + + buffer->buffer = new QSharedMemory(QUuid::createUuid().toString()); + bool ok = buffer->buffer->create(buffer->width * buffer->height * buffer->bytesPerPixel, + QSharedMemory::ReadWrite); + if (!ok) { + qWarning("SharedBufferManager::findAvailableBuffer: Can't create new buffer (%s)", + qPrintable(buffer->buffer->errorString())); + delete buffer; + return 0; + } + qMemSet(buffer->buffer->data(), 0, buffer->buffer->size()); + + m_memoryUsed += buffer->width * buffer->height * buffer->bytesPerPixel; + +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::allocateBuffer: Memory used: %d / %d (%6.2f %%)", + int(m_memoryUsed), int(SHAREDGRAPHICSCACHE_MAX_MEMORY_USED), + 100.0f * float(m_memoryUsed) / float(SHAREDGRAPHICSCACHE_MAX_MEMORY_USED)); +#endif + + return buffer; +} + +void QXcbSharedBufferManager::copyIntoBuffer(Buffer *buffer, + int bufferX, int bufferY, int width, int height, + uchar *data) +{ +#if defined(SHAREDBUFFERMANAGER_DEBUG) + qDebug("QXcbSharedBufferManager::copyIntoBuffer() called for %s (coords: %d, %d)", + buffer->cacheId.constData(), bufferX, bufferY); +#endif + + Q_ASSERT(bufferX >= 0); + Q_ASSERT(bufferX + width <= buffer->width); + Q_ASSERT(bufferY >= 0); + Q_ASSERT(bufferY + height <= buffer->height); + + uchar *dest = reinterpret_cast<uchar *>(buffer->buffer->data()); + dest += bufferX + bufferY * buffer->width; + for (int y=0; y<height; ++y) { + qMemCopy(dest, data, width); + + data += width; + dest += buffer->width; + } +} + +QXcbSharedBufferManager::Items *QXcbSharedBufferManager::itemsForCache(const QByteArray &cacheId) const +{ + Items *items = m_items.value(cacheId); + if (items == 0) { + items = new Items; + items->cacheId = cacheId; + m_items[cacheId] = items; + } + + return items; +} + +QT_END_NAMESPACE + +#endif // QT_USE_XCB_SHARED_GRAPHICS_CACHE diff --git a/src/plugins/platforms/xcb/qxcbsharedbuffermanager.h b/src/plugins/platforms/xcb/qxcbsharedbuffermanager.h new file mode 100644 index 0000000000..ca79b502c2 --- /dev/null +++ b/src/plugins/platforms/xcb/qxcbsharedbuffermanager.h @@ -0,0 +1,215 @@ +/**************************************************************************** +** +** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/ +** +** This file is part of the plugins of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** GNU Lesser General Public License Usage +** This file may be used under the terms of the GNU Lesser General Public +** License version 2.1 as published by the Free Software Foundation and +** appearing in the file LICENSE.LGPL included in the packaging of this +** file. Please review the following information to ensure the GNU Lesser +** General Public License version 2.1 requirements will be met: +** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU General +** Public License version 3.0 as published by the Free Software Foundation +** and appearing in the file LICENSE.GPL included in the packaging of this +** file. Please review the following information to ensure the GNU General +** Public License version 3.0 requirements will be met: +** http://www.gnu.org/copyleft/gpl.html. +** +** Other Usage +** Alternatively, this file may be used in accordance with the terms and +** conditions contained in a signed written agreement between you and Nokia. +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef XCBSHAREDBUFFERMANAGER_H +#define XCBSHAREDBUFFERMANAGER_H + +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + +#include <QtCore/qset.h> +#include <QtCore/qhash.h> +#include <QtCore/qsharedmemory.h> + +#include <GLES2/gl2.h> + +#include <EGL/egl.h> + +#include <EGL/eglext.h> + +class wl_resource; + +QT_BEGIN_HEADER + +QT_BEGIN_NAMESPACE + +class QXcbSharedBufferManager +{ +public: + struct Buffer { + Buffer() + : width(-1) + , height(-1) + , bytesPerPixel(1) + , nextX(-1) + , nextY(-1) + , currentLineMaxHeight(0) + , next(0) + , prev(0) + , buffer(0) + , textureId(0) + { + } + + ~Buffer() + { + delete buffer; + + if (textureId != 0) + glDeleteTextures(1, &textureId); + } + + QByteArray cacheId; + int width; + int height; + int bytesPerPixel; + int nextX; + int nextY; + int currentLineMaxHeight; + + Buffer *next; + Buffer *prev; + + QSharedMemory *buffer; + + GLuint textureId; + + QAtomicInt ref; + }; + + typedef QHash<QByteArray, QSet<quint32> > PendingItemIds; + + QXcbSharedBufferManager(); + ~QXcbSharedBufferManager(); + + void beginSharedBufferAction(const QByteArray &cacheId); + void insertItem(quint32 itemId, uchar *data, int itemWidth, int itemHeight); + void requestItems(const QSet<quint32> &itemIds); + void releaseItems(const QSet<quint32> &itemIds); + void endSharedBufferAction(); + + void getBufferForItem(const QByteArray &cacheId, quint32 itemId, Buffer **buffer, + int *x, int *y) const; + QPair<QByteArray, int> serializeBuffer(QSharedMemory *buffer) const; + + PendingItemIds pendingItemsInvalidated() const + { + Q_ASSERT_X(m_currentCacheId.isEmpty(), Q_FUNC_INFO, + "Call endSharedBufferAction() before accessing data"); + return m_pendingInvalidatedItems; + } + + PendingItemIds pendingItemsReady() const + { + Q_ASSERT_X(m_currentCacheId.isEmpty(), Q_FUNC_INFO, + "Call endSharedBufferAction() before accessing data"); + return m_pendingReadyItems; + } + + PendingItemIds pendingItemsMissing() const + { + Q_ASSERT_X(m_currentCacheId.isEmpty(), Q_FUNC_INFO, + "Call endSharedBufferAction() before accessing data"); + return m_pendingMissingItems; + } + +private: + struct Item { + Item() + : next(0) + , prev(0) + , buffer(0) + , itemId(0) + , x(-1) + , y(-1) + , width(-1) + , height(-1) + { + } + + Item *next; + Item *prev; + + Buffer *buffer; + quint32 itemId; + int x; + int y; + int width; + int height; + }; + + struct Items + { + Items() : leastRecentlyUsed(0), mostRecentlyUsed(0) {} + + Item *leastRecentlyUsed; + Item *mostRecentlyUsed; + + QByteArray cacheId; + QHash<quint32, Item *> items; + }; + + void findAvailableBuffer(int itemWidth, int itemHeight, Buffer **buffer, int *x, int *y); + void recycleItem(Buffer **buffer, int *x, int *y); + void copyIntoBuffer(Buffer *buffer, int x, int y, int itemWidth, int itemHeight, uchar *data); + void touchBuffer(Buffer *buffer); + void deleteLeastRecentlyUsed(); + + Buffer *createNewBuffer(const QByteArray &cacheId, int heightRequired); + Buffer *resizeBuffer(Buffer *buffer, const QSize &newSize); + Buffer *allocateBuffer(int width, int height); + + Items *itemsForCache(const QByteArray &cacheId) const; + void pushItemToBack(Items *items, Item *item); + void touchItem(Items *items, Item *item); + void deleteItem(Items *items, Item *item); + void recycleItem(const QByteArray &cacheId, Buffer **sharedBuffer, int *glyphX, int *glyphY); + + QByteArray m_currentCacheId; + + quint32 m_memoryUsed; + Buffer *m_mostRecentlyUsed; + Buffer *m_leastRecentlyUsed; + + mutable QHash<QByteArray, Items *> m_items; + QMultiHash<QByteArray, Buffer *> m_buffers; + + PendingItemIds m_pendingInvalidatedItems; + PendingItemIds m_pendingReadyItems; + PendingItemIds m_pendingMissingItems; +}; + +QT_END_NAMESPACE + +QT_END_HEADER + +#endif // QT_USE_XCB_SHARED_GRAPHICS_CACHE + +#endif // XCBSHAREDBUFFERMANAGER_H diff --git a/src/plugins/platforms/xcb/qxcbsharedgraphicscache.cpp b/src/plugins/platforms/xcb/qxcbsharedgraphicscache.cpp new file mode 100644 index 0000000000..fa937504ad --- /dev/null +++ b/src/plugins/platforms/xcb/qxcbsharedgraphicscache.cpp @@ -0,0 +1,290 @@ +/**************************************************************************** +** +** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/ +** +** This file is part of the plugins of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** GNU Lesser General Public License Usage +** This file may be used under the terms of the GNU Lesser General Public +** License version 2.1 as published by the Free Software Foundation and +** appearing in the file LICENSE.LGPL included in the packaging of this +** file. Please review the following information to ensure the GNU Lesser +** General Public License version 2.1 requirements will be met: +** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU General +** Public License version 3.0 as published by the Free Software Foundation +** and appearing in the file LICENSE.GPL included in the packaging of this +** file. Please review the following information to ensure the GNU General +** Public License version 3.0 requirements will be met: +** http://www.gnu.org/copyleft/gpl.html. +** +** Other Usage +** Alternatively, this file may be used in accordance with the terms and +** conditions contained in a signed written agreement between you and Nokia. +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + +#include "qxcbsharedgraphicscache.h" +#include "qxcbsharedbuffermanager.h" + +#include <QtCore/qsharedmemory.h> + +#include <QtGui/qopenglcontext.h> +#include <QtGui/qscreen.h> + +#define GL_GLEXT_PROTOTYPES +#include <GLES2/gl2ext.h> + +#define SHAREDGRAPHICSCACHE_DEBUG 1 + +QT_BEGIN_NAMESPACE + +QXcbSharedGraphicsCache::QXcbSharedGraphicsCache(QObject *parent) + : QPlatformSharedGraphicsCache(parent) + , m_bufferManager(new QXcbSharedBufferManager) +{ +} + +void QXcbSharedGraphicsCache::requestItems(const QByteArray &cacheId, + const QVector<quint32> &itemIds) +{ + m_bufferManager->beginSharedBufferAction(cacheId); + + QSet<quint32> itemsForRequest; + for (int i=0; i<itemIds.size(); ++i) + itemsForRequest.insert(itemIds.at(i)); + + m_bufferManager->requestItems(itemsForRequest); + m_bufferManager->endSharedBufferAction(); + + processPendingItems(); +} + +void QXcbSharedGraphicsCache::insertItems(const QByteArray &cacheId, + const QVector<quint32> &itemIds, + const QVector<QImage> &items) +{ + m_bufferManager->beginSharedBufferAction(cacheId); + + QSet<quint32> itemsForRequest; + for (int i=0; i<itemIds.size(); ++i) { + QImage image = items.at(i); + m_bufferManager->insertItem(itemIds.at(i), image.bits(), image.width(), image.height()); + itemsForRequest.insert(itemIds.at(i)); + } + + // ### To avoid loops, we could check missing items here and notify the client + m_bufferManager->requestItems(itemsForRequest); + + m_bufferManager->endSharedBufferAction(); + + processPendingItems(); +} + +void QXcbSharedGraphicsCache::ensureCacheInitialized(const QByteArray &cacheId, + BufferType bufferType, + PixelFormat pixelFormat) +{ + Q_UNUSED(cacheId); + Q_UNUSED(bufferType); + Q_UNUSED(pixelFormat); +} + + +void QXcbSharedGraphicsCache::releaseItems(const QByteArray &cacheId, + const QVector<quint32> &itemIds) +{ + m_bufferManager->beginSharedBufferAction(cacheId); + + QSet<quint32> itemsToRelease; + for (int i=0; i<itemIds.size(); ++i) + itemsToRelease.insert(itemIds.at(i)); + + m_bufferManager->releaseItems(itemsToRelease); + + m_bufferManager->endSharedBufferAction(); + + processPendingItems(); +} + +void QXcbSharedGraphicsCache::serializeBuffer(void *bufferId, + QByteArray *serializedData, + int *fileDescriptor) const +{ + QXcbSharedBufferManager::Buffer *buffer = + reinterpret_cast<QXcbSharedBufferManager::Buffer *>(bufferId); + + QPair<QByteArray, int> bufferName = m_bufferManager->serializeBuffer(buffer->buffer); + + *serializedData = bufferName.first; + *fileDescriptor = bufferName.second; +} + +GLuint QXcbSharedGraphicsCache::textureIdForBuffer(void *bufferId) +{ +# if defined(SHAREDGRAPHICSCACHE_DEBUG) + qDebug("QXcbSharedGraphicsCache::textureIdForBuffer"); +# endif + + QXcbSharedBufferManager::Buffer *buffer = + reinterpret_cast<QXcbSharedBufferManager::Buffer *>(bufferId); + + if (buffer->textureId == 0) { + glGenTextures(1, &buffer->textureId); + if (buffer->textureId == 0) { + qWarning("QXcbSharedGraphicsCache::textureIdForBuffer: Failed to generate texture (gl error: 0x%x)", + glGetError()); + return 0; + } + + glBindTexture(GL_TEXTURE_2D, buffer->textureId); + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); + } + + glBindTexture(GL_TEXTURE_2D, buffer->textureId); + glTexImage2D(GL_TEXTURE_2D, 0, GL_ALPHA, buffer->width, buffer->height, 0, GL_ALPHA, + GL_UNSIGNED_BYTE, buffer->buffer->data()); + glBindTexture(GL_TEXTURE_2D, 0); + + return buffer->textureId; +} + +void QXcbSharedGraphicsCache::referenceBuffer(void *bufferId) +{ + QXcbSharedBufferManager::Buffer *buffer = + reinterpret_cast<QXcbSharedBufferManager::Buffer *>(bufferId); + + buffer->ref.ref(); +} + +bool QXcbSharedGraphicsCache::dereferenceBuffer(void *bufferId) +{ + QXcbSharedBufferManager::Buffer *buffer = + reinterpret_cast<QXcbSharedBufferManager::Buffer *>(bufferId); + + if (buffer->ref.deref()) + return true; + + if (buffer->textureId != 0) { + glDeleteTextures(1, &buffer->textureId); + buffer->textureId = 0; + } + + return false; +} + +void QXcbSharedGraphicsCache::processPendingItems() +{ +# if defined(SHAREDGRAPHICSCACHE_DEBUG) + qDebug("QXcbSharedGraphicsCache::processPendingItems"); +# endif + + { + QXcbSharedBufferManager::PendingItemIds pendingMissingItems = m_bufferManager->pendingItemsMissing(); + QXcbSharedBufferManager::PendingItemIds::const_iterator it; + + + for (it = pendingMissingItems.constBegin(); it != pendingMissingItems.constEnd(); ++it) { + QVector<quint32> missingItems; + + const QSet<quint32> &items = it.value(); + QSet<quint32>::const_iterator itemIt; + for (itemIt = items.constBegin(); itemIt != items.constEnd(); ++itemIt) + missingItems.append(*itemIt); + +# if defined(SHAREDGRAPHICSCACHE_DEBUG) + qDebug("QXcbSharedGraphicsCache::processPendingItems: %d missing items", + missingItems.size()); +# endif + + if (!missingItems.isEmpty()) + emit itemsMissing(it.key(), missingItems); + } + } + + { + QXcbSharedBufferManager::PendingItemIds pendingInvalidatedItems = m_bufferManager->pendingItemsInvalidated(); + QXcbSharedBufferManager::PendingItemIds::const_iterator it; + + for (it = pendingInvalidatedItems.constBegin(); it != pendingInvalidatedItems.constEnd(); ++it) { + QVector<quint32> invalidatedItems; + + const QSet<quint32> &items = it.value(); + QSet<quint32>::const_iterator itemIt; + for (itemIt = items.constBegin(); itemIt != items.constEnd(); ++itemIt) + invalidatedItems.append(*itemIt); + +# if defined(SHAREDGRAPHICSCACHE_DEBUG) + qDebug("QXcbSharedGraphicsCache::processPendingItems: %d invalidated items", + invalidatedItems.size()); +# endif + + if (!invalidatedItems.isEmpty()) + emit itemsInvalidated(it.key(), invalidatedItems); + } + } + + { + QXcbSharedBufferManager::PendingItemIds pendingReadyItems = m_bufferManager->pendingItemsReady(); + QXcbSharedBufferManager::PendingItemIds::const_iterator it; + + for (it = pendingReadyItems.constBegin(); it != pendingReadyItems.constEnd(); ++it) { + QHash<QXcbSharedBufferManager::Buffer *, ReadyItem> readyItemsForBuffer; + const QSet<quint32> &items = it.value(); + + QByteArray cacheId = it.key(); + + QSet<quint32>::const_iterator itemIt; + for (itemIt = items.constBegin(); itemIt != items.constEnd(); ++itemIt) { + QXcbSharedBufferManager::Buffer *buffer; + int x = -1; + int y = -1; + + m_bufferManager->getBufferForItem(cacheId, *itemIt, &buffer, &x, &y); + + readyItemsForBuffer[buffer].itemIds.append(*itemIt); + readyItemsForBuffer[buffer].positions.append(QPoint(x, y)); + } + + QHash<QXcbSharedBufferManager::Buffer*, ReadyItem>::iterator readyItemIt + = readyItemsForBuffer.begin(); + while (readyItemIt != readyItemsForBuffer.end()) { + QXcbSharedBufferManager::Buffer *buffer = readyItemIt.key(); + if (!readyItemIt.value().itemIds.isEmpty()) { +# if defined(SHAREDGRAPHICSCACHE_DEBUG) + qDebug("QXcbSharedGraphicsCache::processPendingItems: %d ready items", + readyItemIt.value().itemIds.size()); +# endif + + emit itemsAvailable(cacheId, buffer, QSize(buffer->width, buffer->height), + readyItemIt.value().itemIds, readyItemIt.value().positions); + } + ++readyItemIt; + } + } + } +} + +QT_END_NAMESPACE + +#endif // QT_USE_XCB_SHARED_GRAPHICS_CACHE diff --git a/src/plugins/platforms/xcb/qxcbsharedgraphicscache.h b/src/plugins/platforms/xcb/qxcbsharedgraphicscache.h new file mode 100644 index 0000000000..e565556463 --- /dev/null +++ b/src/plugins/platforms/xcb/qxcbsharedgraphicscache.h @@ -0,0 +1,91 @@ +/**************************************************************************** +** +** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/ +** +** This file is part of the plugins of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** GNU Lesser General Public License Usage +** This file may be used under the terms of the GNU Lesser General Public +** License version 2.1 as published by the Free Software Foundation and +** appearing in the file LICENSE.LGPL included in the packaging of this +** file. Please review the following information to ensure the GNU Lesser +** General Public License version 2.1 requirements will be met: +** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU General +** Public License version 3.0 as published by the Free Software Foundation +** and appearing in the file LICENSE.GPL included in the packaging of this +** file. Please review the following information to ensure the GNU General +** Public License version 3.0 requirements will be met: +** http://www.gnu.org/copyleft/gpl.html. +** +** Other Usage +** Alternatively, this file may be used in accordance with the terms and +** conditions contained in a signed written agreement between you and Nokia. +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef QXCBSHAREDGRAPHICSCACHE +#define QXCBSHAREDGRAPHICSCACHE + +#if defined(QT_USE_XCB_SHARED_GRAPHICS_CACHE) + +#include <QtGui/qplatformsharedgraphicscache_qpa.h> + +QT_BEGIN_HEADER + +QT_BEGIN_NAMESPACE + +class QXcbSharedBufferManager; +class QXcbSharedGraphicsCache : public QPlatformSharedGraphicsCache +{ + Q_OBJECT +public: + explicit QXcbSharedGraphicsCache(QObject *parent = 0); + + virtual void ensureCacheInitialized(const QByteArray &cacheId, BufferType bufferType, + PixelFormat pixelFormat); + + virtual void requestItems(const QByteArray &cacheId, const QVector<quint32> &itemIds); + virtual void insertItems(const QByteArray &cacheId, + const QVector<quint32> &itemIds, + const QVector<QImage> &items); + virtual void releaseItems(const QByteArray &cacheId, const QVector<quint32> &itemIds); + + virtual void serializeBuffer(void *bufferId, QByteArray *serializedData, int *fileDescriptor) const; + virtual uint textureIdForBuffer(void *bufferId); + virtual void referenceBuffer(void *bufferId); + virtual bool dereferenceBuffer(void *bufferId); + +private: + struct ReadyItem { + QVector<quint32> itemIds; + QVector<QPoint> positions; + }; + + void processPendingItems(); + + QXcbSharedBufferManager *m_bufferManager; +}; + +QT_END_NAMESPACE + +QT_END_HEADER + +#endif // QT_USE_XCB_SHARED_GRAPHICS_CACHE + +#endif // QXCBSHAREDGRAPHICSCACHE diff --git a/src/plugins/platforms/xcb/qxcbwindow.cpp b/src/plugins/platforms/xcb/qxcbwindow.cpp index 2cd2a15fb7..959209dd33 100644 --- a/src/plugins/platforms/xcb/qxcbwindow.cpp +++ b/src/plugins/platforms/xcb/qxcbwindow.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -130,10 +130,8 @@ static inline QImage::Format imageFormatForDepth(int depth) case 32: return QImage::Format_ARGB32_Premultiplied; case 24: return QImage::Format_RGB32; case 16: return QImage::Format_RGB16; - default: break; + default: return QImage::Format_Invalid; } - qFatal("Unsupported display depth %d", depth); - return QImage::Format_Invalid; } QXcbWindow::QXcbWindow(QWindow *window) @@ -211,7 +209,8 @@ void QXcbWindow::create() { #if defined(XCB_USE_GLX) XVisualInfo *visualInfo = qglx_findVisualInfo(DISPLAY_FROM_XCB(m_screen),m_screen->screenNumber(), window()->format()); - + if (!visualInfo) + qFatal("Could not initialize GLX"); #elif defined(XCB_USE_EGL) EGLDisplay eglDisplay = connection()->egl_display(); EGLConfig eglConfig = q_configFromGLFormat(eglDisplay, window()->format(), true); @@ -224,25 +223,25 @@ void QXcbWindow::create() XVisualInfo *visualInfo; int matchingCount = 0; visualInfo = XGetVisualInfo(DISPLAY_FROM_XCB(this), VisualIDMask, &visualInfoTemplate, &matchingCount); + if (!visualInfo) + qFatal("Could not initialize EGL"); #endif //XCB_USE_GLX - if (visualInfo) { - m_depth = visualInfo->depth; - m_imageFormat = imageFormatForDepth(m_depth); - Colormap cmap = XCreateColormap(DISPLAY_FROM_XCB(this), xcb_parent_id, visualInfo->visual, AllocNone); + m_depth = visualInfo->depth; + m_imageFormat = imageFormatForDepth(m_depth); + Colormap cmap = XCreateColormap(DISPLAY_FROM_XCB(this), xcb_parent_id, visualInfo->visual, AllocNone); - XSetWindowAttributes a; - a.background_pixel = WhitePixel(DISPLAY_FROM_XCB(this), m_screen->screenNumber()); - a.border_pixel = BlackPixel(DISPLAY_FROM_XCB(this), m_screen->screenNumber()); - a.colormap = cmap; + XSetWindowAttributes a; + a.background_pixel = WhitePixel(DISPLAY_FROM_XCB(this), m_screen->screenNumber()); + a.border_pixel = BlackPixel(DISPLAY_FROM_XCB(this), m_screen->screenNumber()); + a.colormap = cmap; - m_visualId = visualInfo->visualid; + m_visualId = visualInfo->visualid; - m_window = XCreateWindow(DISPLAY_FROM_XCB(this), xcb_parent_id, rect.x(), rect.y(), rect.width(), rect.height(), - 0, visualInfo->depth, InputOutput, visualInfo->visual, - CWBackPixel|CWBorderPixel|CWColormap, &a); - } else { - qFatal("no window!"); - } + m_window = XCreateWindow(DISPLAY_FROM_XCB(this), xcb_parent_id, rect.x(), rect.y(), rect.width(), rect.height(), + 0, visualInfo->depth, InputOutput, visualInfo->visual, + CWBackPixel|CWBorderPixel|CWColormap, &a); + + XFree(visualInfo); } else #endif //defined(XCB_USE_GLX) || defined(XCB_USE_EGL) { @@ -1148,6 +1147,23 @@ void QXcbWindow::requestActivateWindow() connection()->sync(); } +#if XCB_USE_MAEMO_WINDOW_PROPERTIES +void QXcbWindow::setOrientation(Qt::ScreenOrientation orientation) +{ + int angle = 0; + switch (orientation) { + case Qt::PortraitOrientation: angle = 270; break; + case Qt::LandscapeOrientation: angle = 0; break; + case Qt::InvertedPortraitOrientation: angle = 90; break; + case Qt::InvertedLandscapeOrientation: angle = 180; break; + case Qt::PrimaryOrientation: break; + } + Q_XCB_CALL(xcb_change_property(xcb_connection(), XCB_PROP_MODE_REPLACE, m_window, + atom(QXcbAtom::MeegoTouchOrientationAngle), XCB_ATOM_CARDINAL, 32, + 1, &angle)); +} +#endif + QSurfaceFormat QXcbWindow::format() const { // ### return actual format diff --git a/src/plugins/platforms/xcb/qxcbwindow.h b/src/plugins/platforms/xcb/qxcbwindow.h index f0b6437699..3cbf9e7e0d 100644 --- a/src/plugins/platforms/xcb/qxcbwindow.h +++ b/src/plugins/platforms/xcb/qxcbwindow.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -79,6 +79,10 @@ public: void requestActivateWindow(); +#if XCB_USE_MAEMO_WINDOW_PROPERTIES + void setOrientation(Qt::ScreenOrientation orientation); +#endif + bool setKeyboardGrabEnabled(bool grab); bool setMouseGrabEnabled(bool grab); diff --git a/src/plugins/platforms/xcb/qxcbwmsupport.cpp b/src/plugins/platforms/xcb/qxcbwmsupport.cpp index f06c9c503c..114049f911 100644 --- a/src/plugins/platforms/xcb/qxcbwmsupport.cpp +++ b/src/plugins/platforms/xcb/qxcbwmsupport.cpp @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/qxcbwmsupport.h b/src/plugins/platforms/xcb/qxcbwmsupport.h index faa0934a3d..159aace8ee 100644 --- a/src/plugins/platforms/xcb/qxcbwmsupport.h +++ b/src/plugins/platforms/xcb/qxcbwmsupport.h @@ -1,8 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) +** Contact: http://www.qt-project.org/ ** ** This file is part of the plugins of the Qt Toolkit. ** @@ -35,6 +34,7 @@ ** ** ** +** ** $QT_END_LICENSE$ ** ****************************************************************************/ diff --git a/src/plugins/platforms/xcb/xcb.pro b/src/plugins/platforms/xcb/xcb.pro index 2498581eb7..d80a6df0b6 100644 --- a/src/plugins/platforms/xcb/xcb.pro +++ b/src/plugins/platforms/xcb/xcb.pro @@ -5,6 +5,7 @@ QTDIR_build:DESTDIR = $$QT_BUILD_TREE/plugins/platforms QT += core-private gui-private platformsupport-private + SOURCES = \ qxcbclipboard.cpp \ qxcbconnection.cpp \ @@ -19,7 +20,9 @@ SOURCES = \ main.cpp \ qxcbnativeinterface.cpp \ qxcbcursor.cpp \ - qxcbimage.cpp + qxcbimage.cpp \ + qxcbsharedbuffermanager.cpp \ + qxcbsharedgraphicscache.cpp HEADERS = \ qxcbclipboard.h \ @@ -35,7 +38,9 @@ HEADERS = \ qxcbwmsupport.h \ qxcbnativeinterface.h \ qxcbcursor.h \ - qxcbimage.h + qxcbimage.h \ + qxcbsharedbuffermanager.h \ + qxcbsharedgraphicscache.h contains(QT_CONFIG, xcb-poll-for-queued-event) { DEFINES += XCB_POLL_FOR_QUEUED_EVENT @@ -46,11 +51,14 @@ contains(QT_CONFIG, xcb-xlib) { DEFINES += XCB_USE_XLIB LIBS += -lX11 -lX11-xcb - linux-g++-maemo:contains(QT_CONFIG, xinput2) { - # XInput2 support for Harmattan. - DEFINES += XCB_USE_XINPUT2_MAEMO - SOURCES += qxcbconnection_maemo.cpp - LIBS += -lXi + linux-g++-maemo { + contains(QT_CONFIG, xinput2) { + # XInput2 support for Harmattan. + DEFINES += XCB_USE_XINPUT2_MAEMO + SOURCES += qxcbconnection_maemo.cpp + LIBS += -lXi + } + DEFINES += XCB_USE_MAEMO_WINDOW_PROPERTIES } } |