Variable "allowed keys" for keyboard component won't translate to Javascript

I have a full working experiment in pschoPy, but I am getting an error when I try to generate any javascript. I have tracked the problem down to using a variable name in the “allowed keys” field of a keyboard component. I can successfully generate the javascript if I replace the variables with manually specified keys, but lose important functionality for my experiment.

The problem and error message (repasted below) seem to be the same as in this post from 2021, however that thread says it should have been patched in a much earlier release. I am running v.2024.2.2 on Mac OS 13.2.1.

Error message:

Traceback (most recent call last):
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/experiment/components/keyboard/init.py”, line 409, in writeFrameCodeJS
File “”, line 1, in
NameError: name ‘key1’ is not defined

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/app/builder/builder.py”, line 894, in fileExport
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/scripts/psyexpCompile.py”, line 83, in generateScript
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/scripts/psyexpCompile.py”, line 221, in compileScript
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/scripts/psyexpCompile.py”, line 194, in _makeTarget
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/experiment/_experiment.py”, line 422, in writeScript
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/experiment/routines/_base.py”, line 903, in writeEachFrameCodeJS
File “/Applications/PsychoPy.app/Contents/Resources/lib/python3.8/psychopy/experiment/components/keyboard/init.py”, line 411, in writeFrameCodeJS
psychopy.experiment.utils.CodeGenerationException: choice_2:

key1 is the name of one of the variables in the “allowed keys” field (specified as key1, key2) and choice_2 is the name of the keyboard component in question.

Thanks in advance for any help!

Hello

I get the error message in version 2024.1.4 that

Variables for allowKeys aren’t supported for JS yet:

Perhaps this has been solved in the meantime. Trying the newest PsychoPy-version might be worth a shot.

Best wishes Jens

Hi Jens,

Thanks for the response! That’s a big bummer. I only downloaded psychopy a couple weeks ago so I should be up to date.

Do you know of any workarounds? In our experiment there are some trials where only one of two components appear on the screen and we want to make it such that the user can only select the component on the screen and cannot press the button for the component that doesn’t appear on these trials.

Thanks,

Catrina

Hello

you probably need some code to achieve that. Do not let the keyboard end the routine and add a code-component checking each frame for the key to end the routine.

Best wishes Jens

1 Like

In case anybody else encounters this issue, I sidestepped it by adding a few lines to the “each frame” part of a custom code component that comes after my keyboard component (which no longer force ends routine). The keyboard component allows all possible keys for any kind of trial and the below custom code checks the keys pressed and compares them to variables for allowable keys that I set myself.

keys = event.getKeys()
userChoice = keys[-1]
if userChoice == key1 or userChoice == key2:
    continueRoutine = False

key1 and key2 are variables I set in a custom code component at the beginning of each routine to define which keys are allowable on a given trial.

If you want to use event.getKeys() as your solution I would recommend disabling your keyboard component.

My preferred code would be (for a keyboard component called key_resp):

if key_resp.keys:
     if key1 in key_resp.keys or key2 in key_resp.keys:
          continueRoutine = False

Thanks! Can you explain why it’s best to use this solution as opposed to calling event.getKeys() if I leave the keyboard component in?

Is the keyboard component doing anything?

I think that the biggest issue is if the keyboard component below the code component (I normally recommend code components go at the top) in which case the keyboard would only “see” keys pressed after event.keys and before the keyboard component (not very long at all).

The keyboard component has better accuracy than event.keys (which is based on older code).

Got it, thanks. Following your recommendation I will keep the keyboard component and swap in the code you’ve suggested in place of event.getKeys().

Much appreciated!