kwin: Refactor the decoration code a bit
This commit is contained in:
parent
1f6b791f11
commit
9c348c9a82
1 changed files with 40 additions and 58 deletions
|
@ -1154,75 +1154,58 @@ void SceneOpenGL::Window::paintDecorations(const WindowPaintData &data, const QR
|
||||||
if (t->noBorder() || !redirector) {
|
if (t->noBorder() || !redirector) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
WindowQuadList decoration = data.quads.select(WindowQuadDecoration);
|
|
||||||
QRect topRect, leftRect, rightRect, bottomRect;
|
|
||||||
|
|
||||||
t->layoutDecorationRects(leftRect, topRect, rightRect, bottomRect, Client::WindowRelative);
|
WindowQuadList quads[4];
|
||||||
|
GLTexture *textures[4];
|
||||||
|
QRect rect[4];
|
||||||
|
|
||||||
WindowQuadList topList, leftList, rightList, bottomList;
|
t->layoutDecorationRects(rect[0], rect[1], rect[2], rect[3], Client::WindowRelative);
|
||||||
|
|
||||||
foreach (const WindowQuad & quad, decoration) {
|
// Split the quads into four lists
|
||||||
if (topRect.contains(QPoint(quad.originalLeft(), quad.originalTop()))) {
|
foreach (const WindowQuad &quad, data.quads.select(WindowQuadDecoration)) {
|
||||||
topList.append(quad);
|
for (int i = 0; i < 4; i++) {
|
||||||
continue;
|
if (rect[i].contains(QPoint(quad.originalLeft(), quad.originalTop()))) {
|
||||||
|
quads[i].append(quad);
|
||||||
}
|
}
|
||||||
if (bottomRect.contains(QPoint(quad.originalLeft(), quad.originalTop()))) {
|
|
||||||
bottomList.append(quad);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (leftRect.contains(QPoint(quad.originalLeft(), quad.originalTop()))) {
|
|
||||||
leftList.append(quad);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (rightRect.contains(QPoint(quad.originalLeft(), quad.originalTop()))) {
|
|
||||||
rightList.append(quad);
|
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
redirector->ensurePixmapsPainted();
|
redirector->ensurePixmapsPainted();
|
||||||
GLTexture *left = redirector->leftDecoPixmap<GLTexture*>();
|
textures[0] = redirector->leftDecoPixmap<GLTexture*>();
|
||||||
GLTexture *top = redirector->topDecoPixmap<GLTexture*>();
|
textures[1] = redirector->topDecoPixmap<GLTexture*>();
|
||||||
GLTexture *right = redirector->rightDecoPixmap<GLTexture*>();
|
textures[2] = redirector->rightDecoPixmap<GLTexture*>();
|
||||||
GLTexture *bottom = redirector->bottomDecoPixmap<GLTexture*>();
|
textures[3] = redirector->bottomDecoPixmap<GLTexture*>();
|
||||||
paintDecoration(top, DecorationTop, region, topRect, data, topList, hardwareClipping);
|
|
||||||
paintDecoration(left, DecorationLeft, region, leftRect, data, leftList, hardwareClipping);
|
TextureType type[] = { DecorationLeft, DecorationTop, DecorationRight, DecorationBottom };
|
||||||
paintDecoration(right, DecorationRight, region, rightRect, data, rightList, hardwareClipping);
|
for (int i = 0; i < 4; i++)
|
||||||
paintDecoration(bottom, DecorationBottom, region, bottomRect, data, bottomList, hardwareClipping);
|
paintDecoration(textures[i], type[i], region, rect[i], data, quads[i], hardwareClipping);
|
||||||
|
|
||||||
redirector->markAsRepainted();
|
redirector->markAsRepainted();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void SceneOpenGL::Window::paintDecoration(GLTexture *decorationTexture, TextureType decorationType,
|
void SceneOpenGL::Window::paintDecoration(GLTexture *texture, TextureType decorationType,
|
||||||
const QRegion& region, const QRect& rect, const WindowPaintData& data,
|
const QRegion& region, const QRect& rect, const WindowPaintData& data,
|
||||||
const WindowQuadList& quads, bool hardwareClipping)
|
const WindowQuadList& quads, bool hardwareClipping)
|
||||||
{
|
{
|
||||||
if (!decorationTexture) {
|
if (!texture || quads.isEmpty())
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// We have to update the texture although we do not paint anything.
|
|
||||||
// This is especially needed if we draw the opaque part of the window
|
|
||||||
// and the decoration in two different passes (as we in Scene::paintSimpleWindow do).
|
|
||||||
// Otherwise we run into the situation that in the first pass there are some
|
|
||||||
// pending decoration repaints but we don't paint the decoration and in the
|
|
||||||
// second pass it's the other way around.
|
|
||||||
if (quads.isEmpty())
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (filter == ImageFilterGood)
|
if (filter == ImageFilterGood)
|
||||||
decorationTexture->setFilter(GL_LINEAR);
|
texture->setFilter(GL_LINEAR);
|
||||||
else
|
else
|
||||||
decorationTexture->setFilter(GL_NEAREST);
|
texture->setFilter(GL_NEAREST);
|
||||||
decorationTexture->setWrapMode(GL_CLAMP_TO_EDGE);
|
|
||||||
decorationTexture->bind();
|
texture->setWrapMode(GL_CLAMP_TO_EDGE);
|
||||||
|
texture->bind();
|
||||||
|
|
||||||
prepareStates(decorationType, data.opacity() * data.decorationOpacity(), data.brightness(), data.saturation(), data.screen());
|
prepareStates(decorationType, data.opacity() * data.decorationOpacity(), data.brightness(), data.saturation(), data.screen());
|
||||||
makeDecorationArrays(quads, rect, decorationTexture);
|
makeDecorationArrays(quads, rect, texture);
|
||||||
GLVertexBuffer::streamingBuffer()->render(region, GL_TRIANGLES, hardwareClipping);
|
GLVertexBuffer::streamingBuffer()->render(region, GL_TRIANGLES, hardwareClipping);
|
||||||
restoreStates(decorationType, data.opacity() * data.decorationOpacity(), data.brightness(), data.saturation());
|
restoreStates(decorationType, data.opacity() * data.decorationOpacity(), data.brightness(), data.saturation());
|
||||||
decorationTexture->unbind();
|
|
||||||
|
texture->unbind();
|
||||||
|
|
||||||
#ifndef KWIN_HAVE_OPENGLES
|
#ifndef KWIN_HAVE_OPENGLES
|
||||||
if (m_scene && m_scene->debug) {
|
if (m_scene && m_scene->debug) {
|
||||||
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
|
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
|
||||||
|
@ -1330,6 +1313,7 @@ GLTexture *SceneOpenGL::Window::textureForType(SceneOpenGL::Window::TextureType
|
||||||
{
|
{
|
||||||
GLTexture *tex = NULL;
|
GLTexture *tex = NULL;
|
||||||
PaintRedirector *redirector = NULL;
|
PaintRedirector *redirector = NULL;
|
||||||
|
|
||||||
if (type != Content && type != Shadow) {
|
if (type != Content && type != Shadow) {
|
||||||
if (toplevel->isClient()) {
|
if (toplevel->isClient()) {
|
||||||
redirector = static_cast<Client*>(toplevel)->decorationPaintRedirector();
|
redirector = static_cast<Client*>(toplevel)->decorationPaintRedirector();
|
||||||
|
@ -1337,30 +1321,28 @@ GLTexture *SceneOpenGL::Window::textureForType(SceneOpenGL::Window::TextureType
|
||||||
redirector = static_cast<Deleted*>(toplevel)->decorationPaintRedirector();
|
redirector = static_cast<Deleted*>(toplevel)->decorationPaintRedirector();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
switch(type) {
|
switch(type) {
|
||||||
case Content:
|
case Content:
|
||||||
tex = texture;
|
tex = texture;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case DecorationTop:
|
case DecorationTop:
|
||||||
if (redirector) {
|
tex = redirector ? redirector->topDecoPixmap<GLTexture*>() : 0;
|
||||||
tex = redirector->topDecoPixmap<GLTexture*>();
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case DecorationLeft:
|
case DecorationLeft:
|
||||||
if (redirector) {
|
tex = redirector ? redirector->leftDecoPixmap<GLTexture*>() : 0;
|
||||||
tex = redirector->leftDecoPixmap<GLTexture*>();
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case DecorationRight:
|
case DecorationRight:
|
||||||
if (redirector) {
|
tex = redirector ? redirector->rightDecoPixmap<GLTexture*>() : 0;
|
||||||
tex = redirector->rightDecoPixmap<GLTexture*>();
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case DecorationBottom:
|
case DecorationBottom:
|
||||||
if (redirector) {
|
tex = redirector ? redirector->bottomDecoPixmap<GLTexture*>() : 0;
|
||||||
tex = redirector->bottomDecoPixmap<GLTexture*>();
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Shadow:
|
case Shadow:
|
||||||
tex = static_cast<SceneOpenGLShadow*>(m_shadow)->shadowTexture();
|
tex = static_cast<SceneOpenGLShadow*>(m_shadow)->shadowTexture();
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue