2

我正在开发一个 C# 程序,以便在插入设备后立即检索设备的信息。

我想问有没有什么方法可以根据WM_DEVICECHANGE设备插入/拔出时触发的事件来获取设备的信息(名称、id、...)。

我尝试查看WM_DEVICECHANGE的参数,但其中没有包含有关设备的信息。

提前致谢。

4

1 回答 1

0

我刚刚在这里回答了类似的问题:https ://stackoverflow.com/a/57182910/1886251

以下是您需要执行的详细信息:

要通过WM_DEVICECHANGE获取设备信息,您需要使用正确填充的DEV_BROADCAST_DEVICEINTERFACE_W结构调用 user32.dll 中名为RegisterDeviceNotification的 Win32 API 。

如果这样做正确,您将收到WM_DEVICECHANGE消息,其中包含设备管理事件中描述的事件类型(在我们的例子中为DBT_DEVICEARRIVAL ) ,以及指向详细信息的指针。需要将指针作为DEV_BROADCAST_HDR结构读取,以便您识别这是否确实是DEV_BROADCAST_DEVICEINTERFACE_W结构。如果是这样,这个结构将包含一个设备名称,您需要在它包含 VID 和 PID 时对其进行解析。

这需要处理很多,我花了几个小时才把它弄好。如果您需要一个快速的解决方案,并跳过实现可怕的细节,将 NuGet 包Dapplo.Windows.Messages(VID 和 PID 可用于 0.9.7 及更高版本)添加到您的项目并在 Windows 窗体或 WPF 中使用以下代码应用:

    var deviceNotificationSubscription = DeviceNotification
        .OnDeviceArrival()
        .Subscribe(deviceInterfaceChangeInfo => {
            // Your code goes here, and will be automatically called
            var vid = deviceInterfaceChangeInfo.Device.VendorId;
            var pid = deviceInterfaceChangeInfo.Device.ProductId;
        });

我的库高度依赖System.Reactive,我不会在这里详细介绍,它允许为您的应用程序提供更实用的方法。您可以通过调用库创建它自己的隐藏消息窗口来接收窗口消息来停止接收事件deviceNotificationSubscription.Dispose();,因此您甚至可以继续在后台接收信息。

DeviceInterfaceChangeInfo的Device 属性具有DevBroadcastDeviceInterface结构,其中包含原始 Win32 信息,但还具有一些更高级别的属性,例如:

  1. 从注册表中检索的友好名称
  2. 设备类型,如 USB、HID 等,包括 IsUSB
  3. 供应商 ID
  4. 产品编号
  5. 一个DeviceInterfaceClass枚举,用于更轻松地访问类的代码
  6. 生成的 URL 以获取有关设备的更多信息

如果您想知道删除了什么,您还可以注册 OnDeviceRemoved。

让我知道这是否有效并在这里有所帮助,如果您有任何问题,请在我的Dapplo.Windows GitHub 项目上提出问题!这个库中还有很多,但不幸的是大多数文档仍然需要编写。

于 2019-07-24T12:37:28.997 回答