This post discusses my present thinking about key handling.

I have abandoned the keys branch and created a new keys2 branch.  The keys2 
branch is a clean start, based on devel.  The only survivor from the keys 
branch is a simplified eventFilter that should work *exactly* as before. 
That code has been merged to devel.

I have closed #858 <>, 
based on a faux-Eureka 
<>, and 
started work on #423 <>, 
whose goal is to improve g.KeyStroke. Here is my plan:

*Improve g.KeyStroke*

As #423 <> says, 
g.KeyStroke should be more than a wrapper around a string. The ks.s ivar is 
evil and will be replaced by at two or more ivars:

*ks.mods*: a list of (string modifiers), for example, ['alt', 'shift'].

ks.mods will collapse the complexity of code throughout Leo. No more 
confusion about order of mods, or their spelling, or the separators between 
them. No more confusion about what the non-modifier part of the stroke is.

*ks.char*: a unicode character.

Perhaps ks.char should contain only *visible* characters.  In that case, 
one or more ivars must represent...

- Control (that is, non-visible) characters, like ctrl-s or Alt-1.
- Quasi control characters like Home and End.
- (Maybe) Strange key combinations on various keyboards.

There must be some way to create a g.KeyStroke from user key bindings. 
Details fuzzy, and not too important here.

*Simplify handling of Qt key events*

Simplifying filter.eventFilter was a good start. The next step will be to 
simplify the code in the "filter.Key construction" tree.

Much complexity is unavoidable, because of the inherent difficulty in 
deciphering what the dashed QKeyEvent actually means. Happily, room for 
improvement definitely exists:

- A better g.KeyStroke class will avoid some complications.
- Moving some dicts out of so they are defined where used may 
also help.
- As always, refactoring may help.

This work should help clarify exactly what the ivars of g.KeyStroke should 
actually be.

*Clarify names*

Bad names create needless confusion.  Here are some plans:

The name "shortcut" means too many things, so it means nothing at all. I 
want to kill off as many uses of "shortcut" as possible.  

The names "ch" and "char" are also problematic.  The new code should 
probably use names for temp vars that correspond to g.KeyStroke ivar names. 
Naturally, that requires that I figure out what the g.KeyStroke ivars 
actually mean ;-)

The name "stroke" should *always* refer to a g.KeyStroke.

At present, the "event" name refers both to LeoKeyEvent objects and Qt 
QKeyEvent objects. I am considering using the name "key_event" in 
k.masterKeyHandler in its many helpers.  We shall see whether this makes 

I'll rename g.ShortcutInfo to something like g.BindingInfo.  The docstring 
for this class is:

    A class representing any kind of key binding line.
    This includes other information besides just the KeyStroke.

At present, "si" refers a g.ShortcutInfo. This name is not used all that 
often, so it should have a longer name, say binding_info.

*Improve style without changing classes*

Yesterday's work showed me that I have been grossly misunderstood the 
g.TypedDict and g.TypedDictOfLists classes. For a long time I have thought 
there was something not quite right (un-pythonic) about these classes.  But 
no, they are just dicts, with additional features. 

What *is* "not quite right" about these classes are all the assertions 
involving them. Those assertions are ugly, sclerotic and unpythonic.  We 
don't typically worry about other dicts.  Why should we worry about these 
dicts? These assertions are ironic, because these dicts do type checking!

We can, and should, replace assertion on g.TypedDict and g.TypedDictOfLists 
with better names and naming conventions.  That's *all* that needs to be 

Yes, these classes could be implemented as subclasses of dict, but there is 
no need or advantage in doing so.


The so-called Eureka 
<> was 
misguided. It is the g.KeyStroke class that should be improved, not the 
LeoKeyEvent class.

Adding ivars to g.KeyStroke will collapse code throughout Leo. These 
changes may have side effects. The g.new_keys switch will, as before, 
protect the old code from the new.

Clearer names should make the code easier to understand.

The g.TypedDict and g.TypedDictOfLists classes are fine as they are, but 
there is no need for asserts involving them.


P. S.  Note to myself.  Don't ever again use the word "Eureka" :-)


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 post to this group, send email to
Visit this group at
For more options, visit

Reply via email to