Aceleradores de teclado Python GTK3

0

Estou trabalhando na criação de um aplicativo para o Ubuntu usando Python3 e Gtk3.

Estou tentando adicionar aceleradores de teclado ao programa, mas infelizmente continuo com problemas.

Este é o meu código atm:

#! /bin/python

from gi.repository import Gtk, Gdk

class DeSedit(Gtk.Window):
    def __init__(self):
        Gtk.Window.__init__(self, title="DeSedit")

        self.set_default_size(550, 350)

        # FileChooserDialog - Open File
        dialog = Gtk.FileChooserDialog("Select file to be opened", self,
            Gtk.FileChooserAction.OPEN,
            (Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
            Gtk.STOCK_OK, Gtk.ResponseType.OK))
        # keyboard shortcuts
        accel = Gtk.AccelGroup()
        self.add_accel_group(accel)
        self.add_accelerator(dialog, "<Control>o", signal="open")

        def add_accelerator(self, widget, accelerator, signal="activate"):
            """ adds <Control>o as accelerator for open-file dialog """
            if accelerator is not None:
                key, mod = Gtk.accelerator_parse(accelerator)
            widget.add_accelelator(signal, accel, key, mod, Gtk.AccelFlags.VISIBLE)
            print("works")

        # grid to organize widgets
        self.box = Gtk.Box()
        self.add(self.box)
        # text view
        self.textview = Gtk.TextView()
        self.textview.set_wrap_mode(True)
        # scroll bar
        scrollwindow = Gtk.ScrolledWindow()
        scrollwindow.add(self.textview)

        self.box.pack_start(scrollwindow, True, True, 0)


window = DeSedit()  # create DeSedit object
window.connect("delete-event", Gtk.main_quit)
window.show_all()
Gtk.main()

Eu recebo este erro:

File "file.py", line 41, in 
    window = DeSedit()  # create DeSedit object
  File "file.py", line 19, in __init__
    self.add_accelerator(self.dialog, "o", signal="open")
TypeError: add_accelerator() got an unexpected keyword argument 'signal'
    
por TellMeWhy 01.08.2015 / 21:44

1 resposta

2

O mais provável é que você siga um guia do PyGtk 2 ao tentar implementar isto: De acordo com a documentação do GTK 3, não há nenhuma função chamada gtk_window_add_accelerator , mas existe uma função chamada gtk_accel_group_connect que parece que vai executar o trabalho. Ao trabalhar com a documentação do GTK, normalmente é 80% de intuição e 20% de verificação dos documentos para ver se você está certo. Não espere nenhum tutorial ou guia sofisticado (você ficará desapontado a maior parte do tempo)…

De qualquer forma: olhando para o gtk_accel_group_connect documentação, vemos estes parâmetros: accel_group , accel_key , accel_mods , accel_flags e closure .

Então, como chamar essa função do Python? Vamos fazer isso passo a passo:

  1. Como estamos em Python (linguagem orientada a objetos), podemos esperar que o parâmetro accel_group esteja implícito, já que é o primeiro parâmetro e uma referência ao objeto que estamos tentando modificar.
  2. O próximo parâmetro ( accel_key ) é mais complicado: é um inteiro e a documentação apenas nos diz valor da chave do acelerador que basicamente significa descobrir como encontrar o acelerador valor da chave . Felizmente, algumas pesquisas rápidas revelam a função gdk_keyval_from_name que parece fazer o que queremos. (E chamar Gdk.keyval_from_name('O') na verdade retorna o resultado correto.)
  3. O próximo é o parâmetro accel_mods : clicando em seu tipo ( GdkModifierType ) obtemos uma boa listagem de todos os possíveis tipos de modificadores. Como você queria usar o modificador <Control> , podemos usar apenas Gdk.ModifierType.CONTROL_MASK e seguir em frente.
  4. accel_flags também tem um tipo clicável ( GtkAccelFlags ) e abre sua A descrição revela que nenhum desses parâmetros é necessário, portanto, podemos usar com segurança 0 para esse parâmetro.
  5. Finalmente, estamos no último parâmetro ( closure ): Como closure é apenas uma palavra chique para callback (algo que deve ser chamado quando algo acontece), podemos usar apenas o fato de que as ligações do GTK do Python abstraem fechamentos para nós e e passar algumas funções que podem ser chamadas aqui que são chamadas sempre que <Control>O foi pressionado.

No contexto, o código agora se parece com isso (verificado estar funcionando):

#!/usr/bin/python3

from gi.repository import Gtk, Gdk

class DeSedit(Gtk.Window):
    def __init__(self):
        Gtk.Window.__init__(self, title="DeSedit")

        self.set_default_size(550, 350)

        # FileChooserDialog - Open File
        dialog = Gtk.FileChooserDialog("Select file to be opened", self,
            Gtk.FileChooserAction.OPEN,
            (Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
            Gtk.STOCK_OK, Gtk.ResponseType.OK))
        # keyboard shortcuts
        accel = Gtk.AccelGroup()
        accel.connect(Gdk.keyval_from_name('O'), Gdk.ModifierType.CONTROL_MASK, 0, self.on_accel_pressed)
        self.add_accel_group(accel)

        # grid to organize widgets
        self.box = Gtk.Box()
        self.add(self.box)
        # text view
        self.textview = Gtk.TextView()
        self.textview.set_wrap_mode(True)
        # scroll bar
        scrollwindow = Gtk.ScrolledWindow()
        scrollwindow.add(self.textview)

        self.box.pack_start(scrollwindow, True, True, 0)

    def on_accel_pressed(self, *args):
        dialog = Gtk.FileChooserDialog("Select file to be opened", self,
            Gtk.FileChooserAction.OPEN,
            (Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
            Gtk.STOCK_OK, Gtk.ResponseType.OK))
        dialog.show()


window = DeSedit()  # create DeSedit object
window.connect("delete-event", Gtk.main_quit)

Espero que isso comece com o GTK + 3!

    
por ntninja 01.08.2015 / 23:39