From 2322ef51948ef20afb3a93d1fea7830dfee4f7d6 Mon Sep 17 00:00:00 2001 From: Jorgen Lind Date: Thu, 25 Dec 2014 20:42:56 +0100 Subject: Add a SHM format converter class This class helps keeing one lookuptable for server and client It relies on that wayland-(client|server)-protocol.h being included before the qwaylandshmformathelper.h Change-Id: I12158126a80c8fef5c52427d35792f33716020f1 Reviewed-by: Giulio Camuffo --- src/client/qwaylandshmbackingstore.cpp | 6 +- src/compositor/wayland_wrapper/qwlcompositor.cpp | 4 + .../wayland_wrapper/qwlsurfacebuffer.cpp | 6 +- src/shared/qwaylandshmformathelper.h | 138 +++++++++++++++++++++ 4 files changed, 152 insertions(+), 2 deletions(-) create mode 100644 src/shared/qwaylandshmformathelper.h (limited to 'src') diff --git a/src/client/qwaylandshmbackingstore.cpp b/src/client/qwaylandshmbackingstore.cpp index 64e93d947..8eab510bf 100644 --- a/src/client/qwaylandshmbackingstore.cpp +++ b/src/client/qwaylandshmbackingstore.cpp @@ -49,6 +49,9 @@ #include #include +#include +#include "qwaylandshmformathelper.h" + #include #include #include @@ -89,12 +92,13 @@ QWaylandShmBuffer::QWaylandShmBuffer(QWaylandDisplay *display, return; } + wl_shm_format wl_format = QWaylandShmFormatHelper::fromQImageFormat(format); mImage = QImage(data, size.width(), size.height(), stride, format); mImage.setDevicePixelRatio(qreal(scale)); mShmPool = wl_shm_create_pool(display->shm(), fd, alloc); mBuffer = wl_shm_pool_create_buffer(mShmPool,0, size.width(), size.height(), - stride, WL_SHM_FORMAT_ARGB8888); + stride, wl_format); close(fd); } diff --git a/src/compositor/wayland_wrapper/qwlcompositor.cpp b/src/compositor/wayland_wrapper/qwlcompositor.cpp index 91fd1818a..6eee0770c 100644 --- a/src/compositor/wayland_wrapper/qwlcompositor.cpp +++ b/src/compositor/wayland_wrapper/qwlcompositor.cpp @@ -62,6 +62,7 @@ #include "qwltextinputmanager_p.h" #include "qwaylandglobalinterface.h" #include "qwaylandsurfaceview.h" +#include "qwaylandshmformathelper.h" #include #include @@ -145,6 +146,9 @@ void Compositor::init() m_data_device_manager = new DataDeviceManager(this); wl_display_init_shm(m_display->handle()); + QVector formats = QWaylandShmFormatHelper::supportedWaylandFormats(); + foreach (wl_shm_format format, formats) + wl_display_add_shm_format(m_display->handle(), format); m_output_global = new OutputGlobal(m_display->handle()); diff --git a/src/compositor/wayland_wrapper/qwlsurfacebuffer.cpp b/src/compositor/wayland_wrapper/qwlsurfacebuffer.cpp index 1ed1fefd8..8f12590dd 100644 --- a/src/compositor/wayland_wrapper/qwlsurfacebuffer.cpp +++ b/src/compositor/wayland_wrapper/qwlsurfacebuffer.cpp @@ -50,6 +50,9 @@ #include +#include +#include "qwaylandshmformathelper.h" + QT_BEGIN_NAMESPACE namespace QtWayland { @@ -235,7 +238,8 @@ QImage SurfaceBuffer::image() int stride = wl_shm_buffer_get_stride(m_shmBuffer); int width = wl_shm_buffer_get_width(m_shmBuffer); int height = wl_shm_buffer_get_height(m_shmBuffer); - m_image = QImage(data, width, height, stride, QImage::Format_ARGB32_Premultiplied); + QImage::Format format = QWaylandShmFormatHelper::fromWaylandShmFormat(wl_shm_format(wl_shm_buffer_get_format(m_shmBuffer))); + m_image = QImage(data, width, height, stride, format); } return m_image; diff --git a/src/shared/qwaylandshmformathelper.h b/src/shared/qwaylandshmformathelper.h new file mode 100644 index 000000000..131ad780d --- /dev/null +++ b/src/shared/qwaylandshmformathelper.h @@ -0,0 +1,138 @@ +/**************************************************************************** +** +** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/legal +** +** This file is part of the plugins of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** Commercial License Usage +** Licensees holding valid commercial Qt licenses may use this file in +** accordance with the commercial license agreement provided with the +** Software or, alternatively, in accordance with the terms contained in +** a written agreement between you and Digia. For licensing terms and +** conditions see http://qt.digia.com/licensing. For further information +** use the contact form at http://qt.digia.com/contact-us. +** +** GNU Lesser General Public License Usage +** Alternatively, 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, Digia gives you certain additional +** rights. These rights are described in the Digia 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. +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef QWAYLANDSHMFORMATHELPER_H +#define QWAYLANDSHMFORMATHELPER_H + +#include + +//the correct protocol header for the wayland server or wayland client has to be +//included before this file is included + +QT_BEGIN_NAMESPACE + +class QWaylandShmFormatHelper +{ +public: + static inline wl_shm_format fromQImageFormat(QImage::Format format); + static inline QImage::Format fromWaylandShmFormat(wl_shm_format format); + static inline QVector supportedWaylandFormats(); + +private: +//IMPLEMENTATION (which has to be inline in the header because of the include trick) + struct Array + { + Array(const size_t size, const wl_shm_format *data) + : size(size) + , data(data) + { } + const size_t size; + const wl_shm_format *data; + }; + + static const Array getData() + { + static wl_shm_format formats_array[] = { + wl_shm_format(INT_MIN), //Format_Invalid, + wl_shm_format(INT_MIN), //Format_Mono, + wl_shm_format(INT_MIN), //Format_MonoLSB, + wl_shm_format(INT_MIN), //Format_Indexed8, + WL_SHM_FORMAT_XRGB8888, //Format_RGB32, + WL_SHM_FORMAT_ARGB8888, //Format_ARGB32, + WL_SHM_FORMAT_ARGB8888, //Format_ARGB32_Premultiplied, + WL_SHM_FORMAT_RGB565, //Format_RGB16, + wl_shm_format(INT_MIN), //Format_ARGB8565_Premultiplied, + wl_shm_format(INT_MIN), //Format_RGB666, + wl_shm_format(INT_MIN), //Format_ARGB6666_Premultiplied, + WL_SHM_FORMAT_XRGB1555, //Format_RGB555, + wl_shm_format(INT_MIN), //Format_ARGB8555_Premultiplied, + WL_SHM_FORMAT_RGB888, //Format_RGB888, + WL_SHM_FORMAT_XRGB4444, //Format_RGB444, + WL_SHM_FORMAT_ARGB4444, //Format_ARGB4444_Premultiplied, + WL_SHM_FORMAT_XBGR8888, //Format_RGBX8888, + WL_SHM_FORMAT_ABGR8888, //Format_RGBA8888, + WL_SHM_FORMAT_ABGR8888, //Format_RGBA8888_Premultiplied, + WL_SHM_FORMAT_XBGR2101010, //Format_BGR30, + WL_SHM_FORMAT_ARGB2101010, //Format_A2BGR30_Premultiplied, + WL_SHM_FORMAT_XRGB2101010, //Format_RGB30, + WL_SHM_FORMAT_ARGB2101010, //Format_A2RGB30_Premultiplied, + WL_SHM_FORMAT_C8, //Format_Alpha8, + WL_SHM_FORMAT_C8 //Format_Grayscale8, + }; + const size_t size = sizeof(formats_array) / sizeof(*formats_array); + return Array(size, formats_array); + } +}; + +wl_shm_format QWaylandShmFormatHelper::fromQImageFormat(QImage::Format format) +{ + Array array = getData(); + if (array.size <= size_t(format)) + return wl_shm_format(INT_MIN); + return array.data[format]; +} + +QImage::Format QWaylandShmFormatHelper::fromWaylandShmFormat(wl_shm_format format) +{ + Array array = getData(); + for (size_t i = 0; i < array.size; i++) { + if (array.data[i] == format) + return QImage::Format(i); + } + return QImage::Format_Invalid; +} + +QVector QWaylandShmFormatHelper::supportedWaylandFormats() +{ + QVector retFormats; + Array array = getData(); + for (size_t i = 0; i < array.size; i++) { + if (int(array.data[i]) != INT_MIN + && !retFormats.contains(array.data[i])) { + retFormats.append(array.data[i]); + } + } + return retFormats; +} + +QT_END_NAMESPACE + +#endif //QWAYLANDSHMFORMATHELPER_H -- cgit v1.2.3