VC++ 6.0之MSComm控件安装、使用
Visual C++为我们提供了一种好用的ActiveX控件Microsoft Communications Control(即MSComm)来支持应用程序对串口的访问,在应用程序中插入MSComm控件后就可以较为方便地实现对通过计算机串口收发数据。
要使用ActiveX控件MSComm,程序员必须将其添加入工程,其方法是:
(1)单击主菜单project的子菜单Add To project的Components and Controls选项;
(2)在弹出的"Components and Controls Gallery"对话框中选择Registered ActiveX Controls文件夹中的"Microsoft Communications Control,version 6.0"选项
单击其中的"Insert"按钮,MSComm控件就被增加到工程中了。与此同时,类CMSComm的相关文件mscomm.h和mscomm.cpp也一并被加入Project的Header Files和Source Files中。当然,程序员可以自己修改文件名。直接分析mscomm.h头文件就可以完备地获取这个控件的使用方法(主要是public类型的接口函数),下面我们摘取了头文件的主要代码并对其关键部分给出了注释:
#if !defined(AFX_MSCOMM_H__)
#define AFX_MSCOMM_H__
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
// Machine generated IDispatch wrapper class(es) created by Microsoft Visual C++
// NOTE: Do not modify the contents of this file. If this class is regenerated by
// Microsoft Visual C++, your modifications will be overwritten.
/
// CMSComm wrapper class
class CMSComm : public CWnd
{
protected:
DECLARE_DYNCREATE(CMSComm)
public:
CLSID const& GetClsid()
{
static CLSID const clsid = { 0x648a5600, 0x2c6e, 0x101b, { 0x82, 0xb6, 0x0, 0x0, 0x0, 0x0, 0x0, 0x14 } };
return clsid;
}
virtual BOOL Create(LPCTSTR lpszClassName,
LPCTSTR lpszWindowName, DWORD dwStyle,
const RECT& rect,
CWnd* pParentWnd, UINT nID,
CCreateContext* pContext = NULL)
{ return CreateControl(GetClsid(), lpszWindowName, dwStyle, rect, pParentWnd, nID); }
BOOL Create(LPCTSTR lpszWindowName, DWORD dwStyle,
const RECT& rect, CWnd* pParentWnd, UINT nID,
CFile* pPersist = NULL, BOOL bStorage = FALSE,
BSTR bstrLicKey = NULL)
{ return CreateControl(GetClsid(), lpszWindowName, dwStyle, rect, pParentWnd, nID,
pPersist, bStorage, bstrLicKey); }
// Attributes
public:
// Operations
public:
void SetCDHolding(BOOL bNewValue);
BOOL GetCDHolding();
void SetCommID(long nNewValue);
long GetCommID();
void SetCommPort(short nNewValue);
//设置端口号,如nNewValue =1表示COM1
short GetCommPort();
void SetCTSHolding(BOOL bNewValue);
BOOL GetCTSHolding();
void SetDSRHolding(BOOL bNewValue);
BOOL GetDSRHolding();
void SetDTREnable(BOOL bNewValue);
BOOL GetDTREnable();
void SetHandshaking(long nNewValue);
long GetHandshaking();
void SetInBufferSize(short nNewValue);
short GetInBufferSize();
void SetInBufferCount(short nNewValue);
short GetInBufferCount();
void SetBreak(BOOL bNewValue);
BOOL GetBreak();
void SetInputLen(short nNewValue);
short GetInputLen();
void SetNullDiscard(BOOL bNewValue);
BOOL GetNullDiscard();
void SetOutBufferSize(short nNewValue);
short GetOutBufferSize();
void SetOutBufferCount(short nNewValue);
short GetOutBufferCount();
void SetParityReplace(LPCTSTR lpszNewValue);
CString GetParityReplace();
void SetPortOpen(BOOL bNewValue);
//打开或关闭串口,TRUE:打开,FALSE:关闭
BOOL GetPortOpen();
//串口是否已打开,TRUE:打开,FALSE:关闭
void SetRThreshold(short nNewValue);
//如果设置为1,表示一接收到字符就发送2号事件
short GetRThreshold();
void SetRTSEnable(BOOL bNewValue);
//硬件握手使能?
BOOL GetRTSEnable();
void SetSettings(LPCTSTR lpszNewValue);
//Settings由4部分组成,其格式为:"BBBB,P,D,S",即"波特率,是否奇偶校验,数据位 //个数,停止位",如设置为:"9600,n,8,1"
CString GetSettings();
void SetSThreshold(short nNewValue);
//如果保持缺省值0不变,则表示发送数据的过程中串口上不发生事件
short GetSThreshold();
void SetOutput(const VARIANT& newValue);
//一个非常重要的函数,用于写串口,注意其接收的输入参数为VARIANT类型对象,
//我们需要将字符串转化为VARIANT类型对象
VARIANT GetOutput();
void SetInput(const VARIANT& newValue);
VARIANT GetInput();
//一个非常重要的函数,用于读串口,注意其返回的是VARIANT类型对象,我们需要
//将其转化为字符串
void SetCommEvent(short nNewValue);
short GetCommEvent();
//一个非常重要的函数,获得串口上刚发生的事件("事件"可以理解为软件意义上的
//"消息"或硬件意义上的"中断"),事件的发送会导致OnComm消息的诞生!
void SetEOFEnable(BOOL bNewValue);
BOOL GetEOFEnable();
void SetInputMode(long nNewValue);
long GetInputMode();
};
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.
#endif
分析上述源代码可知,基本上,MSComm的诸多接口可以分为如下几类:
(1)打开与设置串口接口函数;
(2)获得串口设置和串口状态接口函数;
(3)设置串口发送数据方式、缓冲区接口及发送数据接口函数;
(4)设置串口接收数据方式、缓冲区接口及接收数据接口函数;
(5)设置与获取串口上发生的事件接口函数。
2.例程
程序的功能和界面(如下图)都与本文连载三中《基于WIN32 API的串口编程》相同,不同的只是连载三的串口通信以API实现,而本节的串口通信则以MSComm控件实现。
使用第1节的方法将控件添加入工程并添加mscomm.h和mscomm.cpp文件后,为了使用控件,我们将控件拖入对话框内任意一个位置(运行时"电话"图标会隐藏),其操作如下图:
有趣而极富人性化的是我们可以直接右键单击这个"电话",来设置串口的属性,如下图:
接着,我们需要为控件添加一个对应的成员变量m_mscom,其对应的变量类型为CMSComm,如下图:
这样就建立了m_mscom和IDC_MSCOMM1控件的相互映射:
void CSerialPortActivexDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CSerialPortActivexDlg)
DDX_Text(pDX, IDC_RECV_EDIT, m_recv);
DDX_Text(pDX, IDC_SEND_EDIT, m_send);
DDX_Control(pDX, IDC_MSCOMM1, m_mscom);
//}}AFX_DATA_MAP
}
同时,在对话框的头文件也会由"MFC类向导"自动定义CSerialPortActivexDlg类的CMSComm型成员变量m_mscom:
CMSComm m_mscom;
在对话框初始化时(即在CSerialPortActivexDlg::OnInitDialog函数中)打开串口1:
BOOL CSerialPortActivexDlg::OnInitDialog()
{
CDialog::OnInitDialog();
// Add "About..." menu item to system menu.
// IDM_ABOUTBOX must be in the system command range.
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);
}
}
// Set the icon for this dialog. The framework does this automatically
// when the application's main window is not a dialog
SetIcon(m_hIcon, TRUE); // Set big icon
SetIcon(m_hIcon, FALSE); // Set small icon
// TODO: Add extra initialization here
m_mscom.SetCommPort(1); //串口1
m_mscom.SetInBufferSize(1024); //设置输入缓冲区的大小,Bytes
m_mscom.SetOutBufferSize(512); //设置输入缓冲区的大小,Bytes
if(!m_mscom.GetPortOpen()) //打开串口
{
m_mscom.SetPortOpen(true);
}
m_mscom.SetInputMode(1); //设置输入方式为二进制方式
m_mscom.SetSettings("9600,n,8,1"); //设置波特率等参数
m_mscom.SetRThreshold(1); //为1表示有一个字符即引发事件
m_mscom.SetInputLen(0);
return TRUE; // return TRUE unless you set the focus to a control
}
最核心的发送串口数据函数("发送"按钮单击事件)如下:
void CSerialPortActivexDlg::OnSendButton()
{
// TODO: Add your control notification handler code here
UpdateData(true);
CByteArray sendArr;
WORD wLength;
wLength = m_send.GetLength();
sendArr.SetSize(wLength);
for(int i =0; i<wLength; i++)
{
sendArr.SetAt(i, m_send.GetAt(i));
}
m_mscom.SetOutput(COleVariant(sendArr));
}
为了处理接收事件,我们需要为MScomm控件添加对应的消息处理函数。如下图,我们通过"MFC类向导"添加了CSerialPortActivexDlg 类的成员函数OnCommMscomm1():
这样,在对话框的头文件中就会自动增加下面两句:
afx_msg void OnCommMscomm1();//函数声明
DECLARE_EVENTSINK_MAP()
来自AFX_MSG部分:
// Generated message map functions
//{{AFX_MSG(CSerialPortActivexDlg)
virtual BOOL OnInitDialog();
afx_msg void OnSysCommand(UINT nID, LPARAM lParam);
afx_msg void OnPaint();
afx_msg HCURSOR OnQueryDragIcon();
afx_msg void OnClearButton();
afx_msg void OnSendButton();
afx_msg void OnCommMscomm1();
DECLARE_EVENTSINK_MAP()
//}}AFX_MSG
同时在对话框的.cpp文件中会增加下列代码实现串口消息映射:
BEGIN_EVENTSINK_MAP(CSerialPortActivexDlg, CDialog)
//{{AFX_EVENTSINK_MAP(CSerialPortActivexDlg)
ON_EVENT(CSerialPortActivexDlg, IDC_MSCOMM1, 1 /* OnComm */,
OnCommMscomm1, VTS_NONE)
//}}AFX_EVENTSINK_MAP
END_EVENTSINK_MAP()
我们定义CSerialPortActivexDlg::OnCommMscomm1()函数主要处理数据的接收,其源代码为:
void CSerialPortActivexDlg::OnCommMscomm1()
{
// TODO: Add your control notification handler code here
UpdateData(true);
VARIANT variant_inp;
COleSafeArray safearray_inp;
long i = 0;
int len;
char rxdata[1000];
CString tmp;
switch (m_mscom.GetCommEvent())
{
case 2:
//表示接收缓冲区内有字符
{
variant_inp = m_mscom.GetInput();
safearray_inp = variant_inp;
len = safearray_inp.GetOneDimSize();
for (i = 0; i < len; i++)
{
safearray_inp.GetElement(&i, &rxdata[i]);
}
rxdata[i] = '\0';
}
m_recv += rxdata;
UpdateData(false);
break;
default:
break;
}
}
最后,与连载三类似,再次借助"串口调试助手"以实例验证了本程序的正确性,如下图:
最后,需要特别提示的是:如果要在基于"文档/视图"的框架结构程序而非对话框程序中使用串口控件,我们不能轻松地使用"MFC类向导",这时候必须手动地添加相关代码。
在MainFrm.h头文件中加入:
afx_msg void OnCommMscomm();
DECLARE_EVENTSINK_MAP()
并定义CMSComm成员变量:
CMSComm m_ComPort;
在MainFrm.cpp文件中添加
BEGIN_EVENTSINK_MAP(CMainFrame, CFrameWnd)
ON_EVENT(CMainFrame,ID_COMMCTRL,1,OnCommMscomm,VTS_NONE)
//映射ACTIVEX控件的事件
END_EVENTSINK_MAP()
在MainFrm.cpp文件的OnCreate(LPCREATESTRUCT lpCreateStruct)函数中添加:
ComPort.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0,0,0,0),this, ID_COMMCTRL);
以创建CMSComm控件。
此后,我们就可以在CMainFrame类的函数中使用串口控件对应的ComPort控件成员变量。
VC++ 6.0之MSComm控件安装、使用相关推荐
- vc++6.0使用串口控件例程
vc++6.0使用串口控件例程 1.建立项目: 打开VC++6.0,建立一个基于对话框的MFC应用程序SCommTest; 2.在项目中插入MSComm控件 选择Project菜单下Add To Pr ...
- 怎样把vc6的MSComm控件接受的数据实时的显示在编辑框,并把数据实时惠存txt文件中
怎样把vc6的MSComm控件接受的数据实时的显示在编辑框,并把数据实时存入txt文件中 我在做一个基于VC6的MSComm控件的电机上位机控制,数据帧格式采用9600bps,8位数据位,奇校验,1位 ...
- VS2010如何安装MSComm控件
VS2010在默认情况下是不包含MSComm控件的,MSComm是在VC6.0中的控件,据说MSComm控件有些缺陷,看来微软是打算放弃此控件了.不过对于已经熟悉使用此控件的人来说还是不太方便,我是那 ...
- VC基于MSCOMM控件串口通讯
在mfc中进行串口通讯最简单的方法莫过于在对话框中使用MSCOMM控件了,MSComm通信控件提供了一系列标准通信命令的接口,它允许建立串口连接,可以连接到其他通信设备(如Modem). 还可以发送命 ...
- 【GIS开发】VB6.0下MO控件的安装:安装教程及MO破解教程(MapObjects2.x)
[GIS开发]VB6.0下MO控件的安装:安装教程及MO破解教程(MapObjects2.x) 基于MO和VB的GIS开发过程中,普遍使用的还是2.0及以上版本,ESRI公司早已不再对MO组件进行更新 ...
- 串口通讯mscomm控件下载
串口通讯mscomm控件下载 大家知道,当我们安装VC++6.0/VB6.0时,如果选择了ACtiveX控件项(自定义安装),MSComm控件就会自动安装在计算机上了,并在系统文件夹下多了3个文件:M ...
- VB6.0 怎样启用控件comdlg32.ocx
VB6.0 怎样启用控件comdlg32.ocx 怎样启用控件comdlg32.ocx 2008-10-08 09:32 提问者: nefu_20061617 |浏览次数:1502次 vbs文件中有代 ...
- 用VC开发串口通信dll控件
VC串口通信技术网<VC串口上位机编程方法简介>介绍了串口编程的常见方法,其中就有使用串口dll控件的方法,dll是一种动态链接库,使用起来非常方便. 本文利用VC编程工具,对Window ...
- VS2008下用MFC 的MSComm控件编写串口程序
可以在:http://download.csdn.net/detail/plutus_lee/4525446 下载详细文档. 首先感谢网络资源吧,作为一个自动化专业出身的,不懂串口实在让我有点无奈,本 ...
最新文章
- Web项目使用nginx实现代理端口访问,看这篇就够了
- linux输出指定数量脉冲,ESM335x Linux输出脉冲计数
- 为帐户创建一个Apex触发器,以根据自定义字段将送货地址邮政编码与账单地址邮政编码匹配
- jqgrid 服务器端验证,jqGrid获取服务服务器返回的所有数据
- 关于Mybatis的各种配置文件
- 日本比中国快一个小时,泰国比中国慢一个小时
- idea 设置java栈空间,如何为Intellij编译器提供更多堆空间?
- 网站关停就没事了?5100万账户文件被盗
- 大数据之HBase部署
- 清除css,js,img的浏览器缓存
- Adobe应用网络体验管理解决方案
- springboot + vue项目跨域请求解决方案
- XBMC Skinning Manual
- Netty4 学习笔记之一:客户端与服务端通信 demo
- CoreData的数据迁移
- n3k配置vpc是否还需要配置hsrp_HSRP
- Atitit 常用加密算法 aes des rsa 比较 历史演进 目录 1.1. 常规加密算法如下 Aes 3des des rsa	1 2. 加密算法历史演进 按照出现时间和加密强度 流行
- OverFeat 详解
- 【笑话】程序员和青蛙公主
- CodeLite配置
热门文章
- 2020年中国维生素行业发展现状及竞争格局分析,市场空间广阔「图」
- 字节入职福利太香了!7月最新Java面经已更新
- 【Excel】工作中会用到的excel操作和技巧
- 在Centos系统下创建与Windows的共享文件夹
- 中国存储器“3+1”版图初现 行业要再跑5年马拉松
- MYSQL之错误代码----mysql错误代码与JAVA实现
- 和平精英服务器响应超时什么意思,和平精英服务器无响应,和平精英服务器超时...
- 【论文阅读笔记】Deep neural networks are easily fooled- High confidence predictions for unrecognizable image
- JAVA对接短信通知接口
- android6.0权限适配RxPermissions