[gnome-shell/overview-relayout: 14/22] workspaces-view: Remove MosaicView
- From: Florian Müllner <fmuellner src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-shell/overview-relayout: 14/22] workspaces-view: Remove MosaicView
- Date: Fri, 19 Nov 2010 04:25:34 +0000 (UTC)
commit 13f8cd3bcf66cb7f0420b6f0e80fe03d26b7f3de
Author: Florian Müllner <fmuellner gnome org>
Date: Fri Nov 12 10:28:28 2010 +0100
workspaces-view: Remove MosaicView
The new layout does no longer support view switching, so merge
GenericWorkspacesView and SingleView, and remove MosaicView.
Also rename or remove workspace properties and functions which
are now unused.
The grid will have a comeback with the new DND behavior.
https://bugzilla.gnome.org/show_bug.cgi?id=634948
data/org.gnome.shell.gschema.xml.in | 12 -
js/ui/workspace.js | 123 +------
js/ui/workspacesView.js | 761 +++++++++--------------------------
3 files changed, 206 insertions(+), 690 deletions(-)
---
diff --git a/data/org.gnome.shell.gschema.xml.in b/data/org.gnome.shell.gschema.xml.in
index 085db60..031930a 100644
--- a/data/org.gnome.shell.gschema.xml.in
+++ b/data/org.gnome.shell.gschema.xml.in
@@ -41,18 +41,6 @@
<default>[]</default>
<_summary>History for command (Alt-F2) dialog</_summary>
</key>
- <key name="workspaces-view" type="s">
- <default>'single'</default>
- <_summary>Overview workspace view mode</_summary>
- <_description>
- The selected workspace view mode in the overview.
- Supported values are "single" and "grid".
- </_description>
- <choices>
- <choice value="single"/>
- <choice value="grid"/>
- </choices>
- </key>
<child name="clock" schema="org.gnome.shell.clock"/>
<child name="calendar" schema="org.gnome.shell.calendar"/>
<child name="recorder" schema="org.gnome.shell.recorder"/>
diff --git a/js/ui/workspace.js b/js/ui/workspace.js
index 2002175..b496ec6 100644
--- a/js/ui/workspace.js
+++ b/js/ui/workspace.js
@@ -20,9 +20,6 @@ const FOCUS_ANIMATION_TIME = 0.15;
const WINDOW_DND_SIZE = 256;
-const FRAME_COLOR = new Clutter.Color();
-FRAME_COLOR.from_pixel(0xffffffff);
-
const SCROLL_SCALE_AMOUNT = 100 / 5;
const LIGHTBOX_FADE_TIME = 0.1;
@@ -54,11 +51,6 @@ function _clamp(value, min, max) {
return Math.max(min, Math.min(max, value));
}
-// Spacing between workspaces. At the moment, the same spacing is used
-// in both zoomed-in and zoomed-out views; this is slightly
-// metaphor-breaking, but the alternatives are also weird.
-const GRID_SPACING = 15;
-const FRAME_SIZE = GRID_SPACING / 3;
function ScaledPoint(x, y, scaleX, scaleY) {
[this.x, this.y, this.scaleX, this.scaleY] = arguments;
@@ -568,8 +560,6 @@ Workspace.prototype = {
this._visible = false;
- this._frame = null;
-
this.leavingOverview = false;
},
@@ -631,9 +621,6 @@ Workspace.prototype = {
this._lightbox.show();
else
this._lightbox.hide();
-
- if (this._frame)
- this._frame.set_opacity(showLightbox ? 150 : 255);
},
/**
@@ -654,32 +641,6 @@ Workspace.prototype = {
this._lightbox.highlight(actor);
},
- // Mark the workspace selected/not-selected
- setSelected : function(selected) {
- // Don't draw a frame if we only have one workspace
- if (selected && global.screen.n_workspaces > 1) {
- if (this._frame)
- return;
-
- // FIXME: do something cooler-looking using clutter-cairo
- this._frame = new Clutter.Rectangle({ color: FRAME_COLOR });
- this.actor.add_actor(this._frame);
- this._frame.set_position(- FRAME_SIZE / this.actor.scale_x,
- - FRAME_SIZE / this.actor.scale_y);
- this._frame.set_size(this.actor.width + 2 * FRAME_SIZE / this.actor.scale_x,
- this.actor.height + 2 * FRAME_SIZE / this.actor.scale_y);
- this._frame.lower_bottom();
-
- this._framePosHandler = this.actor.connect('notify::scale-x', Lang.bind(this, this._updateFramePosition));
- } else {
- if (!this._frame)
- return;
- this.actor.disconnect(this._framePosHandler);
- this._frame.destroy();
- this._frame = null;
- }
- },
-
/**
* setReactive:
* @reactive: %true iff the workspace should be reactive
@@ -690,13 +651,6 @@ Workspace.prototype = {
this.actor.reactive = reactive;
},
- _updateFramePosition : function() {
- this._frame.set_position(- FRAME_SIZE / this.actor.scale_x,
- - FRAME_SIZE / this.actor.scale_y);
- this._frame.set_size(this.actor.width + 2 * FRAME_SIZE / this.actor.scale_x,
- this.actor.height + 2 * FRAME_SIZE / this.actor.scale_y);
- },
-
_isCloneVisible: function(clone) {
return this._showOnlyWindows == null || (clone.metaWindow in this._showOnlyWindows);
},
@@ -1074,8 +1028,8 @@ Workspace.prototype = {
// be after the workspace animation finishes.
let [cloneX, cloneY] = clone.actor.get_position();
let [cloneWidth, cloneHeight] = clone.actor.get_size();
- cloneX = this.gridX + this.scale * cloneX;
- cloneY = this.gridY + this.scale * cloneY;
+ cloneX = this.x + this.scale * cloneX;
+ cloneY = this.y + this.scale * cloneY;
cloneWidth = this.scale * clone.actor.scale_x * cloneWidth;
cloneHeight = this.scale * clone.actor.scale_y * cloneHeight;
@@ -1114,8 +1068,8 @@ Workspace.prototype = {
let wsHeight = this.actor.height * this.scale;
let pointerHasMoved = (this._cursorX != x && this._cursorY != y);
- let inWorkspace = (this.gridX < x && x < this.gridX + wsWidth &&
- this.gridY < y && y < this.gridY + wsHeight);
+ let inWorkspace = (this.x < x && x < this.x + wsWidth &&
+ this.y < y && y < this.y + wsHeight);
if (pointerHasMoved && inWorkspace) {
// store current cursor position
@@ -1239,7 +1193,7 @@ Workspace.prototype = {
// Animate the full-screen to Overview transition.
zoomToOverview : function() {
- this.actor.set_position(this.gridX, this.gridY);
+ this.actor.set_position(this.x, this.y);
this.actor.set_scale(this.scale, this.scale);
// Position and scale the windows.
@@ -1297,69 +1251,6 @@ Workspace.prototype = {
this._visible = false;
},
- // Animates grid shrinking/expanding when a row or column
- // of workspaces is added or removed
- resizeToGrid : function (oldScale) {
- this._hideAllOverlays();
- Tweener.addTween(this.actor,
- { x: this.gridX,
- y: this.gridY,
- scale_x: this.scale,
- scale_y: this.scale,
- time: Overview.ANIMATION_TIME,
- transition: 'easeOutQuad',
- onComplete: Lang.bind(this, this._fadeInAllOverlays)
- });
- },
-
- // Animates the addition of a new (empty) workspace
- slideIn : function(oldScale) {
- if (this.gridCol > this.gridRow) {
- this.actor.set_position(global.screen_width, this.gridY);
- this.actor.set_scale(oldScale, oldScale);
- } else {
- this.actor.set_position(this.gridX, global.screen_height);
- this.actor.set_scale(this.scale, this.scale);
- }
- Tweener.addTween(this.actor,
- { x: this.gridX,
- y: this.gridY,
- scale_x: this.scale,
- scale_y: this.scale,
- time: Overview.ANIMATION_TIME,
- transition: 'easeOutQuad'
- });
-
- this._visible = true;
- },
-
- // Animates the removal of a workspace
- slideOut : function(onComplete) {
- let destX = this.actor.x, destY = this.actor.y;
-
- this._hideAllOverlays();
-
- if (this.gridCol > this.gridRow)
- destX = global.screen_width;
- else
- destY = global.screen_height;
- Tweener.addTween(this.actor,
- { x: destX,
- y: destY,
- scale_x: this.scale,
- scale_y: this.scale,
- time: Overview.ANIMATION_TIME,
- transition: 'easeOutQuad',
- onComplete: onComplete
- });
-
- this._visible = false;
-
- // Don't let the user try to select this workspace as it's
- // making its exit.
- this.actor.reactive = false;
- },
-
destroy : function() {
this.actor.destroy();
},
@@ -1549,11 +1440,11 @@ function _workspaceRelativeModifier(workspace) {
}
return [ { name: 'x',
- parameters: { workspacePos: workspace.gridX,
+ parameters: { workspacePos: workspace.x,
overviewPos: overviewPosX,
overviewScale: overviewScale } },
{ name: 'y',
- parameters: { workspacePos: workspace.gridY,
+ parameters: { workspacePos: workspace.y,
overviewPos: overviewPosY,
overviewScale: overviewScale } }
];
diff --git a/js/ui/workspacesView.js b/js/ui/workspacesView.js
index 82d4868..7f7f83b 100644
--- a/js/ui/workspacesView.js
+++ b/js/ui/workspacesView.js
@@ -19,24 +19,147 @@ const WORKSPACE_SWITCH_TIME = 0.25;
// Note that mutter has a compile-time limit of 36
const MAX_WORKSPACES = 16;
-// The values here are also used for GSettings, and the key and value
-// names must match
-const WorkspacesViewType = {
- SINGLE: 'single',
- GRID: 'grid'
-};
-const WORKSPACES_VIEW_KEY = 'workspaces-view';
-
const WORKSPACE_DRAGGING_SCALE = 0.85;
-function GenericWorkspacesView(width, height, x, y, workspaces) {
+
+function WorkspaceIndicator(activateWorkspace, workspaceAcceptDrop, workspaceHandleDragOver, scrollEventCb) {
+ this._init(activateWorkspace, workspaceAcceptDrop, workspaceHandleDragOver, scrollEventCb);
+}
+
+WorkspaceIndicator.prototype = {
+ _init: function(activateWorkspace, workspaceAcceptDrop, workspaceHandleDragOver, scrollEventCb) {
+ this._activateWorkspace = activateWorkspace;
+ this._workspaceAcceptDrop = workspaceAcceptDrop;
+ this._workspaceHandleDragOver = workspaceHandleDragOver;
+ this._scrollEventCb = scrollEventCb;
+ let actor = new St.Bin({ style_class: 'panel-button' });
+
+ this._indicatorsPanel = new Shell.GenericContainer();
+ this._indicatorsPanel.connect('get-preferred-width', Lang.bind(this, this._getPreferredWidth));
+ this._indicatorsPanel.connect('get-preferred-height', Lang.bind(this, this._getPreferredHeight));
+ this._indicatorsPanel.connect('allocate', Lang.bind(this, this._allocate));
+ this._indicatorsPanel.clip_to_allocation = true;
+
+ actor.set_child(this._indicatorsPanel);
+ actor.set_alignment(St.Align.MIDDLE, St.Align.MIDDLE);
+ this._indicatorsPanel.hide();
+ actor.connect('destroy', Lang.bind(this, this._onDestroy));
+
+ let workId = Main.initializeDeferredWork(actor, Lang.bind(this, this._workspacesChanged));
+ this._nWorkspacesNotifyId =
+ global.screen.connect('notify::n-workspaces', function() {
+ Main.queueDeferredWork(workId);
+ });
+ this._switchWorkspaceNotifyId =
+ global.window_manager.connect('switch-workspace', function() {
+ Main.queueDeferredWork(workId);
+ });
+
+ this.actor = actor;
+ },
+
+ _workspacesChanged: function() {
+ let active = global.screen.get_active_workspace_index();
+ let n = global.screen.n_workspaces;
+ if (n > 1)
+ this._indicatorsPanel.show();
+ else
+ this._indicatorsPanel.hide();
+ this._fillPositionalIndicator();
+ },
+
+ _onDestroy: function() {
+ if (this._nWorkspacesNotifyId > 0)
+ global.screen.disconnect(this._nWorkspacesNotifyId);
+ this._nWorkspacesNotifyId = 0;
+ if (this._switchWorkspaceNotifyId > 0)
+ global.window_manager.disconnect(this._switchWorkspaceNotifyId);
+ this._switchWorkspaceNotifyId = 0;
+ },
+
+ _allocate: function(actor, box, flags) {
+ let children = actor.get_children();
+ let childBox = new Clutter.ActorBox();
+ for (let i = 0; i < children.length; i++) {
+ childBox.x1 = children[i].x;
+ childBox.y1 = 0;
+ childBox.x2 = children[i].x + children[i].width;
+ childBox.y2 = children[i].height;
+ children[i].allocate(childBox, flags);
+ }
+ },
+
+ _getPreferredWidth: function(actor, fh, alloc) {
+ let children = actor.get_children();
+ let width = 0;
+ for (let i = 0; i < children.length; i++) {
+ if (children[i].x + children[i].width <= width)
+ continue;
+ width = children[i].x + children[i].width;
+ }
+ alloc.min_size = 0;
+ alloc.natural_size = width;
+ },
+
+ _getPreferredHeight: function(actor, fw, alloc) {
+ let children = actor.get_children();
+ let height = 0;
+ if (children.length)
+ height = children[0].height;
+ alloc.min_size = height;
+ alloc.natural_size = height;
+ },
+
+ _addIndicatorClone: function(i, active) {
+ let actor = new St.Button({ style_class: 'workspace-indicator' });
+ if (active) {
+ actor.style_class = 'workspace-indicator active';
+ }
+ actor.connect('clicked', Lang.bind(this, function() {
+ this._activateWorkspace(i);
+ }));
+
+ actor._delegate = {};
+ actor._delegate.acceptDrop = Lang.bind(this, function(source, actor, x, y, time) {
+ if (this._workspaceAcceptDrop(i, source, actor, x, y, time)) {
+ this._activateWorkspace(i);
+ return true;
+ }
+ else
+ return false;
+ });
+ actor._delegate.handleDragOver = Lang.bind(this, function(source, actor, x, y, time) {
+ return this._workspaceHandleDragOver(i, source, actor, x, y, time);
+ });
+
+ actor.connect('scroll-event', this._scrollEventCb);
+
+ this._indicatorsPanel.add_actor(actor);
+
+ let spacing = actor.get_theme_node().get_length('border-spacing');
+ actor.x = spacing * i + actor.width * i;
+ },
+
+ _fillPositionalIndicator: function() {
+ this._indicatorsPanel.remove_all();
+
+ let activeWorkspaceIndex = global.screen.get_active_workspace_index();
+ let n = global.screen.n_workspaces;
+ for (let i = 0; i < n; i++) {
+ this._addIndicatorClone(i, i == activeWorkspaceIndex);
+ }
+ }
+};
+
+function WorkspacesView(width, height, x, y, workspaces) {
this._init(width, height, x, y, workspaces);
}
-GenericWorkspacesView.prototype = {
+WorkspacesView.prototype = {
_init: function(width, height, x, y, workspaces) {
- this.actor = new St.Group({ style_class: 'workspaces' });
+ this.actor = new St.Group({ style_class: 'workspaces single' });
+ this.actor.set_clip(x, y, width, height);
this.actor.connect('destroy', Lang.bind(this, this._onDestroy));
@@ -44,10 +167,7 @@ GenericWorkspacesView.prototype = {
function() {
let node = this.actor.get_theme_node();
this._spacing = node.get_length('spacing');
- if (Main.overview.animationInProgress)
- this._computeWorkspacePositions();
- else
- this._transitionWorkspaces();
+ this._computeWorkspacePositions();
}));
this._width = width;
@@ -55,16 +175,28 @@ GenericWorkspacesView.prototype = {
this._x = x;
this._y = y;
this._spacing = 0;
-
- this._windowSelectionAppId = null;
- this._highlightWindow = null;
+ this._activeWorkspaceX = 0; // x offset of active ws while dragging
+ this._activeWorkspaceY = 0; // y offset of active ws while dragging
+ this._lostWorkspaces = [];
+ this._animating = false; // tweening
+ this._scrolling = false; // dragging desktop
+ this._animatingScroll = false; // programatically updating the adjustment
+ this._inDrag = false; // dragging a window
+ this._lastMotionTime = -1; // used to track "stopping" while dragging workspaces
let activeWorkspaceIndex = global.screen.get_active_workspace_index();
this._workspaces = workspaces;
// Add workspace actors
- for (let w = 0; w < global.screen.n_workspaces; w++)
+ for (let w = 0; w < global.screen.n_workspaces; w++) {
this._workspaces[w].actor.reparent(this.actor);
+ this._workspaces[w]._windowDragBeginId =
+ this._workspaces[w].connect('window-drag-begin',
+ Lang.bind(this, this._dragBegin));
+ this._workspaces[w]._windowDragEndId =
+ this._workspaces[w].connect('window-drag-end',
+ Lang.bind(this, this._dragEnd));
+ }
this._workspaces[activeWorkspaceIndex].actor.raise_top();
// Position/scale the desktop windows and their children after the
@@ -79,12 +211,35 @@ GenericWorkspacesView.prototype = {
this._workspaces[w].zoomToOverview();
}));
+ this._scrollAdjustment = new St.Adjustment({ value: activeWorkspaceIndex,
+ lower: 0,
+ page_increment: 1,
+ page_size: 1,
+ step_increment: 0,
+ upper: this._workspaces.length });
+ this._scrollAdjustment.connect('notify::value',
+ Lang.bind(this, this._onScroll));
+
+ this._dragIndex = -1;
+
+ this._buttonPressId = 0;
+ this._capturedEventId = 0;
+ this._timeoutId = 0;
+
+ this._windowSelectionAppId = null;
+ this._highlightWindow = null;
+
this._switchWorkspaceNotifyId =
global.window_manager.connect('switch-workspace',
Lang.bind(this, this._activeWorkspaceChanged));
this._restackedNotifyId =
global.screen.connect('restacked',
Lang.bind(this, this._onRestacked));
+
+ this._itemDragBeginId = Main.overview.connect('item-drag-begin',
+ Lang.bind(this, this._dragBegin));
+ this._itemDragEndId = Main.overview.connect('item-drag-end',
+ Lang.bind(this, this._dragEnd));
},
_lookupWorkspaceForMetaWindow: function (metaWindow) {
@@ -95,15 +250,6 @@ GenericWorkspacesView.prototype = {
return null;
},
- _lookupCloneForMetaWindow: function (metaWindow) {
- for (let i = 0; i < this._workspaces.length; i++) {
- let clone = this._workspaces[i].lookupCloneForMetaWindow(metaWindow);
- if (clone)
- return clone;
- }
- return null;
- },
-
setHighlightWindow: function (metaWindow) {
// Looping over all workspaces is easier than keeping track of the last
// highlighted window while trying to handle the window or workspace possibly
@@ -184,12 +330,6 @@ GenericWorkspacesView.prototype = {
this.actor.destroy();
},
- _onDestroy: function() {
- Main.overview.disconnect(this._overviewShowingId);
- global.window_manager.disconnect(this._switchWorkspaceNotifyId);
- global.screen.disconnect(this._restackedNotifyId);
- },
-
getScale: function() {
return this._workspaces[0].scale;
},
@@ -218,11 +358,7 @@ GenericWorkspacesView.prototype = {
let activeWorkspaceIndex = global.screen.get_active_workspace_index();
let activeWorkspace = this._workspaces[activeWorkspaceIndex];
- return [activeWorkspace.gridX, activeWorkspace.gridY];
- },
-
- createControllerBar: function() {
- throw new Error('Not implemented');
+ return [activeWorkspace.x, activeWorkspace.y];
},
canAddWorkspace: function() {
@@ -230,16 +366,16 @@ GenericWorkspacesView.prototype = {
},
addWorkspace: function() {
+ let ws = null;
if (!this.canAddWorkspace()) {
Main.overview.shellInfo.setMessage(_("Can't add a new workspace because maximum workspaces limit has been reached."));
- return null;
+ } else {
+ let currentTime = global.get_current_time();
+ ws = global.screen.append_new_workspace(false, currentTime);
+ ws.activate(currentTime);
}
- return global.screen.append_new_workspace(false, global.get_current_time());
- },
-
- _getWorkspaceIndexToRemove: function() {
- throw new Error('Not implemented');
+ return ws;
},
canRemoveWorkspace: function() {
@@ -257,22 +393,6 @@ GenericWorkspacesView.prototype = {
global.get_current_time());
},
- updateWorkspaces: function() {
- throw new Error('Not implemented');
- },
-
- _transitionWorkspaces: function() {
- throw new Error('Not implemented');
- },
-
- _computeWorkspacePositions: function() {
- throw new Error('Not implemented');
- },
-
- _activeWorkspaceChanged: function() {
- throw new Error('Not implemented');
- },
-
_handleDragOverNewWorkspace: function(source, dropActor, x, y, time) {
if (source instanceof Workspace.WindowClone)
return DND.DragMotionResult.MOVE_DROP;
@@ -286,369 +406,6 @@ GenericWorkspacesView.prototype = {
if (ws == null)
return false;
return this.acceptNewWorkspaceDrop(source, dropActor, x, y, time);
- }
-};
-
-function MosaicView(width, height, x, y, workspaces) {
- this._init(width, height, x, y, workspaces);
-}
-
-MosaicView.prototype = {
- __proto__: GenericWorkspacesView.prototype,
-
- _init: function(width, height, x, y, workspaces) {
- GenericWorkspacesView.prototype._init.call(this, width, height, x, y, workspaces);
-
- this.actor.add_style_class_name('mosaic');
- this.actor.set_clip(x - Workspace.FRAME_SIZE,
- y - Workspace.FRAME_SIZE,
- width + 2 * Workspace.FRAME_SIZE,
- height + 2 * Workspace.FRAME_SIZE);
- this._workspaces[global.screen.get_active_workspace_index()].setSelected(true);
- },
-
- // Assign grid positions to workspaces. We can't just do a simple
- // row-major or column-major numbering, because we don't want the
- // existing workspaces to get rearranged when we add a row or
- // column. So we alternate between adding to rows and adding to
- // columns. (So, eg, when going from a 2x2 grid of 4 workspaces to
- // a 3x2 grid of 5 workspaces, the 4 existing workspaces stay
- // where they are, and the 5th one is added to the end of the
- // first row.)
- //
- // FIXME: need to make the metacity internal layout agree with this!
- _computeWorkspacePositions: function() {
- let gridWidth = Math.ceil(Math.sqrt(this._workspaces.length));
- let gridHeight = Math.ceil(this._workspaces.length / gridWidth);
-
- // adjust vertical spacing so workspaces can preserve their aspect
- // ratio without exceeding this._height
- let verticalSpacing = this._spacing * this._height / this._width;
-
- let wsWidth = (this._width - (gridWidth - 1) * this._spacing) / gridWidth;
- let wsHeight = (this._height - (gridHeight - 1) * verticalSpacing) / gridHeight;
- let scale = wsWidth / global.screen_width;
-
- let span = 1, n = 0, row = 0, col = 0, horiz = true;
-
- for (let w = 0; w < this._workspaces.length; w++) {
- let workspace = this._workspaces[w];
-
- workspace.gridRow = row;
- workspace.gridCol = col;
-
- workspace.gridX = this._x + workspace.gridCol * (wsWidth + this._spacing);
- workspace.gridY = this._y + workspace.gridRow * (wsHeight + verticalSpacing);
- workspace.scale = scale;
-
- if (horiz) {
- col++;
- if (col == span) {
- row = 0;
- horiz = false;
- }
- } else {
- row++;
- if (row == span) {
- col = 0;
- horiz = true;
- span++;
- }
- }
- }
- },
-
- _transitionWorkspaces: function() {
- // update workspace parameters
- this._computeWorkspacePositions();
-
- let active = global.screen.get_active_workspace_index();
- let activeWorkspace = this._workspaces[active];
- // scale is the factor needed to translate from the new scale
- // (this view) to the currently active scale (previous view)
- let scale = this._workspaces[0].actor.scale_x / activeWorkspace.scale;
-
- for (let w = 0; w < this._workspaces.length; w++) {
- let workspace = this._workspaces[w];
- let originX, originY;
- let dx, dy;
-
- // The correct transition would be a straightforward animation
- // of each workspace's old position/scale to the new one;
- // however, this looks overly busy, so we only use a zoom effect.
- // Unfortunately this implies that we cannot pretend to not knowing
- // the other view's layout at this point:
- // We position the workspaces in the grid, which we scale up so
- // that the active workspace fills the viewport.
- dx = workspace.gridX - activeWorkspace.gridX;
- dy = workspace.gridY - activeWorkspace.gridY;
- originX = this._x + scale * dx;
- originY = this._y + scale * dy;
-
- workspace.actor.set_position(originX, originY);
-
- workspace.positionWindows(Workspace.WindowPositionFlags.ANIMATE);
- workspace.setSelected(false);
- workspace.hideWindowsOverlays();
-
- Tweener.addTween(workspace.actor,
- { x: workspace.gridX,
- y: workspace.gridY,
- scale_x: workspace.scale,
- scale_y: workspace.scale,
- time: Overview.ANIMATION_TIME,
- transition: 'easeOutQuad',
- onComplete: function() {
- workspace.zoomToOverview(false);
- if (workspace.metaWorkspace.index() == active)
- workspace.setSelected(true);
- }});
- }
- },
-
- updateWorkspaces: function(oldNumWorkspaces, newNumWorkspaces, lostWorkspaces) {
- let oldScale = this._workspaces[0].scale;
- let oldGridWidth = Math.ceil(Math.sqrt(oldNumWorkspaces));
- let oldGridHeight = Math.ceil(oldNumWorkspaces / oldGridWidth);
-
- // Add actors
- if (newNumWorkspaces > oldNumWorkspaces)
- for (let w = oldNumWorkspaces; w < newNumWorkspaces; w++)
- this.actor.add_actor(this._workspaces[w].actor);
-
- // Figure out the new layout
- this._computeWorkspacePositions();
- let newScale = this._workspaces[0].scale;
- let newGridWidth = Math.ceil(Math.sqrt(newNumWorkspaces));
- let newGridHeight = Math.ceil(newNumWorkspaces / newGridWidth);
-
- if (newGridWidth != oldGridWidth || newGridHeight != oldGridHeight) {
- // We need to resize/move the existing workspaces/windows
- let existingWorkspaces = Math.min(oldNumWorkspaces, newNumWorkspaces);
- for (let w = 0; w < existingWorkspaces; w++)
- this._workspaces[w].resizeToGrid(oldScale);
- }
-
- if (newScale != oldScale) {
- // The workspace scale affects window size/positioning because we clamp
- // window size to a 1:1 ratio and never scale them up
- let existingWorkspaces = Math.min(oldNumWorkspaces, newNumWorkspaces);
- for (let w = 0; w < existingWorkspaces; w++)
- this._workspaces[w].positionWindows(Workspace.WindowPositionFlags.ANIMATE);
- }
-
- if (newNumWorkspaces > oldNumWorkspaces) {
- // Slide new workspaces in from offscreen
- // New workspaces can contain windows.
- for (let w = oldNumWorkspaces; w < newNumWorkspaces; w++) {
- this._workspaces[w].positionWindows(0);
- this._workspaces[w].slideIn(oldScale);
- }
- } else {
- // Slide old workspaces out
- for (let w = 0; w < lostWorkspaces.length; w++) {
- let workspace = lostWorkspaces[w];
- workspace.slideOut(function () { workspace.destroy(); });
- }
- }
-
- // Reset the selection state; if we went from > 1 workspace to 1,
- // this has the side effect of removing the frame border
- let activeIndex = global.screen.get_active_workspace_index();
- this._workspaces[activeIndex].setSelected(true);
- },
-
- _activeWorkspaceChanged: function(wm, from, to, direction) {
- this._workspaces[from].setSelected(false);
- this._workspaces[to].setSelected(true);
- },
-
- createControllerBar: function() {
- return null;
- },
-
- _getWorkspaceIndexToRemove: function() {
- return this._workspaces.length - 1;
- }
-};
-
-
-function WorkspaceIndicator(activateWorkspace, workspaceAcceptDrop, workspaceHandleDragOver, scrollEventCb) {
- this._init(activateWorkspace, workspaceAcceptDrop, workspaceHandleDragOver, scrollEventCb);
-}
-
-WorkspaceIndicator.prototype = {
- _init: function(activateWorkspace, workspaceAcceptDrop, workspaceHandleDragOver, scrollEventCb) {
- this._activateWorkspace = activateWorkspace;
- this._workspaceAcceptDrop = workspaceAcceptDrop;
- this._workspaceHandleDragOver = workspaceHandleDragOver;
- this._scrollEventCb = scrollEventCb;
- let actor = new St.Bin({ style_class: 'panel-button' });
-
- this._indicatorsPanel = new Shell.GenericContainer();
- this._indicatorsPanel.connect('get-preferred-width', Lang.bind(this, this._getPreferredWidth));
- this._indicatorsPanel.connect('get-preferred-height', Lang.bind(this, this._getPreferredHeight));
- this._indicatorsPanel.connect('allocate', Lang.bind(this, this._allocate));
- this._indicatorsPanel.clip_to_allocation = true;
-
- actor.set_child(this._indicatorsPanel);
- actor.set_alignment(St.Align.MIDDLE, St.Align.MIDDLE);
- this._indicatorsPanel.hide();
- actor.connect('destroy', Lang.bind(this, this._onDestroy));
-
- let workId = Main.initializeDeferredWork(actor, Lang.bind(this, this._workspacesChanged));
- this._nWorkspacesNotifyId =
- global.screen.connect('notify::n-workspaces', function() {
- Main.queueDeferredWork(workId);
- });
- this._switchWorkspaceNotifyId =
- global.window_manager.connect('switch-workspace', function() {
- Main.queueDeferredWork(workId);
- });
-
- this.actor = actor;
- },
-
- _workspacesChanged: function() {
- let active = global.screen.get_active_workspace_index();
- let n = global.screen.n_workspaces;
- if (n > 1)
- this._indicatorsPanel.show();
- else
- this._indicatorsPanel.hide();
- this._fillPositionalIndicator();
- },
-
- _onDestroy: function() {
- if (this._nWorkspacesNotifyId > 0)
- global.screen.disconnect(this._nWorkspacesNotifyId);
- this._nWorkspacesNotifyId = 0;
- if (this._switchWorkspaceNotifyId > 0)
- global.window_manager.disconnect(this._switchWorkspaceNotifyId);
- this._switchWorkspaceNotifyId = 0;
- },
-
- _allocate: function(actor, box, flags) {
- let children = actor.get_children();
- let childBox = new Clutter.ActorBox();
- for (let i = 0; i < children.length; i++) {
- childBox.x1 = children[i].x;
- childBox.y1 = 0;
- childBox.x2 = children[i].x + children[i].width;
- childBox.y2 = children[i].height;
- children[i].allocate(childBox, flags);
- }
- },
-
- _getPreferredWidth: function(actor, fh, alloc) {
- let children = actor.get_children();
- let width = 0;
- for (let i = 0; i < children.length; i++) {
- if (children[i].x + children[i].width <= width)
- continue;
- width = children[i].x + children[i].width;
- }
- alloc.min_size = 0;
- alloc.natural_size = width;
- },
-
- _getPreferredHeight: function(actor, fw, alloc) {
- let children = actor.get_children();
- let height = 0;
- if (children.length)
- height = children[0].height;
- alloc.min_size = height;
- alloc.natural_size = height;
- },
-
- _addIndicatorClone: function(i, active) {
- let actor = new St.Button({ style_class: 'workspace-indicator' });
- if (active) {
- actor.style_class = 'workspace-indicator active';
- }
- actor.connect('clicked', Lang.bind(this, function() {
- this._activateWorkspace(i);
- }));
-
- actor._delegate = {};
- actor._delegate.acceptDrop = Lang.bind(this, function(source, actor, x, y, time) {
- if (this._workspaceAcceptDrop(i, source, actor, x, y, time)) {
- this._activateWorkspace(i);
- return true;
- }
- else
- return false;
- });
- actor._delegate.handleDragOver = Lang.bind(this, function(source, actor, x, y, time) {
- return this._workspaceHandleDragOver(i, source, actor, x, y, time);
- });
-
- actor.connect('scroll-event', this._scrollEventCb);
-
- this._indicatorsPanel.add_actor(actor);
-
- let spacing = actor.get_theme_node().get_length('border-spacing');
- actor.x = spacing * i + actor.width * i;
- },
-
- _fillPositionalIndicator: function() {
- this._indicatorsPanel.remove_all();
-
- let activeWorkspaceIndex = global.screen.get_active_workspace_index();
- let n = global.screen.n_workspaces;
- for (let i = 0; i < n; i++) {
- this._addIndicatorClone(i, i == activeWorkspaceIndex);
- }
- }
-};
-
-function SingleView(width, height, x, y, workspaces) {
- this._init(width, height, x, y, workspaces);
-}
-
-SingleView.prototype = {
- __proto__: GenericWorkspacesView.prototype,
-
- _init: function(width, height, x, y, workspaces) {
- GenericWorkspacesView.prototype._init.call(this, width, height, x, y, workspaces);
-
- this._itemDragBeginId = Main.overview.connect('item-drag-begin',
- Lang.bind(this, this._dragBegin));
- this._itemDragEndId = Main.overview.connect('item-drag-end',
- Lang.bind(this, this._dragEnd));
- for (let i = 0; i < this._workspaces.length; i++) {
- this._workspaces[i]._windowDragBeginId = this._workspaces[i].connect('window-drag-begin',
- Lang.bind(this, this._dragBegin));
- this._workspaces[i]._windowDragEndId = this._workspaces[i].connect('window-drag-end',
- Lang.bind(this, this._dragEnd));
- }
-
- this.actor.add_style_class_name('single');
- this.actor.set_clip(x, y, width, height);
- this._activeWorkspaceX = 0; // x offset of active ws while dragging
- this._activeWorkspaceY = 0; // y offset of active ws while dragging
- this._lostWorkspaces = [];
- this._animating = false; // tweening
- this._scrolling = false; // dragging desktop
- this._animatingScroll = false; // programatically updating the adjustment
- this._inDrag = false; // dragging a window
- this._lastMotionTime = -1; // used to track "stopping" while dragging workspaces
-
- let active = global.screen.get_active_workspace_index();
- this._scrollAdjustment = new St.Adjustment({ value: active,
- lower: 0,
- page_increment: 1,
- page_size: 1,
- step_increment: 0,
- upper: this._workspaces.length });
- this._scrollAdjustment.connect('notify::value',
- Lang.bind(this, this._onScroll));
-
- this._dragIndex = -1;
-
- this._buttonPressId = 0;
- this._capturedEventId = 0;
- this._timeoutId = 0;
},
// Compute the position, scale and opacity of the workspaces, but don't
@@ -673,55 +430,10 @@ SingleView.prototype = {
workspace.opacity = (this._inDrag && w != active) ? 200 : 255;
- workspace.gridRow = 0;
- workspace.gridCol = 0;
-
workspace.scale = scale;
- workspace.gridX = this._x + this._activeWorkspaceX
- + (w - active) * (_width + this._spacing);
- workspace.gridY = this._y + this._activeWorkspaceY;
-
- workspace.setSelected(false);
- }
- },
-
- _transitionWorkspaces: function() {
- // update workspace parameters
- this._computeWorkspacePositions();
-
- let active = global.screen.get_active_workspace_index();
- let activeActor = this._workspaces[active].actor;
- // scale is the factor needed to translate from the currently
- // active scale (previous view) to the new scale (this view)
- let scale = this._workspaces[active].scale / activeActor.scale_x;
-
- for (let w = 0; w < this._workspaces.length; w++) {
- let workspace = this._workspaces[w];
- let targetX, targetY;
-
- // The correct transition would be a straightforward animation
- // of each workspace's old position/scale to the new one;
- // however, this looks overly busy, so we only use a zoom effect.
- // Therefore we scale up each workspace's distance to the active
- // workspace, so the latter fills the viewport while the other
- // workspaces maintain their relative position
- targetX = this._x + scale * (workspace.actor.x - activeActor.x);
- targetY = this._y + scale * (workspace.actor.y - activeActor.y);
-
- workspace.positionWindows(Workspace.WindowPositionFlags.ANIMATE);
- workspace.setSelected(false);
- workspace._hideAllOverlays();
-
- Tweener.addTween(workspace.actor,
- { x: targetX,
- y: targetY,
- scale_x: workspace.scale,
- scale_y: workspace.scale,
- time: Overview.ANIMATION_TIME,
- transition: 'easeOutQuad',
- onComplete: function() {
- workspace.zoomToOverview(false);
- }});
+ workspace.x = this._x + this._activeWorkspaceX
+ + (w - active) * (_width + this._spacing);
+ workspace.y = this._y + this._activeWorkspaceY;
}
},
@@ -855,7 +567,7 @@ SingleView.prototype = {
_updateWorkspaceActors: function(showAnimation) {
let active = global.screen.get_active_workspace_index();
let targetWorkspaceNewX = this._x + this._activeWorkspaceX;
- let targetWorkspaceCurrentX = this._workspaces[active].gridX;
+ let targetWorkspaceCurrentX = this._workspaces[active].x;
let dx = targetWorkspaceNewX - targetWorkspaceCurrentX;
this._setWorkspaceDraggable(active, true);
@@ -866,11 +578,11 @@ SingleView.prototype = {
Tweener.removeTweens(workspace.actor);
- workspace.gridX += dx;
+ workspace.x += dx;
if (showAnimation) {
- let params = { x: workspace.gridX,
- y: workspace.gridY,
+ let params = { x: workspace.x,
+ y: workspace.y,
scale_x: workspace.scale,
scale_y: workspace.scale,
opacity: workspace.opacity,
@@ -891,7 +603,7 @@ SingleView.prototype = {
Tweener.addTween(workspace.actor, params);
} else {
workspace.actor.set_scale(workspace.scale, workspace.scale);
- workspace.actor.set_position(workspace.gridX, workspace.gridY);
+ workspace.actor.set_position(workspace.x, workspace.y);
workspace.actor.opacity = workspace.opacity;
if (w == 0)
this._updateVisibility();
@@ -903,13 +615,13 @@ SingleView.prototype = {
Tweener.removeTweens(workspace.actor);
- workspace.gridX += dx;
+ workspace.x += dx;
workspace.actor.show();
workspace.hideWindowsOverlays();
if (showAnimation) {
Tweener.addTween(workspace.actor,
- { x: workspace.gridX,
+ { x: workspace.x,
time: WORKSPACE_SWITCH_TIME,
transition: 'easeOutQuad',
onComplete: Lang.bind(this,
@@ -1011,7 +723,10 @@ SingleView.prototype = {
},
_onDestroy: function() {
- GenericWorkspacesView.prototype._onDestroy.call(this);
+ Main.overview.disconnect(this._overviewShowingId);
+ global.window_manager.disconnect(this._switchWorkspaceNotifyId);
+ global.screen.disconnect(this._restackedNotifyId);
+
this._setWorkspaceDraggable(this._dragIndex, false);
if (this._timeoutId) {
Mainloop.source_remove(this._timeoutId);
@@ -1210,14 +925,6 @@ SingleView.prototype = {
return actor;
},
- addWorkspace: function() {
- let ws = GenericWorkspacesView.prototype.addWorkspace.call(this);
- if (ws != null)
- ws.activate(global.get_current_time());
-
- return ws;
- },
-
_getWorkspaceIndexToRemove: function() {
return global.screen.get_active_workspace_index();
}
@@ -1232,27 +939,8 @@ WorkspacesControls.prototype = {
this.actor = new St.BoxLayout({ style_class: 'workspaces-bar' });
this.actor.connect('destroy', Lang.bind(this, this._onDestroy));
- let view = global.settings.get_string(WORKSPACES_VIEW_KEY).toUpperCase();
- if (view in WorkspacesViewType)
- this._currentViewType = WorkspacesViewType[view];
- else
- this._currentViewType = WorkspacesViewType.SINGLE;
-
this._currentView = null;
- // View switcher button
- this._toggleViewButton = new St.Button();
- this._updateToggleButtonStyle();
-
- this._toggleViewButton.connect('clicked', Lang.bind(this, function() {
- if (this._currentViewType == WorkspacesViewType.SINGLE)
- this._setView(WorkspacesViewType.GRID);
- else
- this._setView(WorkspacesViewType.SINGLE);
- }));
-
- this.actor.add(this._toggleViewButton, { y_fill: false, y_align: St.Align.START });
-
// View specific controls
this._viewControls = new St.Bin({ x_fill: true, y_fill: true });
this.actor.add(this._viewControls, { expand: true, x_fill: true });
@@ -1283,12 +971,12 @@ WorkspacesControls.prototype = {
this._nWorkspacesNotifyId =
global.screen.connect('notify::n-workspaces',
- Lang.bind(this, this._workspacesChanged));
+ Lang.bind(this, this.updateControlsSensitivity));
this._switchWorkspaceNotifyId =
global.window_manager.connect('switch-workspace',
Lang.bind(this, this.updateControlsSensitivity));
- this._workspacesChanged();
+ this.updateControlsSensitivity();
},
updateControls: function(view) {
@@ -1316,26 +1004,6 @@ WorkspacesControls.prototype = {
}
},
- _updateToggleButtonStyle: function() {
- if (this._currentViewType == WorkspacesViewType.SINGLE)
- this._toggleViewButton.set_style_class_name('workspace-controls switch-mosaic');
- else
- this._toggleViewButton.set_style_class_name('workspace-controls switch-single');
- },
-
- _setView: function(view) {
- if (this._currentViewType == view)
- return;
-
- if (WorkspacesViewType.SINGLE == view)
- this._toggleViewButton.set_style_class_name('workspace-controls switch-mosaic');
- else
- this._toggleViewButton.set_style_class_name('workspace-controls switch-single');
-
- this._currentViewType = view;
- global.settings.set_string(WORKSPACES_VIEW_KEY, view);
- },
-
_onDestroy: function() {
if (this._nWorkspacesNotifyId > 0) {
global.screen.disconnect(this._nWorkspacesNotifyId);
@@ -1358,15 +1026,6 @@ WorkspacesControls.prototype = {
this._setButtonSensitivity(this._removeButton, this._currentView.canRemoveWorkspace());
this._setButtonSensitivity(this._addButton, this._currentView.canAddWorkspace());
}
- },
-
- _workspacesChanged: function() {
- let showToggleButton = (global.screen.n_workspaces > 1);
- Tweener.addTween(this._toggleViewButton,
- { opacity: showToggleButton ? 255 : 0,
- time: WORKSPACE_SWITCH_TIME,
- transition: 'easeOutQuad' });
- this.updateControlsSensitivity();
}
};
Signals.addSignalMethods(WorkspacesControls.prototype);
@@ -1394,40 +1053,18 @@ WorkspacesManager.prototype = {
this.controlsBar.actor.connect('destroy',
Lang.bind(this, this._onDestroy));
- this._viewChangedId =
- global.settings.connect('changed::' + WORKSPACES_VIEW_KEY,
- Lang.bind(this, this._updateView));
this._nWorkspacesNotifyId =
global.screen.connect('notify::n-workspaces',
Lang.bind(this, this._workspacesChanged));
},
_updateView: function() {
- let viewType, newView;
-
- let view = global.settings.get_string(WORKSPACES_VIEW_KEY).toUpperCase();
- if (view in WorkspacesViewType)
- viewType = WorkspacesViewType[view];
- else
- viewType = WorkspacesViewType.SINGLE;
-
- switch (viewType) {
- case WorkspacesViewType.SINGLE:
- newView = new SingleView(this._workspacesWidth,
+ let newView = new WorkspacesView(this._workspacesWidth,
this._workspacesHeight,
this._workspacesX,
this._workspacesY,
this._workspaces);
- break;
- case WorkspacesViewType.GRID:
- default:
- newView = new MosaicView(this._workspacesWidth,
- this._workspacesHeight,
- this._workspacesX,
- this._workspacesY,
- this._workspaces);
- break;
- }
+
if (this.workspacesView)
this.workspacesView.destroy();
this.workspacesView = newView;
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]