core: Introduce GraphicsBufferView

GraphicsBufferView provides a way to map the contents of a graphics
buffer as an image.
This commit is contained in:
Vlad Zahorodnii 2023-05-25 10:40:01 +03:00
parent 592948e5ab
commit f1d6366d4a
5 changed files with 136 additions and 0 deletions

View file

@ -42,6 +42,7 @@ target_sources(kwin PRIVATE
core/gbmgraphicsbufferallocator.cpp
core/graphicsbuffer.cpp
core/graphicsbufferallocator.cpp
core/graphicsbufferview.cpp
core/inputbackend.cpp
core/inputdevice.cpp
core/output.cpp

View file

@ -53,6 +53,15 @@ void GraphicsBuffer::drop()
}
}
void *GraphicsBuffer::map()
{
return nullptr;
}
void GraphicsBuffer::unmap()
{
}
const DmaBufAttributes *GraphicsBuffer::dmabufAttributes() const
{
return nullptr;

View file

@ -58,6 +58,9 @@ public:
void unref();
void drop();
virtual void *map();
virtual void unmap();
virtual QSize size() const = 0;
virtual bool hasAlphaChannel() const = 0;

View file

@ -0,0 +1,91 @@
/*
SPDX-FileCopyrightText: 2023 Vlad Zahorodnii <vlad.zahorodnii@kde.org>
SPDX-License-Identifier: GPL-2.0-or-later
*/
#include "core/graphicsbufferview.h"
#include "core/graphicsbuffer.h"
#include "utils/common.h"
#include <drm_fourcc.h>
namespace KWin
{
static QImage::Format drmFormatToQImageFormat(uint32_t drmFormat)
{
switch (drmFormat) {
#if Q_BYTE_ORDER == Q_LITTLE_ENDIAN
case DRM_FORMAT_ABGR16161616:
return QImage::Format_RGBA64_Premultiplied;
case DRM_FORMAT_XBGR16161616:
return QImage::Format_RGBX64;
case DRM_FORMAT_ARGB2101010:
return QImage::Format_A2RGB30_Premultiplied;
case DRM_FORMAT_XRGB2101010:
return QImage::Format_RGB30;
case DRM_FORMAT_ABGR2101010:
return QImage::Format_A2BGR30_Premultiplied;
case DRM_FORMAT_XBGR2101010:
return QImage::Format_BGR30;
#endif
case DRM_FORMAT_ARGB8888:
return QImage::Format_ARGB32_Premultiplied;
case DRM_FORMAT_XRGB8888:
return QImage::Format_RGB32;
default:
return QImage::Format_Invalid;
}
}
GraphicsBufferView::GraphicsBufferView(GraphicsBuffer *buffer)
: m_buffer(buffer)
{
int width;
int height;
int stride;
int format;
if (auto dmabuf = buffer->dmabufAttributes()) {
if (dmabuf->planeCount != 1) {
return;
}
width = dmabuf->width;
height = dmabuf->height;
stride = dmabuf->pitch[0];
format = dmabuf->format;
} else if (auto shm = buffer->shmAttributes()) {
width = shm->size.width();
height = shm->size.height();
stride = shm->stride;
format = shm->format;
} else {
qCWarning(KWIN_CORE) << "Cannot create a graphics buffer view for unknown buffer type" << buffer;
return;
}
void *data = buffer->map();
if (data) {
m_image = QImage(static_cast<uchar *>(data), width, height, stride, drmFormatToQImageFormat(format));
}
}
GraphicsBufferView::~GraphicsBufferView()
{
if (!m_image.isNull()) {
m_buffer->unmap();
}
}
QImage *GraphicsBufferView::image()
{
return &m_image;
}
const QImage *GraphicsBufferView::image() const
{
return &m_image;
}
} // namespace KWin

View file

@ -0,0 +1,32 @@
/*
SPDX-FileCopyrightText: 2023 Vlad Zahorodnii <vlad.zahorodnii@kde.org>
SPDX-License-Identifier: GPL-2.0-or-later
*/
#pragma once
#include "kwin_export.h"
#include <QImage>
namespace KWin
{
class GraphicsBuffer;
class KWIN_EXPORT GraphicsBufferView
{
public:
explicit GraphicsBufferView(GraphicsBuffer *buffer);
~GraphicsBufferView();
QImage *image();
const QImage *image() const;
private:
GraphicsBuffer *m_buffer;
QImage m_image;
};
} // namespace KWin