zoukankan      html  css  js  c++  java
  • VC++ 动态检测串口的热插拔(一)通过注册表实现

    在上一篇文章中讲述了如何通过循环遍历的方法获取可用串口,可是这样的方法过于暴力,难免会想有没有其他的办法那,嘿嘿,那是肯定会有的,不管什么问题,解决问题的方法永远都不止一种。下面讲述如何通过注册表来获取可用串口。

    大家都知道,通过设备管理器我们可以看到可用串口号的列表,windows肯定有自己管理各种设备的方法,那就是大家所熟悉的注册表,注册表中记录各种设备信息以及其他重要信息。在HKEY_LOCAL_MACHINE下逐级展开到Hardware\DeviceMap\SerialComm,这里记录的就是串口信息。只要通过简单的注册表读取操作我们就可以得到串口列表。

    这里将展示给大家,通过注册表读取,并将结果展示到列表框中的例子。

    1遍历串口源码如下:

    OnInitDialog中如下:

    BOOL CDetectComDlg::OnInitDialog()
    {
    	CDialog::OnInitDialog();
    
    	ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
    	ASSERT(IDM_ABOUTBOX < 0xF000);
    
    	CMenu* pSysMenu = GetSystemMenu(FALSE);
    	if (pSysMenu != NULL)
    	{
    		CString strAboutMenu;
    		strAboutMenu.LoadString(IDS_ABOUTBOX);
    		if (!strAboutMenu.IsEmpty())
    		{
    			pSysMenu->AppendMenu(MF_SEPARATOR);
    			pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
    		}
    	}
    	SetIcon(m_hIcon, TRUE);			// 设置大图标
    	SetIcon(m_hIcon, FALSE);		// 设置小图标
    
    	DWORD sStyle = m_ListShow.GetExtendedStyle();
    	sStyle |= LVS_EX_GRIDLINES;
    	sStyle |= LVS_EX_FULLROWSELECT;
    	m_ListShow.SetExtendedStyle(sStyle);
    	m_ListShow.InsertColumn(0,_T("索引"),LVCFMT_LEFT,100);
    	m_ListShow.InsertColumn(1,_T("串口号"),LVCFMT_LEFT,100);
    	TraversalCom();
    	return TRUE;  // 除非将焦点设置到控件,否则返回 TRUE
    }
    


    TraversalCom()函数如下:

    void CDetectComDlg::TraversalCom()
    {
    	HKEY   hKey;
    
    	if(RegOpenKeyEx(HKEY_LOCAL_MACHINE, _T("Hardware\DeviceMap\SerialComm"), NULL, KEY_READ, &hKey)==ERROR_SUCCESS)
    	{
    		TCHAR		szPortName[256], szComName[256];
    		DWORD		dwLong, dwSize;
    		int			nCount	= 0;
    		while(true)
    		{
    			dwLong	= dwSize	= 256;
    			if(RegEnumValue(hKey, nCount, szPortName, &dwLong, NULL, NULL, (PUCHAR)szComName, &dwSize)==ERROR_NO_MORE_ITEMS)
    				break;
    			CString str;
    			str.Format("%d",nCount);
    			m_ListShow.InsertItem(nCount,str);
    			str.Format(_T("%s "),szComName);
    			m_ListShow.SetItemText(nCount,1,str);
    			nCount++;
    		}
    		RegCloseKey(hKey);
    		
    	}
    }


    这时再刚登陆窗口时便可罗列出可用串口。

     

    2.检测串口的热插拔

    这里主要利用Cwnd的ON_WM_DEVICECHANGE消息来处理。
    ON_WM_DEVICECHANGE消息在VS是通过手动添加的
    因此,首先得手动添加ON_WM_DEVICECHANGE消息:
    第一步:在消息映射BEGIN_MESSAGE_MAP(Ctbox_debug_viewDlg, CDialogEx)中添加:

    afx_msg BOOL OnDeviceChange(UINT nEventType, DWORD dwData);


    第二步:在cpp文件中添加函数声明

    afx_msg BOOL OnDeviceChange(UINT nEventType, DWORD dwData);

    第三步:实现

    BOOL CDetectComDlg::OnDeviceChange(UINT nEventType,DWORD dwData)
    {
    	//DEV_BROADCAST_DEVICEINTERFACE* dbd = (DEV_BROADCAST_DEVICEINTERFACE*) dwData;
    	switch (nEventType)
    	{
    	case DBT_DEVICEREMOVECOMPLETE://移除设备
    	case DBT_DEVICEARRIVAL://添加设备
    		ReDetectCom();//刷新列表框的内容
    		break;
    
    	default:
    		break;
    	}
    	return TRUE;
    }


    RefreshCom的内容

    void CDetectComDlg::RefreshCom(void)
    {
    	m_ListShow.DeleteAllItems();
    	TraversalCom();
    }

    至此,通过注册表的方法便已实现。

    源码:通过注册表实现

  • 相关阅读:
    一个python实现重试机制的简要实践
    元编程技术和动态编译
    NDoc使用简要手册增加了例子代码
    问dudu,评论是否只能删除,不可以直接修改?
    《C#类设计手册》读书随笔(4)
    .NET下几种动态生成代码方式比较
    NDoc使用简要手册
    "引用"表示什么?
    .NET环境编程全景不错的书
    C#实现动态灵活调用业务方法的机制
  • 原文地址:https://www.cnblogs.com/jiangu66/p/3237188.html
Copyright © 2011-2022 走看看