Launching pipewire and wireplumber is racy, as there is an arbitrary
amount of time between pipewire is launched, and that the socket is
bound.
In order to eliminate this race, bind the pipewire sockets ourselves,
and launch pipewire (and wireplumber) when there is activity on the
socket. This is using the systemd method of doing socket activation,
which consists of passing the number of passed file descriptors via
$LISTEN_FDS, and the pid of the launchee via $LISTEN_PID.
The former is easy, just pass the file descriptors, but the former is
more tricky when using python, as executing code before exec() is poorly
supported and likely to be deprecated. To address this, socket
activation services are wrapped in a socket-launch.sh helper which sets
the $LISTEN_PID to itself before calling exec().
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3973>
list = ['one']
list.append('two,three'.split(','))
results in ['one', ['two', 'three']]
while
list += 'two,three'.split(',')
results in ['one', 'two', 'three']
which is what is expected.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3973>
While when running with meson, we want the output to be in meson-logs
for convenience, such a path isn't feasible when running as an installed
test. To address this, make the destination path configurable via an
environment variable.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3973>
This aims to replace a reoccuring arbitrary sleep followed by a focus
assertion. The problem with these is that the sleep does not reliably
wait for long enough, due to arbitrary system resource usage in CI and
elsewhere. By instead waiting, and instead asserting we don't have any
intermediate wrong focus, we remove the race, and test for more invalid
situations.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3973>
See previous commit log on the effects of this.
This means the deadline evasion needs to be added in both cases in
clutter_frame_clock_notify_presented.
v2:
* Use meta_kms_update_set_sync_fd. (Jonas Ådahl)
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3958>
If the KMS thread is using the deadline timer, and a valid sync_file
descriptor is passed in:
1. The update is deferred, and the deadline timer is left armed, until
the sync_fd signals (becomes readable).
2. Implicit synchronization is disabled for the KMS update.
This means cursor updates should no longer miss a display refresh
cycle due to mutter's compositing GPU work finishing too late.
v2:
* Use g_autoptr for GSource in meta_kms_impl_device_handle_update.
(Sebastian Wick)
v3:
* Use meta_kms_update_get_sync_fd, don't track sync_fd in
CrtcFrame::submitted_update. (Jonas Ådahl)
v4:
* Clean up CrtcFrame::submitted_update members in crtc_frame_free.
v5:
* Coding style cleanup in meta_kms_impl_device_handle_update.
(Jonas Ådahl)
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3958>
If the window_drag->handle ClutterActor:visible property is FALSE,
then we avoid a full-framebuffer damage on the monitor when beginning
and ending a drag.
Testing with `mutter --wayland --display-server` still shows a full-
framebuffer damage on the first drag, but that appears to be unrelated
to this. Subsequent full-framebuffer damage which would occur on
drag-begin and drag-end have been elided.
Related: #3630
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3975>
Toplevels get the main monitor from their MetaWindow and have no main
monitor when the toplevel is not mapped.
Subsurfaces get the main monitor from their parent surface.
DnD and cursors get the main monitor from the current cursor position no
matter if the cursor is actually being shown or not.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3941>
The main monitor is role dependent. For a toplevel this comes from the
MetaWindow main monitor, for a subsurface from the parent surface, for
pointer and dnd from the cursor position.
The next commit will use meta_wayland_surface_set_main_monitor in the
different roles to keep the property up-to-date.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3941>
So far, the tests relied on the host system to provide pipewire and
wireplumber. This seperates the tests from the host system which is
especially useful if the tests are run in a toolbox which has a
different pipewire installed than the host. It also should make it
harder to have a mismatch between the pipewire library and the pipewire
daemon.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3966>
We're already inhibiting real time scheduling when reading new KMS state
after hot plugs, as well as when during mode sets, due to the kernel not
being able to reliably handle these within the 250 ms limit. However, we
didn't do this during initial probing, which meant that occasionally
we'd run into these kind of issues during startup.
Handle this by always inhibiting real time scheduling up front, and
don't uninhibit until all initially discovered device have finished
processing their initial mode set.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/3628
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3960>
If an application is maximised, clutter_stage_pick_and_update_device()
goes into the
if ((flags & CLUTTER_DEVICE_UPDATE_IGNORE_CACHE) == 0)
condition and returns the current actor for the device. This means no
CLUTTER_LEAVE/ENTER events are generated and in turn means the focus is
never invalidated and updated.
This leads to tool->focus_surface always being NULL and all events are
discarded.
Notably, tool->current is set to the right surface but
that one never changes either so meta_wayland_tablet_tool_set_current_surface()
exits early too because surface == tool->current and we thus never call
meta_wayland_input_invalidate_focus().
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/3616
Fixes: fb8ac5dff7 ("wayland: Track current tablet tool focus surface")
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3956>
Clutter's "device-removed" signal is sent in
clutter_seat_handle_event_post(). Our tablet code is set up to handle
that signal to then notify wayland clients of removed tablet devices.
However, returning CLUTTER_EVENT_STOP for a DEVICE_REMOVED event means
we never get to the point where we send out the signals and thus never
remove the tablets.
Fixes: a37fd34bbb ("wayland: Make MetaWaylandSeat in charge of its own tablet seat")
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/3615
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3955>
This leads to possibly missed key release events being propagated down to
clients, and in the case of X11 clients, to stuck keys e.g. after switching
workspace with Ctrl+Alt+Left/Right and ending up with a X11 client focused.
Fixes: 11a4d56185 ("keybindings: Send trigger when a key accelerator is deactivated")
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3935>
And take it into account in meta_kms_crtc_get_deadline_evasion.
This uses the same fundamental approach as clutter frame clock scheduling:
Measure the deadline timer dispatch duration, keep track of the longest
duration, and set the timer to fire such that the longest measured
dispatch duration would result in it completing shortly before start of
vblank.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/3612
v2:
* Move DEADLINE_EVASION_CONSTANT_US addition from
meta_kms_crtc_determine_deadline to meta_kms_crtc_get_deadline_evasion.
* Calculate how long before start of vblank dispatch completed for
debug output in crtc_frame_deadline_dispatch.
* Shorten over-long lines in crtc_frame_deadline_dispatch.
v3:
* Take VRR into account in crtc_frame_deadline_dispatch &
meta_kms_crtc_update_shortterm_max_dispatch_duration. (Robert Mader)
v4:
* Check if deadline has already passed in meta_kms_crtc_determine_deadline,
set the deadline for one refresh interval later if so.
* Fix indentation in crtc_frame_deadline_dispatch.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3934>
Let's add a bunch of tests for the newly introduced monitor config
migration code. We're verifying that:
- monitor configs get migrated and monitors.xml is updated on startup
- existing monitor configs in LOGICAL layout mode (ie.
"scale-monitor-framebuffers" was enabled before updating mutter) get
migrated
- the migration of various more complex monitor layouts from PHYSICAL
to LOGICAL layout mode works
- for monitor layouts where conversion to LOGICAL fails, the PHYSICAL
layout mode still is migrated, while for LOGICAL at least primary
monitor and disabled monitors are preserved
- simple monitor configurations (with no scaled monitors, or with only
"irrelevant" scaled monitors at the end of the layout) do not go through
the conversion code paths
- monitor configs in PHYSICAL layout mode with integer scale factors
which will result in non-integer logical monitor sizes get converted
to the closest fractional scale factor
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
We don't want to do the work of the layout mode detection and conversion
every time we read the monitors.xml file.
Instead, when the detection logic is used, set a flag to automatically
update the config files after the parsing is finished.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
Introduce some "best effort" conversion code to migrate monitor configurations
from PHYSICAL (the old default) to LOGICAL (the new default on wayland)
layout mode.
This conversion will only be used when the old PHYSICAL layout-mode
configuration is not compatible with the new LOGICAL layout-mode one.
This only applies if 1) there's a monitor that needs scaling in the
layout, and 2) the scaled monitor comes before other monitors in the
coordinate system (ie. it's not the rightmost or bottommost monitor).
There are two algorithms added here to convert monitor layouts:
- One for "simple" 1-dimensional monitor layouts, where all monitors are
aligned on a vertical or horizontal strip.
Here's a few (inaccurate) examples of how this would look with different
layouts (left side is PHYSICAL, right side is LOGICAL, x is the origin of
the coordinate system, the numbers are scales of the monitors):
```
x──────┬──────┬──────┐ x ┌──────┐
│ 2 │ 1 │ 2 │ 2┌──┤ 1 ├──┐2
│ │ │ │ ──► └──┤ ├──┘
└──────┴──────┴──────┘ └──────┘
x ┌──────┐ x ┌──────┐
┌────┤ 1 │ ┌──┤ 1 │
│ 2 │ │ ──► └──┤ │
└────┴──────┘ 2 └──────┘
x ┌────┐
┌──────┤ │ x──────┐
│ │ │ │ ├─┬────┐
│ 1 │ 3 │ ──► │ 1 │3│ 1 │
│ │ │ │ ├─┴────┘
└──────┤ │ └──────┘
│ ├────┐
│ │ 1 │
└────┴────┘
```
- A second more complex algorithm for 2-dimensional monitor layouts with
a common baseline that all monitors are aligned to.
And examples for this one:
```
x ┌──────┐
┌──────┤ │
│ 1 │ 2 │ x──────┐
│ │ │ │ 1 ├────┐
└──┬───┴───┬──┘ ──► │ │ 2 │
│ 3 │ ├──┬───┴────┘
│ │ └──┘3
└───────┘
x ┌──────┬──────┐
│ 1 │ │
│ │ │ x──────┬──────┐
┌─────┴──────┤ 1 │ │ 1 │ │
│ │ │ │ │ │
│ │ │ ──► └──┬───┤ 1 │
│ 3 │ │ │ 3 │ │
│ ├──────┘ └───┤ │
│ │ │ │
│ │ └──────┘
└────────────┘
x ┌───────┐
┌──────┐ │ │ x ┌───────┐
│ 2 │ ┌──────┤ 1 │ │ │
│ │ │ 1 │ │ 2 ┌──────┤ 1 │
└────┬─┴────┴─┬────┴───────┘ ──► ┌──┤ 1 │ │
│ │ ├──┴┬─────┴───────┘
│ 2 │ │ 2 │
│ │ └───┘
└────────┘
```
These algorithms will fail for any more complex 2d monitor layout, eg.
```
x ┌───┬────┐
│ 2 │ 1 │
│ ├────┘
┌───┴┬──┘
│ 1 │
└────┘
x───┬───┬───┐
│ 1 │ 2 │ 1 │
├───┼───┼───┤
│ 1 │ 1 │ 1 │
├───┼───┼───┤
│ 1 │ 1 │ 1 │
└───┴───┴───┘
```
In those cases where the conversion failed, we fall back to aligning
the monitors on a horizontal line, preserving the scale, the primary
monitor and the disabled monitors.
Note that we also need to convert the scale factor in some cases,
because LOGICAL layout mode also behaves different here:
When the scale results in a fractional logical monitor size (eg.
the native monitor width is 2560px, and a scale of 3 is set =>
2560px / 3 = 853.333px), in LOGICAL mode we won't use that scale.
Instead we have an algorithm (see
meta_monitor_get_closest_scale_factor_for_resolution()) to find
the nearest fractional scale factor which doesn't result in
fractional logical monitor size. We reuse this algorithm here for
the conversion.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
We'll reuse meta_monitor_get_closest_scale_factor_for_resolution() for the
conversion of monitor configs, and during those conversions, we probably don't
want to impose the same limits to fractional scales that we usually impose.
This means that we can even convert physical layout configs where the user
manually changed to a value higher than what our fractional scale calculations
would allow.
Move this check into the calling function so that it's not imposed by
meta_monitor_get_closest_scale_factor_for_resolution() directly.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
When there is no layout mode set in a logical monitor config, we currently just
assume the configuration matches the mode that the system expects. This blows
up when the layout mode expected by the system changes (eg. by turning on
"scale-monitor-framebuffers" in mutter): Suddenly configs fail the validation
check and get thrown away.
Since we now can add one configuration for each layout mode to the config store,
we can do better here: Let's only add configurations to the store where we
verified beforehand that the monitor layout is compatible with that mode, either
because we set it ourselves using the <layout_mode> key, or by detecting which
modes the layout is compatible with.
Also update monitor config ifiles to adjust for the new layout_mode, as
they all are assumed to be "logical".
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
Verify even more assumptions we make about logical monitor configs:
- Have a more explicit check that the monitor modes in the logical monitor are
all equal
- Complain if scale factor with physical layout mode is fractional
- Make sure that scale factor with logical layout mode actually scales to a
non-fractional width and height
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
We'll need a few of those things from the monitor config store soon, also it's
generally useful to have a prefix which makes it clear where functions are
defined.
So factor some things out into a new monitor-config-utils.c file.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
Store and load the layout mode for each logical monitor configuration in
monitors.xml by introducing a new <layoutmode> element. The value of the
element can be either "logical" or "physical". The layout mode is also
made part of the monitor configuration key.
Right now this isn't doing a lot:
When no <layoutmode> is found on the config (this is the case with all
existing configs), we'll keep using the layout mode expected by the system,
without updating the config file.
When changing an existing, or introducing a new configuration, we'll now
store the current layout mode with the config though, and load it again
on the next start of mutter. This is still not problematic as long as
mutters expected layout mode doesn't change (eg. by turning on/off
"scale-monitor-framebuffers").
When the expected layout mode of mutter switches between
restarts, the monitor config is now still loaded but remains unused,
and mutter will create (and store) a new one with the other layout mode.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
We'll introduce some new migration code with the next few commits to introduce
a layout_mode property in monitors.xml. This will be significantly easier
without keeping around the old monitor migration code, so drop it.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
We have meta_verify_logical_monitor_config() already, and it does a few checks that
meta_verify_monitors_config() doesn't do yet, so let's also call
meta_verify_logical_monitor_config() when verifying the whole config.
We'll rely on this being part of meta_verify_monitors_config() soon, because we'll
stop calling meta_verify_logical_monitor_config() from the config parser.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
We forgot to check whether multiple groups of monitors are actually
all connected with each other, so fix that.
[jadahl: Rewrote algorithm to detect split groups]
[jadahl: Added test case]
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3596>
The first event happening for a new touch will be the CLUTTER_ENTER
event generated when picking it. Use this event for registration of
the touch info, so that MetaWaylandEventHandler.get_focus_surface may
get the right focus surface for the device/sequence on the first try.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3889>
And notably, don't cancel touch when an event handler is being
removed. Touch events are largely unaffected by most Wayland
grabs (pointer constraints, popups), so we might be cancelling
input too early if one of these wayland grabs was effective when
touch interaction began, but stopped sometime between touch updates.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3889>
Touch events are implicitly grabbed to the surface they began in,
and are not affected by the focus handler. However these events
will appear to come from the core pointer device, which might lead
to the wrong device being updated.
Ignore events with a sequence, since the default focus handler
does not intend to do anything with them.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3889>
On a hybrid machine with i915 primary and nvidia-drm (470) secondary,
`meta_render_device_egl_stream_initable_init` calls
`meta_kms_inhibit_kernel_thread` to change from the default 'kernel'
thread type to 'user'. And soon after that it would
`meta_render_device_egl_stream_finalize` because I'm not actually
using that GPU, and calls `meta_kms_uninhibit_kernel_thread`.
So during startup Mutter would default to a realtime kernel thread,
switch to a user thread (which doesn't support realtime), and then
switch back to a realtime kernel thread.
In the middle of all that, while the thread type was 'user' and
realtime disabled, something was invoking `ensure_crtc_frame` which
created a `CrtcFrame` without a deadline timer. Soon after that the
thread type changed back to 'kernel' with deadline timers expected, but
our existing `CrtcFrame` has no deadline timer associated with it. And
so it would never fire, causing the cursor to freeze whenever the primary
plane isn't changing. And the problem was permanent, not just the first
frame because each `CrtcFrame` gets repeatedly reused (maybe shouldn't
be called a "Frame"?).
Now we adapt to switching between kernel and user thread types by adding
and removing the deadline timer as required.
Close: https://gitlab.gnome.org/GNOME/mutter/-/issues/3464
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3950>
Colord is a system service which will result in a polkit dialog showing
up when connecting a remote session.
We want to get rid of colord eventually anyway, so disconnecting virtual
monitors from colord isn't an issue.
Fixes: f5ce2ddf3c ("color-manager: Create color devices also for virtual monitors")
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3942>
If we finish compositing in time, the composited result will be
submitted prior to the deadline timer is triggered, and we'll be fine,
and if not, at least the cursor updates will be smooth, which makes it
appear smoother than not.
There is a risk that this can negatively impact composited updates when
moving the cursor, so make it possible to toggle a paint-debug flag for
now until this has been more tested.
This also mean we need to disarm the deadline timer after handling
update, as there might be a scheduled cursor update pending, but we
already handled it, so disarm the timer.
Here is an illustration of the difference.
In the following scenario, with disarming, the composited frame E, and
the cursor movement C gets presented. With this branch, only the cursor
movement C gets presented.
```
* A: beginning of composited frame
* B: begin notification reaches KMS thread
* C: cursor moved
* D: calculated deadline dispatch time (disabled with the branch)
* E: KMS update posted
* F: KMS update reaches KMS thread
* G: actual deadline (and with branch and gets committed)
Compositor thread: --------A---------------E---------
\ \
\ \
KMS thread: -----------B------C----D---F-G----
```
In the following scenario, by not disarming, the cursor update C will be
presented, and the would-be-delayed composited frame E would be delayed
anyway, i.e. fixing cursor stutter.
```
* A: beginning of composited frame
* B: begin notification reaches KMS thread
* C: cursor moved
* D: calculated deadline dispatch time (and with branch will be dispatched)
* E: KMS update posted
* F: actual deadline
* G: KMS update reaches KMS thread (and with branch gets postponed)
Compositor thread: --------A---------------E---------
\ \
\ \
KMS thread: -----------B------C----D-F-G------
```
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3184>
Although we track updates for EGL_DEVICE, they are often empty because
the primary plane has a custom page flip method. That means there's
no CRTC latched yet, but we do know exactly which CRTC is associated
with the flip. Set it so the update can still be processed.
Fixes: 27ed069766 ("kms/impl-device: Add deadline based KMS commit scheduling")
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3939>
If other handlers (e.g. DnD) are on top of the popup grab focus, we
may want it to move outside same-client surfaces as the popup grab
specifies.
Check that it is the current handler before making same-client checks,
so that these handlers on top have an opportunity to find other
surfaces, e.g. during DnD from a popup.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/1681
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3937>
Move away from tracking presses/releases directly, since there might be
other event handlers on top that might prevent the popup event handler
to fully track all events. The replacement is using event state modifiers,
which will use information set from the backend, and is enough to determine
there's no more pressed buttons without tracking prior event history.
This makes the popup event handler able to interact with other event
handlers that might be on top, and consume button release events for
themselves (e.g. DnD), no longer resulting in a stuck popup grab.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3937>
The relationship between MetaKmsConnector and MetaDrmLease is already
stored in MetaDrmLeaseManager::leased_connectors.
Change the type of MetaDrmLeaseManager::connectors to a GList.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3922>
As in the protocol definition for wp_drm_lease_connector_v1::withdrawn:
Sent to indicate that the compositor will no longer honor requests
for DRM leases which include this connector. [...] Compositors are
encouraged to send this event when [...] the connector gets leased
to a client.
Withdrawn the leased connectors and, if they are available once the
lease finishes, advertise them again.
Related to: https://gitlab.freedesktop.org/wayland/wayland-protocols/-/merge_requests/322/
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3922>
And stop passing in the color states from the RendererNative. We also
keep the color states updated by listening for changes in the color
device.
The RendererX11Cm has a single view and no mapping to a specific color
device, so we handle the absense of a color device as well and rely on
ClutterStageView to have the default color states.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3930>
This allows us to destroy and create a new offscreen dynamically, when
the rotation or color state changes.
An idle gsource with priority higher than CLUTTER_PRIORITY_REDRAW is
used to ensure the an offscreen exists when required without having to
allocate in the redraw process.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3930>
This is usually an indication of a failed drop operation if the
drop site didn't request any target. Check for this specifically
on XDnD button release, so that we can cancel the DnD operation
right away.
Inspired on a fix from Jonas Ådahl.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3821>
We were relying on the drag source surface to keep receiving events
thanks to it being implicitly grabbed by the button press. This
broke at some point, making the Xdnd drag source unable to keep
directing the DnD operation as it is expected by X11 clients.
To fix this, make the Xdnd MetaWaylandEventInterface stick itself
to the drag source surface keeping the focus of the device driving
the DnD operation, so that the X11 client can still handle events
from it.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/3511
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3821>
Currently, we would only disable a11y if a certain flag is passed
but the function is always called with NONE flag. Instead
drop the flag, use a new environment variable for that
That value is then used by actors to short-circuit get_accessible
implementation and return NULL if the accessibility is not enabled
Also clean the other accessibility functions
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3917>
Instead of doing that in both MetaStage & CallyStage.
This allows ClutterStage to also emits the relavant acessibility
bits directly without having a roundtrip through Cally
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3917>
The generic term updated can mean anything. This is specifically about
calibration related updates like changing the sink colorimetry
(Colorspace, HDR metadata) and changes to the white point for night
light etc.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3904>
Previously the color device was destroyed when it was attached to a
monitor that was going away. However, the MetaMonitor objects are
ref-counted and can stay around for longer, even if the underlying
resources went away. We need color devices for as long as the
MetaMonitors are alive.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3904>
Every monitor should eventually have a corresponding color device. To
make sure this can work, we must handle situations where the color
manager didn't connect to colord yet, and thus isn't ready.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3904>
When triple buffering, `meta_onscreen_native_prepare_frame` for the next
frame is called before `notify_view_crtc_presented` for the previous frame.
So our booleans were unfortunately still TRUE in the second prepare_frame,
resulting in two frames with the same property updates.
When double buffering, having roughly one frame interval between
`meta_onscreen_native_prepare_frame` and `notify_view_crtc_presented`
meant that property updates signalled between the swap and presentation
wouldn't get attached to a KMS update, and would be forgotten when
`notify_view_crtc_presented` resets the flags to FALSE.
To solve these we now keep a separate flag and counter per property,
tracking invalidation and pending updates respectively. The latter is a
counter rather than a boolean in support of triple buffering where two
updates may be pending concurrently (next and posted).
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3912>
Add a new service client type for a filechooser portal client, and
expose the x11_interop protocol to it.
This will be used to make Nautilus a file chooser portal implementation.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3694>
Because if the current theme has exceeded the dimensions of
`DRM_CAP_CURSOR_WIDTH/HEIGHT` then the warning is just going to repeat
every time the cursor changes. We still fall back to software cursors
just fine so it's not important to repeat the warning.
In Mutter 46 the warning was "Invalid theme cursor size". Same problem.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/3597
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3924>
As it was originally the function to be used before
making it private and providing safer wrappers around it for x11/win32.
Nowadays, it is only used in x11 and only internally in mutter, exposing
a 'safer' variant costs us exposing more of x11 renderer APIs without
much benefits.
With this change, the only internal xlib renderer we need from meta is
set_foreign_display which can't be easily worked around
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3910>
material is almost no longer used in the code base and the
few remaining references makes it confusing when looking at parts
of the codebase. So rename the rest as well.
Note that this renames a DeformEffect property and the only extension
making use of it doesn't use the property so i think it is okay to do
so without deprecating the old property for a few releases
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3910>
The OpenGL specs say rounding is preferred, but not required. Let's
avoid that uncertainty by choosing a test value that rounds and truncates
to the same integer either way. Only green needs fixing since our red,
blue and alpha values already follow this rule.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3903>
Simply to make it clear that the renamed function is specific to a
particular X11 initialization mode (mandatory Xwayland), put that in the
name, so that it's easier to understand when this function is relevant.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3329>
This means that for X11 sessions we'll do it before any windows are
mapped, and before any plugin implementation is started. Doing it before
a plugin is started is important, because things that the plugin does
during startup can have consequences on how compositing on Xorg works.
For the Xwayland case, we'll do it relatively in the setup phase. It
appears to have been harmless to do it later in the post-opened signal,
but there is no harm in doing it as one of the earlier steps.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/3089
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3329>
by executing `global.context.get_debug_control().exported = true`.
This makes it possible to get access to the debug service without having
to start with `--enable-debug`.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3902>
This means the pipeline can be manipulated after retrieving. This also
fixes a leak when adding pipelines to the cache, as we the pipeline
would take a ref, but when adding, we wouldn't clean up our own ref.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3897>
The drm subsystem has been moving over to gitlab for some time now and
the old anongit.freedesktop.org remote is becoming unusable. Contains
the same repo with the same tags, so this shouldn't result in any
differences.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3896>
Having an always-on-top window affects focus granting logic if the
to be showing window overlaps with any of them. Instead of triggering
the focus denying logic if a new window ever so slightly touches an
always-on-top window to only triggering if it's covered more than 60% by
always-on-top windows.
This is intended to make using always-on-top windows a bit less annoying
and not cause as many unintended focus-on-map denials.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3879>
When we show a window, we'll check if it overlaps with an existing
always-on-top window with the intention to deny focus. However, we did
this potentially before having placed the window, meaning we effectively
checked as if it was placed at (0, 0), which created unexpected results.
Instead check the overlap state after placing. A window placement test
case is added to verify this works as expected.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3879>
Replace a boolean argument and a temporary MetaWindow struct field with
a `MetaPlaceFlag` passed where relevant. This includes
`meta_window_move_resize_internal()` and `meta_window_constrain()`, as
placement may happen during constraining, and also
`meta_window_force_placement()`.
The struct field (denied_focus_and_not_transient) was only ever set in
meta_window_show(), before meta_window_force_placement(), and
immediately unset as a side effect of that. In .._show() we'll always
force placement if the window wasn't already placed, and in
meta_window_constrain(), we'd only ever call meta_window_place() if the
window wasn't already placed, meaning the variable would only ever be
relevant during `meta_window_show()`. Having it as a flag makes that
relationship and temporary state clearer.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3879>
The function checking whether a 'always-on-top' window covers the
showing window now has that in the name, to make it more obvious. That
function was also changed to use the more common way of iterating a
list, and now uses auto cleanup pointers for the list.
The condition itself was updated to follow the current coding style.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3879>
It won't be used until later when we flip, and in fact assigning
it early could have led to its own assertion failing on the next frame
in the unlikely event that we return with "Failed to ensure KMS FB ID...
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3891>
This avoids the following critical warning happening sometimes when a
Wayland client exits taking all its window with it in an arbitrary
order:
CRITICAL: meta_window_set_stack_position_no_sync: assertion 'window->stack_position >= 0' failed
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3870>
This, in contrast to 'assert_stacking' only checks showing windows. This
is useful when doing workspace tests, where one want to check what
windows are currently visible.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3870>
When a transient window becomes transient, check if the parent is
sticky, and if it is, make the transient sticky as well. This handles
situations where e.g. a utility dialog (such as search and replace) is
opened on a sticky window, also making the utility dialog sharing the
same stickyness state.
This is also more in line with the semantics of making a window sticky,
where transient would implicitly become sticky as a side effect.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3870>
If a transient window is sticky (visible on all workspaces) and it gets
activated, we'd call move_worskpace() which would effectively unstick
it, which is rather unexpected. It'd also effectively unstick its parent
as well, due to moving a transient window also moves its descendants and
ascendants.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3870>
Introduced in libinput 1.26 this feature allows restricting the
tablet tool pressure range to a subset of its physical range. The
use-case is either to require some higher-than-usual minimum pressure
before the pen reacts, or lower-than-usual pressure to reach the maximum
logical pressure.
libinput takes a [0.0, 1.0] normalized range which we expose as percent
in the gsettings. The wacom driver doesn't have an exact equivalent but
it has a Threshold setting (range [1, 2048]) that defines when a button
is generated for tip down.
See gsettings-desktop-schemas!84
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3794>
This mapper hooks into CLUTTER_BUTTON_PRESS/RELEASE events with a
clutter button of zero but a nonzero evcode (e.g. BTN_STYLUS).
It then looks up the available button actions and implements
switch-monitor and keybindings using the MetaTabletActionMapper parent
class.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3649>
Unlike most other schemas the path for a tool requires a bit of
processing (serial number or tablet vid/pid if there's no serial number).
Let's make the tool settings available through the MetaInputSettings
instead of having to duplicate that path composition in the caller.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3649>
Stylus actions that don't map into LMR or back/forward are now created
as a clutter button event with a button number of zero. Nothing is
actually done with those events for now, they're just discarded later.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3649>
For stylus buttons we apply a button mapping, e.g. secondary button ->
right. This mapping was previously applied to the clutter event's evdev
code only, not the actual clutter button. As a result, gnome-shell would
always treat the BTN_STYLUS as middle and BTN_STYLUS2 as right,
regardless of the mapping.
Move the mapping up so we first adjust our evcode, then proceed with
the usual mappings.
Note that this temporary breaks the stylus mapping to Back/Forward which
will be fixed in a follow-up commit.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3649>
Use the helper function for mapping a stylus tool evdev code to a
clutter button code. This fixes a (theoretical) issue - if a tool were
to send any button other than the one we handled those would likely be
BTN_SIDE and friends and we'd likely end up with negative button
numbers. The BTN_TOOL_PEN range is not predicable enough to do any sort
of calculation conversion because things like BTN_TOOL_DOUBLETAP have
specific meanings that aren't actually buttons.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3649>
This complements the existing clutter->evdev and evdev->clutter helpers,
but this time for buttons we expect from a stylus tool. We also need to
convert left/middle/right for the Wacom puck/lens cursor tools but that
particular conversion is lossy.
Note that these are more restrictive than the normal codes - if we
get "other" buttons from a stylus we don't really know what they could
possibly map to. So we safely map what looks like buttons from a mouse
but otherwise complain and return zero.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3649>
This is prep work for using the same functionality for tablet tools as
well. The new MetaTabletActionMapper takes care of the event bubbling
via the device-added/removed and input-event signals and provides the
helper functions to cycle outputs and/or emulate keybindings.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3649>
Instead of using cairo for scaling and rotating cursors before putting
them on a plane, use Cogl. For now still download them back to the CPU
so we can place them on a dumb buffer, but can explore rendering to a
DMA buffer directly as a future improvement.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3433>
This looks at the color state it got from the actor on construction, and
the target color state from the paint context and generates (and caches)
color aware pipelines used for painting. One of the purposes here is for
mixing SDR and HDR content and painting to a HDR monitor. If HDR (or
optical blending) isn't activated, the produced shaders will be
equivalent to what we had before.
Also add some names to the piplines, as this helps identifying what
pipeline source is associated with what pipeline.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3433>
In some of the places we need more context than just the CoglContext, so
prepare for that by passing around the paint context, which carries
this, everywhere instead. It won't be needed everywhere, but lets stay
consistent.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3433>
Color aware rendering needs shaders / pipelines that adapt to what
output they render to. For example if we want to render to a linear
BT.2020 intermediate framebuffer on one monitor, and a non-linear sRGB
direct target buffer on another, the shader for the same paint node or
content will depend on where they are going to be presented.
In order to help keeping track of what shader should target what
monitor, without having to regenerate them each time, introduce a
pipeline cache that knows how to handle differentiating between
transforming between different color state.
The cache is meant to handle caches for multiple pipeline users, where
each user might potentially want to keep track of multiple pipelines
itself. Lookup should be O(1), and in order to achieve this, separate
the cache into 3 levels.
The first level is the "pipeline group", where e.g. a ClutterContent
type allocates a group where it can store its pipelines. Each group has
a fixed number of "slots" where it can store a pipeline. Each slot has a
hash table where the key is derived from a color state transform, and
where the value is a CoglPipeline where the thame color state
transformation is expected to be handled.
A content will when painting know about its own color state, and the
target state it should render into, retrieve a cached pipeline for the
correct transform, or if the cache didn't have it, generate it.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3433>
Allow compositing in a linear color space and do so either when forcing
it via the debug controls D-Bus API, or when the experimental HDR mode
is enabled.
This relies on paint nodes etc to actually transform everything into the
linear target color space, which isn't done yet, so enabling it right
now will cause a broken result. Yet, introduce this now, so that
painting can be fixed piece by piece.
Linear blending is automatically enabled on monitors where HDR is
enabled, as this makes it possible to use an linear color space when
blending content from different color spaces with different transfer
functions.
Linear blending requires extra precision, i.e. 16 bit per channel
in the intermediate buffer due how the values are distributed,
so only enable the experimental HDR mode if the Cogl context supports
half float formats.
By default, no intermadiate linear offscreen framebuffer is used.
To test, do e.g.
./tools/debug-control.py --toggle ForceLinearBlending
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3433>
The initial target color state is the color state of the stage view
being painted to. If we're painting to an arbitrary framebuffer, it's
currently hard coded to sRGB/electrical.
The content color state is not set on construction, but when starting to
paint, it's set to the color state of the stage itself. Whenever an
actor is painted, it'll set the color state to the color state of
itself. The intention is that offscreen rendering pushes a target color
state that causes painting to it to not necessarily be in the stage view
color state.
Pass color state with offscreen framebuffer, as this avoids hard coding
sRGB in the lower level bits of paint contexts. It's still practically
hard coded, only that it's derived from somewhere else (e.g. the stage
or window actor).
Nothing is actually using this yet, but will eventually.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3433>