If the ShellClient got created for a Qt internal window, we try to
find the QWindow and if we get one, we use the geometry directly as
it got set by KWin in the first place.
Also a windowId() is added to ShellClient which can be used by the
effect system to find an EffectWindow. If it's an internal QWindow
we just use that window id. For other clients we still need some
smart solution.
The signal might be emited by Workspace just before a Client gets
destroyed. In that case the argument carried by the queued event is no
longer valid and causes problems. In EffectsHandlerImpl we can queue
it without problems as the EffectWindow also stays valid if the Client
gets destroyed. The referenced Deleted gets destroyed with a deleteLater,
thus will be after the signal is emitted.
BUG: 347490
REVIEW: 123729
The change is mostly straight forward. Effects are straight forward
adjusted. Client::findModal is moved up, this causes still a few
dynamic_casts to Client. Mostly because Workspace::activateClient still
operates on Client.
The ShellClient is a Toplevel subclass for a
KWayland::Server::ShellSurfaceInterface. It gets created when a new
ShellSurfaceInterface is created and destoryed when it gets unmapped.
So far the usage is still rather limited. The ShellClient is opened
at position (0/0). While it's possible to pass pointer events to it,
it's not yet possible to activate it, so no keyboard focus.
The AbstractBackend registers itself in the WaylandServer allowing
external users to easily get to the backend and not needing to test
manually which backend is used.
The xcb_cursor_t returned by xcb-cursor library might be broken. If we
set such a broken cursor directly in the create window call it will fail
with a BadCursor value causing effects to break.
This change works around this problem by creating just the window and
moving the possible breaking call into a change window call. That will
still fail, but the window is working.
In addition it performs a safety check by only installing the cursor
if it's not XCB_CURSOR_NONE.
BUG: 344006
REVIEW: 123025
Instead of getting size from displayWidth() and displayHeight() use
the information we have from Screens. This means there is only one
place to have the information and by that we can ensure that all
components use the same data to rely on. displayWidth/displayHeight
seem to provide the wrong information when unplugging an output
without disabling the output. This results in rendering artefacts.
But KWin::Screens has the correct information available.
The build option got introduced for Plasma Active back in a time
when we did not properly aim for convergence. In a Plasma 5 world
we want to have only one shell and one window manager which adjust
itself. This means we don't want a differently compiled kwin for
plasma active, but the same one. Thus the build option doesn't
make much sense any more. A KWin for touch interface needs to support
screenedges for the case that mouse is plugged in.
CCBUG: 340960
REVIEW: 121200
NOTE: this is not working completely yet, lots of code is still ifdefed
other parts are still broken.
The main difference for the new decoration API is that it is neither
QWidget nor QWindow based. It's just a QObject which processes input
events and has a paint method to render the decoration. This means all
the workarounds for the QWidget interception are removed. Also the paint
redirector is removed. Instead each compositor has now its own renderer
which can be optimized for the specific case. E.g. the OpenGL compositor
renders to a scratch image which gets copied into the combined texture,
the XRender compositor copies into the XPixmaps.
Input events are also changed. The events are composed into QMouseEvents
and passed through the decoration, which might accept them. If they are
not accpted we assume that it's a press on the decoration area allowing
us to resize/move the window. Input events are not completely working
yet, e.g. wheel events are not yet processed and double click on deco
is not yet working.
Overall KDecoration2 is way more stateful and KWin core needs more
adjustments for it. E.g. borders are allowed to be disabled at any time.
This removes all the hacks to add kwin4_effect_ to the name of the Effect
and adjusts the desktop files of the effect configuration's parent
component.
Note: the scripted effects still start with kwin4_effect_ prefix.
REVIEW: 117367
The Xcb::Property can wrap the xcb_get_property call and provides
convenient access methods to read the value of the reply with checks
applied. For this it provides a templated ::value method for reading a
single value or reading an array. There's also a ::toBool and
::toByteArray which performs the conversion directly with default values
for the type and format checks.
Xcb::TransientFor is changed to be derived from Property instead of
Wrapper directly, so that the reading of the property value can be
shared.
Xcb::StringProperty is a convenient wrapper derived from Property to
handle the reading of a string property providing a cast to QByteArray
operator. This replaces the ::getStringProperty from utils. Though the
separator functionality from ::getStringProperty is not provided as that
is only used in one function and handled there.
All the custom usages of xcb_get_property or getStringProperty are
replaced to use this new wrapper. That simplifies the code and ensures
that all properties are read in the same way.
REVIEW: 117574
The EffectLoader is a subclass of AbstractEffectLoader delegating all
methods to instances of:
* BuiltInEffectLoader
* ScriptedEffectLoader
* PluginEffectLoader
It's used by the EffectsHandlerImpl and replaces the complete Effect
loading mechanism we so far found in it. This also means that KLibrary
is no longer needed to load the Effects as the PluginEffectLoader uses
the KPluginTrader, which removes lots of deprecated functionality.
REVIEW: 117054
This method replaces the X-KDE-ORDERING property in the Effect's desktop
files. This change is a preparation step for integrating the new Effect
Loader which doesn't read the ordering information. Thus it needs to be
provided by the Effect itself so that the EffectsHandler can properly
insert it into the chain.
Also for the built-in Effects on the long run it doesn't make much sense
to install the desktop files. And binary plugin effects will migrate to
json metadata which also doesn't have the KService::Ptr. Thus overall it
simplifies to read this information directly from the Effect.
The functionality is to check whether the effect should be enabled by
default. It's not about whether the effect is enabled by default. This
is also needed as it's currently still taken from the plugin data.
All the connections in EffectsHandlerImpl are replaced by the new syntax.
Where it makes sense the wrapping slot method is added as a lambda and
the slot method is removed.
REVIEW: 117076
When the Effect has to be reconfigured the configuration most likely
changed, thus we should reload it. Of course it would be possible to also
do this in each Effect::reconfigureEffect, but this would mean that the
configuration would be reloaded during startup, which we do not want.
Instead of passing the macro based Predicate to findClient it now
expects a function which can be passed to std::find_if.
Existing code like:
xcb_window_t window; // our test window
Client *c = findClient(WindowMatchPredicated(window));
becomes:
Client *c = findClient([window](const Client *c) {
return c->window() == window;
});
The advantage is that it is way more flexible and has the logic what
to check for directly with the code and not hidden in the macro
definition.
In addition there is a simplified overload for the very common case of
matching a window id against one of Client's windows. This overloaded
method takes a Predicate and the window id.
Above example becomes:
Client *c = findClient(Predicate::WindowMatch, w);
Existing code is migrated to use the simplified method taking
MatchPredicate and window id. The very few cases where a more complex
condition is tested the lambda function is used. As these are very
local tests only used in one function it's not worthwhile to add further
overloads to the findClient method in Workspace.
With this change all the Predicate macro definitions are removed from
utils.h as they are now completely unused.
REVIEW: 116916
Instead of passing the macro based Predicate to findUnmanaged it now
expects a function which can be passed to std::find_if.
Existing code like:
xcb_window_t window; // our test window
Unmanaged *u = findUnmanaged(WindowMatchPredicated(window));
becomes:
Unmanaged *u = findUnmanaged([window](const Unmanaged *u) {
return u->window() == window;
});
In addition an overload is added which takes the window id to cover
the common case to search for an Unmanaged by its ID. The above example
becomes:
Unmanaged *u = findUnmanaged(window);
The advantage is that it is way more flexible and has the logic what
to check for directly with the code and not hidden in the macro
definition.
Implemented in KWin core to forward to new global shortcut system. This
method should be extended/changed once we go to Qt5/KF5 to make the usage
easier (no more KAction).
Each global shortcut in the effects makes use of this new method.
Major new functionality is xkbcommon support. InputRedirection holds an
instance to a small wrapper class which has the xkb context, keymap and
state. The keymap is initialied from the file descriptor we get from the
Wayland backend.
InputRedirection uses this to translate the keycodes into keysymbols and
to QString and to track the modifiers as provided by the
Qt::KeybordModifiers flags.
This provides us enough information for internal usage (e.g. pass through
effects if they have "grabbed" the keyboard).
If KWin doesn't filter out the key events, it passes them on to the
currently active Client respectively an unmanaged on top of the stack.
This needs still some improvement (not each unmanaged should get the
event). The Client/Unmnaged still uses xtest extension to send the key
events to the window. So keylogging is still possible.
Unfortunately this is extremely platform specific with code for X11 and
Wayland. But at the moment it doesn't make much sense to abstract as
Effects are the only case where a fullscreen low level input area is
used.
A small problem is also that the mouse cursor doesn't get restored and
is changed when the X11 cursor changes. This will be fixed once we start
to properly track the cursor of the individual X windows.
InputRedirection forwards pointer events (currently motion, press and
release) through the EffectsHandlerImpl for the case that an effect has
intercepted pointer events.
If the KWin operation mode is not X11 only, the window for intercepting
the mouse events is no longer created.
EffectsHandlerImpl::isEffectsSupported performs the check whether the
effect with the given name is supported by the current compositor.
The check is the following:
* if effect is already loaded, it is supported
* if the effect cannot be found, it is not supported
* if it's a scripted effect, it's always supported
* if it's a built-in effect, we ask BuiltInEffects::supported
* for all other effects we resolve the library and the supported
method
The idea behind providing this functionality in the DBus interface is
to allow filtering in the effects KCM for the effects which are
supported by the current compositor.
In addition a areEffectsSupported method is added which takes a
list of names and returns a list of bools.
REVIEW: 116665
Screens provides a size which is constructed from the size of
the bounding geometry of all screens and provides an overload taking
an int to return the size of a specified screen. For geometry() a new
ovload is added without an argument, which is just a convenient wrapper
for QRect(QPoint(0, 0), size()).
Both new methods are exported to effects and scripting as new
properties there called virtualScreenSize and virtualScreenGeometry.
The (virtual) size gets cached in screens and is updated whenever the
count or geometry changes.
Construction of Screens is slightly changed by moving the init code
from ctor into a virtual method init(). Reason is that we ended in
a loop with accessing the singleton pointer before it was set.
REVIEW: 116114
Scripting has proved it's point of being useful so it's time to turn it
into a mandatory part of KWin.
Also I start to use features provided by Scripting in more and more
parts of KWin core (e.g. sharing QQmlEngine) which makes it in the
long to complicated to have a build option and ifdefs for it.
REVIEW: 116587
Loading all effects during startup can take some time[1] and during
that time the screen is frozen as the loading blocks the compositor.
This change doesn't load effects directly but puts them into a queue.
The loading is controlled by invoking the dequeue through a queued
connection. Thus we get a firing compositing timer in between and can
ensure that a frame is rendered when needed and also react to X events
during the loading.
[1] On my high-end system the set of effects I use take about 200 msec
to load.
REVIEW: 115297
As all effects have always been compiled into the same .so file it's
questionable whether resolving the effects through a library is useful
at all. By linking against the built-in effects we gain the following
advantages:
* don't have to load/unload the KLibrary
* don't have to resolve the create, supported and enabled functions
* no version check required
* no dependency resolving (effects don't use it)
* remove the KWIN_EFFECT macros from the effects
All the effects are now registered in an effects_builtins file which
maps the name to a factory method and supported or enabled by default
methods.
During loading the effects we first check whether there is a built-in
effect by the given name and make a shortcut to create it through that.
If that's not possible the normal plugin loading is used.
Completely unscientific testing [1] showed an improvement of almost 10
msec during loading all the effects I use.
[1] QElapsedTimer around the loading code, start kwin five times, take
average.
REVIEW: 115073