在Windows平台上,使用Qt识别USB设备类型(如U盘、鼠标、打印机)可以通过以下几种方式实现:
1. 使用Windows API + Qt
Qt本身没有直接提供USB设备类型检测的接口,但可以通过调用Windows API获取设备信息,再与Qt结合。
步骤:
- 获取设备信息
使用SetupAPI(设备安装函数)枚举USB设备,获取设备的GUID和设备实例句柄。 - 解析设备属性
通过设备属性(如DeviceDesc、HardwareID、CompatibleIDs)判断设备类型。
示例代码:
#include <windows.h>
#include <setupapi.h>
#include <cfgmgr32.h>
#include <QDebug>
#pragma comment(lib, "setupapi.lib")
void checkUSBDevices() {
HDEVINFO hDevInfo = SetupDiGetClassDevs(NULL, L"USB", NULL, DIGCF_ALLCLASSES | DIGCF_PRESENT);
if (hDevInfo == INVALID_HANDLE_VALUE) return;
SP_DEVINFO_DATA devInfoData;
devInfoData.cbSize = sizeof(SP_DEVINFO_DATA);
for (DWORD i = 0; SetupDiEnumDeviceInfo(hDevInfo, i, &devInfoData); i++) {
WCHAR deviceName[256];
DWORD size = 0;
// 获取设备描述
if (SetupDiGetDeviceRegistryProperty(hDevInfo, &devInfoData, SPDRP_DEVICEDESC, NULL,
(PBYTE)deviceName, sizeof(deviceName), &size)) {
QString desc = QString::fromWCharArray(deviceName).toLower();
// 简单关键词匹配(实际需更精确的规则)
if (desc.contains("storage") || desc.contains("usb drive")) {
qDebug() << "U盘:" << desc;
} else if (desc.contains("mouse")) {
qDebug() << "鼠标:" << desc;
} else if (desc.contains("printer")) {
qDebug() << "打印机:" << desc;
}
}
}
SetupDiDestroyDeviceInfoList(hDevInfo);
}
2. 使用WMI查询(推荐)
WMI(Windows Management Instrumentation)可以更系统地获取硬件信息。
步骤:
- 使用WMI查询
Win32_USBHub、Win32_Keyboard、Win32_Printer等类。 - 通过Qt的
QAxObject调用WMI接口(需启用ActiveQt模块)。
示例代码:
#include <QAxObject>
#include <QDebug>
void queryWMI() {
QAxObject* wmi = new QAxObject("WbemScripting.SWbemLocator");
QAxObject* services = wmi->querySubObject("ConnectServer(QString)", "root\\cimv2");
// 查询存储设备
QAxObject* items = services->querySubObject("ExecQuery(QString)",
"SELECT * FROM Win32_LogicalDisk WHERE DriveType=2");
int count = items->property("Count").toInt();
for (int i = 0; i < count; ++i) {
QAxObject* item = items->querySubObject("ItemIndex", i);
qDebug() << "U盘:" << item->property("DeviceID").toString();
delete item;
}
// 查询鼠标(需管理员权限)
QAxObject* mice = services->querySubObject("ExecQuery(QString)",
"SELECT * FROM Win32_PointingDevice");
count = mice->property("Count").toInt();
for (int i = 0; i < count; ++i) {
QAxObject* item = mice->querySubObject("ItemIndex", i);
qDebug() << "鼠标:" << item->property("Name").toString();
delete item;
}
delete items;
delete mice;
delete services;
delete wmi;
}
3. 使用第三方库(libusb)
通过libusb库直接与USB设备通信,读取设备描述符中的设备类(bDeviceClass)和接口类(bInterfaceClass)。
关键分类码:
0x08: Mass Storage(U盘)0x03: HID(鼠标/键盘)0x07: Printer
注意事项:
- 权限问题
WMI和设备枚举可能需要管理员权限。 - 动态监测
如需实时监测USB热插拔,可监听Windows消息WM_DEVICECHANGE,并在Qt中重写nativeEvent方法。 - 跨平台限制
上述方法仅适用于Windows,Linux需使用udev等机制。
如果需要完整的项目示例或进一步优化,请参考零声教育相关课程中的《Qt高级开发》章节。
内容由零声教学AI助手提供,问题来源于学员提问




