​​On Thu, Sep 24, 2015 at 10:58 AM, john lunzer <[email protected]> wrote:

I'm finding myself stumped by the KeyHandler class. One thing that the
> autocomplete Qt popup doesn't handle right now is PgUp and PgDown, both of
> these keybinding exit the popup. I was trying to fix this but I'm having
> difficulty figuring out where to do this.
>
> Any guidance would be much appreciated.
>

​No doubt about it, key handling is complex.  I never remember the
details.

Here is how I found the interesting code.  I recommend variations of this
technique to find relevant code.

1. I started with the gui *independent* code in leoPy.leo#Code-->Gui base
classes-->@file leoKeys.py-->class AutoCompleterClass​

2. I knew there was an ivar that tells whether to use inline completion or
a Qt popup. I found the use_qcompleter ivar in the ctor.  Searching for
usages of that ivar, I eventually found ac.show_completion_list, which has
this code:

    if self.use_qcompleter:
        # Put the completions in the QListView.
        if self.qw:
            self.qw.show_completions(tabList)

​3. The qw ivar is the Qt-related widget​, so I searched for "def
show_completions".  I found this class:

leoPy.leo#re: qt completer-->class LeoQListWidget(QListWidget)

Now we're getting somewhere :-)

BTW, I could have found this class another way.  I knew that this
Qt-related class existed somewhere in this tree: leoPy.leo#Code-->Qt gui,
but I had forgotten which file.  So an alternate way of finding this class
would have been to look for all the classes in the Qt-related tree, that is
leoPy.leo#Code-->Qt gui

Anyway, the relevant method of the LeoQListWidget class is:

    def keyPressEvent(self, event):
        '''Handle a key event from QListWidget.'''
        trace = False and not g.unitTesting
        c = self.leo_c
        w = c.frame.body.wrapper
        qt = QtCore.Qt
        key = event.key()
        if event.modifiers() != qt.NoModifier and not event.text():
            # A modifier key on it's own.
            pass
        elif key in (qt.Key_Up, qt.Key_Down):
            QtWidgets.QListWidget.keyPressEvent(self, event)
        elif key == qt.Key_Tab:
            if trace: g.trace('<tab>')
            self.tab_callback()
        elif key in (qt.Key_Enter, qt.Key_Return):
            if trace: g.trace('<return>')
            self.select_callback()
        else:
            # Pass all other keys to the autocompleter
            # via the event filter.
            w.ev_filter.eventFilter(obj=self, event=event)

So this is where the change should be made.  *Important*: the default
eventFilter method, that is, LeoQtEventFilter.eventFilter, is insanely
complicated.  Don't change it!  So you have to special case PageUp and
PageDown in lqlw.keyPressEvent.

To repeat, I *never *try to remember implementation details.  I had
forgotten that LeoQListWidget.keyPressEvent event existed.  The only things
I knew at the start was:

1. The gui-independent autocompleter in @file leoKeys.py-->class
AutoCompleterClass​
 has one or more ivars that would tell when to use Qt popup completions
rather than inline completions.

2. There was a Qt-specific class that handles Qt popup completions. This
class is defined somewhere in the tree whose root is leoPy.leo#Code-->Qt
gui.

3.
​Changing LeoQtEventFilter.eventFilter should be a last resort.

HTH. Please feel free to ask more questions.

Edward

-- 
You received this message because you are subscribed to the Google Groups 
"leo-editor" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
Visit this group at http://groups.google.com/group/leo-editor.
For more options, visit https://groups.google.com/d/optout.

Reply via email to