windowManager: Handle window dimming animation getting cancelled

When a window with a modal dialog gets minimized and at the same time
the dialog is closed, the WindowDimmer undim animation starts and gets
cancelled when the minimize animation is done, because that unmaps the
window actor.

In this case we want ensure the dimming effect still goes into a
proper state instead of being stuck mid-animation, so listen to
onStopped instead of onComplete for syncing state of the window dimmer.

While at it, clean things up a little and move the check for the
attach-modal-dialogs pref inside the _syncEnabled() function.

Fixes https://gitlab.gnome.org/GNOME/gnome-shell/-/issues/5581

Part-of: <https://gitlab.gnome.org/GNOME/gnome-shell/-/merge_requests/2349>
This commit is contained in:
Jonas Dreßler 2022-06-30 09:40:51 +02:00 committed by Marge Bot
parent 31acf30bfa
commit 4fd2719dc5

View File

@ -132,18 +132,12 @@ class WindowDimmer extends Clutter.BrightnessContrastEffect {
name: WINDOW_DIMMER_EFFECT_NAME, name: WINDOW_DIMMER_EFFECT_NAME,
enabled: false, enabled: false,
}); });
this._enabled = true;
} }
_syncEnabled() { _syncEnabled(dimmed) {
let animating = this.actor.get_transition(`@effects.${this.name}.brightness`) !== null; let animating = this.actor.get_transition(`@effects.${this.name}.brightness`) !== null;
let dimmed = this.brightness.red != 127;
this.enabled = this._enabled && (animating || dimmed);
}
setEnabled(enabled) { this.enabled = Meta.prefs_get_attach_modal_dialogs() && (animating || dimmed);
this._enabled = enabled;
this._syncEnabled();
} }
setDimmed(dimmed, animate) { setDimmed(dimmed, animate) {
@ -153,20 +147,17 @@ class WindowDimmer extends Clutter.BrightnessContrastEffect {
this.actor.ease_property(`@effects.${this.name}.brightness`, color, { this.actor.ease_property(`@effects.${this.name}.brightness`, color, {
mode: Clutter.AnimationMode.LINEAR, mode: Clutter.AnimationMode.LINEAR,
duration: (dimmed ? DIM_TIME : UNDIM_TIME) * (animate ? 1 : 0), duration: (dimmed ? DIM_TIME : UNDIM_TIME) * (animate ? 1 : 0),
onComplete: () => this._syncEnabled(), onStopped: () => this._syncEnabled(dimmed),
}); });
this._syncEnabled(); this._syncEnabled(dimmed);
} }
}); });
function getWindowDimmer(actor) { function getWindowDimmer(actor) {
let enabled = Meta.prefs_get_attach_modal_dialogs();
let effect = actor.get_effect(WINDOW_DIMMER_EFFECT_NAME); let effect = actor.get_effect(WINDOW_DIMMER_EFFECT_NAME);
if (effect) { if (!effect) {
effect.setEnabled(enabled);
} else if (enabled) {
effect = new WindowDimmer(); effect = new WindowDimmer();
actor.add_effect(effect); actor.add_effect(effect);
} }