[aurorae] Hack to get Aurorae work with compositing
This is a temporary solution! A proper solution needs changes in libkdecoration and paint redirector. The hack redirects the rendering into an FBO. After each rendering we get a QImage from the FBO and store that in a buffer. As we unfortunately do not know what changed, we schedule a complete update on the deco's widget. Once we get the paint event we just render the buffer on the widget. And thus we have copied the content to a place where it integrates with the paint redirector. As already written, this is a horrible hack and I'm not proud about it. There are just too many copies involved. So how to improve? * deco should be able to just provide a QImage to the PaintRedirector without the paint to the QWidget. * only do the FBO -> QImage step if it is needed by the compositor, that is compress the events * for OpenGL compositing it would be totally awesome if we could just make the contexts sharing so that we can just reuse the texture from the FBO directly.
This commit is contained in:
parent
93c2eea528
commit
dd6598c1ff
2 changed files with 28 additions and 0 deletions
|
@ -21,6 +21,8 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|||
|
||||
#include <QApplication>
|
||||
#include <QDebug>
|
||||
#include <QOpenGLFramebufferObject>
|
||||
#include <QPainter>
|
||||
#include <QQmlComponent>
|
||||
#include <QQmlContext>
|
||||
#include <QQmlEngine>
|
||||
|
@ -259,6 +261,24 @@ void AuroraeClient::init()
|
|||
widget()->setAttribute(Qt::WA_NoSystemBackground);
|
||||
widget()->installEventFilter(this);
|
||||
m_view = new QQuickWindow();
|
||||
if (compositingActive()) {
|
||||
connect(m_view, &QQuickWindow::beforeRendering, [this]() {
|
||||
if (m_fbo.isNull() || m_fbo->size() != QSize(width(), height())) {
|
||||
m_fbo.reset(new QOpenGLFramebufferObject(QSize(width(), height()), QOpenGLFramebufferObject::CombinedDepthStencil));
|
||||
if (!m_fbo->isValid()) {
|
||||
qWarning() << "Creating FBO as render target failed";
|
||||
m_fbo.reset();
|
||||
return;
|
||||
}
|
||||
}
|
||||
m_view->setRenderTarget(m_fbo.data());
|
||||
});
|
||||
connect(m_view, &QQuickWindow::afterRendering, [this]{
|
||||
m_buffer = m_fbo->toImage();
|
||||
});
|
||||
connect(m_view, &QQuickWindow::afterRendering, widget(),
|
||||
static_cast<void (QWidget::*)(void)>(&QWidget::update), Qt::QueuedConnection);
|
||||
}
|
||||
m_view->setColor(Qt::transparent);
|
||||
m_container = QWidget::createWindowContainer(m_view, widget(), Qt::X11BypassWindowManagerHint);
|
||||
m_container->setAttribute(Qt::WA_TranslucentBackground);
|
||||
|
@ -275,6 +295,11 @@ void AuroraeClient::init()
|
|||
|
||||
bool AuroraeClient::eventFilter(QObject *object, QEvent *event)
|
||||
{
|
||||
if (compositingActive() && !m_fbo.isNull() && object == widget() && QEvent::Paint) {
|
||||
QPainter painter(widget());
|
||||
painter.drawImage(QPoint(0, 0), m_buffer);
|
||||
return false;
|
||||
}
|
||||
// we need to filter the wheel events on the decoration
|
||||
// QML does not yet provide a way to accept wheel events, this will change with Qt 5
|
||||
// TODO: remove in KDE5
|
||||
|
|
|
@ -23,6 +23,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|||
#include <kdecoration.h>
|
||||
#include <kdecorationfactory.h>
|
||||
|
||||
class QOpenGLFramebufferObject;
|
||||
class QQmlComponent;
|
||||
class QQmlEngine;
|
||||
class QQuickItem;
|
||||
|
@ -160,6 +161,8 @@ private:
|
|||
QQuickWindow *m_view;
|
||||
QQuickItem *m_item;
|
||||
QWidget *m_container;
|
||||
QScopedPointer<QOpenGLFramebufferObject> m_fbo;
|
||||
QImage m_buffer;
|
||||
};
|
||||
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue