diff --git a/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/applet.js b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/applet.js new file mode 100644 index 0000000000..8bee06ab70 --- /dev/null +++ b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/applet.js @@ -0,0 +1,45 @@ +const Applet = imports.ui.applet; +const Lang = imports.lang; +const Main = imports.ui.main; +const Settings = imports.ui.settings; + +class CinnamonScaleAppApplet extends Applet.IconApplet { + constructor(metadata, orientation, panel_height, instance_id) { + super(orientation, panel_height, instance_id); + + try { + this.set_applet_icon_symbolic_name("cinnamon-scaleapp"); + this.set_applet_tooltip(_("Scale App")); + this._hover_activates = false; + + this.settings = new Settings.AppletSettings(this, metadata.uuid, this.instance_id); + + this.settings.bind("activate-on-hover", "_hover_activates"); + + this.actor.connect('enter-event', Lang.bind(this, this._onEntered)); + } + catch (e) { + global.logError(e); + } + } + + on_applet_clicked(event) { + if (this._hover_activates) + return; + this.doAction(); + } + + _onEntered(event) { + if (!this._hover_activates || global.settings.get_boolean("panel-edit-mode")) + return; + this.doAction(); + } + + doAction() { + Main.overview.toggle("scaleapp"); + } +} + +function main(metadata, orientation, panel_height, instance_id) { + return new CinnamonScaleAppApplet(metadata, orientation, panel_height, instance_id); +} diff --git a/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/icons/cinnamon-scaleapp-symbolic.svg b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/icons/cinnamon-scaleapp-symbolic.svg new file mode 100644 index 0000000000..94492a34fe --- /dev/null +++ b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/icons/cinnamon-scaleapp-symbolic.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/metadata.json b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/metadata.json new file mode 100644 index 0000000000..a7d494819f --- /dev/null +++ b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/metadata.json @@ -0,0 +1,7 @@ +{ +"uuid": "scaleapp@cinnamon.org", +"name": "Scale App", +"description": "Click or hover to activate Scale App view", +"icon": "cs-overview", + "max-instances": -1 +} diff --git a/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/settings-schema.json b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/settings-schema.json new file mode 100644 index 0000000000..0207ff1a77 --- /dev/null +++ b/files/usr/share/cinnamon/applets/scaleapp@cinnamon.org/settings-schema.json @@ -0,0 +1,8 @@ +{ + "activate-on-hover": { + "type": "switch", + "default" : false, + "description" : "Activate scale on hover" + } +} + diff --git a/files/usr/share/cinnamon/cinnamon-settings/modules/cs_hotcorner.py b/files/usr/share/cinnamon/cinnamon-settings/modules/cs_hotcorner.py index 4cd46cbf7a..5acb3f13c0 100755 --- a/files/usr/share/cinnamon/cinnamon-settings/modules/cs_hotcorner.py +++ b/files/usr/share/cinnamon/cinnamon-settings/modules/cs_hotcorner.py @@ -195,6 +195,7 @@ def __init__(self, index, updateCallback): self.functionStore.append(['expo', _("Show all workspaces")]) #Expo self.functionStore.append(['scale', _("Show all windows")]) #Scale self.functionStore.append(['desktop', _("Show the desktop")]) + self.functionStore.append(['scaleapp', _("Show application windows")]) # like Mac 'Application Windows' self.functionStore.append(['custom', _("Run a command")]) enableBox = Gtk.Box(spacing=8) @@ -241,9 +242,11 @@ def setValues(self, function, enabled, delay): self.functionCombo.set_active(1) elif function == "desktop": self.functionCombo.set_active(2) + elif function == "scaleapp": + self.functionCombo.set_active(3) else: showCommandEntry = True - self.functionCombo.set_active(3) + self.functionCombo.set_active(4) if self.commandEntry.get_text() != function: self.commandEntry.set_text(function) diff --git a/js/ui/hotCorner.js b/js/ui/hotCorner.js index 918faf23c2..97ae613f96 100755 --- a/js/ui/hotCorner.js +++ b/js/ui/hotCorner.js @@ -161,11 +161,14 @@ class HotCorner extends Clutter.Actor { Main.expo.toggle(); break; case 'scale': - Main.overview.toggle(); + Main.overview.toggle(this.action); break; case 'desktop': global.workspace_manager.toggle_desktop(timestamp); break; + case 'scaleapp': + Main.overview.toggle(this.action); + break; default: Util.spawnCommandLine(this.action); } @@ -222,7 +225,7 @@ class HotCorner extends Clutter.Actor { shouldRunAction(timestamp, click) { /* Expo and scale disable hot corners except theirs */ if ((Main.expo.visible && this.action != 'expo') || - (Main.overview.visible && this.action != 'scale')) + (Main.overview.visible && ((this.action != 'scale') && (this.action != 'scaleapp')))) return false; if (Main.overview.animationInProgress) diff --git a/js/ui/overview.js b/js/ui/overview.js index 76bb0aaeb7..06e98cef7f 100644 --- a/js/ui/overview.js +++ b/js/ui/overview.js @@ -63,6 +63,7 @@ var Overview = GObject.registerClass({ this._windowSwitchTimestamp = 0; this._lastActiveWorkspaceIndex = -1; this._lastHoveredWindow = null; + this._optCallerActionName = null; Main.layoutManager.connect('monitors-changed', this.hide.bind(this)); } @@ -305,7 +306,8 @@ var Overview = GObject.registerClass({ } } - toggle() { + toggle(optCallerActionName) { + Main.overview._optCallerActionName = optCallerActionName; if (this._shown) this.hide(); else diff --git a/js/ui/workspace.js b/js/ui/workspace.js index ea56cc6414..2d74b29f4e 100644 --- a/js/ui/workspace.js +++ b/js/ui/workspace.js @@ -684,7 +684,35 @@ class WorkspaceMonitor extends Clutter.Actor { let initialPositioning = flags & WindowPositionFlags.INITIAL; let animate = flags & WindowPositionFlags.ANIMATE; - let clones = this._windows; + let focusedWindow = global.display.get_focus_window(); + let tracker = Cinnamon.WindowTracker.get_default(); + let focusedApp = tracker.get_window_app(focusedWindow); + let focusedAppName = focusedApp.get_name(); + + let clones; + let callerActionName = Main.overview._optCallerActionName; + if (callerActionName === 'scaleapp') { + let clones2 = this._windows; + clones = []; + for (let i = 0; i < clones2.length; ++i) { + let clone = clones2[i]; + let app = tracker.get_window_app(clone.metaWindow); + let appName = app.get_name(); + if (appName === focusedAppName) { // this window belongs to the current active app + clones.push(clone); + } else { // this window does not belong to the current active app + // hide other windows otherwise they continue to show and may obscure the selection view. + clone.opacity = 0; + clone.scale_x = 0; + clone.scale_y = 0; + // captions for these other windows also need to be hidden + clone.overlay.caption.hide(); + } + } + } else { // original 'scale' case + clones = this._windows; + } + // Start the animations let slots = this._computeAllWindowSlots(clones.length);