检测 USB OTG 设备何时断开连接

Detect when a USB OTG device disconnects

我有一个与 USB OTG 设备交互的应用程序:

现在,如果我插入 USB 设备,我会得到确认并启动服务,当我拔下设备时,服务会再次停止。到目前为止,还不错。

但是,在某些情况下,即使设备被拔掉,服务仍会保持 运行。我注意到当我连接设备时主 activity 打开时总是会发生这种情况。日志显示 服务从未收到 UsbManager.ACTION_USB_DEVICE_DETACHED 广播

在进行进一步测试时(打开主 activity 并在连接设备之前离开它),我发现证据表明 可能有两个服务实例 运行 出于某种原因。

这里发生了什么,我如何才能可靠地检测到 USB 设备已断开连接?

此行为似乎是由两个因素引起的:

  • 如上所述,该服务不仅在 USB 设备连接时启动,而且在其他事件时启动,例如设备连接到交流适配器或主 activity 打开。在这些情况下,它将寻找蓝牙设备(“自动连接”)并在找到 none 或 USB 设备已连接时退出。
  • 因此,当启用自动连接时,打开主 activity 将始终启动第一个服务实例。如果 USB 设备在 之后 连接,我们可能显然有两个服务实例 运行。我怀疑断开广播可能会被错误的实例接收到。
  • 如果我禁用自动连接,该服务确实会收到断开连接事件但会忽略它,因为设备不被视为相等。然而日志输出显示两个设备的设备路径是相同的。进一步的分析表明,我只是简单地使用 != 来比较两个 UsbDevice 实例,这未能捕获引用同一设备的两个不同 class 实例。

所以我们需要做两件事:

  • 使用 UsbDevice#equals() 而不是相等运算符进行比较。
  • 防止来自 运行 的服务的多个实例。确保在找不到设备时服务退出,并且将 Intent 传递给现有实例而不是启动新实例。