Wednesday, June 20, 2012

Static workspaces and Keyboard Shortcuts in Gnome Shell 3.4

I've been a KDE and Xfce user for a long time, but I've been experimenting with Gnome Shell lately out of curiosity.  I tend to use a lot of workspaces (or virtual desktops) to organize my work — email on workspace 2, developing code on workspace 3, web browser on 4, etc. — so I really do not like the dynamic workspaces feature in Gnome Shell because closing the last window on a workspace destroys that workspace and shifts all the others around which confuses me.

But with Fedora 17 and Gnome Shell 3.4, it is possible to disable dynamic workspaces and set a fixed number of workspaces instead.  (It was possible to do this earlier with the Frippery extensions.)  Fire up gnome-tweak-tool and go to the Shell settings to make the change:


I also like to use keyboard shortcuts to switch between workspaces and move windows to various workspaces.  CTRL-F1 to go to workspaces 1, CTRL-F2 for workspace 2, etc.  And CTRL-SHIFT-FN to move a window to workspace N.  Unfortunately, the Keyboard Settings Shortcuts GUI only shows the hotkey settings for desktops 1 through 4:


It is possible to create keyboard shortcuts for desktops 5 and up, but the settings are hidden away in the gsettings database.  So fire up a terminal window and run:

[user@localhost ~]$ gsettings set org.gnome.desktop.wm.keybindings \
    switch-to-workspace-5 "[\"<Control>F5\"]"
[user@localhost ~]$ gsettings set org.gnome.desktop.wm.keybindings \
    move-to-workspace-5 "[\"<Control><Shift>F5\"]"

This sets CTRL-F5 to switch to workspace 5, and CTRL-SHIFT-F5 to move the current window to workspace 5.  Feel free to choose other keys like ALT or SUPER.

To make life easier, I wrote this simple script to change all the hotkeys for desktops 1 through 12:

#!/bin/bash

# Disable dynamic workspaces and set 12 fixed workspaces, and set the
# hot-keys for switching and moving windows to the workspaces.
#
# The Gnome 3.4 Shell keyboard settings GUI only exposes hot-key configuration
# for workspaces 1-4 so you have to use the command line for spaces 5+.
#
# Jeff Bastian, 2012-06-20

echo "Disabling dynamic workspaces"
gsettings set org.gnome.shell.overrides dynamic-workspaces false

echo "Setting 12 fixed workspaces"
gsettings set org.gnome.desktop.wm.preferences num-workspaces 12

for ((x=1 ; x <= 12 ; x++)) ; do
    echo "Setting hotkeys for workspace $x"
    gsettings set org.gnome.desktop.wm.keybindings \
        switch-to-workspace-$x "[\"<Control>F$x\"]"
    gsettings set org.gnome.desktop.wm.keybindings \
        move-to-workspace-$x "[\"<Control><Shift>F$x\"]"
done

echo "Done"
echo "~~~~"
echo "Verify Settings:"
gsettings list-recursively org.gnome.shell.overrides | grep dynamic-workspaces
gsettings list-recursively org.gnome.desktop.wm.preferences | grep num-workspaces
gsettings list-recursively org.gnome.desktop.wm.keybindings | grep to-workspace

5 comments:

  1. This is great post, thank you for this! However, it does not work fully: immediately after I set the number of workspaces and verify that the commands worked, something sets them back to the original value. Any ideas?

    $ gsettings set org.gnome.shell.overrides dynamic-workspaces false

    $ gsettings set org.gnome.desktop.wm.preferences num-workspaces 9

    $ gsettings list-recursively org.gnome.shell.overrides | grep dynamic-workspaces
    org.gnome.shell.overrides dynamic-workspaces false

    $ gsettings list-recursively org.gnome.desktop.wm.preferences | grep num-workspaces
    org.gnome.desktop.wm.preferences num-workspaces 9

    $ sleep 1
    $ gsettings list-recursively org.gnome.desktop.wm.preferences | grep num-workspaces
    org.gnome.desktop.wm.preferences num-workspaces 5


    ReplyDelete
  2. Petr, that's really odd. I'm not sure what might be resetting your changes. Do you have any mandatory system-wide settings that might be overriding your personal settings? See https://live.gnome.org/dconf/SystemAdministrators for info on making system-wide settings.

    You could try using the dconf(*) watch feature to see if/when the setting changes. Open a terminal and just leave this running:
    $ dconf watch /org/gnome/desktop/wm/preferences/num-workspaces

    * gsettings uses dconf as its back-end

    ReplyDelete
  3. Great tip Jeff!

    Do you know if there is a way to start an application in a specific workspace? I.e., so I don't have to move it after it opens.

    ReplyDelete
    Replies
    1. Try devilspie or wmctrl. Devil's Pie is a daemon that watches for new windows and then applies rules such as make the window sticky or move to a certain desktop. wmctrl can be used to control existing windows.

      Delete