Gdzie są przechowywane skróty klawiaturowe GNOME?

53

Zwykle ładuję nową wersję dla każdej wersji, aby zachować świeżość mojego systemu operacyjnego, zachowując ostatnią wersję na innej partycji jako kopię zapasową. Korzystam również z wielu niestandardowych mapowań kluczy.

Do tej pory wymyśliłem, jak przenieść większość mojej konfiguracji między systemami, ale nie wiem, gdzie są przechowywane niestandardowe mapowania skrótów klawiaturowych.

Czy ktoś wie, gdzie gnome je umieszcza? Czy istnieją osobne pliki konfiguracji użytkownika (tj. ~ /) I konfiguracji systemu (tj. / Etc)?

Evan Plaice
źródło
2
Jak zmieniłeś ustawienia? Korzystasz z GConf Editor? Zgaduję, że chcesz gconftool-2 --dump /apps/metacityczy coś takiego.
Mikel
1
@Mikel Wielkie dzięki za komentarz. Z tego, co mogę powiedzieć w edytorze gconf, większość skrótów klawiszowych jest przechowywana w katalogu / apps / metacity, a pozostałe są rozłożone. Obecnie piszę importowane / eksportowane skrypty pythonowe, aby tworzenie kopii zapasowych / przywracanie skrótów klawiszowych odbywało się jednym kliknięciem.
Evan Plaice,
Powiązane: askubuntu.com/questions/17626/…
Ciro Santilli 15 改造 中心 法轮功 六四 事件

Odpowiedzi:

45

Ubuntu zmieniło się od czasu napisania innych odpowiedzi na to pytanie.

Skróty klawiszowe zostały przeniesione z gconf do dconf. Gconf przechowuje swoje dane w plikach xml i był dostępny przez gconf-editori gconf-tool2. Dconf przechowuje swoje dane w formacie binarnym i jest dostępny przez dconf-editori gsettings.

Liczba miejsc, w których są przechowywane skróty klawiszowe, jest zmniejszona. Istnieje teraz scentralizowana ścieżka dconf do przechowywania skrótów klawiszowych menedżera okien ( org.gnome.desktop.wm.keybindings). W katalogu znajdują się pliki odwzorowań, /usr/share/gnome-control-center/keybindings/które pokazują, w jaki sposób są one stosowane na podstawie aktualnie używanego menedżera okien (compiz lub metacity).

Drugi zestaw powiązań klawiszy niezwiązanych z menedżerem okien jest przechowywany w ścieżce dconf org.gnome.settings-daemon.plugins.media-keys

Istnieje trzeci zestaw skrótów klawiszowych związanych z przyciskami zasilania, który jest przechowywany na ścieżce dconf org.gnome.settings-daemon.plugins.power. Obecnie w interfejsie GUI występuje błąd, który umożliwia konfigurowanie skrótów klawiszowych. Nie wie o tych ustawieniach. Na klawiaturze mam przycisk „uśpienia”. Jeśli chcę ponownie przypisać to do innej funkcji, muszę org.gnome.settings-daemon.plugins.powerręcznie wyłączyć to ustawienie . GUI nie robi tego dla mnie (chociaż dobrze przypisuje nową funkcjonalność).

Drugim zmarszczeniem są niestandardowe przypisania klawiszy. Są one przechowywane w dconf przy użyciu schematu relokowalnego. Dokonano tego w ten sposób, ponieważ jest ich dowolna liczba. Rozsądne podejście, ale sprawia, że ​​lista lub modyfikacja ich za pomocą wiersza poleceń jest trudniejsza niż powinna.

Dowiedziałem się również, że GUI, które pozwala przypisywać skróty klawiszowe, jest ograniczone w sposób, który mnie denerwuje. GUI pozwala przypisać dokładnie JEDEN skrót klawiszowy do każdej akcji. W dconf możesz ustawić tablicę powiązań dla pojedynczej akcji. To mi się przydaje. Na przykład lubię mieć przypisaną akcję „zamknij okno” do tradycyjnego Alt-F4, a także do łatwiejszego do naciśnięcia jednego przycisku na klawiaturze.

Napisałem skrypt Perla, aby zrzucić wszystkie skróty klawiszowe do pliku csv lub przywrócić je z pliku csv. Na przykład, aby zrzucić skróty, których możesz użyć:

./keybindings.pl -e /tmp/keys.csv

i aby je przywrócić, możesz użyć:

./keybindings.pl -i /tmp/keys.csv

#!/usr/bin/perl

use strict;

my $action = '';
my $filename = '-';

for my $arg (@ARGV){
    if ($arg eq "-e" or $arg eq "--export"){
        $action = 'export';
    } elsif ($arg eq "-i" or $arg eq "--import"){
        $action = 'import';
    } elsif ($arg eq "-h" or $arg eq "--help"){
        print "Import and export keybindings\n";
        print " -e, --export <filename>\n";
        print " -i, --import <filename>\n";
        print " -h, --help\n";
        exit;
    } elsif ($arg =~ /^\-/){
        die "Unknown argument $arg";
    } else {
        $filename = $arg;
        if (!$action){
            if ( -e $filename){
                $action='import';
            } else {
                $action='export';
            }
        }
    }
}

$action='export' if (!$action);
if ($action eq 'export'){
    &export();
} else {
    &import();
}

sub export(){
    my $gsettingsFolders = [
        ['org.gnome.desktop.wm.keybindings','.'],
        ['org.gnome.settings-daemon.plugins.power','button'],
        ['org.gnome.settings-daemon.plugins.media-keys','.'],
    ];

    my $customBindings = [
    ];

    $filename = ">$filename";
    open (my $fh, $filename) || die "Can't open file $filename: $!";

    for my $folder (@$gsettingsFolders){
        my @keylist = split(/\n/, `gsettings list-recursively $folder->[0]`);
        foreach my $line (@keylist){
            if ($line =~ /^([^ ]+) ([^ ]+)(?: \@[a-z]+)? (.*)/){
                my ($path, $name, $value) = ($1,$2,$3);
                if ($name eq "custom-keybindings"){
                    $value =~ s/[\[\]\' ]//g;
                    my @c = split(/,/, $value);
                    $customBindings = \@c;
                } elsif ($name =~ /$folder->[1]/){
                    if ($value =~ /^\[|\'/){
                        if ($value =~ /^\[\'(?:disabled)?\'\]$/){
                            $value = '[]';
                        } 
                        print $fh "$path\t$name\t$value\n";
                    }
                }        
            } else {
                die "Could note parse $line";
            }
        }
    }   

    for my $folder (@$customBindings){
        my $gs = `gsettings list-recursively org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:$folder`;
        my ($binding) = $gs =~ /org.gnome.settings-daemon.plugins.media-keys.custom-keybinding binding (\'[^\n]+\')/g;
        my ($command) = $gs =~ /org.gnome.settings-daemon.plugins.media-keys.custom-keybinding command (\'[^\n]+\')/g;
        my ($name) = $gs =~ /org.gnome.settings-daemon.plugins.media-keys.custom-keybinding name (\'[^\n]+\')/g;
        $command =~ s/\"/\\\"/g;
        $command =~ s/^'(.*)'$/$1/g;
        $command =~ s/\'/\'\\\'\'/g;
        $command = "\'$command\'";
        print $fh "custom\t$name\t$command\t$binding\n"    
    }

    close($fh);
}

sub import(){

    $filename = "<$filename";
    open (my $fh, $filename) || die "Can't open file $filename: $!";

    my $customcount=0;

    while (my $line = <$fh>){
        chomp $line;
        if ($line){
            my @v = split(/\t/, $line);
            if (@v[0] eq 'custom'){
                my ($custom, $name, $command, $binding) = @v;
                print "Installing custom keybinding: $name\n";
                    print `gsettings set org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$customcount/ name \"$name\"`;
                print `gsettings set org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$customcount/ command \"$command\"`;
                print `gsettings set org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$customcount/ binding \"$binding\"`;
                $customcount++;
            } else {
                my ($path, $name, $value) = @v;
                print "Importing $path $name\n";
                print `gsettings set \"$path\" \"$name\" \"$value\"`;
            }
        }       
    }
    if ($customcount > 0){
        my $customlist = "";
        for (my $i=0; $i<$customcount; $i++){
            $customlist .= "," if ($customlist);
            $customlist .= "'/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$i/'";            
        }
        $customlist = "[$customlist]";
        print "Importing list of custom keybindings.\n";
        print `gsettings set org.gnome.settings-daemon.plugins.media-keys custom-keybindings \"$customlist\"`;
    }

    close($fh);
}

Obejmuje to poprawkę użytkownika 2589537, która zezwala na niestandardowe polecenia z cytatami.

Stephen Ostermiller
źródło
2
Złożyłem dwa błędy przeciwko skrótom klawiaturowym Ubuntu-Control-Center. Znalazłem je podczas tworzenia tego skryptu. bugs.launchpad.net/ubuntu/+source/gnome-control-center/+bug/… i bugs.launchpad.net/ubuntu/+source/gnome-control-center/+bug/…
Stephen Ostermiller
1
Dzięki za skrypt @Stephen, właśnie wypróbowałem Ubuntu 13.10 i po prostu działało! Utworzono listę ułatwiającą udostępnianie: gist.github.com/elgalu/8511861#file-keybindings-pl
Leo Gallucci
Świetna robota i dobra robota dokumentująca specyfikę.
Evan Plaice
2
Nadal działa na Ubuntu GNOME 3.2 - Dziękujemy!
klequis
1
„działa” technicznie dla mnie, ale prawdopodobnie trzeba uważać na różne sekcje dconf ubuntu-MATE (tj [org/mate/marco/global-keybindings], [org/mate/marco/window-keybindings]...)
Frank Nocke
17

Jak wykonać kopię zapasową ustawień dconf, takich jak skróty klawiaturowe

  1. Zrzuć je wszystkie do pliku:

    dconf dump / >~/.config/dconf/user.conf
    
  2. Otwórz ten plik w edytorze tekstu i wybierz ustawienia, które Cię interesują:

    editor ~/.config/dconf/user.conf
    

    Jeśli używasz Vima, będziesz chciał wyróżnić tę składnię .

    Wkrótce zapytasz siebie, co jest<Primary> .

  3. Jeśli nie znasz nazwy ustawienia, ale wiesz, jak to zmienić w interfejsie GUI unity-control-center, uruchom:

    dconf watch /
    

    a następnie zmodyfikuj je. Dokładne ustawienie pojawi się na terminalu.

  4. Aby przywrócić te ustawienia, uruchom:

    dconf load / <~/.config/dconf/user.conf
    
  5. Git śledzi plik konfiguracyjny, aby go nigdy nie utracić. https://github.com/andsens/homeshick to moja obecna ulubiona metoda.

Testowane na Ubuntu 15.10. Wskazówka dostosowana z: http://catern.com/2014/12/21/plain-text-configuration-gnome.html

Terminal Gnome jest niestety odporny na takie zmiany z powodu nieprzewidywalnych identyfikatorów profili: Edytuj profil Gnome-Terminal z wiersza poleceń 18.04

Ciro Santilli
źródło
15

Skróty klawiaturowe nie są przechowywane w jednym miejscu

W zależności od wersji dystrybucyjnej aplikacja skrótów klawiaturowych może być nazywana w GUI różnymi rzeczami, ale w wierszu poleceń powinna być nazywana „gnome-keybinding-properties”. Okazuje się, że ta zgrabna mała aplikacja łączy wszystkie skróty w jednym wygodnym miejscu do edycji przez użytkowników.

Ponieważ nie istnieje żadne narzędzie do eksportowania / importowania jednym kliknięciem dla skrótów klawiszowych w Ubuntu, napisałem jedno w python:

Oto link do skryptu

Eksport pobiera ustawienia z systemu. Zasadniczo zawiera listę wszystkich lokalizacji skrótów klawiszowych zapisanych na stałe w słowniku w skrypcie. Skrypt wylicza listę i uruchamia polecenie „gconftool-2 --get [lokalizacja]” dla każdego klucza i zapisuje wartość w słowniku wraz z kluczem. Następnie, gdy określisz lokalizację do zapisania ustawień, zapisuje słownik w pliku w formacie json.

Skrypt importu odwraca ten proces. Ładuje słownik z pliku json. Następnie wylicza je i uruchamia polecenie „gconftool-2 --type string --set [lokalizacja] [wartość]”, aby przywrócić wszystkie zapisane ustawienia.

Jeden strzał na każdym końcu i zapisuje / przywraca każdy pojedynczy skrót klawiaturowy bez dotykania żadnego z pozostałych ustawień konfiguracji systemu.

Jedyne zależności dla tych skryptów to:

  • python (przetestowany i działający w wersjach 2.6, 2.7 i 3.1)
  • gconftool-2 (dostarczany standardowo z instalacją Ubuntu)
  • zenity (dostarczany standardowo z instalacją Ubuntu)

Do wykonania skryptu potrzebny jest Python, gconftool-2 służy do pobierania / ustawiania ustawień, zenity jest potrzebne do okien dialogowych ładowania / zapisywania plików GUI.

Utworzyłem wpis w Ubuntu Brainstorm i robię postępy, aby wprowadzić tę funkcję do menu GUI „właściwości gnome-keybinding-Właściwości”.

Aktualizacja:

Zaktualizowałem połączenie skryptów importu i eksportu w jeden, dodałem pełną funkcjonalność wiersza poleceń (w tym --help info) i uczyniłem ją kompatybilną zarówno dla python2x, jak i python3k. Dodano także link do pomysłu na Ubuntu Brainstorm.

Evan Plaice
źródło
Brainstorm nie jest dobrym miejscem na faktyczne ulepszenia Ubuntu - tylko 10 najważniejszych problemów w rzeczywistości przyciąga uwagę programistów. Sugeruję, abyś znalazł stronę Launchpad gnome-keybinding-propertiesi opublikował łatkę ze swoim skryptem.
Oxwivi,
Twój skrypt jest dobry dla skrótów wymienionych w / obsługiwanych przez gconftool-2 / gconf-editor ... i przypuszczam, że zależy to od tego, co nazywa się skrótem klawiaturowym GNOME ... ale nie rozpoznaje dodanych skrótów użytkownika dla całego systemu przez Keyboard Shortcutsnp. gnome-keybinding-properties... ani innych Xbindkeysskrótów klawiszowych dodanych na przykład przez ... więc podejrzewam, że gconf nie jest tam, gdzie są „przechowywane” skróty w całym systemie, ale że jest to interfejs do czegoś / gdzieś głębiej ... (I szukałem tego miejsca .. :). może po prostu muszę teraz zachować 3 listy „wyeksportowane” ...
Peter.O,
@ fred.bear Jestem prawie pewien, że wszystkie są przechowywane w gconf, ale odkrywam, że nowe właściwości klawiszy są dodawane do właściwości gnome-keybinding-po zmianie domyślnych ustawień w panelu sterowania. Bieżący skrypt wykona domyślne skróty znalezione w GUI, ale nie będzie w stanie obsłużyć wszystkich skrótów bez ściślejszej integracji z GUI. Obecnie jest już otwarty plan dla tego, więc próbuję skontaktować się z innym programistą, który zaproponował to, aby opracować szczegóły na starterze. Na razie ... to działa.
Evan Plaice
3

W 11.10 z uruchomionym Gnome classic znalazłem zestaw katalogów (Custom0, Custom1 ...) pod

$HOME/.gconf/desktop/gnome/keybindings

Skopiowałem te katalogi do tego samego folderu w czystej instalacji 12.04 (ponownie działającej z rezerwową wersją Gnome), wylogowałem się i zalogowałem ponownie. Skróty klawiszowe zostały nieco popsute podczas przejścia (coś dziwnego stało się z modyfikatorem SUPER), ale poza tym były.

EntropyReduction
źródło
2

Istnieje niewielki problem z zaakceptowaną odpowiedzią, polegający na tym, że nie obsługuje ona niestandardowych poleceń z cudzysłowami. Zmieniłem tylko przetwarzanie poleceń niestandardowych, aby wygenerować prawidłowe dane wyjściowe.

#!/usr/bin/perl

use strict;

my $action = '';
my $filename = '-';

for my $arg (@ARGV){
    if ($arg eq "-e" or $arg eq "--export"){
        $action = 'export';
    } elsif ($arg eq "-i" or $arg eq "--import"){
        $action = 'import';
    } elsif ($arg eq "-h" or $arg eq "--help"){
        print "Import and export keybindings\n";
        print " -e, --export <filename>\n";
        print " -i, --import <filename>\n";
        print " -h, --help\n";
        exit;
    } elsif ($arg =~ /^\-/){
        die "Unknown argument $arg";
    } else {
        $filename = $arg;
        if (!$action){
            if ( -e $filename){
                $action='import';
            } else {
                $action='export';
            }
        }
    }
}

$action='export' if (!$action);
if ($action eq 'export'){
    &export();
} else {
    &import();
}

sub export(){
    my $gsettingsFolders = [
        ['org.gnome.desktop.wm.keybindings','.'],
        ['org.gnome.settings-daemon.plugins.power','button'],
        ['org.gnome.settings-daemon.plugins.media-keys','.'],
    ];

    my $customBindings = [
    ];

    $filename = ">$filename";
    open (my $fh, $filename) || die "Can't open file $filename: $!";

    for my $folder (@$gsettingsFolders){
        my @keylist = split(/\n/, `gsettings list-recursively $folder->[0]`);
        foreach my $line (@keylist){
            if ($line =~ /^([^ ]+) ([^ ]+)(?: \@[a-z]+)? (.*)/){
                my ($path, $name, $value) = ($1,$2,$3);
                if ($name eq "custom-keybindings"){
                    $value =~ s/[\[\]\' ]//g;
                    my @c = split(/,/, $value);
                    $customBindings = \@c;
                } elsif ($name =~ /$folder->[1]/){
                    if ($value =~ /^\[|\'/){
                        if ($value =~ /^\[\'(?:disabled)?\'\]$/){
                            $value = '[]';
                        } 
                        print $fh "$path\t$name\t$value\n";
                    }
                }        
            } else {
                die "Could note parse $line";
            }
        }
    }   

    for my $folder (@$customBindings){
        my $gs = `gsettings list-recursively org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:$folder`;
        my ($binding) = $gs =~ /org.gnome.settings-daemon.plugins.media-keys.custom-keybinding binding (\'[^\n]+\')/g;
        my ($command) = $gs =~ /org.gnome.settings-daemon.plugins.media-keys.custom-keybinding command (\'[^\n]+\')/g;
        my ($name) = $gs =~ /org.gnome.settings-daemon.plugins.media-keys.custom-keybinding name (\'[^\n]+\')/g;
        $command =~ s/\"/\\\"/g;
        $command =~ s/^'(.*)'$/$1/g;
        $command =~ s/\'/\'\\\'\'/g;
        $command = "\'$command\'";
        print $fh "custom\t$name\t$command\t$binding\n"    
    }

    close($fh);
}

sub import(){

    $filename = "<$filename";
    open (my $fh, $filename) || die "Can't open file $filename: $!";

    my $customcount=0;

    while (my $line = <$fh>){
        chomp $line;
        if ($line){
            my @v = split(/\t/, $line);
            if (@v[0] eq 'custom'){
                my ($custom, $name, $command, $binding) = @v;
                print "Installing custom keybinding: $name\n";
                print `gsettings set org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$customcount/ name \"$name\"`;
                print `gsettings set org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$customcount/ command \"$command\"`;
                print `gsettings set org.gnome.settings-daemon.plugins.media-keys.custom-keybinding:/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$customcount/ binding \"$binding\"`;
                $customcount++;
            } else {
                my ($path, $name, $value) = @v;
                print "Importing $path $name\n";
                print `gsettings set \"$path\" \"$name\" \"$value\"`;
            }
        }       
    }
    if ($customcount > 0){
        my $customlist = "";
        for (my $i=0; $i<$customcount; $i++){
            $customlist .= "," if ($customlist);
            $customlist .= "'/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom$i/'";            
        }
        $customlist = "[$customlist]";
        print "Importing list of custom keybindings.\n";
        print `gsettings set org.gnome.settings-daemon.plugins.media-keys custom-keybindings \"$customlist\"`;
    }

    close($fh);
}
Jordan Weitz
źródło
Doskonała pierwsza odpowiedź na AskUbuntu! Gratulacje!
Fabby,
Zintegrowałem twoje zmiany z zaakceptowaną odpowiedzią.
Stephen Ostermiller