一.某MFC开发代码:
BEGIN_MESSAGE_MAP(CHWDetectDlg, CDialog)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_MESSAGE(WM_DEVICECHANGE, OnMyDeviceChange)
//}}AFX_MSG_MAP
ON_WM_CONTEXTMENU()
ON_COMMAND(ID_POPUP_DISABLE, OnPopupDisable)
END_MESSAGE_MAP()
//-----------处理函数---------------
LRESULT CHWDetectDlg::OnMyDeviceChange(WPARAM wParam, LPARAM lParam)
{
if ( DBT_DEVICEARRIVAL == wParam || DBT_DEVICEREMOVECOMPLETE == wParam ) {
PDEV_BROADCAST_HDR pHdr = (PDEV_BROADCAST_HDR)lParam;
PDEV_BROADCAST_DEVICEINTERFACE pDevInf;
PDEV_BROADCAST_HANDLE pDevHnd;
PDEV_BROADCAST_OEM pDevOem;
PDEV_BROADCAST_PORT pDevPort;
PDEV_BROADCAST_VOLUME pDevVolume;
switch( pHdr->dbch_devicetype ) {
case DBT_DEVTYP_DEVICEINTERFACE:
pDevInf = (PDEV_BROADCAST_DEVICEINTERFACE)pHdr;
UpdateDevice(pDevInf, wParam);
break;
case DBT_DEVTYP_HANDLE:
pDevHnd = (PDEV_BROADCAST_HANDLE)pHdr;
break;
case DBT_DEVTYP_OEM:
pDevOem = (PDEV_BROADCAST_OEM)pHdr;
break;
case DBT_DEVTYP_PORT:
pDevPort = (PDEV_BROADCAST_PORT)pHdr;
break;
case DBT_DEVTYP_VOLUME:
pDevVolume = (PDEV_BROADCAST_VOLUME)pHdr;
break;
}
}
return 0;
}
二.说明
WM_DEVICECHANGE的使用方式有二種,一種是透過WindowProc()的方式,一種是直接在程式裡加上OnDeviceChange()的函數,底下就先介紹第二種方式。
1. 新增消息 -- 在Dialog的.cpp裡加上藍色部份:
BEGIN_MESSAGE_MAP(CDeviceMonitorDlg, CDialog)
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
//}}AFX_MSG_MAP
ON_WM_DEVICECHANGE()
END_MESSAGE_MAP()
注意:不添加新增消息,就不能响应OnDeviceChange函数
2.新增一個函數 -- 這是Microsoft所提供的函數型態
DECLARE_MESSAGE_MAP()
public:
afx_msg BOOL OnDeviceChange(UINT nEventType,DWORD_PTR dwData);
3.函数內容的实现
下面是以USB插入响应为例
BOOL CCLMemTestDlg::OnDeviceChange( UINT nEventType, DWORD_PTR dwData )
{
switch(nEventType)
{
case DBT_DEVICEARRIVAL:
UpdateUsbDeviceList();
break;
case DBT_DEVICEREMOVECOMPLETE:
UpdateUsbDeviceList();
UpdateWindow();
break;
}
return TRUE;
}
三.
串口热拔插监听
关于串口热拔插监听,请更多地参考
《Qt中捕获Windows消息》
《USB转串口突然拔出检测解决方案》
《USB设备监控深入分析》
代码
- #include <dbt.h>
-
- bool WndTest::winEvent( MSG * message, long * result )
- {
- if( WM_DEVICECHANGE == message->message ){
- }
- else
- goto ev_out;
-
- if( 0x8004 == message->wParam ){
- DEV_BROADCAST_PORT *vol = (DEV_BROADCAST_PORT*)message->lParam;
- QString str = QString::fromWCharArray(vol->dbcp_name); //获取要处理的串口名称
-
- if( 3 != vol->dbcp_devicetype )
- goto ev_out;
-
- if( m_serial ){
- if( str.size() > 0 ){
- if( str.compare(cbComPort->currentText()) ==0 && m_connected ){ //比较串口名称,判定是否为当前使用的串口
- closeport(); //关闭串口
- qDebug()<<"close port:"<<str;
- }
- }
- }
- }
- if( 0x8000 == message->wParam ){
- DEV_BROADCAST_PORT * vol = (DEV_BROADCAST_PORT*)message->lParam; //DEV_BROADCAST_VOLUME
- QString str = QString::fromWCharArray(vol->dbcp_name);
- if( str.size() > 0 ){
- qDebug()<<"to open port:"<<str; //在DEBUG信息中输出要处理的串口名称
- }
-
- }
- ev_out:
- return false;
- }