We track changes to windows fullscreen state and stacking order
to determine a monitor's in-fullscreen state, but missed the
obvious case of moving a fullscreen window between monitors.
https://bugzilla.gnome.org/show_bug.cgi?id=728395
Commit 585fdd781c not only removed the tabpopup, but set invalid
handlers (a.k.a. NULL) for those shortcuts; add back handling of
basic handling of those shortcuts by switching instantly without any
popups.
https://bugzilla.gnome.org/show_bug.cgi?id=728423
dx/dy should be against the regular window's rect, and need to
be ignored when we're resizing. Instead, we use gravity to anchor
the window's new rectangle when resizing.
Doing this synchronously means that zenity tries to initialize GTK+.
Under Wayland, that will try to connect back to mutter as a display
server. We're waiting on zenity to exit, and zenity is waiting for
a connection response. Deadlock.
Simply assume that zenity will support all the options we feed it,
since it should be the correct version. Perhaps we should replace
our use of zenity with a simple helper binary that we know will
have all the right options if this still isn't good enough.
Our focus stealing prevention is still mostly inherited from metacity;
in particular, a (non-transient) window that is not on the current
workspace will not be given focus. This behavior made sense in the
GNOME 2 days, where workspaces were separated much more strictly.
However this is no longer the case in GNOME 3 - activating a launcher
will switch workspaces if necessary, and so will the app switcher.
There is no good reason to not do the same for other user actions
like clicking a URL or activating a search result, so allow activation
of windows on non-active workspaces if a proper timestamp is supplied,
assuming that this is a strong enough indication that we are dealing
with a legitimate user action.
https://bugzilla.gnome.org/show_bug.cgi?id=728018
Effectively we have been accepting CurrentTime timestamps for years,
but still complained about "stupid pagers" when encountering them;
just accept that we will never limit treating 0 timestamps as current
time to pagers.
https://bugzilla.gnome.org/show_bug.cgi?id=728018
The code that restacks X11 windows at the end first tracks any
old windows we know about, and then handles any windows created.
It starts when it ended, and then walks forwards and then
back looking for the first X11 window it doesn't know about.
However, when there aren't any X11 windows, it flies off the end
of the array and starts looking through random memory.
When it finds the X11 window, it then goes through and then tries
to restack the remaining windows according to how we've sorted
them.
Unfortunately, META_WINDOW_CLIENT_TYPE_X11 is 0, which is quite
common in random memory we have lying around, so we enter that
path and then just crash.
Fix the buffer overrun by adding the proper bounds check to the
search.
You can easily reproduce this by opening a menu while bloatpad
is full-screen. Why it only crashes when full-screen and not
when a standard window, I have no idea.
The idea here is that while we take a WM-side grab, like a compositor
grab or a resizing grab, we need to remove the focus from the Wayland
client.
We make a special exception for CLICKING operations, because these
are really an internal state machine while you're pressing on a button
inside a frame, and in this case, we need to not kill the focus.
Except while reading _NET_WM_WINDOW_OPACITY, opacity is between 0 and 255. With
guint8, we'll get compiler warnings if arbitrary int values are passed.
https://bugzilla.gnome.org/show_bug.cgi?id=727874
A careful analysis of mutter's codebase shows that nothing actually
passes anything but 0 to this. gnome-shell has one instance, but it's
most likely a mistake.
Remove the grab_mask field and the one place in keybindings.c that uses it.
The parameter to begin_grab_op is left in for API compatibility reasons.
The make_toplevel / window_unmanaging interface has never made
a lot of sense to me. Replace it with set_window, which does
effectively the same thing.
It's still not perfect in the case of XWayland, but I don't think
XWayland will ever make me happy.
Right now this just has all of the files in one directory. We'll
be introducing more structure to this in the future, and build
a proper backend system.
This will allow us to have a MetaCursorReference 'subclass' that's
lazily loaded. We currently always load all the images.
The long-term plan is to have a subclass for each "backend" and only
have CoglTexture as a common denominator. For the nested X11 backend,
we use XDefineCursor on our stage window. For the Wayland backend, we
would use set_cursor on our stage surface. For the native backend, we
would use the GBM code that's there right now.
The CoglTexture is there to be a "shared fallback" between all devices,
and also for the get_sprite API.
The odd man out is the X11 compositor case. For that, we need to move
the responsibility of setting the final cursor image out of
MetaCursorTracker, and simply have it be about tracking the used sprite
image and pointer position.
We want to make this private, and have MetaCursorReference be
backend-defined, with the texture possibly loaded on demand.
We can't make the definition of MetaCursorReference truly private yet
because of the XFixes cursor. A victim of MetaCursorTracker trying to
do too many things at once...
I want the MetaCursorTracker to mostly be about retrieving cursor
information. Start moving the code that loads cursor images to a
new file, MetaCursor. Eventually, MetaCursorTracker's APIs will
all take MetaCursorReferences, and we can have a clean backend
split here.
For whatever reason, this hash table was in the generic
implementation section instead of the XSync implementation,
even though it's only used by the XSync implementation.
Use it as a first pass of things to move over.
The reason we don't simply use gdk_window_add_filter directly is
because of some twisted idea that any GDK symbol being used from
core/ is a layer violation. While we certainly want to keep any
serious GDK code out of ui/, event handling is quite important
to have in core/, so simply use a GDK event filter directly.
Really, visible_to_compositor means that the window is shown, e.g.
not minimized. We need to be using a boolean tracking whether we've
called meta_compositor_add_window / meta_compositor_remove_window.
This fixes a jump during window placement when a window appears.
visible_to_compositor should always be in sync with show_window /
hide_window calls, even when unmananging.
This fixes a crash where we call sync_window_state when the window
is unmanaging, since we use visible_to_compositor to determine whether
the compositor will crash.
This is actually wrong; we should be using the knowledge about
whether we have called add_window / remove_window. We'll introduce
this with a new boolean next time.
Compositors haven't been able to manage more than one screen for
quite a while. Merge MetaCompScreen into MetaCompositor, and update
the API to match.
We still keep MetaScreen in the public compositor API for compatibility
purposes.
We previously separated out MetaDisplay and MetaScreen. mutter
would only manage one screen, but we still kept a list of screens
for simplicity.
With Wayland support, we no longer care about the ability to
manage more than one screen at a time. Remove this by killing
the list of screens, in favor of having just one MetaScreen
in MetaDisplay.
We also kill off active_screen at the same time, since it's
not necessary anymore.
A future cleanup should merge MetaDisplay and MetaScreen. To avoid
breaking API, we should probably keep MetaScreen around as a dummy
type.
When I refactored this out into a vfunc, I forgot to change the
code that interprets the result flags to actually respect the
new FRAME_SHAPE_CHANGED result flag.
Since we weren't ever clearing the frame bounds, this meant that
the "shadow clip" wasn't ever updated as a result. Since right now
all Wayland surfaces are considered ARGB32, we always clip shadows
under frames, and thus shadows had this weird "punch-out" from the
first frame shape.
While the ICCCM mandates the use of this, it's not necessary under
a composited environment from my understanding, and it's a flat
out no-op under XWayland.
Looking at the other rootless servers like Xwin/Xquartz, it seems
that they contain code for colormap emulation, but they're actually
never used -- a bug prevents the code from ever being called. Given
that it's been this way since 2003, I'm going to hazard a guess that
not many apps using colormaps. Kill them off.
display.c is getting a bit crowded. Move most of the handling
out to another file, events.c.
The long-term goal is to have generic event handling here, with
backend-specific handling for the types of windows and such.
If we have a CLICKING grab op we still need to send events to xwayland
so that we get them back for gtk+ to process thus we can't steer
wayland input focus away from it.
https://bugzilla.gnome.org/show_bug.cgi?id=726123
This ensures that we send the proper leave and enter events to wayland
clients.
Particularly, this solves a bug in SSD xwayland windows where clicking
and dragging on the title bar to move the window only works on the odd
turn (unless the pointer moves away from the title bar between
tries). This happens because xwayland gets a button press but doesn't
see the release so when it gets the next button press it discards it
because its pointer button tracking logic says that the button is
already pressed. Sending the proper wayland pointer leave event fixes
it since wayland clients must forget about button state at that point.
https://bugzilla.gnome.org/show_bug.cgi?id=726123
At one point, it was supported to run mutter without a compositor,
but we don't allow that any longer. A lot of code already assumes
display->compositor exists and doesn't check for a NULL pointer,
so just kill the rest of the checks.
This is specifically about managing X11 windows, not necessarily
running as an X11 compositor. By that I mean that this code is
still used for XWayland windows, and event handling is still and
modesetting / monitor management is still in core/.
This is also a fairly conservative move. We don't move anything
like screen.c or bell.c in here, even though those are really
only for X11 clients.
This is fairly simple and basic for now, with just skip_taskbar /
skip_pager, but eventually a lot of "WM policy" like this, including
move-resize, will be in subclasses for each individual surface.
We try to exempt CSD windows from being forced fullscreen if they are
undecorated and the size of the screen; however, we also catch almost
all windows that *do* need to be forced fullscreen in this check, since
they also have decorations turned off.
Identify actual CSD windows by checking whether _GTK_FRAME_EXTENTS is set -
GTK+ will always set this on CSD windows even if they have no invisible
borders or shadows at the current time.
We explicitly turn off the legacy-fullscreen check for native wayland windows
so we don't start legacy-fullscreening them if the new
meta_window_is_client_decorated() is later made more accurate.
https://bugzilla.gnome.org/show_bug.cgi?id=723029
The user_rect represents the unconstrainted window size, and lots
of code in mutter assumes it can resize to the user_rect at any
time. If we wait for an attach to ACK and save the user rect, we'll
see lots of flickering as code is resizing to the old user_rect
at any time.
Make it a compile-time flag rather than a run-time flag, because
practically any time you're going to be debugging event spewing,
you're going to have to recompile anyway. Remove the WITH_VERBOSE_MODE
checks, too.
Which is used for Wayland popup grabs.
The issue here is that we don't want the code that raises or focuses
windows based on mouse ops to run while a client has a grab.
We still keep the "old" grab infrastructure in place for now, but
ideally we'd replace it eventually with a better grab-op infrastructure.
Clutter's input device initial position defaults to (-1, -1) on most
backends but for the evdev backend we changed it to be inside the
stage to prevent the pointer from wandering outside the stage until it
first enters, after which our constraining callback won't let it go
out.
This makes us be in sync with the real position from the start.
_SVID_SOURCE has been deprecated in newer versions of glibc breaking
-WError; the recommended replacement of _DEFAULT_SOURCE is fairly
new, so switch to _XOPEN_SOURCE instead.
The "original coordinates" passed into meta_window_place() were the
coordinates of the client rectangle not the frame rectangle. When
meta_window_place() didn't place because the window was manually
positioned (e.g., 'xterm -geometry +x+y') that resulted in a window
being offset by the frame dimensions.
https://bugzilla.gnome.org/show_bug.cgi?id=724049
We need to resolve the keycode from the keysym again since the keycode
might have changed if there was a keymap switch between the grab and
the ungrab.
Before starting to use display_get_keybinding() we could compare
MetaKeyBinding.modifiers with MetaKeyCombo.modifiers directly. Now, we
need to resolve the virtual modifiers to match with the mask.
This allows us to look for a match with an O(1) search instead of O(n)
which is nice, particularly when running as a wayland compositor in
which case we have to do this search for every key press event (as
opposed to only when our passive grab triggers in the X compositor
case).
We actually need two hash tables. On one we keep all the keybindings
themselves which allows us to add external grabs without constantly
re-allocating the array we were using previously.
The other hash table is an index of the keybindings in the first table
by their keycodes and mask which is how we actually match the key
press events. This second table thus needs to be rebuilt when the
keymap changes since keycodes have to be resolved then but since we're
only keeping pointers to the first table it's a fast operation.
https://bugzilla.gnome.org/show_bug.cgi?id=725588
Instead of looping over an array of keybindings to find the correct
binding, just use display_get_keybinding().
In the next commit, we'll change the array to be a hash map, so this
helps the patch be cleaner.
https://bugzilla.gnome.org/show_bug.cgi?id=725588
We don't want to match the keysym so that e.g. an accelerator
specified as "<Super>a" works if the current keymap has a keysym other
than 'a' for that keycode which means that the accelerator would
become inaccessible in a non-latin keymap.
This is inconvenient for users that often switch keyboard layouts, or
even have different layouts in different windows, since they expect
system-level keybindings to not be affected by the current layout.
https://bugzilla.gnome.org/show_bug.cgi?id=678001
The only events we handle as XIEvents are FocusIn/Out, Enter and
Leave. Motion, ButtonPress/Release, KeyPress/Release are handled
through clutter instead.
Among other things, this means we don't need to fake motion compression
by peeking over gdk event queue...
Mouse event handling was duplicated, resulting in weird interactions
if clutter was allowed to see certain events (for example under
wayland, where it gets all events). Because now clutter sees all
X events, even when running as an x11 compositor, we can handle
everything using the clutter variants.
At the same time, rewrite a little the passive button grab code,
to make it clear what is being matched on what and why.
We must spoof events to clutter even if they are associated
with a MetaWindow, because keyboard events are always associated
with one (the focus window), and we must process keybindings
for window togheter with the global ones if they include Super,
because we're not going to see them again.
... and individually. It turns out that updating the opaque region
was causing the shape region to be updated, which was causing a new
shape mask to be generated and uploaded to the GPU. Considering
GTK+ regenerates the opaque region on pretty much any focus change,
this is not good.
The handler pointer is dangling in MetaKeyBinding until
rebuild_key_binding_table() is run, so we can't dereference it.
Because we only need the flags at ungrab time, store a copy
in the MetaKeyBinding structure.
https://bugzilla.gnome.org/show_bug.cgi?id=724402
For decorated windows, we don't want to apply any input
shape, because the frame is always rectangular and eats
all the input.
The real check is in meta-window-actor, where we consider
if we need to apply the bounding shape and the input shape
(or the intersection of the two) to the surface-actor,
but as an optimization we avoid querying the server in
meta-window.
Additionally, for undecorated windows, the "has input shape"
check is wrong if the window has a bounding shape but not an
input shape.
It triggers too often, making G_DEBUG=fatal-warnings quite useless.
Owen is going to rewrite this code sometime in the near future, so
I'm just gonna kill this warning for now.
If the last reference of a MetaIdleMonitor is held by the caller, it may
happen that the last reference is lost when calling the GDestroyNotify,
if this happens when the watched DBus name vanishes, the object (and the
watches hashtable) are destroyed while manipulating the watches hashtable,
so bad things may happen then.
Fix this by wrapping the operation by a ref/unref pair, so the object would
be destroyed after operating on the hashtable.
https://bugzilla.gnome.org/show_bug.cgi?id=724969
The rendering logic before was somewhat complex. We had three independent
cases to take into account when doing rendering:
* X11 compositor. In this case, we're a traditional X11 compositor,
not a Wayland compositor. We use XCompositeNameWindowPixmap to get
the backing pixmap for the window, and deal with the COMPOSITE
extension messiness.
In this case, meta_is_wayland_compositor() is FALSE.
* Wayland clients. In this case, we're a Wayland compositor managing
Wayland surfaces. The rendering for this is fairly straightforward,
as Cogl handles most of the complexity with EGL and SHM buffers...
Wayland clients give us the input and opaque regions through
wl_surface.
In this case, meta_is_wayland_compositor() is TRUE and
priv->window->client_type == META_WINDOW_CLIENT_TYPE_WAYLAND.
* XWayland clients. In this case, we're a Wayland compositor, like
above, and XWayland hands us Wayland surfaces. XWayland handles
the COMPOSITE extension messiness for us, and hands us a buffer
like any other Wayland client. We have to fetch the input and
opaque regions from the X11 window ourselves.
In this case, meta_is_wayland_compositor() is TRUE and
priv->window->client_type == META_WINDOW_CLIENT_TYPE_X11.
We now split the rendering logic into two subclasses, which are:
* MetaSurfaceActorX11, which handles the X11 compositor case, in that
it uses XCompositeNameWindowPixmap to get the backing pixmap, and
deal with all the COMPOSITE extension messiness.
* MetaSurfaceActorWayland, which handles the Wayland compositor case
for both native Wayland clients and XWayland clients. XWayland handles
COMPOSITE for us, and handles pushing a surface over through the
xf86-video-wayland DDX.
Frame sync is still in MetaWindowActor, as it needs to work for both the
X11 compositor and XWayland client cases. When Wayland's video display
protocol lands, this will need to be significantly overhauled, as it would
have to work for any wl_surface, including subsurfaces, so we would need
surface-level discretion.
https://bugzilla.gnome.org/show_bug.cgi?id=720631
The input region was set on the shaped texture, but the shaped texture
was never picked properly, as it was never set to be reactive. Move the
pick implementation and reactivity to the MetaSurfaceActor, and update
the code everywhere else to expect a MetaSurfaceActor.
I implemented pinging, but never actually enabled the feature
properly on Wayland surfaces by setting the net_wm_ping hint to
TRUE, causing the fallback path to always be hit.
Rename net_wm_ping to can_ping so it doesn't take on an
implementation-specific meaning, and set it for all Wayland windows.
To prevent the MetaSurfaceActor from being destroyed, we normally
unparent it before we unmanage the window. However, this doesn't
work for XWayland windows, which we unmanage when we get UnmapNotify
or DestroyNotify, not when we get the wl_surface_destroy.
To solve this, add an early hook in meta_window_unmanage that
unparents the surface actor if we have one. At the same time, clean
up the destruction code to remove old comments and assumptions about
how wl_shell behaves.
This was a bad idea, as ping/pong has moved to a client-specific
request/event pair, rather than a surface-specific one. Revert
the changes we made here and correct the code to make up for it.
This reverts commit aa3643cdde.
If we fail to find the IDLETIME counter, then the alarm variable will be
uninitialised. Most code paths are careful to check this before
submitting XSync calls, but there is one check missing.
https://bugzilla.gnome.org/show_bug.cgi?id=724364
In order for the compositor to properly determine whether a client
is an X11 client or not, we need to wait until XWayland calls
set_window_id to mark the surface as an XWayland client. To prevent
the compositor from getting tripped up over this, make sure that
the window has been fully initialized by the time we call
meta_compositor_add_window.
https://bugzilla.gnome.org/show_bug.cgi?id=720631
Traditionally, WMs unmap windows when minimizing them, and map them
when restoring them or wanting to show them for other reasons, like
upon creation.
However, as metacity morphed into mutter, we optionally chose to keep
windows mapped for the lifetime of the window under the user option
"live-window-previews", which makes the code keep windows mapped so it
can show window preview for minimized windows in other places, like
Alt-Tab and Expose.
I removed this preference two years ago mechanically, by removing all
the if statements, but never went through and cleaned up the code so
that windows are simply mapped for the lifetime of the window -- the
"architecture" of the old code that maps and unmaps on show/hide was
still there.
Remove this now.
The one case we still need to be careful of is shaded windows, in which
we do still unmap the client window. In the future, we might want to
show previews of shaded windows in the overview and Alt-Tab. In that
we'd also keep shaded windows mapped, and could remove all unmap logic,
but we'd need a more complex method of showing the shaded titlebar, such
as using a different actor.
At the same time, simplify the compositor interface by removing
meta_compositor_window_[un]mapped API, and instead adding/removing the
window on-demand.
https://bugzilla.gnome.org/show_bug.cgi?id=720631
Prior to the DisplayConfig merge, we would set _NET_WM_FULLSCREEN_MONITORS
to (unsigned)-1 when unset. After that, we would have invalid
reads inside meta_screen_monitor_index_to_xinerama_index() (called
with -1).
The way I read the specification, the proper way to indicate
that the window is back to fullscreen on all monitors is to
remove the property, so do that.
Also, add an assertion that meta_screne_monitor_index_to_xinerama_index()
is doing the right thing.
https://bugzilla.gnome.org/show_bug.cgi?id=724258