Pywinusb:处理来自多个键盘的事件

qlt*_*qlt 5 python pywinusb

我正在尝试处理来自多个 USB 键盘的事件,以便代码知道输入来自哪个键盘。该代码通过设备实例 ID 识别不同的键盘(它们都具有相同的产品和供应商 ID),但不识别用户输入的来源(它只是在它们之间切换)。

这对于 pywinusb 来说是可能的吗?我尝试使用事件处理程序但没有运气。

from time import sleep
from msvcrt import kbhit

import pywinusb.hid as hid

# feel free to test
target_vendor_id = 0xffff
target_product_id = 0x0035

def sample_handler(data):
    print("Raw data: {0}".format(data))

def getinput(data, id):
    print data
    print id
    if(id == "8&2754010&0&0000" and data == "09008708"):
        print "Success"
    else:
        print "Failed"

def raw_test():

   # example, handle the HidDeviceFilter().get_devices() result grouping items by parent ID
   all_hids = hid.HidDeviceFilter(vendor_id = target_vendor_id, product_id = target_product_id).get_devices()
   #print all_hids
   if all_hids:
       while True:
           for index, device in enumerate(all_hids):
               result = device.instance_id.split('\\')[-1]
               try:
                   device.open()
                   getinput(raw_input(), result)
               finally:
                   device.close()

if __name__ == '__main__':
    # first be kind with local encodings
    import sys

    if sys.version_info >= (3,):
       # as is, don't handle unicodes
       unicode = str
       raw_input = input
    else:
       # allow to show encoded strings
       import codecs
       sys.stdout = codecs.getwriter('mbcs')(sys.stdout)
    raw_test()
Run Code Online (Sandbox Code Playgroud)

Von*_*onC 0

在您的代码中,有一个循环遍历所有 HID 设备(键盘,在本例中是来自rene-aguirre/pywinusb HidDevice,并一一打开它们以检查输入:

for index, device in enumerate(all_hids):
    result = device.instance_id.split('\\')[-1]
    try:
        device.open()
        getinput(raw_input(), result)
    finally:
        device.close()
Run Code Online (Sandbox Code Playgroud)

该循环打开每个设备,等待输入 ( raw_input()),然后关闭设备。它对 中的每个设备重复此过程all_hids

它按顺序一个接一个地访问设备。因此它一次只能监听一台设备。每个设备都会打开,等待单个输入,然后关闭。没有对每个键盘进行连续监控。
使用设备实例 ID 和用户输入调用该getinput函数,但这是在同一循环内完成的,不允许您区分来自不同键盘的输入。

因此,您的问题是:您的代码通过设备实例 ID 识别不同的键盘,但无法实时识别输入来自哪个特定键盘。


from time import sleep
import pywinusb.hid as hid

target_vendor_id = 0xffff
target_product_id = 0x0035

# Handler to process the data
def sample_handler(data, device_instance_id):
    print(f"Data from {device_instance_id}: {data}")

# Function to open devices and assign handlers
def raw_test():
    all_hids = hid.HidDeviceFilter(vendor_id=target_vendor_id, product_id=target_product_id).get_devices()
    if all_hids:
        for device in all_hids:
            device_instance_id = device.instance_id.split('\\')[-1]
            try:
                device.open()
                # Set the handler for the device
                device.set_raw_data_handler(lambda data, id=device_instance_id: sample_handler(data, id))
            except IOError as e:
                print(f"Could not open the device: {e}")

        # Keep the script running
        print("Press Ctrl+C to stop")
        try:
            while True:
                sleep(0.1)
        except KeyboardInterrupt:
            pass
        finally:
            for device in all_hids:
                device.close()

if __name__ == '__main__':
    raw_test()
Run Code Online (Sandbox Code Playgroud)

这将打开每个设备并设置一个包含设备实例 ID 的处理程序。当接收到数据时,sample_handler将使用数据和数据来源设备的 ID 来调用。
处理程序保持活动状态并持续侦听专门来自其指定键盘的输入:您的代码可以区分来自不同键盘的输入。

device.set_raw_data_handler(lambda data, id=device_instance_id: sample_handler(data, id))
Run Code Online (Sandbox Code Playgroud)

每个设备保持打开状态,并且其处理程序保持活动状态:持续监视每个键盘的输入。
当输入事件发生时,会触发相应的处理程序。由于每个处理程序都知道device_instance_id其键盘的键盘,因此它可以立即识别并报告输入来自哪个键盘。

def sample_handler(data, device_instance_id):
     print(f"Data from {device_instance_id}: {data}")
Run Code Online (Sandbox Code Playgroud)

用于device_instance_id识别输入数据的源键盘。