在
C++ Builder
中利用串行通信控件编程
转发别人的文章,阅读时可以使用IE的,查看--字体大小--最大;这样可以看到大字体的文章。
摘要:串口是常用的计算机与外部串行设备之间的数据传输通道,由于串行通信方便易行,所以应用广泛。本文介绍了在
C++ Builder
中如何利用串行通信控件进行串行通信编程。
一、引言
目前,在用计算机进行数据传输时,常用的是串行通信方式。用
C
++
Builder
来编写串行通信程序时,可以调用
Windows API
函数,也可以利用
VB
中的
MSComm
控件。
利用
API
函数编写实际应用程序时,往往要考虑多线程的问题,这样编出来的程序不但十分庞大,而且结构比较复杂,继承性差,维护困难。但是使用串行通信控件就相对简单一些,而且功能强大,性能安全可靠。本文就简单的介绍一下在
C++ Builder
中利用
MSComm
控件进行编程。
二、
MSComm
控件的常用属性和事件
MSComm
控件通过串行端口传输和接收数据,为应用程序提供串行通讯功能。具体的来说,它提供了两种处理通信问题的方法:一是事件驱动
(Event
-
driven)
方法,一是查询法。
事件驱动方式
在使用事件驱动法设计程序时,每当有新字符到达,或端口状态改变,或发生错误时,
MSComm
控件将解发
OnComm
事件,而应用程序在捕获该事件后,通过检查
MSComm
控件的
CommEvent
属性可以获知所发生的事件或错误,从而采取相应的操作。这种方法的优点是程序响应及时,可靠性高。
查询方式
查询方式实质上还是事件驱动,但在有些情况下,这种方式显得更为便捷。在程序的每个关键功能之后,可以通过检查
CommEvent
属性的值来查询事件和错误。如果应用程序较小,并且是自保持的,这种方法可能是更可取的。
1.MSComm
控件的常用属性
CommPort
属性:设置或返回通讯端口号,可以设置为
1
到
16
之间的任何值,本系统采用缺省值
2
;
Settings
属性:以字符串形式设置或返回波特率、奇偶校验、数据位和停止位,本系统采用缺省值
"9600
,
n
,
8
,
1";
PortOpen
属性:设置或返回通讯口的状态以及打开和关闭端口,可通过把该属性设置为
true
或者
false
来打开或者关闭端口;
InBufferSize
和
OutBufferSize
属性:分别设置接收和发送缓冲区分配的内存数量,单位为字节,缺省值分别为
1024byte
和
512byte
;
InputLen
属性:确定希望从接收缓冲区移出的字符数量,当
InputLen
=
0
时,一次把接收缓冲区的字符全部移出;
Input
属性:从接收缓冲区中读出数据,然后将该数据从缓冲区移走。
OutPut
属性:向发送缓冲区传递待发送的数据。
InBufferCount
和
OutBufferCount
属性:分别确定当前驻留在接收缓冲区等待被取出和发送缓冲区准备发送的字符数量,这两个属性设置为
0
,接收和发送缓冲区的内容将被清除;
InputMode
属性:设置接收传入数据的格式,设置为
0
采用文本形式,设置为
1
采用二进制格式,本系统设置为二进制格式进行发送和接收;
SThreshold
属性:保存一个产生发送
OnComm
事件的界限值,本系统设置该属性为
0
,发送数据时不产生
OnComm
事件;
RThreshold
属性:设定当接收几个字符时触发
OnComm
事件,本系统设置该属性为
1
,每接收一个字符就产生一个
OnComm
事件;
2
.
MSComm
控件的事件
MSCOMM
控件只使用一个事件
OnComm
,用属性
CommEvent
的十七个值来区分不同的触发时机。主要有以下几个:
(1)CommEvent=1
时:传输缓冲区中的字符个数已少于
Sthreshold(
可设置的属性值
)
个。
(2)CommEvent=2
时:接收缓冲区中收到
Rthreshold(
可设置的属性值
)
个字符,利用此事件可编写接收数据的过程。
(3)CommEvent=3
时:
CTS
线发生变化。
(4)CommEvent=4
时:
DSR
线发生变化。
(5)CommEvent=5
时:
CD
线发生变化。
(6)CommEvent=6
时:检测到振铃信号。
另外十种情况是通信错误时产生,即错误代码。
三、程序的实现
1.
注册
MSComm
控件
众所周知,
C++Builder
本身并不提供串行通讯控件
MSComm
,但我们却可以通过注册后直接使用它。启动
C++Builder5.0
后,然后选择
C++Builder
主菜单中的
Component
菜单项,单击
Import Active Control
命令,弹出
Import Active
窗口,选择
Microsoft Comm Control6.0
,再选择
Install
按钮执行安装命令
,
系统将自动进行编译
,
编译完成后即完成
MSComm
控件在
C++Builder
中的注册
,
系统默认安装在控件板的
Active
页
,
接下来我们就可以像使用
C++Builder
本身提供的控件那样使用新注册的
MSComm
控件了。(前提条件是你的机子上安装了
Visual Basic
,或者有它的库)
2.
具体实现
新建一个工程
Project1
,把注册好的
MSComm
控件加入到窗体中,然后再加入
5
个
ComboBox
用来设置串口的属性,
4
个
Button
分别用来
"
打开串口
" "
关闭串口
""
发送数据
""
保存数据
"
,
2
个
Memo
控件分别用来显示接收到的数据和发送的数据。再加入一个
Shape
控件用来标明串口是否打开。
ComboBox1
用来设置串口号,通过它的
Items
属性设置
1
,
2
,
3
,
4
四个列表项分别表示
COM1,COM2,COM3,COM4
口。
ComboBox2
用来设置波特率,
ComboBox3
用来设置奇偶校验位,
ComboBox4
用来设置数据位,
ComboBox5
用来设置停止位。他们的缺省值分别是
9600
,
n
,
8
,
1
。
Button1
用来打开串口,
Button2
用来关闭串口,
Button3
用来发送数据,
Button4
用来保存数据。
Memo1
用来显示发送的数据,
Memo2
显示接收的数据。
Shape1
的
Shape
属性设置为
stCircle
。
下面给出部分源码:
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
if(MSComm1->PortOpen==true)
{
Button1->Enabled=false;
Button2->Enabled=true;
Button3->Enabled=true;
Button4->Enabled=true;
Shape1->Brush->Color=clGreen;
}
else
{
Button2->Enabled=true;
Button2->Enabled=false;
Button3->Enabled=false;
Button4->Enabled=false;
Shape1->Brush->Color=clRed;
}
}
void __fastcall TForm1::Button1Click(TObject *Sender) / /
打开串口
{
if(MSComm1->PortOpen!=true)
{
MSComm1->CommPort=StrToInt(ComboBox1->Text);//
选择串口号
MSComm1->Settings=
ComboBox2->Text+","+
ComboBox3->Text+","+
ComboBox4->Text+","+
ComboBox5->Text; file://
设置串口的属性波特率、奇偶校验、数据位和、
//
停止位。
MSComm1->InputMode=0;//
设置传入数据的格式,
0
表示文本形式
MSComm1->PortOpen=true;//
打开串口
Button1->Enabled=false;
Button2->Enabled=true;
Button3->Enabled=true;
Button4->Enabled=true;
Shape1->Brush->Color=clGreen;
}
}
void __fastcall TForm1::Button2Click(TObject *Sender) / /
关闭串口
{
if(MSComm1->PortOpen!=false)
{
MSComm1->PortOpen=false;
Button1->Enabled=true;
Button2->Enabled=false;
Button3->Enabled=false;
Button4->Enabled=false;
Shape1->Brush->Color=clRed;
}
else
{
Button1->Enabled=false;
Button2->Enabled=true;
Shape1->Brush->Color=clRed;
}
}
MSComm
控件的
Input
和
Output
属性在
Object Inspector
中是看不到的,而且在
C++Builder
环境下这两个属性已不在是
VB
、
VC
中的原类型,而是
OleVariant
类型,也就是
Ole
万能变量,这就需要我们在发送接收数据时要把数据转换成
Ole
类型。
void __fastcall TForm1::Button3Click(TObject *Sender) file://
发送
Memo2
中的数据
{
MSComm1->Output=StringToOleStr(Memo2->Text); file://
把
AnsiString
型转化成
//Ole
形式。
}
通过
OnComm
事件接收数据,必须把
MSComm
的
RThreshold
属性设置为大于
0
,只有这样在接收到字符时才会产生一个
OnComm
事件。
void __fastcall TForm1::MSComm1Comm(TObject *Sender)
{
AnsiString str; file://
声明一个
AnsiString
类型的变量
OleVariant s; file://
声明一个用于接收数据的
OleVariant
变量。
if(MSComm1->CommEvent==comEvReceive)
//
接收缓冲区中是否收到
Rthreshold
个字符。
{
if(MSComm1->InBufferCount)//
是否有字符驻留在接收缓冲区等待被取出
{
s=MSComm1->Input;//
接收数据
str=s.AsType(varString); file://
把接收到的
OleVariant
变量转换成
AnsiString
类型
Memo1->Text=Memo1->Text+str;//
把接收到的数据显示在
Memo1
中。
}
}
}
要保存数据应该再加入一个
SaveDialog
模块
void __fastcall TForm1::Button4Click(TObject *Sender)
file://
把
Memo1
中的数据保存在指定的文件中
{
AnsiString filename1;
SaveDialog1->Filter="Text files (*.txt)|*.txt|All files (*.*)|*.*";//
文件类型过滤器
SaveDialog1->FilterIndex=2;
if(SaveDialog1->Execute())
{
filename1=SaveDialog1->FileName;
Memo1->Lines->SaveToFile(filename1);//
把收到的数据保存在文件
filename1
中
}
}
四、结束语
上面给出了
C++ Builder
中利用
MSComm
控件进行串行通信编程的实现和部分源码,有了上面的参照读者可以根据实际需要编写出具有发送文件和接收文件功能的程序。
posted on 2006-07-05 16:22
石正 阅读(1298)
评论(1) 编辑 收藏