Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

make_key not working; issue with lambda? #573

Closed
dschil138 opened this issue Sep 6, 2022 · 10 comments · Fixed by #578
Closed

make_key not working; issue with lambda? #573

dschil138 opened this issue Sep 6, 2022 · 10 comments · Fixed by #578

Comments

@dschil138
Copy link

when I use the code from the docs (combos page), I get an error:

Traceback (most recent call last):
  File "code.py", line 191, in <module>
  File "kmk/kmk_keyboard.py", line 424, in go
  File "kmk/kmk_keyboard.py", line 477, in _main_loop
  File "kmk/kmk_keyboard.py", line 101, in _handle_matrix_report
  File "kmk/kmk_keyboard.py", line 151, in _on_matrix_changed
  File "kmk/kmk_keyboard.py", line 182, in pre_process_key
  File "kmk/kmk_keyboard.py", line 188, in process_key
  File "kmk/keys.py", line 474, in on_press
TypeError: function takes 0 positional arguments but 4 were given

(in this instance, I am not trying to use it in a combo yet, just assigning KC.MYKEY to a key on my keyboard)

If I do try to use it in a combo, I get a different error:

Traceback (most recent call last):
  File "code.py", line 192, in <module>
  File "kmk/kmk_keyboard.py", line 424, in go
  File "kmk/kmk_keyboard.py", line 484, in _main_loop
  File "kmk/kmk_keyboard.py", line 255, in _process_timeouts
  File "kmk/modules/combos.py", line 153, in <lambda>
  File "kmk/modules/combos.py", line 240, in on_timeout
ValueError: object not in sequence

I attempted to look for a keymap in the repo which used make_key to see if I could use their code and try to make it work. I ended up finding the "shrek_is_love" code (lol) in the Klarank keymap. This code works, in that it will print Shrek's face to my debug console, but it won't actually type anything like an HID keyboard. I attempted to change the print statements to send_string and even simple_key_sequence, but neither worked. The keyboard functions fine, it even registers the keypresses. That key just doesn't type anything.

I also tried incorporating lambda into the shrek code, but receive the same error as before with the code from the docs (but often with different numbers - "takes 4 positional arguments and 5 were given" etc)

So, I can print stuff to the console just fine, but if I try to use it to actually output text using lambda, I get the positional arguments error.

I am not sure if this is a bug or I am simply making a mistake somehow! Any help would be appreciated.

I am using an ItsyBitsy nRF52840 Express

@xs5871
Copy link
Collaborator

xs5871 commented Sep 7, 2022

That sounds like a configuration issue and may be best addressed in matrix/discord chat.

@dschil138
Copy link
Author

I'm not sure I totally understand what you mean by configuration issue, could you be more specific? Like configuration in the OS?

I forgot to mention in the original post that I have made three different KMK keyboards now, with three different MCUs (ItsyBitsy, SeeedStudio nRF, and a wired board with the Pi Pico) and have had this same issue across all the boards.

@kdb424
Copy link
Contributor

kdb424 commented Sep 8, 2022

TLDR: bad code. Feel free to stop by to get real time support in the matrix/discord bridge. Harder to work on when we don't have real time chat.

@dschil138
Copy link
Author

The thing is that I have now stripped almost everything out of my code and it still has the same problem. In general I find Discord servers to be really unhelpful, so before moving there, I just want to post this - if people look at this and tell me this is still something I am doing wrong in my code, I will take it to discord for further help.

Here is my entire code.py file:

print("Starting")

import board
from kb import KMKKeyboard
from kmk.keys import KC, make_key
from kmk.handlers.sequences import simple_key_sequence
from kmk.handlers.sequences import send_string
from kmk.modules.combos import Combos, Chord, Sequence

combos = Combos()

keyboard = KMKKeyboard()
keyboard.modules.append(combos)

keyboard.debug_enabled = True

make_key(
    names=('MYKEY',),
    on_press=lambda: print('I pressed MYKEY'),
)

keyboard.keymap = [
    [
        KC.MYKEY, KC.B,\
        KC.C, KC.D,\
    ],
]

if __name__ == '__main__':
    keyboard.go()

and my entire kb.py file:

import board

from kmk.kmk_keyboard import KMKKeyboard as _KMKKeyboard
from kmk.scanners import DiodeOrientation

class KMKKeyboard(_KMKKeyboard):
    row_pins = (board.GP4, board.GP5,)

    col_pins = (board.GP9, board.GP8,)

    diode_orientation = DiodeOrientation.COL2ROW

I am currently running this on a Pi Pico. Everything works except for KC.MYKEY, which gives me the positional arguments error mentioned above.

@kdb424
Copy link
Contributor

kdb424 commented Sep 8, 2022

Docs have been changed to reflect the problem in #578 Closing for now, but let us know if you have any more issues

@kdb424 kdb424 closed this as completed Sep 8, 2022
@dschil138
Copy link
Author

This fixed the "positional arguments" error for me, but it still just prints the text to the debug console, doesn't output HID text.

In general, should a print statement act like a key? Should running print('a') "type" the same as pressing KC.A? I tried substituting send_string but I get the same behavior. I also tried turning off the debug console, but still no output.

@xs5871
Copy link
Collaborator

xs5871 commented Sep 8, 2022

print is a python builtin and "prints" to standard out, which in this case is the serial console.
Check out our sequences doc if you want macros.

@dschil138
Copy link
Author

I've got a bunch of those, and they work great. But when you use them in conjunction with make_key, they no longer actually type the text. And since the output of a combo must be another key, you have to use make_key to get that sequence to be the output of your combo.

If I want a combo to actually type several letters, how would I do that? Specifically I want a U+Y combo to type "you". The docs seem to suggest this is possible using make_key, but from what I can tell, make_key only can output text to the console - is that the case?

Even ignoring the combo use, just replacing the print statement in make_key with send_string or simple_key_sequence also just outputs the text to the console.

I guess the base question here is: can you use make_key make a key that actually types HID output? or can it only output to the console?

@klardotsh
Copy link
Member

It's possible something has regressed (the sequences section of KMK is practically an easter egg at this point: I wrote it in 2018-19 at some point with almost no docs (oops) and the core of KMK has been refactored a lot since then, so this is probably barely-if-at-all tested), but in general, send_string is what you want. It creates a key object which can be put into a keymap directly, or into TapDance sequences:

HELLA_TD = KC.TD(
KC.A,
KC.B,
send_string('macros in a tap dance? I think yes'),
KC.TG(1),
)

KC.LCTL, KC.DBG, HELLA_TD, xxxxxxx, _______, _______, xxxxxxx, xxxxxxx, KC.MUTE, KC.VOLD, KC.VOLU, xxxxxxx,

@klardotsh
Copy link
Member

Impl of send_string if it helps you (see that it calls a fn that then in turn calls make_key for you. this whole file could do with #205)

def simple_key_sequence(seq):
return make_key(
meta=KeySequenceMeta(seq),
on_press=sequence_press_handler,
on_release=passthrough,
)
def send_string(message):
seq = []
for char in message:
kc = getattr(KC, char.upper())
if char.isupper():
kc = KC.LSHIFT(kc)
seq.append(kc)
return simple_key_sequence(seq)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants