PTB-WARNING:在 PsychHID 调用期间:其他 运行 应用程序阻止我访问 keyboard/keypad/mouse/

PTB-WARNING: During PsychHID invocation: Some other running application is preventing me from accessing the keyboard/keypad/mouse/

我在 Python 中使用 Psychopy 模块。我的代码调用 waitKeys(...) 来获取按键和反应时间。 90% 的时间它运行完美,但偶尔当我启动它时我得到这个(正是这个,不是无限重复):

PTB-WARNING: During PsychHID invocation: Some other running application is preventing me from accessing the keyboard/keypad/mouse/...!
PTB-WARNING: This is likely a security measure, e.g., to protect some active password entry field.
PTB-WARNING: Please identify and quit the offending application. E.g., some versions of Firefox are known to cause such problems...
PTB-WARNING: During PsychHID invocation: Some other running application is preventing me from accessing the keyboard/keypad/mouse/...!
PTB-WARNING: This is likely a security measure, e.g., to protect some active password entry field.
PTB-WARNING: Please identify and quit the offending application. E.g., some versions of Firefox are known to cause such problems...
PTB-WARNING: During PsychHID invocation: Some other running application is preventing me from accessing the keyboard/keypad/mouse/...!
PTB-WARNING: This is likely a security measure, e.g., to protect some active password entry field.
PTB-WARNING: Please identify and quit the offending application. E.g., some versions of Firefox are known to cause such problems...
PTB-WARNING: During PsychHID invocation: Some other running application is preventing me from accessing the keyboard/keypad/mouse/...!
PTB-WARNING: This is likely a security measure, e.g., to protect some active password entry field.
PTB-WARNING: Please identify and quit the offending application. E.g., some versions of Firefox are known to cause such problems...
PTB-WARNING: During PsychHID invocation: Some other running application is preventing me from accessing the keyboard/keypad/mouse/...!
PTB-WARNING: This is likely a security measure, e.g., to protect some active password entry field.
PTB-WARNING: Please identify and quit the offending application. E.g., some versions of Firefox are known to cause such problems...

毫不奇怪,它不会响应我的任何击键,只会响应 control-C。

我只是 运行 终端(启动脚本),Xcode(编辑 python 脚本)和 Safari,只打开了几个普通网站(stackoverlow.com、discourse.psychopy.org 和 google.com 用于搜索)。我可以停止此行为的唯一方法是注销然后重新登录。关闭终端 window 并打开一个新终端并不能解决问题。从终端退出并重新启动它并不能解决问题。退出所有 运行 应用程序然后重新启动终端无法解决问题。

有时,当它发生时,我会在下次启动时发生这种情况之前用 control-C 退出应用程序。因此,也许 Psychopy 仍在后台留下一些孤立的线程 运行,来自之前的脚本调用,并且该线程尚未放弃其对键盘的要求?我怎么知道?我该如何在我的代码中解决这个问题?

相关代码如下:

**from** psychopy **import** prefs
prefs.hardware['audioLib'] = ['PTB']  # Prepare to use the right audio backend before importing sound
latencyMode = 4    # For PTB. 0, 1, 2, 3, 4
prefs.hardware['audioLatencyMode'] = [str(latencyMode)]
from psychopy.sound.backend_ptb **import** SoundPTB
from psychopy.hardware **import** keyboard
kb = keyboard.Keyboard() # Set up a keyboard device
targetAudio = SoundPTB(listFiles[thisAudioIndex])
targetAudio.play()
 keys = kb.waitKeys(keyList = ["return", "space", "down", "right"],
                           waitRelease=False)
targetAudio.stop()

2017 款 MacBook Pro,使用内置键盘。 macOS 11.4,Python 3.8。 我还在 discourse.psychopy.org

上发布了这个

已解决(有点!)。

出于 UI 原因,我阻止了在实验期间键入的键被回显到屏幕(否则屏幕会充满随机垃圾)。我通过将 stty -echo 发送给父 shell.

来做到这一点

但是当退出程序时(出于任何原因)我需要通过发送 stty echo 来撤消它。所以我设置了一个退出处理程序:

def onExit():
    """Restore keystroke echo when we exit"""
    os.system('stty echo')

但是如果用户键入 control-C 那么这样的退出处理程序将不会被执行,所以我还必须捕获 control-C:

def captureControl_C(signum, frame):
    """If user types control-c, restore keystroke echo before quitting"""
    # Restore the original signal handler, otherwise evil things will happen
    # if CTRL+C is pressed while we are already here, e.g. "c" key bounced
    signal.signal(signal.SIGINT, originalSigintHandler)
    os.system('stty echo')
    raise KeyboardInterrupt # So we still see the stack trace on the screen

详情见here

这给我们带来了问题。我连接上面的退出处理程序并在 __main__:

中使用以下 3 行进行陷阱
os.system('stty -echo') # Stop any echo of keystrokes to the Terminal window.
atexit.register(onExit) # Restore keyboard echo when quitting
#
# BUT if user types control-c, then restore keyboard echo!
# Otherwise the Terminal window looks unresponsive.
#
originalSigintHandler = signal.signal(signal.SIGINT, captureControl_C)

当这 3 行在 __main__ 中时,一切都完美无缺。但后来我将它们转移到一个从 main 调用的函数 initialSetup() 中。为此,我当然必须先于他们

global originalSigintHandler # So that captureControl_C() can see it

将关键的 3 行移动到 initialSetup() 导致对 waitKeys() 的后续调用挂起,并在我最初的 post 中出现所有这些警告。将它们移回 __main__ 修复了它。

如果有人能解释原因,我会很高兴。