diff --git a/autotests/mock_effectshandler.h b/autotests/mock_effectshandler.h index beed94a1d8..fba13cdd45 100644 --- a/autotests/mock_effectshandler.h +++ b/autotests/mock_effectshandler.h @@ -223,5 +223,8 @@ public: xcb_window_t x11RootWindow() const override { return QX11Info::appRootWindow(); } + KWayland::Server::Display *waylandDisplay() const override { + return nullptr; + } }; #endif diff --git a/effects.cpp b/effects.cpp index d7c6462461..f10441039c 100644 --- a/effects.cpp +++ b/effects.cpp @@ -1477,6 +1477,14 @@ QStringList EffectsHandlerImpl::activeEffects() const return ret; } +KWayland::Server::Display *EffectsHandlerImpl::waylandDisplay() const +{ + if (waylandServer()) { + return waylandServer()->display(); + } + return nullptr; +} + EffectFrame* EffectsHandlerImpl::effectFrame(EffectFrameStyle style, bool staticSize, const QPoint& position, Qt::Alignment alignment) const { return new EffectFrameImpl(style, staticSize, position, alignment); diff --git a/effects.h b/effects.h index 59f4abd28c..97c2f8761c 100644 --- a/effects.h +++ b/effects.h @@ -35,6 +35,14 @@ namespace Plasma { class Theme; } +namespace KWayland +{ +namespace Server +{ +class Display; +} +} + class QDBusPendingCallWatcher; class QDBusServiceWatcher; class OrgFreedesktopScreenSaverInterface; @@ -214,6 +222,8 @@ public: return m_currentRenderedDesktop; } + KWayland::Server::Display *waylandDisplay() const override; + public Q_SLOTS: void slotCurrentTabAboutToChange(EffectWindow* from, EffectWindow* to); void slotTabAdded(EffectWindow* from, EffectWindow* to); diff --git a/effects/blur/blur.cpp b/effects/blur/blur.cpp index e32b17fa34..7603a55ee3 100644 --- a/effects/blur/blur.cpp +++ b/effects/blur/blur.cpp @@ -19,6 +19,7 @@ */ #include "blur.h" +#include "effects.h" #include "blurshader.h" // KConfigSkeleton #include "blurconfig.h" @@ -26,6 +27,11 @@ #include #include +#include +#include +#include +#include + namespace KWin { @@ -33,6 +39,11 @@ static const QByteArray s_blurAtomName = QByteArrayLiteral("_KDE_NET_WM_BLUR_BEH BlurEffect::BlurEffect() { + KWayland::Server::Display *display = effects->waylandDisplay(); + if (display) { + display->createBlurManager(this)->create(); + } + shader = BlurShader::create(); // Offscreen texture that's used as the target for the horizontal blur pass @@ -109,7 +120,15 @@ void BlurEffect::updateBlurRegion(EffectWindow *w) const } } - if (region.isEmpty() && !value.isNull()) { + KWayland::Server::SurfaceInterface *surf = w->surface(); + + if (surf && surf->blur()) { + region = surf->blur()->region(); + } + + //!value.isNull() full window in X11 case, surf->blur() + //valid, full window in wayland case + if (region.isEmpty() && (!value.isNull() || (surf && surf->blur()))) { // Set the data to a dummy value. // This is needed to be able to distinguish between the value not // being set, and being set to an empty region. @@ -120,12 +139,23 @@ void BlurEffect::updateBlurRegion(EffectWindow *w) const void BlurEffect::slotWindowAdded(EffectWindow *w) { + KWayland::Server::SurfaceInterface *surf = w->surface(); + + if (surf) { + windows[w].blurChangedConnection = connect(surf, &KWayland::Server::SurfaceInterface::blurChanged, this, [this, w] () { + + if (w) { + updateBlurRegion(w); + } + }); + } updateBlurRegion(w); } void BlurEffect::slotWindowDeleted(EffectWindow *w) { if (windows.contains(w)) { + disconnect(windows[w].blurChangedConnection); windows.remove(w); } } diff --git a/effects/blur/blur.h b/effects/blur/blur.h index fe70b6de45..c908ede8d8 100644 --- a/effects/blur/blur.h +++ b/effects/blur/blur.h @@ -93,6 +93,7 @@ private: QRegion damagedRegion; QPoint windowPos; bool dropCache; + QMetaObject::Connection blurChangedConnection; }; QHash< const EffectWindow*, BlurWindowInfo > windows; diff --git a/libkwineffects/CMakeLists.txt b/libkwineffects/CMakeLists.txt index 0a369c6e0f..800b9bdbf9 100644 --- a/libkwineffects/CMakeLists.txt +++ b/libkwineffects/CMakeLists.txt @@ -5,7 +5,7 @@ ecm_setup_version(${PROJECT_VERSION} VARIABLE_PREFIX KWINEFFECTS VERSION_HEADER "${CMAKE_CURRENT_BINARY_DIR}/kwineffects_version.h" PACKAGE_VERSION_FILE "${CMAKE_CURRENT_BINARY_DIR}/KWinEffectsConfigVersion.cmake" - SOVERSION 6 + SOVERSION 7 ) ### xrenderutils lib ### @@ -23,6 +23,7 @@ target_link_libraries(kwinxrenderutils XCB::XCB XCB::XFIXES XCB::RENDER + KF5::WaylandServer ) set_target_properties(kwinxrenderutils PROPERTIES diff --git a/libkwineffects/kwineffects.cpp b/libkwineffects/kwineffects.cpp index 41f091f6f0..3647542bb6 100644 --- a/libkwineffects/kwineffects.cpp +++ b/libkwineffects/kwineffects.cpp @@ -42,6 +42,8 @@ along with this program. If not, see . #include +#include + #ifdef KWIN_HAVE_XRENDER_COMPOSITING #include #endif @@ -744,6 +746,7 @@ WINDOW_HELPER(bool, hasOwnShape, "shaped") WINDOW_HELPER(QString, windowRole, "windowRole") WINDOW_HELPER(QStringList, activities, "activities") WINDOW_HELPER(bool, skipsCloseAnimation, "skipsCloseAnimation") +WINDOW_HELPER(KWayland::Server::SurfaceInterface *, surface, "surface") QString EffectWindow::windowClass() const { diff --git a/libkwineffects/kwineffects.h b/libkwineffects/kwineffects.h index 151cc48310..20a07687a1 100644 --- a/libkwineffects/kwineffects.h +++ b/libkwineffects/kwineffects.h @@ -59,6 +59,13 @@ class QMatrix4x4; **/ Q_DECLARE_LOGGING_CATEGORY(KWINEFFECTS); +namespace KWayland { + namespace Server { + class SurfaceInterface; + class Display; + } +} + namespace KWin { @@ -1085,6 +1092,13 @@ public: virtual xcb_connection_t *xcbConnection() const = 0; virtual xcb_window_t x11RootWindow() const = 0; + /** + * Interface to the Wayland display: this is relevant only + * on Wayland, on X11 it will be nullptr + * @since 5.5 + */ + virtual KWayland::Server::Display *waylandDisplay() const = 0; + /** * @return @ref KConfigGroup which holds given effect's config options **/ @@ -1638,6 +1652,12 @@ class KWINEFFECTS_EXPORT EffectWindow : public QObject * @since 5.0 **/ Q_PROPERTY(bool skipsCloseAnimation READ skipsCloseAnimation) + + /** + * Interface to the corresponding wayland surface. + * relevant only in Wayland, on X11 it will be nullptr + */ + Q_PROPERTY(KWayland::Server::SurfaceInterface *surface READ surface) public: /** Flags explaining why painting should be disabled */ enum { @@ -1870,6 +1890,11 @@ public: **/ bool skipsCloseAnimation() const; + /** + * @since 5.5 + */ + KWayland::Server::SurfaceInterface *surface() const; + /** * Can be used to by effects to store arbitrary data in the EffectWindow. */ diff --git a/toplevel.h b/toplevel.h index c71a905df7..9b372c1194 100644 --- a/toplevel.h +++ b/toplevel.h @@ -202,6 +202,13 @@ class Toplevel * On X11 only setups the value is @c 0. **/ Q_PROPERTY(quint32 surfaceId READ surfaceId NOTIFY surfaceIdChanged) + + /** + * Interface to the Wayland Surface. + * Relevant only in Wayland, in X11 it will be nullptr + */ + Q_PROPERTY(KWayland::Server::SurfaceInterface *surface READ surface) + public: explicit Toplevel(); virtual xcb_window_t frameId() const; diff --git a/wayland_server.cpp b/wayland_server.cpp index 3ad2d93ec2..562edec95a 100644 --- a/wayland_server.cpp +++ b/wayland_server.cpp @@ -41,6 +41,7 @@ along with this program. If not, see . #include #include #include +#include #include // Qt @@ -61,6 +62,7 @@ KWIN_SINGLETON_FACTORY(WaylandServer) WaylandServer::WaylandServer(QObject *parent) : QObject(parent) { + qRegisterMetaType("KWayland::Server::SurfaceInterface *"); } WaylandServer::~WaylandServer()