From 25ab2b53dde1362310cac9e16a567684a6550874 Mon Sep 17 00:00:00 2001 From: Vlad Zahorodnii Date: Mon, 20 Nov 2023 16:17:27 +0200 Subject: [PATCH] Extract EffectWindow into its own header --- src/CMakeLists.txt | 2 + src/compositor_wayland.cpp | 1 + src/effect/anidata.cpp | 1 + src/effect/anidata_p.h | 2 +- src/effect/animationeffect.cpp | 1 + src/effect/effects.cpp | 499 ---------- src/effect/effects.h | 969 +------------------ src/effect/effectwindow.cpp | 522 ++++++++++ src/effect/effectwindow.h | 999 ++++++++++++++++++++ src/plugins/blendchanges/blendchanges.cpp | 1 + src/plugins/blendchanges/blendchanges.h | 1 - src/plugins/fallapart/fallapart.cpp | 1 + src/plugins/fallapart/fallapart.h | 2 +- src/plugins/glide/glide.cpp | 1 + src/plugins/glide/glide.h | 3 +- src/plugins/kscreen/kscreen.cpp | 1 + src/plugins/kscreen/kscreen.h | 4 +- src/plugins/magiclamp/magiclamp.cpp | 1 + src/plugins/magiclamp/magiclamp.h | 2 +- src/plugins/magnifier/magnifier.cpp | 1 + src/plugins/magnifier/magnifier.h | 2 +- src/plugins/sheet/sheet.cpp | 1 + src/plugins/sheet/sheet.h | 3 +- src/plugins/showfps/showfpseffect.cpp | 1 + src/plugins/showfps/showfpseffect.h | 2 +- src/plugins/slide/slide.cpp | 1 + src/plugins/slide/slide.h | 6 +- src/plugins/slideback/slideback.cpp | 1 + src/plugins/slideback/slideback.h | 2 +- src/plugins/slidingpopups/slidingpopups.cpp | 1 + src/plugins/slidingpopups/slidingpopups.h | 3 +- src/scene/itemrenderer_opengl.cpp | 1 + src/scene/itemrenderer_opengl.h | 1 - 33 files changed, 1557 insertions(+), 1482 deletions(-) create mode 100644 src/effect/effectwindow.cpp create mode 100644 src/effect/effectwindow.h diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 2786209ad3..3e119276af 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -88,6 +88,7 @@ target_sources(kwin PRIVATE effect/effectloader.cpp effect/effects.cpp effect/effecttogglablestate.cpp + effect/effectwindow.cpp effect/logging.cpp effect/offscreeneffect.cpp effect/offscreenquickview.cpp @@ -440,6 +441,7 @@ install(FILES effect/effect.h effect/effects.h effect/effecttogglablestate.h + effect/effectwindow.h effect/globals.h effect/offscreeneffect.h effect/offscreenquickview.h diff --git a/src/compositor_wayland.cpp b/src/compositor_wayland.cpp index f82cacbf14..10829abfdf 100644 --- a/src/compositor_wayland.cpp +++ b/src/compositor_wayland.cpp @@ -12,6 +12,7 @@ #include "core/outputbackend.h" #include "core/renderbackend.h" #include "core/renderlayer.h" +#include "effect/effects.h" #include "main.h" #include "opengl/glplatform.h" #include "platformsupport/scenes/opengl/openglbackend.h" diff --git a/src/effect/anidata.cpp b/src/effect/anidata.cpp index 3758574a74..fcf1ae3638 100644 --- a/src/effect/anidata.cpp +++ b/src/effect/anidata.cpp @@ -9,6 +9,7 @@ */ #include "effect/anidata_p.h" +#include "effect/effects.h" #include "logging_p.h" diff --git a/src/effect/anidata_p.h b/src/effect/anidata_p.h index e490907885..8014d2e9a0 100644 --- a/src/effect/anidata_p.h +++ b/src/effect/anidata_p.h @@ -11,7 +11,7 @@ #pragma once #include "effect/animationeffect.h" -#include "effect/effects.h" +#include "effect/effectwindow.h" #include "effect/timeline.h" #include diff --git a/src/effect/animationeffect.cpp b/src/effect/animationeffect.cpp index 05d7492509..131844dfb7 100644 --- a/src/effect/animationeffect.cpp +++ b/src/effect/animationeffect.cpp @@ -10,6 +10,7 @@ #include "effect/animationeffect.h" #include "effect/anidata_p.h" +#include "effect/effects.h" #include "opengl/glutils.h" #include diff --git a/src/effect/effects.cpp b/src/effect/effects.cpp index 00c5b9b346..8141b187cb 100644 --- a/src/effect/effects.cpp +++ b/src/effect/effects.cpp @@ -23,12 +23,10 @@ #include "effect/effectloader.h" #include "effect/offscreenquickview.h" #include "effectsadaptor.h" -#include "group.h" #include "input.h" #include "input_event.h" #include "inputmethod.h" #include "inputpanelv1window.h" -#include "internalwindow.h" #include "opengl/glutils.h" #include "osd.h" #include "pointer_input.h" @@ -40,7 +38,6 @@ #include "sm.h" #include "virtualdesktops.h" #include "wayland_server.h" -#include "waylandwindow.h" #include "window_property_notify_x11_filter.h" #include "workspace.h" #include "x11window.h" @@ -92,14 +89,6 @@ static QByteArray readWindowProperty(xcb_window_t win, xcb_atom_t atom, xcb_atom } } -static void deleteWindowProperty(xcb_window_t win, long int atom) -{ - if (win == XCB_WINDOW_NONE) { - return; - } - xcb_delete_property(kwinApp()->x11Connection(), win, atom); -} - static xcb_atom_t registerSupportProperty(const QByteArray &propertyName) { auto c = kwinApp()->x11Connection(); @@ -1631,494 +1620,6 @@ QQmlEngine *EffectsHandler::qmlEngine() const EffectsHandler *effects = nullptr; -//**************************************** -// EffectWindow -//**************************************** - -class Q_DECL_HIDDEN EffectWindow::Private -{ -public: - Private(EffectWindow *q, WindowItem *windowItem); - - EffectWindow *q; - Window *m_window; - WindowItem *m_windowItem; // This one is used only during paint pass. - QHash dataMap; - bool managed = false; - bool m_waylandWindow; - bool m_x11Window; -}; - -EffectWindow::Private::Private(EffectWindow *q, WindowItem *windowItem) - : q(q) - , m_window(windowItem->window()) - , m_windowItem(windowItem) -{ -} - -EffectWindow::EffectWindow(WindowItem *windowItem) - : d(new Private(this, windowItem)) -{ - // Deleted windows are not managed. So, when windowClosed signal is - // emitted, effects can't distinguish managed windows from unmanaged - // windows(e.g. combo box popups, popup menus, etc). Save value of the - // managed property during construction of EffectWindow. At that time, - // parent can be Client, XdgShellClient, or Unmanaged. So, later on, when - // an instance of Deleted becomes parent of the EffectWindow, effects - // can still figure out whether it is/was a managed window. - d->managed = d->m_window->isClient(); - - d->m_waylandWindow = qobject_cast(d->m_window) != nullptr; - d->m_x11Window = qobject_cast(d->m_window) != nullptr; - - connect(d->m_window, &Window::windowShown, this, [this]() { - Q_EMIT windowShown(this); - }); - connect(d->m_window, &Window::windowHidden, this, [this]() { - Q_EMIT windowHidden(this); - }); - connect(d->m_window, &Window::maximizedChanged, this, [this]() { - const MaximizeMode mode = d->m_window->maximizeMode(); - Q_EMIT windowMaximizedStateChanged(this, mode & MaximizeHorizontal, mode & MaximizeVertical); - }); - connect(d->m_window, &Window::maximizedAboutToChange, this, [this](MaximizeMode m) { - Q_EMIT windowMaximizedStateAboutToChange(this, m & MaximizeHorizontal, m & MaximizeVertical); - }); - connect(d->m_window, &Window::frameGeometryAboutToChange, this, [this]() { - Q_EMIT windowFrameGeometryAboutToChange(this); - }); - connect(d->m_window, &Window::interactiveMoveResizeStarted, this, [this]() { - Q_EMIT windowStartUserMovedResized(this); - }); - connect(d->m_window, &Window::interactiveMoveResizeStepped, this, [this](const QRectF &geometry) { - Q_EMIT windowStepUserMovedResized(this, geometry); - }); - connect(d->m_window, &Window::interactiveMoveResizeFinished, this, [this]() { - Q_EMIT windowFinishUserMovedResized(this); - }); - connect(d->m_window, &Window::opacityChanged, this, [this](Window *window, qreal oldOpacity) { - Q_EMIT windowOpacityChanged(this, oldOpacity, window->opacity()); - }); - connect(d->m_window, &Window::minimizedChanged, this, [this]() { - if (d->m_window->isMinimized()) { - Q_EMIT windowMinimized(this); - } else { - Q_EMIT windowUnminimized(this); - } - }); - connect(d->m_window, &Window::modalChanged, this, [this]() { - Q_EMIT windowModalityChanged(this); - }); - connect(d->m_window, &Window::frameGeometryChanged, this, [this](const QRectF &oldGeometry) { - Q_EMIT windowFrameGeometryChanged(this, oldGeometry); - }); - connect(d->m_window, &Window::damaged, this, [this]() { - Q_EMIT windowDamaged(this); - }); - connect(d->m_window, &Window::unresponsiveChanged, this, [this](bool unresponsive) { - Q_EMIT windowUnresponsiveChanged(this, unresponsive); - }); - connect(d->m_window, &Window::keepAboveChanged, this, [this]() { - Q_EMIT windowKeepAboveChanged(this); - }); - connect(d->m_window, &Window::keepBelowChanged, this, [this]() { - Q_EMIT windowKeepBelowChanged(this); - }); - connect(d->m_window, &Window::fullScreenChanged, this, [this]() { - Q_EMIT windowFullScreenChanged(this); - }); - connect(d->m_window, &Window::visibleGeometryChanged, this, [this]() { - Q_EMIT windowExpandedGeometryChanged(this); - }); - connect(d->m_window, &Window::decorationChanged, this, [this]() { - Q_EMIT windowDecorationChanged(this); - }); - connect(d->m_window, &Window::desktopsChanged, this, [this]() { - Q_EMIT windowDesktopsChanged(this); - }); -} - -EffectWindow::~EffectWindow() -{ -} - -Window *EffectWindow::window() const -{ - return d->m_window; -} - -WindowItem *EffectWindow::windowItem() const -{ - return d->m_windowItem; -} - -bool EffectWindow::isOnActivity(const QString &activity) const -{ - const QStringList _activities = activities(); - return _activities.isEmpty() || _activities.contains(activity); -} - -bool EffectWindow::isOnAllActivities() const -{ - return activities().isEmpty(); -} - -void EffectWindow::setMinimized(bool min) -{ - if (min) { - minimize(); - } else { - unminimize(); - } -} - -bool EffectWindow::isOnCurrentActivity() const -{ - return isOnActivity(effects->currentActivity()); -} - -bool EffectWindow::isOnCurrentDesktop() const -{ - return isOnDesktop(effects->currentDesktop()); -} - -bool EffectWindow::isOnDesktop(VirtualDesktop *desktop) const -{ - const QList ds = desktops(); - return ds.isEmpty() || ds.contains(desktop); -} - -bool EffectWindow::isOnAllDesktops() const -{ - return desktops().isEmpty(); -} - -bool EffectWindow::hasDecoration() const -{ - return contentsRect() != QRect(0, 0, width(), height()); -} - -bool EffectWindow::isVisible() const -{ - return !isMinimized() - && isOnCurrentDesktop() - && isOnCurrentActivity(); -} - -void EffectWindow::refVisible(const EffectWindowVisibleRef *holder) -{ - d->m_windowItem->refVisible(holder->reason()); -} - -void EffectWindow::unrefVisible(const EffectWindowVisibleRef *holder) -{ - d->m_windowItem->unrefVisible(holder->reason()); -} - -void EffectWindow::addRepaint(const QRect &r) -{ - d->m_windowItem->scheduleRepaint(QRegion(r)); -} - -void EffectWindow::addRepaintFull() -{ - d->m_windowItem->scheduleRepaint(d->m_windowItem->boundingRect()); -} - -void EffectWindow::addLayerRepaint(const QRect &r) -{ - d->m_windowItem->scheduleRepaint(d->m_windowItem->mapFromGlobal(r)); -} - -const EffectWindowGroup *EffectWindow::group() const -{ - if (auto c = qobject_cast(d->m_window)) { - return c->group()->effectGroup(); - } - return nullptr; // TODO -} - -void EffectWindow::refWindow() -{ - if (d->m_window->isDeleted()) { - return d->m_window->ref(); - } - Q_UNREACHABLE(); // TODO -} - -void EffectWindow::unrefWindow() -{ - if (d->m_window->isDeleted()) { - return d->m_window->unref(); - } - Q_UNREACHABLE(); // TODO -} - -Output *EffectWindow::screen() const -{ - return d->m_window->output(); -} - -#define WINDOW_HELPER(rettype, prototype, toplevelPrototype) \ - rettype EffectWindow::prototype() const \ - { \ - return d->m_window->toplevelPrototype(); \ - } - -WINDOW_HELPER(double, opacity, opacity) -WINDOW_HELPER(qreal, x, x) -WINDOW_HELPER(qreal, y, y) -WINDOW_HELPER(qreal, width, width) -WINDOW_HELPER(qreal, height, height) -WINDOW_HELPER(QPointF, pos, pos) -WINDOW_HELPER(QSizeF, size, size) -WINDOW_HELPER(QRectF, frameGeometry, frameGeometry) -WINDOW_HELPER(QRectF, bufferGeometry, bufferGeometry) -WINDOW_HELPER(QRectF, clientGeometry, clientGeometry) -WINDOW_HELPER(QRectF, expandedGeometry, visibleGeometry) -WINDOW_HELPER(QRectF, rect, rect) -WINDOW_HELPER(bool, isDesktop, isDesktop) -WINDOW_HELPER(bool, isDock, isDock) -WINDOW_HELPER(bool, isToolbar, isToolbar) -WINDOW_HELPER(bool, isMenu, isMenu) -WINDOW_HELPER(bool, isNormalWindow, isNormalWindow) -WINDOW_HELPER(bool, isDialog, isDialog) -WINDOW_HELPER(bool, isSplash, isSplash) -WINDOW_HELPER(bool, isUtility, isUtility) -WINDOW_HELPER(bool, isDropdownMenu, isDropdownMenu) -WINDOW_HELPER(bool, isPopupMenu, isPopupMenu) -WINDOW_HELPER(bool, isTooltip, isTooltip) -WINDOW_HELPER(bool, isNotification, isNotification) -WINDOW_HELPER(bool, isCriticalNotification, isCriticalNotification) -WINDOW_HELPER(bool, isAppletPopup, isAppletPopup) -WINDOW_HELPER(bool, isOnScreenDisplay, isOnScreenDisplay) -WINDOW_HELPER(bool, isComboBox, isComboBox) -WINDOW_HELPER(bool, isDNDIcon, isDNDIcon) -WINDOW_HELPER(bool, isDeleted, isDeleted) -WINDOW_HELPER(QString, windowRole, windowRole) -WINDOW_HELPER(QStringList, activities, activities) -WINDOW_HELPER(bool, skipsCloseAnimation, skipsCloseAnimation) -WINDOW_HELPER(SurfaceInterface *, surface, surface) -WINDOW_HELPER(bool, isPopupWindow, isPopupWindow) -WINDOW_HELPER(bool, isOutline, isOutline) -WINDOW_HELPER(bool, isLockScreen, isLockScreen) -WINDOW_HELPER(pid_t, pid, pid) -WINDOW_HELPER(QUuid, internalId, internalId) -WINDOW_HELPER(bool, isMinimized, isMinimized) -WINDOW_HELPER(bool, isHidden, isHidden) -WINDOW_HELPER(bool, isHiddenByShowDesktop, isHiddenByShowDesktop) -WINDOW_HELPER(bool, isModal, isModal) -WINDOW_HELPER(bool, isFullScreen, isFullScreen) -WINDOW_HELPER(bool, keepAbove, keepAbove) -WINDOW_HELPER(bool, keepBelow, keepBelow) -WINDOW_HELPER(QString, caption, caption) -WINDOW_HELPER(bool, isMovable, isMovable) -WINDOW_HELPER(bool, isMovableAcrossScreens, isMovableAcrossScreens) -WINDOW_HELPER(bool, isUserMove, isInteractiveMove) -WINDOW_HELPER(bool, isUserResize, isInteractiveResize) -WINDOW_HELPER(QRectF, iconGeometry, iconGeometry) -WINDOW_HELPER(bool, isSpecialWindow, isSpecialWindow) -WINDOW_HELPER(bool, acceptsFocus, wantsInput) -WINDOW_HELPER(QIcon, icon, icon) -WINDOW_HELPER(bool, isSkipSwitcher, skipSwitcher) -WINDOW_HELPER(bool, decorationHasAlpha, decorationHasAlpha) -WINDOW_HELPER(bool, isUnresponsive, unresponsive) -WINDOW_HELPER(QList, desktops, desktops) -WINDOW_HELPER(bool, isInputMethod, isInputMethod) - -#undef WINDOW_HELPER - -qlonglong EffectWindow::windowId() const -{ - if (X11Window *x11Window = qobject_cast(d->m_window)) { - return x11Window->window(); - } - return 0; -} - -QString EffectWindow::windowClass() const -{ - return d->m_window->resourceName() + QLatin1Char(' ') + d->m_window->resourceClass(); -} - -QRectF EffectWindow::contentsRect() const -{ - return QRectF(d->m_window->clientPos(), d->m_window->clientSize()); -} - -NET::WindowType EffectWindow::windowType() const -{ - return d->m_window->windowType(); -} - -QSizeF EffectWindow::basicUnit() const -{ - if (auto window = qobject_cast(d->m_window)) { - return window->basicUnit(); - } - return QSize(1, 1); -} - -QRectF EffectWindow::decorationInnerRect() const -{ - return d->m_window->rect() - d->m_window->frameMargins(); -} - -KDecoration2::Decoration *EffectWindow::decoration() const -{ - return d->m_window->decoration(); -} - -QByteArray EffectWindow::readProperty(long atom, long type, int format) const -{ - auto x11Window = qobject_cast(d->m_window); - if (!x11Window) { - return QByteArray(); - } - if (!kwinApp()->x11Connection()) { - return QByteArray(); - } - return readWindowProperty(x11Window->window(), atom, type, format); -} - -void EffectWindow::deleteProperty(long int atom) const -{ - auto x11Window = qobject_cast(d->m_window); - if (!x11Window) { - return; - } - if (kwinApp()->x11Connection()) { - deleteWindowProperty(x11Window->window(), atom); - } -} - -EffectWindow *EffectWindow::findModal() -{ - Window *modal = d->m_window->findModal(); - if (modal) { - return modal->effectWindow(); - } - - return nullptr; -} - -EffectWindow *EffectWindow::transientFor() -{ - Window *transientFor = d->m_window->transientFor(); - if (transientFor) { - return transientFor->effectWindow(); - } - - return nullptr; -} - -QWindow *EffectWindow::internalWindow() const -{ - if (auto window = qobject_cast(d->m_window)) { - return window->handle(); - } - return nullptr; -} - -template -QList getMainWindows(T *c) -{ - const auto mainwindows = c->mainWindows(); - QList ret; - ret.reserve(mainwindows.size()); - std::transform(std::cbegin(mainwindows), std::cend(mainwindows), - std::back_inserter(ret), - [](auto window) { - return window->effectWindow(); - }); - return ret; -} - -QList EffectWindow::mainWindows() const -{ - return getMainWindows(d->m_window); -} - -void EffectWindow::setData(int role, const QVariant &data) -{ - if (!data.isNull()) { - d->dataMap[role] = data; - } else { - d->dataMap.remove(role); - } - Q_EMIT effects->windowDataChanged(this, role); -} - -QVariant EffectWindow::data(int role) const -{ - return d->dataMap.value(role); -} - -void EffectWindow::elevate(bool elevate) -{ - effects->setElevatedWindow(this, elevate); -} - -void EffectWindow::minimize() -{ - if (d->m_window->isClient()) { - d->m_window->setMinimized(true); - } -} - -void EffectWindow::unminimize() -{ - if (d->m_window->isClient()) { - d->m_window->setMinimized(false); - } -} - -void EffectWindow::closeWindow() -{ - if (d->m_window->isClient()) { - d->m_window->closeWindow(); - } -} - -bool EffectWindow::isManaged() const -{ - return d->managed; -} - -bool EffectWindow::isWaylandClient() const -{ - return d->m_waylandWindow; -} - -bool EffectWindow::isX11Client() const -{ - return d->m_x11Window; -} - -//**************************************** -// EffectWindowGroup -//**************************************** - -EffectWindowGroup::EffectWindowGroup(Group *group) - : m_group(group) -{ -} - -EffectWindowGroup::~EffectWindowGroup() -{ -} - -QList EffectWindowGroup::members() const -{ - const auto memberList = m_group->members(); - QList ret; - ret.reserve(memberList.size()); - std::transform(std::cbegin(memberList), std::cend(memberList), std::back_inserter(ret), [](auto window) { - return window->effectWindow(); - }); - return ret; -} - } // namespace #include "moc_effects.cpp" diff --git a/src/effect/effects.h b/src/effect/effects.h index 78317f9166..be95540897 100644 --- a/src/effect/effects.h +++ b/src/effect/effects.h @@ -13,6 +13,7 @@ #pragma once #include "effect/effect.h" +#include "effect/effectwindow.h" #include #include @@ -1108,979 +1109,11 @@ protected: std::unique_ptr m_x11WindowPropertyNotify; }; -class EffectWindowVisibleRef; -/** - * @short Representation of a window used by/for Effect classes. - * - * The purpose is to hide internal data and also to serve as a single - * representation for the case when Client/Unmanaged becomes Deleted. - */ -class KWIN_EXPORT EffectWindow : public QObject -{ - Q_OBJECT - Q_PROPERTY(QRectF geometry READ frameGeometry) - Q_PROPERTY(QRectF expandedGeometry READ expandedGeometry) - Q_PROPERTY(qreal height READ height) - Q_PROPERTY(qreal opacity READ opacity) - Q_PROPERTY(QPointF pos READ pos) - Q_PROPERTY(KWin::Output *screen READ screen) - Q_PROPERTY(QSizeF size READ size) - Q_PROPERTY(qreal width READ width) - Q_PROPERTY(qreal x READ x) - Q_PROPERTY(qreal y READ y) - Q_PROPERTY(QList desktops READ desktops) - Q_PROPERTY(bool onAllDesktops READ isOnAllDesktops) - Q_PROPERTY(bool onCurrentDesktop READ isOnCurrentDesktop) - Q_PROPERTY(QRectF rect READ rect) - Q_PROPERTY(QString windowClass READ windowClass) - Q_PROPERTY(QString windowRole READ windowRole) - /** - * Returns whether the window is a desktop background window (the one with wallpaper). - * See _NET_WM_WINDOW_TYPE_DESKTOP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool desktopWindow READ isDesktop) - /** - * Returns whether the window is a dock (i.e. a panel). - * See _NET_WM_WINDOW_TYPE_DOCK at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool dock READ isDock) - /** - * Returns whether the window is a standalone (detached) toolbar window. - * See _NET_WM_WINDOW_TYPE_TOOLBAR at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool toolbar READ isToolbar) - /** - * Returns whether the window is a torn-off menu. - * See _NET_WM_WINDOW_TYPE_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool menu READ isMenu) - /** - * Returns whether the window is a "normal" window, i.e. an application or any other window - * for which none of the specialized window types fit. - * See _NET_WM_WINDOW_TYPE_NORMAL at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool normalWindow READ isNormalWindow) - /** - * Returns whether the window is a dialog window. - * See _NET_WM_WINDOW_TYPE_DIALOG at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool dialog READ isDialog) - /** - * Returns whether the window is a splashscreen. Note that many (especially older) applications - * do not support marking their splash windows with this type. - * See _NET_WM_WINDOW_TYPE_SPLASH at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool splash READ isSplash) - /** - * Returns whether the window is a utility window, such as a tool window. - * See _NET_WM_WINDOW_TYPE_UTILITY at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool utility READ isUtility) - /** - * Returns whether the window is a dropdown menu (i.e. a popup directly or indirectly open - * from the applications menubar). - * See _NET_WM_WINDOW_TYPE_DROPDOWN_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool dropdownMenu READ isDropdownMenu) - /** - * Returns whether the window is a popup menu (that is not a torn-off or dropdown menu). - * See _NET_WM_WINDOW_TYPE_POPUP_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool popupMenu READ isPopupMenu) - /** - * Returns whether the window is a tooltip. - * See _NET_WM_WINDOW_TYPE_TOOLTIP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool tooltip READ isTooltip) - /** - * Returns whether the window is a window with a notification. - * See _NET_WM_WINDOW_TYPE_NOTIFICATION at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool notification READ isNotification) - /** - * Returns whether the window is a window with a critical notification. - * using the non-standard _KDE_NET_WM_WINDOW_TYPE_CRITICAL_NOTIFICATION - */ - Q_PROPERTY(bool criticalNotification READ isCriticalNotification) - /** - * Returns whether the window is an on screen display window - * using the non-standard _KDE_NET_WM_WINDOW_TYPE_ON_SCREEN_DISPLAY - */ - Q_PROPERTY(bool onScreenDisplay READ isOnScreenDisplay) - /** - * Returns whether the window is a combobox popup. - * See _NET_WM_WINDOW_TYPE_COMBO at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool comboBox READ isComboBox) - /** - * Returns whether the window is a Drag&Drop icon. - * See _NET_WM_WINDOW_TYPE_DND at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(bool dndIcon READ isDNDIcon) - /** - * Returns the NETWM window type - * See https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(int windowType READ windowType) - /** - * Whether this EffectWindow is managed by KWin (it has control over its placement and other - * aspects, as opposed to override-redirect windows that are entirely handled by the application). - */ - Q_PROPERTY(bool managed READ isManaged) - /** - * Whether this EffectWindow represents an already deleted window and only kept for the compositor for animations. - */ - Q_PROPERTY(bool deleted READ isDeleted) - /** - * The Caption of the window. Read from WM_NAME property together with a suffix for hostname and shortcut. - */ - Q_PROPERTY(QString caption READ caption) - /** - * Whether the window is set to be kept above other windows. - */ - Q_PROPERTY(bool keepAbove READ keepAbove) - /** - * Whether the window is set to be kept below other windows. - */ - Q_PROPERTY(bool keepBelow READ keepBelow) - /** - * Whether the window is minimized. - */ - Q_PROPERTY(bool minimized READ isMinimized WRITE setMinimized) - /** - * Whether the window represents a modal window. - */ - Q_PROPERTY(bool modal READ isModal) - /** - * Whether the window is moveable. Even if it is not moveable, it might be possible to move - * it to another screen. - * @see moveableAcrossScreens - */ - Q_PROPERTY(bool moveable READ isMovable) - /** - * Whether the window can be moved to another screen. - * @see moveable - */ - Q_PROPERTY(bool moveableAcrossScreens READ isMovableAcrossScreens) - /** - * By how much the window wishes to grow/shrink at least. Usually QSize(1,1). - * MAY BE DISOBEYED BY THE WM! It's only for information, do NOT rely on it at all. - */ - Q_PROPERTY(QSizeF basicUnit READ basicUnit) - /** - * Whether the window is currently being moved by the user. - */ - Q_PROPERTY(bool move READ isUserMove) - /** - * Whether the window is currently being resized by the user. - */ - Q_PROPERTY(bool resize READ isUserResize) - /** - * The optional geometry representing the minimized Client in e.g a taskbar. - * See _NET_WM_ICON_GEOMETRY at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - Q_PROPERTY(QRectF iconGeometry READ iconGeometry) - /** - * Returns whether the window is any of special windows types (desktop, dock, splash, ...), - * i.e. window types that usually don't have a window frame and the user does not use window - * management (moving, raising,...) on them. - */ - Q_PROPERTY(bool specialWindow READ isSpecialWindow) - Q_PROPERTY(QIcon icon READ icon) - /** - * Whether the window should be excluded from window switching effects. - */ - Q_PROPERTY(bool skipSwitcher READ isSkipSwitcher) - /** - * Geometry of the actual window contents inside the whole (including decorations) window. - */ - Q_PROPERTY(QRectF contentsRect READ contentsRect) - /** - * Geometry of the transparent rect in the decoration. - * May be different from contentsRect if the decoration is extended into the client area. - */ - Q_PROPERTY(QRectF decorationInnerRect READ decorationInnerRect) - Q_PROPERTY(bool hasDecoration READ hasDecoration) - Q_PROPERTY(QStringList activities READ activities) - Q_PROPERTY(bool onCurrentActivity READ isOnCurrentActivity) - Q_PROPERTY(bool onAllActivities READ isOnAllActivities) - /** - * Whether the decoration currently uses an alpha channel. - * @since 4.10 - */ - Q_PROPERTY(bool decorationHasAlpha READ decorationHasAlpha) - /** - * Whether the window is currently visible to the user, that is: - *
    - *
  • Not minimized
  • - *
  • On current desktop
  • - *
  • On current activity
  • - *
- * @since 4.11 - */ - Q_PROPERTY(bool visible READ isVisible) - /** - * Whether the window does not want to be animated on window close. - * In case this property is @c true it is not useful to start an animation on window close. - * The window will not be visible, but the animation hooks are executed. - * @since 5.0 - */ - Q_PROPERTY(bool skipsCloseAnimation READ skipsCloseAnimation) - - /** - * Whether the window is fullscreen. - * @since 5.6 - */ - Q_PROPERTY(bool fullScreen READ isFullScreen) - - /** - * Whether this client is unresponsive. - * - * When an application failed to react on a ping request in time, it is - * considered unresponsive. This usually indicates that the application froze or crashed. - * - * @since 5.10 - */ - Q_PROPERTY(bool unresponsive READ isUnresponsive) - - /** - * Whether this is a Wayland client. - * @since 5.15 - */ - Q_PROPERTY(bool waylandClient READ isWaylandClient CONSTANT) - - /** - * Whether this is an X11 client. - * @since 5.15 - */ - Q_PROPERTY(bool x11Client READ isX11Client CONSTANT) - - /** - * Whether the window is a popup. - * - * A popup is a window that can be used to implement tooltips, combo box popups, - * popup menus and other similar user interface concepts. - * - * @since 5.15 - */ - Q_PROPERTY(bool popupWindow READ isPopupWindow CONSTANT) - - /** - * KWin internal window. Specific to Wayland platform. - * - * If the EffectWindow does not reference an internal window, this property is @c null. - * @since 5.16 - */ - Q_PROPERTY(QWindow *internalWindow READ internalWindow CONSTANT) - - /** - * Whether this EffectWindow represents the outline. - * - * When compositing is turned on, the outline is an actual window. - * - * @since 5.16 - */ - Q_PROPERTY(bool outline READ isOutline CONSTANT) - - /** - * The PID of the application this window belongs to. - * - * @since 5.18 - */ - Q_PROPERTY(pid_t pid READ pid CONSTANT) - - /** - * Whether this EffectWindow represents the screenlocker greeter. - * - * @since 5.22 - */ - Q_PROPERTY(bool lockScreen READ isLockScreen CONSTANT) - - /** - * Whether this EffectWindow is hidden because the show desktop mode is active. - */ - Q_PROPERTY(bool hiddenByShowDesktop READ isHiddenByShowDesktop) - -public: - /** Flags explaining why painting should be disabled */ - enum { - /** Window will not be painted */ - PAINT_DISABLED = 1 << 0, - /** Window will not be painted because of which desktop it's on */ - PAINT_DISABLED_BY_DESKTOP = 1 << 1, - /** Window will not be painted because it is minimized */ - PAINT_DISABLED_BY_MINIMIZE = 1 << 2, - /** Window will not be painted because it's not on the current activity */ - PAINT_DISABLED_BY_ACTIVITY = 1 << 3, - }; - - explicit EffectWindow(WindowItem *windowItem); - ~EffectWindow() override; - - Q_SCRIPTABLE void addRepaint(const QRect &r); - Q_SCRIPTABLE void addRepaint(int x, int y, int w, int h); - Q_SCRIPTABLE void addRepaintFull(); - Q_SCRIPTABLE void addLayerRepaint(const QRect &r); - Q_SCRIPTABLE void addLayerRepaint(int x, int y, int w, int h); - - void refWindow(); - void unrefWindow(); - - bool isDeleted() const; - bool isHidden() const; - bool isHiddenByShowDesktop() const; - - bool isMinimized() const; - double opacity() const; - - bool isOnCurrentActivity() const; - Q_SCRIPTABLE bool isOnActivity(const QString &id) const; - bool isOnAllActivities() const; - QStringList activities() const; - - Q_SCRIPTABLE bool isOnDesktop(KWin::VirtualDesktop *desktop) const; - bool isOnCurrentDesktop() const; - bool isOnAllDesktops() const; - /** - * All the desktops by number that the window is in. On X11 this list will always have - * a length of 1, on Wayland can be any subset. - * If the list is empty it means the window is on all desktops - */ - QList desktops() const; - - qreal x() const; - qreal y() const; - qreal width() const; - qreal height() const; - /** - * By how much the window wishes to grow/shrink at least. Usually QSize(1,1). - * MAY BE DISOBEYED BY THE WM! It's only for information, do NOT rely on it at all. - */ - QSizeF basicUnit() const; - /** - * Returns the geometry of the window excluding server-side and client-side - * drop-shadows. - * - * @since 5.18 - */ - QRectF frameGeometry() const; - /** - * Returns the geometry of the pixmap or buffer attached to this window. - * - * For X11 clients, this method returns server-side geometry of the Window. - * - * For Wayland clients, this method returns rectangle that the main surface - * occupies on the screen, in global screen coordinates. - * - * @since 5.18 - */ - QRectF bufferGeometry() const; - QRectF clientGeometry() const; - /** - * Geometry of the window including decoration and potentially shadows. - * May be different from geometry() if the window has a shadow. - * @since 4.9 - */ - QRectF expandedGeometry() const; - Output *screen() const; - QPointF pos() const; - QSizeF size() const; - QRectF rect() const; - bool isMovable() const; - bool isMovableAcrossScreens() const; - bool isUserMove() const; - bool isUserResize() const; - QRectF iconGeometry() const; - - /** - * Geometry of the actual window contents inside the whole (including decorations) window. - */ - QRectF contentsRect() const; - /** - * Geometry of the transparent rect in the decoration. - * May be different from contentsRect() if the decoration is extended into the client area. - * @since 4.5 - */ - QRectF decorationInnerRect() const; - bool hasDecoration() const; - bool decorationHasAlpha() const; - /** - * Returns the decoration - * @since 5.25 - */ - KDecoration2::Decoration *decoration() const; - QByteArray readProperty(long atom, long type, int format) const; - void deleteProperty(long atom) const; - - QString caption() const; - QIcon icon() const; - QString windowClass() const; - QString windowRole() const; - const EffectWindowGroup *group() const; - - /** - * Returns whether the window is a desktop background window (the one with wallpaper). - * See _NET_WM_WINDOW_TYPE_DESKTOP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isDesktop() const; - /** - * Returns whether the window is a dock (i.e. a panel). - * See _NET_WM_WINDOW_TYPE_DOCK at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isDock() const; - /** - * Returns whether the window is a standalone (detached) toolbar window. - * See _NET_WM_WINDOW_TYPE_TOOLBAR at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isToolbar() const; - /** - * Returns whether the window is a torn-off menu. - * See _NET_WM_WINDOW_TYPE_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isMenu() const; - /** - * Returns whether the window is a "normal" window, i.e. an application or any other window - * for which none of the specialized window types fit. - * See _NET_WM_WINDOW_TYPE_NORMAL at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isNormalWindow() const; // normal as in 'NET::Normal or NET::Unknown non-transient' - /** - * Returns whether the window is any of special windows types (desktop, dock, splash, ...), - * i.e. window types that usually don't have a window frame and the user does not use window - * management (moving, raising,...) on them. - */ - bool isSpecialWindow() const; - /** - * Returns whether the window is a dialog window. - * See _NET_WM_WINDOW_TYPE_DIALOG at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isDialog() const; - /** - * Returns whether the window is a splashscreen. Note that many (especially older) applications - * do not support marking their splash windows with this type. - * See _NET_WM_WINDOW_TYPE_SPLASH at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isSplash() const; - /** - * Returns whether the window is a utility window, such as a tool window. - * See _NET_WM_WINDOW_TYPE_UTILITY at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isUtility() const; - /** - * Returns whether the window is a dropdown menu (i.e. a popup directly or indirectly open - * from the applications menubar). - * See _NET_WM_WINDOW_TYPE_DROPDOWN_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isDropdownMenu() const; - /** - * Returns whether the window is a popup menu (that is not a torn-off or dropdown menu). - * See _NET_WM_WINDOW_TYPE_POPUP_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isPopupMenu() const; // a context popup, not dropdown, not torn-off - /** - * Returns whether the window is a tooltip. - * See _NET_WM_WINDOW_TYPE_TOOLTIP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isTooltip() const; - /** - * Returns whether the window is a window with a notification. - * See _NET_WM_WINDOW_TYPE_NOTIFICATION at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isNotification() const; - /** - * Returns whether the window is a window with a critical notification. - * using the non-standard _KDE_NET_WM_WINDOW_TYPE_CRITICAL_NOTIFICATION - */ - bool isCriticalNotification() const; - /** - * Returns whether the window is a window used for applet popups. - */ - bool isAppletPopup() const; - /** - * Returns whether the window is an on screen display window - * using the non-standard _KDE_NET_WM_WINDOW_TYPE_ON_SCREEN_DISPLAY - */ - bool isOnScreenDisplay() const; - /** - * Returns whether the window is a combobox popup. - * See _NET_WM_WINDOW_TYPE_COMBO at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isComboBox() const; - /** - * Returns whether the window is a Drag&Drop icon. - * See _NET_WM_WINDOW_TYPE_DND at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - bool isDNDIcon() const; - /** - * Returns the NETWM window type - * See https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . - */ - NET::WindowType windowType() const; - /** - * Returns whether the window is managed by KWin (it has control over its placement and other - * aspects, as opposed to override-redirect windows that are entirely handled by the application). - */ - bool isManaged() const; // whether it's managed or override-redirect - /** - * Returns whether or not the window can accept keyboard focus. - */ - bool acceptsFocus() const; - /** - * Returns whether or not the window is kept above all other windows. - */ - bool keepAbove() const; - /** - * Returns whether the window is kept below all other windows. - */ - bool keepBelow() const; - - bool isModal() const; - Q_SCRIPTABLE KWin::EffectWindow *findModal(); - Q_SCRIPTABLE KWin::EffectWindow *transientFor(); - Q_SCRIPTABLE QList mainWindows() const; - - /** - * Returns whether the window should be excluded from window switching effects. - * @since 4.5 - */ - bool isSkipSwitcher() const; - - void setMinimized(bool minimize); - void minimize(); - void unminimize(); - Q_SCRIPTABLE void closeWindow(); - - /** - * @since 4.11 - */ - bool isVisible() const; - - /** - * @since 5.0 - */ - bool skipsCloseAnimation() const; - - /** - * @since 5.5 - */ - SurfaceInterface *surface() const; - - /** - * @since 5.6 - */ - bool isFullScreen() const; - - /** - * @since 5.10 - */ - bool isUnresponsive() const; - - /** - * @since 5.15 - */ - bool isWaylandClient() const; - - /** - * @since 5.15 - */ - bool isX11Client() const; - - /** - * @since 5.15 - */ - bool isPopupWindow() const; - - /** - * @since 5.16 - */ - QWindow *internalWindow() const; - - /** - * @since 5.16 - */ - bool isOutline() const; - - /** - * @since 5.22 - */ - bool isLockScreen() const; - - /** - * @since 5.18 - */ - pid_t pid() const; - - /** - * @since 5.21 - */ - qlonglong windowId() const; - /** - * Returns the internal id of the window that uniquely identifies it. The main difference - * between internalId() and windowId() is that the latter one works as expected only on X11, - * while the former is unique regardless of the window system. - * - * Note that the internaId() has special meaning only to kwin. - * @since 5.24 - */ - QUuid internalId() const; - - /** - * @since 6.0 - */ - bool isInputMethod() const; - - /** - * Can be used to by effects to store arbitrary data in the EffectWindow. - * - * Invoking this method will emit the signal EffectsHandler::windowDataChanged. - * @see EffectsHandler::windowDataChanged - */ - Q_SCRIPTABLE void setData(int role, const QVariant &data); - Q_SCRIPTABLE QVariant data(int role) const; - - Window *window() const; - WindowItem *windowItem() const; - void elevate(bool elevate); - -Q_SIGNALS: - /** - * Signal emitted when a user begins a window move or resize operation. - * To figure out whether the user resizes or moves the window use - * isUserMove or isUserResize. - * Whenever the geometry is updated the signal @ref windowStepUserMovedResized - * is emitted with the current geometry. - * The move/resize operation ends with the signal @ref windowFinishUserMovedResized. - * Only one window can be moved/resized by the user at the same time! - * @param w The window which is being moved/resized - * @see windowStepUserMovedResized - * @see windowFinishUserMovedResized - * @see EffectWindow::isUserMove - * @see EffectWindow::isUserResize - */ - void windowStartUserMovedResized(KWin::EffectWindow *w); - /** - * Signal emitted during a move/resize operation when the user changed the geometry. - * Please note: KWin supports two operation modes. In one mode all changes are applied - * instantly. This means the window's geometry matches the passed in @p geometry. In the - * other mode the geometry is changed after the user ended the move/resize mode. - * The @p geometry differs from the window's geometry. Also the window's pixmap still has - * the same size as before. Depending what the effect wants to do it would be recommended - * to scale/translate the window. - * @param w The window which is being moved/resized - * @param geometry The geometry of the window in the current move/resize step. - * @see windowStartUserMovedResized - * @see windowFinishUserMovedResized - * @see EffectWindow::isUserMove - * @see EffectWindow::isUserResize - */ - void windowStepUserMovedResized(KWin::EffectWindow *w, const QRectF &geometry); - /** - * Signal emitted when the user finishes move/resize of window @p w. - * @param w The window which has been moved/resized - * @see windowStartUserMovedResized - * @see windowFinishUserMovedResized - */ - void windowFinishUserMovedResized(KWin::EffectWindow *w); - - /** - * Signal emitted when the maximized state of the window @p w changed. - * A window can be in one of four states: - * @li restored: both @p horizontal and @p vertical are @c false - * @li horizontally maximized: @p horizontal is @c true and @p vertical is @c false - * @li vertically maximized: @p horizontal is @c false and @p vertical is @c true - * @li completely maximized: both @p horizontal and @p vertical are @c true - * @param w The window whose maximized state changed - * @param horizontal If @c true maximized horizontally - * @param vertical If @c true maximized vertically - */ - void windowMaximizedStateChanged(KWin::EffectWindow *w, bool horizontal, bool vertical); - - /** - * Signal emitted when the maximized state of the window @p w is about to change, - * but before windowMaximizedStateChanged is emitted or any geometry change. - * Useful for OffscreenEffect to grab a window image before any actual change happens - * - * A window can be in one of four states: - * @li restored: both @p horizontal and @p vertical are @c false - * @li horizontally maximized: @p horizontal is @c true and @p vertical is @c false - * @li vertically maximized: @p horizontal is @c false and @p vertical is @c true - * @li completely maximized: both @p horizontal and @p vertical are @c true - * @param w The window whose maximized state changed - * @param horizontal If @c true maximized horizontally - * @param vertical If @c true maximized vertically - */ - void windowMaximizedStateAboutToChange(KWin::EffectWindow *w, bool horizontal, bool vertical); - - /** - * This signal is emitted when the frame geometry of a window changed. - * @param window The window whose geometry changed - * @param oldGeometry The previous geometry - */ - void windowFrameGeometryChanged(KWin::EffectWindow *window, const QRectF &oldGeometry); - - /** - * This signal is emitted when the frame geometry is about to change, the new one is not known yet. - * Useful for OffscreenEffect to grab a window image before any actual change happens. - * - * @param window The window whose geometry is about to change - */ - void windowFrameGeometryAboutToChange(KWin::EffectWindow *window); - - /** - * Signal emitted when the windows opacity is changed. - * @param w The window whose opacity level is changed. - * @param oldOpacity The previous opacity level - * @param newOpacity The new opacity level - */ - void windowOpacityChanged(KWin::EffectWindow *w, qreal oldOpacity, qreal newOpacity); - /** - * Signal emitted when a window got minimized. - * @param w The window which was minimized - */ - void windowMinimized(KWin::EffectWindow *w); - /** - * Signal emitted when a window got unminimized. - * @param w The window which was unminimized - */ - void windowUnminimized(KWin::EffectWindow *w); - /** - * Signal emitted when a window either becomes modal (ie. blocking for its main client) or looses that state. - * @param w The window which was unminimized - */ - void windowModalityChanged(KWin::EffectWindow *w); - /** - * Signal emitted when a window either became unresponsive (eg. app froze or crashed) - * or respoonsive - * @param w The window that became (un)responsive - * @param unresponsive Whether the window is responsive or unresponsive - */ - void windowUnresponsiveChanged(KWin::EffectWindow *w, bool unresponsive); - /** - * Signal emitted when an area of a window is scheduled for repainting. - * Use this signal in an effect if another area needs to be synced as well. - * @param w The window which is scheduled for repainting - */ - void windowDamaged(KWin::EffectWindow *w); - - /** - * This signal is emitted when the keep above state of @p w was changed. - * - * @param w The window whose the keep above state was changed. - */ - void windowKeepAboveChanged(KWin::EffectWindow *w); - - /** - * This signal is emitted when the keep below state of @p was changed. - * - * @param w The window whose the keep below state was changed. - */ - void windowKeepBelowChanged(KWin::EffectWindow *w); - - /** - * This signal is emitted when the full screen state of @p w was changed. - * - * @param w The window whose the full screen state was changed. - */ - void windowFullScreenChanged(KWin::EffectWindow *w); - - /** - * This signal is emitted when decoration of @p was changed. - * - * @param w The window for which decoration changed - */ - void windowDecorationChanged(KWin::EffectWindow *window); - - /** - * This signal is emitted when the visible geometry of a window changed. - */ - void windowExpandedGeometryChanged(KWin::EffectWindow *window); - - /** - * This signal is emitted when a window enters or leaves a virtual desktop. - */ - void windowDesktopsChanged(KWin::EffectWindow *window); - - /** - * The window @p w gets shown again. The window was previously - * initially shown with windowAdded and hidden with windowHidden. - * - * @see windowHidden - * @see windowAdded - */ - void windowShown(KWin::EffectWindow *w); - - /** - * The window @p w got hidden but not yet closed. - * This can happen when a window is still being used and is supposed to be shown again - * with windowShown. On X11 an example is autohiding panels. On Wayland every - * window first goes through the window hidden state and might get shown again, or might - * get closed the normal way. - * - * @see windowShown - * @see windowClosed - */ - void windowHidden(KWin::EffectWindow *w); - -protected: - friend EffectWindowVisibleRef; - void refVisible(const EffectWindowVisibleRef *holder); - void unrefVisible(const EffectWindowVisibleRef *holder); - -private: - class Private; - std::unique_ptr d; -}; - -/** - * The EffectWindowDeletedRef provides a convenient way to prevent deleting a closed - * window until an effect has finished animating it. - */ -class KWIN_EXPORT EffectWindowDeletedRef -{ -public: - EffectWindowDeletedRef() - : m_window(nullptr) - { - } - - explicit EffectWindowDeletedRef(EffectWindow *window) - : m_window(window) - { - m_window->refWindow(); - } - - EffectWindowDeletedRef(const EffectWindowDeletedRef &other) - : m_window(other.m_window) - { - if (m_window) { - m_window->refWindow(); - } - } - - ~EffectWindowDeletedRef() - { - if (m_window) { - m_window->unrefWindow(); - } - } - - EffectWindowDeletedRef &operator=(const EffectWindowDeletedRef &other) - { - if (other.m_window) { - other.m_window->refWindow(); - } - if (m_window) { - m_window->unrefWindow(); - } - m_window = other.m_window; - return *this; - } - - bool isNull() const - { - return m_window == nullptr; - } - -private: - EffectWindow *m_window; -}; - -/** - * The EffectWindowVisibleRef provides a convenient way to force the visible status of a - * window until an effect is finished animating it. - */ -class KWIN_EXPORT EffectWindowVisibleRef -{ -public: - EffectWindowVisibleRef() - : m_window(nullptr) - , m_reason(0) - { - } - - explicit EffectWindowVisibleRef(EffectWindow *window, int reason) - : m_window(window) - , m_reason(reason) - { - m_window->refVisible(this); - } - - EffectWindowVisibleRef(const EffectWindowVisibleRef &other) - : m_window(other.m_window) - , m_reason(other.m_reason) - { - if (m_window) { - m_window->refVisible(this); - } - } - - ~EffectWindowVisibleRef() - { - if (m_window) { - m_window->unrefVisible(this); - } - } - - int reason() const - { - return m_reason; - } - - EffectWindowVisibleRef &operator=(const EffectWindowVisibleRef &other) - { - if (other.m_window) { - other.m_window->refVisible(&other); - } - if (m_window) { - m_window->unrefVisible(this); - } - m_window = other.m_window; - m_reason = other.m_reason; - return *this; - } - - bool isNull() const - { - return m_window == nullptr; - } - -private: - EffectWindow *m_window; - int m_reason; -}; - -class KWIN_EXPORT EffectWindowGroup -{ -public: - explicit EffectWindowGroup(Group *group); - virtual ~EffectWindowGroup(); - - QList members() const; - -private: - Group *m_group; -}; - /** * Pointer to the global EffectsHandler object. */ extern KWIN_EXPORT EffectsHandler *effects; -/*************************************************************** - EffectWindow -***************************************************************/ - -inline void EffectWindow::addRepaint(int x, int y, int w, int h) -{ - addRepaint(QRect(x, y, w, h)); -} - -inline void EffectWindow::addLayerRepaint(int x, int y, int w, int h) -{ - addLayerRepaint(QRect(x, y, w, h)); -} - } // namespace -Q_DECLARE_METATYPE(KWin::EffectWindow *) /** @} */ diff --git a/src/effect/effectwindow.cpp b/src/effect/effectwindow.cpp new file mode 100644 index 0000000000..71c45bcf23 --- /dev/null +++ b/src/effect/effectwindow.cpp @@ -0,0 +1,522 @@ +/* + SPDX-FileCopyrightText: 2006 Lubos Lunak + SPDX-FileCopyrightText: 2009 Lucas Murray + SPDX-FileCopyrightText: 2010, 2011 Martin Gräßlin + SPDX-FileCopyrightText: 2018 Vlad Zahorodnii + + SPDX-License-Identifier: GPL-2.0-or-later +*/ + +#include "effect/effectwindow.h" +#include "core/output.h" +#include "effect/effects.h" +#include "group.h" +#include "internalwindow.h" +#include "scene/windowitem.h" +#include "virtualdesktops.h" +#include "waylandwindow.h" +#include "x11window.h" + +namespace KWin +{ + +class Q_DECL_HIDDEN EffectWindow::Private +{ +public: + Private(EffectWindow *q, WindowItem *windowItem); + + EffectWindow *q; + Window *m_window; + WindowItem *m_windowItem; // This one is used only during paint pass. + QHash dataMap; + bool managed = false; + bool m_waylandWindow; + bool m_x11Window; +}; + +EffectWindow::Private::Private(EffectWindow *q, WindowItem *windowItem) + : q(q) + , m_window(windowItem->window()) + , m_windowItem(windowItem) +{ +} + +EffectWindow::EffectWindow(WindowItem *windowItem) + : d(new Private(this, windowItem)) +{ + // Deleted windows are not managed. So, when windowClosed signal is + // emitted, effects can't distinguish managed windows from unmanaged + // windows(e.g. combo box popups, popup menus, etc). Save value of the + // managed property during construction of EffectWindow. At that time, + // parent can be Client, XdgShellClient, or Unmanaged. So, later on, when + // an instance of Deleted becomes parent of the EffectWindow, effects + // can still figure out whether it is/was a managed window. + d->managed = d->m_window->isClient(); + + d->m_waylandWindow = qobject_cast(d->m_window) != nullptr; + d->m_x11Window = qobject_cast(d->m_window) != nullptr; + + connect(d->m_window, &Window::windowShown, this, [this]() { + Q_EMIT windowShown(this); + }); + connect(d->m_window, &Window::windowHidden, this, [this]() { + Q_EMIT windowHidden(this); + }); + connect(d->m_window, &Window::maximizedChanged, this, [this]() { + const MaximizeMode mode = d->m_window->maximizeMode(); + Q_EMIT windowMaximizedStateChanged(this, mode & MaximizeHorizontal, mode & MaximizeVertical); + }); + connect(d->m_window, &Window::maximizedAboutToChange, this, [this](MaximizeMode m) { + Q_EMIT windowMaximizedStateAboutToChange(this, m & MaximizeHorizontal, m & MaximizeVertical); + }); + connect(d->m_window, &Window::frameGeometryAboutToChange, this, [this]() { + Q_EMIT windowFrameGeometryAboutToChange(this); + }); + connect(d->m_window, &Window::interactiveMoveResizeStarted, this, [this]() { + Q_EMIT windowStartUserMovedResized(this); + }); + connect(d->m_window, &Window::interactiveMoveResizeStepped, this, [this](const QRectF &geometry) { + Q_EMIT windowStepUserMovedResized(this, geometry); + }); + connect(d->m_window, &Window::interactiveMoveResizeFinished, this, [this]() { + Q_EMIT windowFinishUserMovedResized(this); + }); + connect(d->m_window, &Window::opacityChanged, this, [this](Window *window, qreal oldOpacity) { + Q_EMIT windowOpacityChanged(this, oldOpacity, window->opacity()); + }); + connect(d->m_window, &Window::minimizedChanged, this, [this]() { + if (d->m_window->isMinimized()) { + Q_EMIT windowMinimized(this); + } else { + Q_EMIT windowUnminimized(this); + } + }); + connect(d->m_window, &Window::modalChanged, this, [this]() { + Q_EMIT windowModalityChanged(this); + }); + connect(d->m_window, &Window::frameGeometryChanged, this, [this](const QRectF &oldGeometry) { + Q_EMIT windowFrameGeometryChanged(this, oldGeometry); + }); + connect(d->m_window, &Window::damaged, this, [this]() { + Q_EMIT windowDamaged(this); + }); + connect(d->m_window, &Window::unresponsiveChanged, this, [this](bool unresponsive) { + Q_EMIT windowUnresponsiveChanged(this, unresponsive); + }); + connect(d->m_window, &Window::keepAboveChanged, this, [this]() { + Q_EMIT windowKeepAboveChanged(this); + }); + connect(d->m_window, &Window::keepBelowChanged, this, [this]() { + Q_EMIT windowKeepBelowChanged(this); + }); + connect(d->m_window, &Window::fullScreenChanged, this, [this]() { + Q_EMIT windowFullScreenChanged(this); + }); + connect(d->m_window, &Window::visibleGeometryChanged, this, [this]() { + Q_EMIT windowExpandedGeometryChanged(this); + }); + connect(d->m_window, &Window::decorationChanged, this, [this]() { + Q_EMIT windowDecorationChanged(this); + }); + connect(d->m_window, &Window::desktopsChanged, this, [this]() { + Q_EMIT windowDesktopsChanged(this); + }); +} + +EffectWindow::~EffectWindow() +{ +} + +Window *EffectWindow::window() const +{ + return d->m_window; +} + +WindowItem *EffectWindow::windowItem() const +{ + return d->m_windowItem; +} + +bool EffectWindow::isOnActivity(const QString &activity) const +{ + const QStringList _activities = activities(); + return _activities.isEmpty() || _activities.contains(activity); +} + +bool EffectWindow::isOnAllActivities() const +{ + return activities().isEmpty(); +} + +void EffectWindow::setMinimized(bool min) +{ + if (min) { + minimize(); + } else { + unminimize(); + } +} + +bool EffectWindow::isOnCurrentActivity() const +{ + return isOnActivity(effects->currentActivity()); +} + +bool EffectWindow::isOnCurrentDesktop() const +{ + return isOnDesktop(effects->currentDesktop()); +} + +bool EffectWindow::isOnDesktop(VirtualDesktop *desktop) const +{ + const QList ds = desktops(); + return ds.isEmpty() || ds.contains(desktop); +} + +bool EffectWindow::isOnAllDesktops() const +{ + return desktops().isEmpty(); +} + +bool EffectWindow::hasDecoration() const +{ + return contentsRect() != QRect(0, 0, width(), height()); +} + +bool EffectWindow::isVisible() const +{ + return !isMinimized() + && isOnCurrentDesktop() + && isOnCurrentActivity(); +} + +void EffectWindow::refVisible(const EffectWindowVisibleRef *holder) +{ + d->m_windowItem->refVisible(holder->reason()); +} + +void EffectWindow::unrefVisible(const EffectWindowVisibleRef *holder) +{ + d->m_windowItem->unrefVisible(holder->reason()); +} + +void EffectWindow::addRepaint(const QRect &r) +{ + d->m_windowItem->scheduleRepaint(QRegion(r)); +} + +void EffectWindow::addRepaintFull() +{ + d->m_windowItem->scheduleRepaint(d->m_windowItem->boundingRect()); +} + +void EffectWindow::addLayerRepaint(const QRect &r) +{ + d->m_windowItem->scheduleRepaint(d->m_windowItem->mapFromGlobal(r)); +} + +const EffectWindowGroup *EffectWindow::group() const +{ + if (auto c = qobject_cast(d->m_window)) { + return c->group()->effectGroup(); + } + return nullptr; // TODO +} + +void EffectWindow::refWindow() +{ + if (d->m_window->isDeleted()) { + return d->m_window->ref(); + } + Q_UNREACHABLE(); // TODO +} + +void EffectWindow::unrefWindow() +{ + if (d->m_window->isDeleted()) { + return d->m_window->unref(); + } + Q_UNREACHABLE(); // TODO +} + +Output *EffectWindow::screen() const +{ + return d->m_window->output(); +} + +#define WINDOW_HELPER(rettype, prototype, toplevelPrototype) \ + rettype EffectWindow::prototype() const \ + { \ + return d->m_window->toplevelPrototype(); \ + } + +WINDOW_HELPER(double, opacity, opacity) +WINDOW_HELPER(qreal, x, x) +WINDOW_HELPER(qreal, y, y) +WINDOW_HELPER(qreal, width, width) +WINDOW_HELPER(qreal, height, height) +WINDOW_HELPER(QPointF, pos, pos) +WINDOW_HELPER(QSizeF, size, size) +WINDOW_HELPER(QRectF, frameGeometry, frameGeometry) +WINDOW_HELPER(QRectF, bufferGeometry, bufferGeometry) +WINDOW_HELPER(QRectF, clientGeometry, clientGeometry) +WINDOW_HELPER(QRectF, expandedGeometry, visibleGeometry) +WINDOW_HELPER(QRectF, rect, rect) +WINDOW_HELPER(bool, isDesktop, isDesktop) +WINDOW_HELPER(bool, isDock, isDock) +WINDOW_HELPER(bool, isToolbar, isToolbar) +WINDOW_HELPER(bool, isMenu, isMenu) +WINDOW_HELPER(bool, isNormalWindow, isNormalWindow) +WINDOW_HELPER(bool, isDialog, isDialog) +WINDOW_HELPER(bool, isSplash, isSplash) +WINDOW_HELPER(bool, isUtility, isUtility) +WINDOW_HELPER(bool, isDropdownMenu, isDropdownMenu) +WINDOW_HELPER(bool, isPopupMenu, isPopupMenu) +WINDOW_HELPER(bool, isTooltip, isTooltip) +WINDOW_HELPER(bool, isNotification, isNotification) +WINDOW_HELPER(bool, isCriticalNotification, isCriticalNotification) +WINDOW_HELPER(bool, isAppletPopup, isAppletPopup) +WINDOW_HELPER(bool, isOnScreenDisplay, isOnScreenDisplay) +WINDOW_HELPER(bool, isComboBox, isComboBox) +WINDOW_HELPER(bool, isDNDIcon, isDNDIcon) +WINDOW_HELPER(bool, isDeleted, isDeleted) +WINDOW_HELPER(QString, windowRole, windowRole) +WINDOW_HELPER(QStringList, activities, activities) +WINDOW_HELPER(bool, skipsCloseAnimation, skipsCloseAnimation) +WINDOW_HELPER(SurfaceInterface *, surface, surface) +WINDOW_HELPER(bool, isPopupWindow, isPopupWindow) +WINDOW_HELPER(bool, isOutline, isOutline) +WINDOW_HELPER(bool, isLockScreen, isLockScreen) +WINDOW_HELPER(pid_t, pid, pid) +WINDOW_HELPER(QUuid, internalId, internalId) +WINDOW_HELPER(bool, isMinimized, isMinimized) +WINDOW_HELPER(bool, isHidden, isHidden) +WINDOW_HELPER(bool, isHiddenByShowDesktop, isHiddenByShowDesktop) +WINDOW_HELPER(bool, isModal, isModal) +WINDOW_HELPER(bool, isFullScreen, isFullScreen) +WINDOW_HELPER(bool, keepAbove, keepAbove) +WINDOW_HELPER(bool, keepBelow, keepBelow) +WINDOW_HELPER(QString, caption, caption) +WINDOW_HELPER(bool, isMovable, isMovable) +WINDOW_HELPER(bool, isMovableAcrossScreens, isMovableAcrossScreens) +WINDOW_HELPER(bool, isUserMove, isInteractiveMove) +WINDOW_HELPER(bool, isUserResize, isInteractiveResize) +WINDOW_HELPER(QRectF, iconGeometry, iconGeometry) +WINDOW_HELPER(bool, isSpecialWindow, isSpecialWindow) +WINDOW_HELPER(bool, acceptsFocus, wantsInput) +WINDOW_HELPER(QIcon, icon, icon) +WINDOW_HELPER(bool, isSkipSwitcher, skipSwitcher) +WINDOW_HELPER(bool, decorationHasAlpha, decorationHasAlpha) +WINDOW_HELPER(bool, isUnresponsive, unresponsive) +WINDOW_HELPER(QList, desktops, desktops) +WINDOW_HELPER(bool, isInputMethod, isInputMethod) + +#undef WINDOW_HELPER + +qlonglong EffectWindow::windowId() const +{ + if (X11Window *x11Window = qobject_cast(d->m_window)) { + return x11Window->window(); + } + return 0; +} + +QString EffectWindow::windowClass() const +{ + return d->m_window->resourceName() + QLatin1Char(' ') + d->m_window->resourceClass(); +} + +QRectF EffectWindow::contentsRect() const +{ + return QRectF(d->m_window->clientPos(), d->m_window->clientSize()); +} + +NET::WindowType EffectWindow::windowType() const +{ + return d->m_window->windowType(); +} + +QSizeF EffectWindow::basicUnit() const +{ + if (auto window = qobject_cast(d->m_window)) { + return window->basicUnit(); + } + return QSize(1, 1); +} + +QRectF EffectWindow::decorationInnerRect() const +{ + return d->m_window->rect() - d->m_window->frameMargins(); +} + +KDecoration2::Decoration *EffectWindow::decoration() const +{ + return d->m_window->decoration(); +} + +QByteArray EffectWindow::readProperty(long atom, long type, int format) const +{ + auto x11Window = qobject_cast(d->m_window); + if (!x11Window) { + return QByteArray(); + } + if (!kwinApp()->x11Connection()) { + return QByteArray(); + } + uint32_t len = 32768; + for (;;) { + Xcb::Property prop(false, x11Window->window(), atom, XCB_ATOM_ANY, 0, len); + if (prop.isNull()) { + // get property failed + return QByteArray(); + } + if (prop->bytes_after > 0) { + len *= 2; + continue; + } + return prop.toByteArray(format, type); + } +} + +void EffectWindow::deleteProperty(long int atom) const +{ + auto x11Window = qobject_cast(d->m_window); + if (!x11Window) { + return; + } + if (!kwinApp()->x11Connection()) { + return; + } + xcb_delete_property(kwinApp()->x11Connection(), x11Window->window(), atom); +} + +EffectWindow *EffectWindow::findModal() +{ + Window *modal = d->m_window->findModal(); + if (modal) { + return modal->effectWindow(); + } + + return nullptr; +} + +EffectWindow *EffectWindow::transientFor() +{ + Window *transientFor = d->m_window->transientFor(); + if (transientFor) { + return transientFor->effectWindow(); + } + + return nullptr; +} + +QWindow *EffectWindow::internalWindow() const +{ + if (auto window = qobject_cast(d->m_window)) { + return window->handle(); + } + return nullptr; +} + +template +QList getMainWindows(T *c) +{ + const auto mainwindows = c->mainWindows(); + QList ret; + ret.reserve(mainwindows.size()); + std::transform(std::cbegin(mainwindows), std::cend(mainwindows), + std::back_inserter(ret), + [](auto window) { + return window->effectWindow(); + }); + return ret; +} + +QList EffectWindow::mainWindows() const +{ + return getMainWindows(d->m_window); +} + +void EffectWindow::setData(int role, const QVariant &data) +{ + if (!data.isNull()) { + d->dataMap[role] = data; + } else { + d->dataMap.remove(role); + } + Q_EMIT effects->windowDataChanged(this, role); +} + +QVariant EffectWindow::data(int role) const +{ + return d->dataMap.value(role); +} + +void EffectWindow::elevate(bool elevate) +{ + effects->setElevatedWindow(this, elevate); +} + +void EffectWindow::minimize() +{ + if (d->m_window->isClient()) { + d->m_window->setMinimized(true); + } +} + +void EffectWindow::unminimize() +{ + if (d->m_window->isClient()) { + d->m_window->setMinimized(false); + } +} + +void EffectWindow::closeWindow() +{ + if (d->m_window->isClient()) { + d->m_window->closeWindow(); + } +} + +bool EffectWindow::isManaged() const +{ + return d->managed; +} + +bool EffectWindow::isWaylandClient() const +{ + return d->m_waylandWindow; +} + +bool EffectWindow::isX11Client() const +{ + return d->m_x11Window; +} + +//**************************************** +// EffectWindowGroup +//**************************************** + +EffectWindowGroup::EffectWindowGroup(Group *group) + : m_group(group) +{ +} + +EffectWindowGroup::~EffectWindowGroup() +{ +} + +QList EffectWindowGroup::members() const +{ + const auto memberList = m_group->members(); + QList ret; + ret.reserve(memberList.size()); + std::transform(std::cbegin(memberList), std::cend(memberList), std::back_inserter(ret), [](auto window) { + return window->effectWindow(); + }); + return ret; +} + +} // namespace KWin + +#include "moc_effectwindow.cpp" diff --git a/src/effect/effectwindow.h b/src/effect/effectwindow.h new file mode 100644 index 0000000000..6ef32b7448 --- /dev/null +++ b/src/effect/effectwindow.h @@ -0,0 +1,999 @@ +/* + SPDX-FileCopyrightText: 2006 Lubos Lunak + SPDX-FileCopyrightText: 2009 Lucas Murray + SPDX-FileCopyrightText: 2010, 2011 Martin Gräßlin + SPDX-FileCopyrightText: 2018 Vlad Zahorodnii + + SPDX-License-Identifier: GPL-2.0-or-later +*/ + +#pragma once + +#include "kwin_export.h" + +#include + +#include + +class QWindow; + +namespace KDecoration2 +{ +class Decoration; +} + +namespace KWin +{ + +class EffectWindowGroup; +class EffectWindowVisibleRef; +class Group; +class Output; +class SurfaceInterface; +class VirtualDesktop; +class Window; +class WindowItem; + +/** + * @short Representation of a window used by/for Effect classes. + * + * The purpose is to hide internal data and also to serve as a single + * representation for the case when Client/Unmanaged becomes Deleted. + */ +class KWIN_EXPORT EffectWindow : public QObject +{ + Q_OBJECT + Q_PROPERTY(QRectF geometry READ frameGeometry) + Q_PROPERTY(QRectF expandedGeometry READ expandedGeometry) + Q_PROPERTY(qreal height READ height) + Q_PROPERTY(qreal opacity READ opacity) + Q_PROPERTY(QPointF pos READ pos) + Q_PROPERTY(KWin::Output *screen READ screen) + Q_PROPERTY(QSizeF size READ size) + Q_PROPERTY(qreal width READ width) + Q_PROPERTY(qreal x READ x) + Q_PROPERTY(qreal y READ y) + Q_PROPERTY(QList desktops READ desktops) + Q_PROPERTY(bool onAllDesktops READ isOnAllDesktops) + Q_PROPERTY(bool onCurrentDesktop READ isOnCurrentDesktop) + Q_PROPERTY(QRectF rect READ rect) + Q_PROPERTY(QString windowClass READ windowClass) + Q_PROPERTY(QString windowRole READ windowRole) + /** + * Returns whether the window is a desktop background window (the one with wallpaper). + * See _NET_WM_WINDOW_TYPE_DESKTOP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool desktopWindow READ isDesktop) + /** + * Returns whether the window is a dock (i.e. a panel). + * See _NET_WM_WINDOW_TYPE_DOCK at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool dock READ isDock) + /** + * Returns whether the window is a standalone (detached) toolbar window. + * See _NET_WM_WINDOW_TYPE_TOOLBAR at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool toolbar READ isToolbar) + /** + * Returns whether the window is a torn-off menu. + * See _NET_WM_WINDOW_TYPE_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool menu READ isMenu) + /** + * Returns whether the window is a "normal" window, i.e. an application or any other window + * for which none of the specialized window types fit. + * See _NET_WM_WINDOW_TYPE_NORMAL at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool normalWindow READ isNormalWindow) + /** + * Returns whether the window is a dialog window. + * See _NET_WM_WINDOW_TYPE_DIALOG at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool dialog READ isDialog) + /** + * Returns whether the window is a splashscreen. Note that many (especially older) applications + * do not support marking their splash windows with this type. + * See _NET_WM_WINDOW_TYPE_SPLASH at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool splash READ isSplash) + /** + * Returns whether the window is a utility window, such as a tool window. + * See _NET_WM_WINDOW_TYPE_UTILITY at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool utility READ isUtility) + /** + * Returns whether the window is a dropdown menu (i.e. a popup directly or indirectly open + * from the applications menubar). + * See _NET_WM_WINDOW_TYPE_DROPDOWN_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool dropdownMenu READ isDropdownMenu) + /** + * Returns whether the window is a popup menu (that is not a torn-off or dropdown menu). + * See _NET_WM_WINDOW_TYPE_POPUP_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool popupMenu READ isPopupMenu) + /** + * Returns whether the window is a tooltip. + * See _NET_WM_WINDOW_TYPE_TOOLTIP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool tooltip READ isTooltip) + /** + * Returns whether the window is a window with a notification. + * See _NET_WM_WINDOW_TYPE_NOTIFICATION at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool notification READ isNotification) + /** + * Returns whether the window is a window with a critical notification. + * using the non-standard _KDE_NET_WM_WINDOW_TYPE_CRITICAL_NOTIFICATION + */ + Q_PROPERTY(bool criticalNotification READ isCriticalNotification) + /** + * Returns whether the window is an on screen display window + * using the non-standard _KDE_NET_WM_WINDOW_TYPE_ON_SCREEN_DISPLAY + */ + Q_PROPERTY(bool onScreenDisplay READ isOnScreenDisplay) + /** + * Returns whether the window is a combobox popup. + * See _NET_WM_WINDOW_TYPE_COMBO at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool comboBox READ isComboBox) + /** + * Returns whether the window is a Drag&Drop icon. + * See _NET_WM_WINDOW_TYPE_DND at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(bool dndIcon READ isDNDIcon) + /** + * Returns the NETWM window type + * See https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(int windowType READ windowType) + /** + * Whether this EffectWindow is managed by KWin (it has control over its placement and other + * aspects, as opposed to override-redirect windows that are entirely handled by the application). + */ + Q_PROPERTY(bool managed READ isManaged) + /** + * Whether this EffectWindow represents an already deleted window and only kept for the compositor for animations. + */ + Q_PROPERTY(bool deleted READ isDeleted) + /** + * The Caption of the window. Read from WM_NAME property together with a suffix for hostname and shortcut. + */ + Q_PROPERTY(QString caption READ caption) + /** + * Whether the window is set to be kept above other windows. + */ + Q_PROPERTY(bool keepAbove READ keepAbove) + /** + * Whether the window is set to be kept below other windows. + */ + Q_PROPERTY(bool keepBelow READ keepBelow) + /** + * Whether the window is minimized. + */ + Q_PROPERTY(bool minimized READ isMinimized WRITE setMinimized) + /** + * Whether the window represents a modal window. + */ + Q_PROPERTY(bool modal READ isModal) + /** + * Whether the window is moveable. Even if it is not moveable, it might be possible to move + * it to another screen. + * @see moveableAcrossScreens + */ + Q_PROPERTY(bool moveable READ isMovable) + /** + * Whether the window can be moved to another screen. + * @see moveable + */ + Q_PROPERTY(bool moveableAcrossScreens READ isMovableAcrossScreens) + /** + * By how much the window wishes to grow/shrink at least. Usually QSize(1,1). + * MAY BE DISOBEYED BY THE WM! It's only for information, do NOT rely on it at all. + */ + Q_PROPERTY(QSizeF basicUnit READ basicUnit) + /** + * Whether the window is currently being moved by the user. + */ + Q_PROPERTY(bool move READ isUserMove) + /** + * Whether the window is currently being resized by the user. + */ + Q_PROPERTY(bool resize READ isUserResize) + /** + * The optional geometry representing the minimized Client in e.g a taskbar. + * See _NET_WM_ICON_GEOMETRY at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + Q_PROPERTY(QRectF iconGeometry READ iconGeometry) + /** + * Returns whether the window is any of special windows types (desktop, dock, splash, ...), + * i.e. window types that usually don't have a window frame and the user does not use window + * management (moving, raising,...) on them. + */ + Q_PROPERTY(bool specialWindow READ isSpecialWindow) + Q_PROPERTY(QIcon icon READ icon) + /** + * Whether the window should be excluded from window switching effects. + */ + Q_PROPERTY(bool skipSwitcher READ isSkipSwitcher) + /** + * Geometry of the actual window contents inside the whole (including decorations) window. + */ + Q_PROPERTY(QRectF contentsRect READ contentsRect) + /** + * Geometry of the transparent rect in the decoration. + * May be different from contentsRect if the decoration is extended into the client area. + */ + Q_PROPERTY(QRectF decorationInnerRect READ decorationInnerRect) + Q_PROPERTY(bool hasDecoration READ hasDecoration) + Q_PROPERTY(QStringList activities READ activities) + Q_PROPERTY(bool onCurrentActivity READ isOnCurrentActivity) + Q_PROPERTY(bool onAllActivities READ isOnAllActivities) + /** + * Whether the decoration currently uses an alpha channel. + * @since 4.10 + */ + Q_PROPERTY(bool decorationHasAlpha READ decorationHasAlpha) + /** + * Whether the window is currently visible to the user, that is: + *
    + *
  • Not minimized
  • + *
  • On current desktop
  • + *
  • On current activity
  • + *
+ * @since 4.11 + */ + Q_PROPERTY(bool visible READ isVisible) + /** + * Whether the window does not want to be animated on window close. + * In case this property is @c true it is not useful to start an animation on window close. + * The window will not be visible, but the animation hooks are executed. + * @since 5.0 + */ + Q_PROPERTY(bool skipsCloseAnimation READ skipsCloseAnimation) + + /** + * Whether the window is fullscreen. + * @since 5.6 + */ + Q_PROPERTY(bool fullScreen READ isFullScreen) + + /** + * Whether this client is unresponsive. + * + * When an application failed to react on a ping request in time, it is + * considered unresponsive. This usually indicates that the application froze or crashed. + * + * @since 5.10 + */ + Q_PROPERTY(bool unresponsive READ isUnresponsive) + + /** + * Whether this is a Wayland client. + * @since 5.15 + */ + Q_PROPERTY(bool waylandClient READ isWaylandClient CONSTANT) + + /** + * Whether this is an X11 client. + * @since 5.15 + */ + Q_PROPERTY(bool x11Client READ isX11Client CONSTANT) + + /** + * Whether the window is a popup. + * + * A popup is a window that can be used to implement tooltips, combo box popups, + * popup menus and other similar user interface concepts. + * + * @since 5.15 + */ + Q_PROPERTY(bool popupWindow READ isPopupWindow CONSTANT) + + /** + * KWin internal window. Specific to Wayland platform. + * + * If the EffectWindow does not reference an internal window, this property is @c null. + * @since 5.16 + */ + Q_PROPERTY(QWindow *internalWindow READ internalWindow CONSTANT) + + /** + * Whether this EffectWindow represents the outline. + * + * When compositing is turned on, the outline is an actual window. + * + * @since 5.16 + */ + Q_PROPERTY(bool outline READ isOutline CONSTANT) + + /** + * The PID of the application this window belongs to. + * + * @since 5.18 + */ + Q_PROPERTY(pid_t pid READ pid CONSTANT) + + /** + * Whether this EffectWindow represents the screenlocker greeter. + * + * @since 5.22 + */ + Q_PROPERTY(bool lockScreen READ isLockScreen CONSTANT) + + /** + * Whether this EffectWindow is hidden because the show desktop mode is active. + */ + Q_PROPERTY(bool hiddenByShowDesktop READ isHiddenByShowDesktop) + +public: + /** Flags explaining why painting should be disabled */ + enum { + /** Window will not be painted */ + PAINT_DISABLED = 1 << 0, + /** Window will not be painted because of which desktop it's on */ + PAINT_DISABLED_BY_DESKTOP = 1 << 1, + /** Window will not be painted because it is minimized */ + PAINT_DISABLED_BY_MINIMIZE = 1 << 2, + /** Window will not be painted because it's not on the current activity */ + PAINT_DISABLED_BY_ACTIVITY = 1 << 3, + }; + + explicit EffectWindow(WindowItem *windowItem); + ~EffectWindow() override; + + Q_SCRIPTABLE void addRepaint(const QRect &r); + Q_SCRIPTABLE void addRepaint(int x, int y, int w, int h); + Q_SCRIPTABLE void addRepaintFull(); + Q_SCRIPTABLE void addLayerRepaint(const QRect &r); + Q_SCRIPTABLE void addLayerRepaint(int x, int y, int w, int h); + + void refWindow(); + void unrefWindow(); + + bool isDeleted() const; + bool isHidden() const; + bool isHiddenByShowDesktop() const; + + bool isMinimized() const; + double opacity() const; + + bool isOnCurrentActivity() const; + Q_SCRIPTABLE bool isOnActivity(const QString &id) const; + bool isOnAllActivities() const; + QStringList activities() const; + + Q_SCRIPTABLE bool isOnDesktop(KWin::VirtualDesktop *desktop) const; + bool isOnCurrentDesktop() const; + bool isOnAllDesktops() const; + /** + * All the desktops by number that the window is in. On X11 this list will always have + * a length of 1, on Wayland can be any subset. + * If the list is empty it means the window is on all desktops + */ + QList desktops() const; + + qreal x() const; + qreal y() const; + qreal width() const; + qreal height() const; + /** + * By how much the window wishes to grow/shrink at least. Usually QSize(1,1). + * MAY BE DISOBEYED BY THE WM! It's only for information, do NOT rely on it at all. + */ + QSizeF basicUnit() const; + /** + * Returns the geometry of the window excluding server-side and client-side + * drop-shadows. + * + * @since 5.18 + */ + QRectF frameGeometry() const; + /** + * Returns the geometry of the pixmap or buffer attached to this window. + * + * For X11 clients, this method returns server-side geometry of the Window. + * + * For Wayland clients, this method returns rectangle that the main surface + * occupies on the screen, in global screen coordinates. + * + * @since 5.18 + */ + QRectF bufferGeometry() const; + QRectF clientGeometry() const; + /** + * Geometry of the window including decoration and potentially shadows. + * May be different from geometry() if the window has a shadow. + * @since 4.9 + */ + QRectF expandedGeometry() const; + Output *screen() const; + QPointF pos() const; + QSizeF size() const; + QRectF rect() const; + bool isMovable() const; + bool isMovableAcrossScreens() const; + bool isUserMove() const; + bool isUserResize() const; + QRectF iconGeometry() const; + + /** + * Geometry of the actual window contents inside the whole (including decorations) window. + */ + QRectF contentsRect() const; + /** + * Geometry of the transparent rect in the decoration. + * May be different from contentsRect() if the decoration is extended into the client area. + * @since 4.5 + */ + QRectF decorationInnerRect() const; + bool hasDecoration() const; + bool decorationHasAlpha() const; + /** + * Returns the decoration + * @since 5.25 + */ + KDecoration2::Decoration *decoration() const; + QByteArray readProperty(long atom, long type, int format) const; + void deleteProperty(long atom) const; + + QString caption() const; + QIcon icon() const; + QString windowClass() const; + QString windowRole() const; + const EffectWindowGroup *group() const; + + /** + * Returns whether the window is a desktop background window (the one with wallpaper). + * See _NET_WM_WINDOW_TYPE_DESKTOP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isDesktop() const; + /** + * Returns whether the window is a dock (i.e. a panel). + * See _NET_WM_WINDOW_TYPE_DOCK at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isDock() const; + /** + * Returns whether the window is a standalone (detached) toolbar window. + * See _NET_WM_WINDOW_TYPE_TOOLBAR at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isToolbar() const; + /** + * Returns whether the window is a torn-off menu. + * See _NET_WM_WINDOW_TYPE_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isMenu() const; + /** + * Returns whether the window is a "normal" window, i.e. an application or any other window + * for which none of the specialized window types fit. + * See _NET_WM_WINDOW_TYPE_NORMAL at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isNormalWindow() const; // normal as in 'NET::Normal or NET::Unknown non-transient' + /** + * Returns whether the window is any of special windows types (desktop, dock, splash, ...), + * i.e. window types that usually don't have a window frame and the user does not use window + * management (moving, raising,...) on them. + */ + bool isSpecialWindow() const; + /** + * Returns whether the window is a dialog window. + * See _NET_WM_WINDOW_TYPE_DIALOG at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isDialog() const; + /** + * Returns whether the window is a splashscreen. Note that many (especially older) applications + * do not support marking their splash windows with this type. + * See _NET_WM_WINDOW_TYPE_SPLASH at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isSplash() const; + /** + * Returns whether the window is a utility window, such as a tool window. + * See _NET_WM_WINDOW_TYPE_UTILITY at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isUtility() const; + /** + * Returns whether the window is a dropdown menu (i.e. a popup directly or indirectly open + * from the applications menubar). + * See _NET_WM_WINDOW_TYPE_DROPDOWN_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isDropdownMenu() const; + /** + * Returns whether the window is a popup menu (that is not a torn-off or dropdown menu). + * See _NET_WM_WINDOW_TYPE_POPUP_MENU at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isPopupMenu() const; // a context popup, not dropdown, not torn-off + /** + * Returns whether the window is a tooltip. + * See _NET_WM_WINDOW_TYPE_TOOLTIP at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isTooltip() const; + /** + * Returns whether the window is a window with a notification. + * See _NET_WM_WINDOW_TYPE_NOTIFICATION at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isNotification() const; + /** + * Returns whether the window is a window with a critical notification. + * using the non-standard _KDE_NET_WM_WINDOW_TYPE_CRITICAL_NOTIFICATION + */ + bool isCriticalNotification() const; + /** + * Returns whether the window is a window used for applet popups. + */ + bool isAppletPopup() const; + /** + * Returns whether the window is an on screen display window + * using the non-standard _KDE_NET_WM_WINDOW_TYPE_ON_SCREEN_DISPLAY + */ + bool isOnScreenDisplay() const; + /** + * Returns whether the window is a combobox popup. + * See _NET_WM_WINDOW_TYPE_COMBO at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isComboBox() const; + /** + * Returns whether the window is a Drag&Drop icon. + * See _NET_WM_WINDOW_TYPE_DND at https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + bool isDNDIcon() const; + /** + * Returns the NETWM window type + * See https://standards.freedesktop.org/wm-spec/wm-spec-latest.html . + */ + NET::WindowType windowType() const; + /** + * Returns whether the window is managed by KWin (it has control over its placement and other + * aspects, as opposed to override-redirect windows that are entirely handled by the application). + */ + bool isManaged() const; // whether it's managed or override-redirect + /** + * Returns whether or not the window can accept keyboard focus. + */ + bool acceptsFocus() const; + /** + * Returns whether or not the window is kept above all other windows. + */ + bool keepAbove() const; + /** + * Returns whether the window is kept below all other windows. + */ + bool keepBelow() const; + + bool isModal() const; + Q_SCRIPTABLE KWin::EffectWindow *findModal(); + Q_SCRIPTABLE KWin::EffectWindow *transientFor(); + Q_SCRIPTABLE QList mainWindows() const; + + /** + * Returns whether the window should be excluded from window switching effects. + * @since 4.5 + */ + bool isSkipSwitcher() const; + + void setMinimized(bool minimize); + void minimize(); + void unminimize(); + Q_SCRIPTABLE void closeWindow(); + + /** + * @since 4.11 + */ + bool isVisible() const; + + /** + * @since 5.0 + */ + bool skipsCloseAnimation() const; + + /** + * @since 5.5 + */ + SurfaceInterface *surface() const; + + /** + * @since 5.6 + */ + bool isFullScreen() const; + + /** + * @since 5.10 + */ + bool isUnresponsive() const; + + /** + * @since 5.15 + */ + bool isWaylandClient() const; + + /** + * @since 5.15 + */ + bool isX11Client() const; + + /** + * @since 5.15 + */ + bool isPopupWindow() const; + + /** + * @since 5.16 + */ + QWindow *internalWindow() const; + + /** + * @since 5.16 + */ + bool isOutline() const; + + /** + * @since 5.22 + */ + bool isLockScreen() const; + + /** + * @since 5.18 + */ + pid_t pid() const; + + /** + * @since 5.21 + */ + qlonglong windowId() const; + /** + * Returns the internal id of the window that uniquely identifies it. The main difference + * between internalId() and windowId() is that the latter one works as expected only on X11, + * while the former is unique regardless of the window system. + * + * Note that the internaId() has special meaning only to kwin. + * @since 5.24 + */ + QUuid internalId() const; + + /** + * @since 6.0 + */ + bool isInputMethod() const; + + /** + * Can be used to by effects to store arbitrary data in the EffectWindow. + * + * Invoking this method will emit the signal EffectsHandler::windowDataChanged. + * @see EffectsHandler::windowDataChanged + */ + Q_SCRIPTABLE void setData(int role, const QVariant &data); + Q_SCRIPTABLE QVariant data(int role) const; + + Window *window() const; + WindowItem *windowItem() const; + void elevate(bool elevate); + +Q_SIGNALS: + /** + * Signal emitted when a user begins a window move or resize operation. + * To figure out whether the user resizes or moves the window use + * isUserMove or isUserResize. + * Whenever the geometry is updated the signal @ref windowStepUserMovedResized + * is emitted with the current geometry. + * The move/resize operation ends with the signal @ref windowFinishUserMovedResized. + * Only one window can be moved/resized by the user at the same time! + * @param w The window which is being moved/resized + * @see windowStepUserMovedResized + * @see windowFinishUserMovedResized + * @see EffectWindow::isUserMove + * @see EffectWindow::isUserResize + */ + void windowStartUserMovedResized(KWin::EffectWindow *w); + /** + * Signal emitted during a move/resize operation when the user changed the geometry. + * Please note: KWin supports two operation modes. In one mode all changes are applied + * instantly. This means the window's geometry matches the passed in @p geometry. In the + * other mode the geometry is changed after the user ended the move/resize mode. + * The @p geometry differs from the window's geometry. Also the window's pixmap still has + * the same size as before. Depending what the effect wants to do it would be recommended + * to scale/translate the window. + * @param w The window which is being moved/resized + * @param geometry The geometry of the window in the current move/resize step. + * @see windowStartUserMovedResized + * @see windowFinishUserMovedResized + * @see EffectWindow::isUserMove + * @see EffectWindow::isUserResize + */ + void windowStepUserMovedResized(KWin::EffectWindow *w, const QRectF &geometry); + /** + * Signal emitted when the user finishes move/resize of window @p w. + * @param w The window which has been moved/resized + * @see windowStartUserMovedResized + * @see windowFinishUserMovedResized + */ + void windowFinishUserMovedResized(KWin::EffectWindow *w); + + /** + * Signal emitted when the maximized state of the window @p w changed. + * A window can be in one of four states: + * @li restored: both @p horizontal and @p vertical are @c false + * @li horizontally maximized: @p horizontal is @c true and @p vertical is @c false + * @li vertically maximized: @p horizontal is @c false and @p vertical is @c true + * @li completely maximized: both @p horizontal and @p vertical are @c true + * @param w The window whose maximized state changed + * @param horizontal If @c true maximized horizontally + * @param vertical If @c true maximized vertically + */ + void windowMaximizedStateChanged(KWin::EffectWindow *w, bool horizontal, bool vertical); + + /** + * Signal emitted when the maximized state of the window @p w is about to change, + * but before windowMaximizedStateChanged is emitted or any geometry change. + * Useful for OffscreenEffect to grab a window image before any actual change happens + * + * A window can be in one of four states: + * @li restored: both @p horizontal and @p vertical are @c false + * @li horizontally maximized: @p horizontal is @c true and @p vertical is @c false + * @li vertically maximized: @p horizontal is @c false and @p vertical is @c true + * @li completely maximized: both @p horizontal and @p vertical are @c true + * @param w The window whose maximized state changed + * @param horizontal If @c true maximized horizontally + * @param vertical If @c true maximized vertically + */ + void windowMaximizedStateAboutToChange(KWin::EffectWindow *w, bool horizontal, bool vertical); + + /** + * This signal is emitted when the frame geometry of a window changed. + * @param window The window whose geometry changed + * @param oldGeometry The previous geometry + */ + void windowFrameGeometryChanged(KWin::EffectWindow *window, const QRectF &oldGeometry); + + /** + * This signal is emitted when the frame geometry is about to change, the new one is not known yet. + * Useful for OffscreenEffect to grab a window image before any actual change happens. + * + * @param window The window whose geometry is about to change + */ + void windowFrameGeometryAboutToChange(KWin::EffectWindow *window); + + /** + * Signal emitted when the windows opacity is changed. + * @param w The window whose opacity level is changed. + * @param oldOpacity The previous opacity level + * @param newOpacity The new opacity level + */ + void windowOpacityChanged(KWin::EffectWindow *w, qreal oldOpacity, qreal newOpacity); + /** + * Signal emitted when a window got minimized. + * @param w The window which was minimized + */ + void windowMinimized(KWin::EffectWindow *w); + /** + * Signal emitted when a window got unminimized. + * @param w The window which was unminimized + */ + void windowUnminimized(KWin::EffectWindow *w); + /** + * Signal emitted when a window either becomes modal (ie. blocking for its main client) or looses that state. + * @param w The window which was unminimized + */ + void windowModalityChanged(KWin::EffectWindow *w); + /** + * Signal emitted when a window either became unresponsive (eg. app froze or crashed) + * or respoonsive + * @param w The window that became (un)responsive + * @param unresponsive Whether the window is responsive or unresponsive + */ + void windowUnresponsiveChanged(KWin::EffectWindow *w, bool unresponsive); + /** + * Signal emitted when an area of a window is scheduled for repainting. + * Use this signal in an effect if another area needs to be synced as well. + * @param w The window which is scheduled for repainting + */ + void windowDamaged(KWin::EffectWindow *w); + + /** + * This signal is emitted when the keep above state of @p w was changed. + * + * @param w The window whose the keep above state was changed. + */ + void windowKeepAboveChanged(KWin::EffectWindow *w); + + /** + * This signal is emitted when the keep below state of @p was changed. + * + * @param w The window whose the keep below state was changed. + */ + void windowKeepBelowChanged(KWin::EffectWindow *w); + + /** + * This signal is emitted when the full screen state of @p w was changed. + * + * @param w The window whose the full screen state was changed. + */ + void windowFullScreenChanged(KWin::EffectWindow *w); + + /** + * This signal is emitted when decoration of @p was changed. + * + * @param w The window for which decoration changed + */ + void windowDecorationChanged(KWin::EffectWindow *window); + + /** + * This signal is emitted when the visible geometry of a window changed. + */ + void windowExpandedGeometryChanged(KWin::EffectWindow *window); + + /** + * This signal is emitted when a window enters or leaves a virtual desktop. + */ + void windowDesktopsChanged(KWin::EffectWindow *window); + + /** + * The window @p w gets shown again. The window was previously + * initially shown with windowAdded and hidden with windowHidden. + * + * @see windowHidden + * @see windowAdded + */ + void windowShown(KWin::EffectWindow *w); + + /** + * The window @p w got hidden but not yet closed. + * This can happen when a window is still being used and is supposed to be shown again + * with windowShown. On X11 an example is autohiding panels. On Wayland every + * window first goes through the window hidden state and might get shown again, or might + * get closed the normal way. + * + * @see windowShown + * @see windowClosed + */ + void windowHidden(KWin::EffectWindow *w); + +protected: + friend EffectWindowVisibleRef; + void refVisible(const EffectWindowVisibleRef *holder); + void unrefVisible(const EffectWindowVisibleRef *holder); + +private: + class Private; + std::unique_ptr d; +}; + +/** + * The EffectWindowDeletedRef provides a convenient way to prevent deleting a closed + * window until an effect has finished animating it. + */ +class KWIN_EXPORT EffectWindowDeletedRef +{ +public: + EffectWindowDeletedRef() + : m_window(nullptr) + { + } + + explicit EffectWindowDeletedRef(EffectWindow *window) + : m_window(window) + { + m_window->refWindow(); + } + + EffectWindowDeletedRef(const EffectWindowDeletedRef &other) + : m_window(other.m_window) + { + if (m_window) { + m_window->refWindow(); + } + } + + ~EffectWindowDeletedRef() + { + if (m_window) { + m_window->unrefWindow(); + } + } + + EffectWindowDeletedRef &operator=(const EffectWindowDeletedRef &other) + { + if (other.m_window) { + other.m_window->refWindow(); + } + if (m_window) { + m_window->unrefWindow(); + } + m_window = other.m_window; + return *this; + } + + bool isNull() const + { + return m_window == nullptr; + } + +private: + EffectWindow *m_window; +}; + +/** + * The EffectWindowVisibleRef provides a convenient way to force the visible status of a + * window until an effect is finished animating it. + */ +class KWIN_EXPORT EffectWindowVisibleRef +{ +public: + EffectWindowVisibleRef() + : m_window(nullptr) + , m_reason(0) + { + } + + explicit EffectWindowVisibleRef(EffectWindow *window, int reason) + : m_window(window) + , m_reason(reason) + { + m_window->refVisible(this); + } + + EffectWindowVisibleRef(const EffectWindowVisibleRef &other) + : m_window(other.m_window) + , m_reason(other.m_reason) + { + if (m_window) { + m_window->refVisible(this); + } + } + + ~EffectWindowVisibleRef() + { + if (m_window) { + m_window->unrefVisible(this); + } + } + + int reason() const + { + return m_reason; + } + + EffectWindowVisibleRef &operator=(const EffectWindowVisibleRef &other) + { + if (other.m_window) { + other.m_window->refVisible(&other); + } + if (m_window) { + m_window->unrefVisible(this); + } + m_window = other.m_window; + m_reason = other.m_reason; + return *this; + } + + bool isNull() const + { + return m_window == nullptr; + } + +private: + EffectWindow *m_window; + int m_reason; +}; + +class KWIN_EXPORT EffectWindowGroup +{ +public: + explicit EffectWindowGroup(Group *group); + virtual ~EffectWindowGroup(); + + QList members() const; + +private: + Group *m_group; +}; + +inline void EffectWindow::addRepaint(int x, int y, int w, int h) +{ + addRepaint(QRect(x, y, w, h)); +} + +inline void EffectWindow::addLayerRepaint(int x, int y, int w, int h) +{ + addLayerRepaint(QRect(x, y, w, h)); +} + +} // namespace KWin diff --git a/src/plugins/blendchanges/blendchanges.cpp b/src/plugins/blendchanges/blendchanges.cpp index ce75c67f9b..f62d75d340 100644 --- a/src/plugins/blendchanges/blendchanges.cpp +++ b/src/plugins/blendchanges/blendchanges.cpp @@ -8,6 +8,7 @@ */ // own #include "blendchanges.h" +#include "effect/effects.h" #include "opengl/glutils.h" #include diff --git a/src/plugins/blendchanges/blendchanges.h b/src/plugins/blendchanges/blendchanges.h index 3ee3f13321..6ec9c9a8f1 100644 --- a/src/plugins/blendchanges/blendchanges.h +++ b/src/plugins/blendchanges/blendchanges.h @@ -7,7 +7,6 @@ SPDX-License-Identifier: GPL-2.0-or-later */ #pragma once -#include "effect/effects.h" #include "effect/offscreeneffect.h" #include "effect/timeline.h" #include diff --git a/src/plugins/fallapart/fallapart.cpp b/src/plugins/fallapart/fallapart.cpp index 59a0911cf6..a13af586ad 100644 --- a/src/plugins/fallapart/fallapart.cpp +++ b/src/plugins/fallapart/fallapart.cpp @@ -8,6 +8,7 @@ */ #include "fallapart.h" +#include "effect/effects.h" // KConfigSkeleton #include "fallapartconfig.h" diff --git a/src/plugins/fallapart/fallapart.h b/src/plugins/fallapart/fallapart.h index 7655cd7657..b670e38de6 100644 --- a/src/plugins/fallapart/fallapart.h +++ b/src/plugins/fallapart/fallapart.h @@ -9,7 +9,7 @@ #pragma once -#include "effect/effects.h" +#include "effect/effectwindow.h" #include "effect/offscreeneffect.h" namespace KWin diff --git a/src/plugins/glide/glide.cpp b/src/plugins/glide/glide.cpp index a9356aaa4e..5901dc9e19 100644 --- a/src/plugins/glide/glide.cpp +++ b/src/plugins/glide/glide.cpp @@ -18,6 +18,7 @@ #include "core/rendertarget.h" #include "core/renderviewport.h" +#include "effect/effects.h" // Qt #include diff --git a/src/plugins/glide/glide.h b/src/plugins/glide/glide.h index dbe4adc287..5db87716dc 100644 --- a/src/plugins/glide/glide.h +++ b/src/plugins/glide/glide.h @@ -13,7 +13,8 @@ #pragma once // kwineffects -#include "effect/effects.h" +#include "effect/effect.h" +#include "effect/effectwindow.h" #include "effect/timeline.h" namespace KWin diff --git a/src/plugins/kscreen/kscreen.cpp b/src/plugins/kscreen/kscreen.cpp index 35240e62b6..ac7079e5b0 100644 --- a/src/plugins/kscreen/kscreen.cpp +++ b/src/plugins/kscreen/kscreen.cpp @@ -9,6 +9,7 @@ // own #include "kscreen.h" #include "core/output.h" +#include "effect/effects.h" // KConfigSkeleton #include "kscreenconfig.h" #include diff --git a/src/plugins/kscreen/kscreen.h b/src/plugins/kscreen/kscreen.h index 1907056b41..ffd35da458 100644 --- a/src/plugins/kscreen/kscreen.h +++ b/src/plugins/kscreen/kscreen.h @@ -8,9 +8,11 @@ */ #pragma once -#include "effect/effects.h" +#include "effect/effect.h" #include "effect/timeline.h" +#include + namespace KWin { diff --git a/src/plugins/magiclamp/magiclamp.cpp b/src/plugins/magiclamp/magiclamp.cpp index d41105d708..b5f1833fc8 100644 --- a/src/plugins/magiclamp/magiclamp.cpp +++ b/src/plugins/magiclamp/magiclamp.cpp @@ -10,6 +10,7 @@ // based on minimize animation by Rivo Laks #include "magiclamp.h" +#include "effect/effects.h" // KConfigSkeleton #include "magiclampconfig.h" diff --git a/src/plugins/magiclamp/magiclamp.h b/src/plugins/magiclamp/magiclamp.h index 22bc43608c..e82c8bd52e 100644 --- a/src/plugins/magiclamp/magiclamp.h +++ b/src/plugins/magiclamp/magiclamp.h @@ -9,7 +9,7 @@ #pragma once -#include "effect/effects.h" +#include "effect/effectwindow.h" #include "effect/offscreeneffect.h" #include "effect/timeline.h" diff --git a/src/plugins/magnifier/magnifier.cpp b/src/plugins/magnifier/magnifier.cpp index a422c9cdfc..85470386c8 100644 --- a/src/plugins/magnifier/magnifier.cpp +++ b/src/plugins/magnifier/magnifier.cpp @@ -17,6 +17,7 @@ #include #include "core/renderviewport.h" +#include "effect/effects.h" #include "opengl/glutils.h" #include diff --git a/src/plugins/magnifier/magnifier.h b/src/plugins/magnifier/magnifier.h index b3a16377a7..62c429c8df 100644 --- a/src/plugins/magnifier/magnifier.h +++ b/src/plugins/magnifier/magnifier.h @@ -10,7 +10,7 @@ #pragma once -#include "effect/effects.h" +#include "effect/effect.h" namespace KWin { diff --git a/src/plugins/sheet/sheet.cpp b/src/plugins/sheet/sheet.cpp index 3eb21582e7..7414910dac 100644 --- a/src/plugins/sheet/sheet.cpp +++ b/src/plugins/sheet/sheet.cpp @@ -16,6 +16,7 @@ #include "sheetconfig.h" #include "core/renderviewport.h" +#include "effect/effects.h" // Qt #include diff --git a/src/plugins/sheet/sheet.h b/src/plugins/sheet/sheet.h index 5e81e5dc26..69ed3c500f 100644 --- a/src/plugins/sheet/sheet.h +++ b/src/plugins/sheet/sheet.h @@ -12,7 +12,8 @@ #pragma once // kwineffects -#include "effect/effects.h" +#include "effect/effect.h" +#include "effect/effectwindow.h" #include "effect/timeline.h" namespace KWin diff --git a/src/plugins/showfps/showfpseffect.cpp b/src/plugins/showfps/showfpseffect.cpp index e4d2a4588e..d06ee64881 100644 --- a/src/plugins/showfps/showfpseffect.cpp +++ b/src/plugins/showfps/showfpseffect.cpp @@ -9,6 +9,7 @@ #include "showfpseffect.h" #include "core/output.h" #include "core/renderviewport.h" +#include "effect/effects.h" #include diff --git a/src/plugins/showfps/showfpseffect.h b/src/plugins/showfps/showfpseffect.h index 6296ea812c..ff57ed01a3 100644 --- a/src/plugins/showfps/showfpseffect.h +++ b/src/plugins/showfps/showfpseffect.h @@ -8,7 +8,7 @@ #pragma once -#include "effect/effects.h" +#include "effect/effect.h" #include "effect/offscreenquickview.h" #include diff --git a/src/plugins/slide/slide.cpp b/src/plugins/slide/slide.cpp index 3f05dd233d..ed5f689eea 100644 --- a/src/plugins/slide/slide.cpp +++ b/src/plugins/slide/slide.cpp @@ -12,6 +12,7 @@ // own #include "slide.h" #include "core/output.h" +#include "effect/effects.h" // KConfigSkeleton #include "slideconfig.h" diff --git a/src/plugins/slide/slide.h b/src/plugins/slide/slide.h index f80e7d62c7..8332518bb4 100644 --- a/src/plugins/slide/slide.h +++ b/src/plugins/slide/slide.h @@ -12,9 +12,9 @@ #pragma once // kwineffects -#include "effect/effects.h" - -#include "springmotion.h" +#include "effect/effect.h" +#include "effect/effectwindow.h" +#include "plugins/slide/springmotion.h" namespace KWin { diff --git a/src/plugins/slideback/slideback.cpp b/src/plugins/slideback/slideback.cpp index 399b130b08..7c56ac691d 100644 --- a/src/plugins/slideback/slideback.cpp +++ b/src/plugins/slideback/slideback.cpp @@ -8,6 +8,7 @@ */ #include "slideback.h" +#include "effect/effects.h" namespace KWin { diff --git a/src/plugins/slideback/slideback.h b/src/plugins/slideback/slideback.h index 0f48438e56..1e6e66c61b 100644 --- a/src/plugins/slideback/slideback.h +++ b/src/plugins/slideback/slideback.h @@ -10,7 +10,7 @@ #pragma once // Include with base class for effects. -#include "effect/effects.h" +#include "effect/effect.h" #include "plugins/slideback/motionmanager.h" namespace KWin diff --git a/src/plugins/slidingpopups/slidingpopups.cpp b/src/plugins/slidingpopups/slidingpopups.cpp index a399b14bba..012080338e 100644 --- a/src/plugins/slidingpopups/slidingpopups.cpp +++ b/src/plugins/slidingpopups/slidingpopups.cpp @@ -11,6 +11,7 @@ #include "slidingpopups.h" #include "slidingpopupsconfig.h" +#include "effect/effects.h" #include "wayland/display.h" #include "wayland/slide.h" #include "wayland/surface.h" diff --git a/src/plugins/slidingpopups/slidingpopups.h b/src/plugins/slidingpopups/slidingpopups.h index 621ce6241d..6c7b5ef5e7 100644 --- a/src/plugins/slidingpopups/slidingpopups.h +++ b/src/plugins/slidingpopups/slidingpopups.h @@ -11,7 +11,8 @@ #pragma once // Include with base class for effects. -#include "effect/effects.h" +#include "effect/effect.h" +#include "effect/effectwindow.h" #include "effect/timeline.h" namespace KWin diff --git a/src/scene/itemrenderer_opengl.cpp b/src/scene/itemrenderer_opengl.cpp index 7a48049e47..4a60031e18 100644 --- a/src/scene/itemrenderer_opengl.cpp +++ b/src/scene/itemrenderer_opengl.cpp @@ -7,6 +7,7 @@ #include "scene/itemrenderer_opengl.h" #include "core/rendertarget.h" #include "core/renderviewport.h" +#include "effect/effect.h" #include "platformsupport/scenes/opengl/openglsurfacetexture.h" #include "scene/decorationitem.h" #include "scene/imageitem.h" diff --git a/src/scene/itemrenderer_opengl.h b/src/scene/itemrenderer_opengl.h index 27ffae047e..c35839335c 100644 --- a/src/scene/itemrenderer_opengl.h +++ b/src/scene/itemrenderer_opengl.h @@ -6,7 +6,6 @@ #pragma once -#include "effect/effects.h" #include "opengl/glutils.h" #include "platformsupport/scenes/opengl/openglsurfacetexture.h" #include "scene/itemrenderer.h"