zoukankan      html  css  js  c++  java
  • C++ Builder中串口通讯的经验之谈

    转自网址:http://blog.csdn.net/henhen2002/article/details/4485158

      经验。(串口部分),相信不少的人都知道在VB中有一个控件MSComm(图标是一个小黄电话),它可以帮你完成普通的串口传输功能(比如字符串什么的,但有的却实现起来比较烦琐),

      在BCB中要用VB的控件,我想很多人都知道怎么办,在菜单中点Component——>Import ActiveX Control在打开的框中找到你想要的Microsoft Comm Control6.0然后直接安装就可以了,注意,前提是你必须要装了VB或者有它的库,否则你可找不到的然后你就可以在组件板的Activex中看到一个小黄电话的图标了。

      它是不可见的控件,它有不少属性,不过我认为最关键的几个属性就是

      CommPort---设置或返回通讯端口号。

      Settings---以字符串形式设置或返回波特率、奇偶校验、数据位和停止位。

      PortOpen---设置或返回通讯端口的状态,以及打开和关闭端口(BOOL型)。

      Input---从接收缓冲区返回和删除字符。

      Output---向缓冲区写一个字符串。

      这五个属性就可以帮你完成简单的串口传送接收(当然,你要保证你的传、收的可靠性,你还需要借助其他的属性,这些属性可以在VB中得到)下边我将介绍一下怎么来用这个控件,以及在程序中怎么组织程序。首先,你要建立一个新的工程,然后把MSComm控件放到窗体上,别忘了再放一个Button控件(Name属性就是Button1)。好了,双击Button1,得到如下:

    (请注意:本例的工程文件为Project1.bpr窗体文件为Unit.cpp头文件为Unit.h)
    #include <vcl.h>
    #pragma hdrstop
    #include "Unit1.h"
    //---------------------------------------------------------------------------
    #pragma package(smart_init)
    #pragma resource "*.dfm"
    TForm1 *Form1;
    AnsiString buff[10]; //****************************声明了一个缓冲,请注意,一定要设置为全局变量
    //---------------------------------------------------------------------------
    __fastcall TForm1::TForm1(TComponent* Owner)
    : TForm(Owner)
    {
    }
    //---------------------------------------------------------------------------
    void __fastcall TForm1::Button1Click(TObject *Sender) 在此加入程序代码
    {
      MSComm1->CommPort=1;
      MSComm1->Settings="9600,N,8,1";
      MSComm1->PortOpen=true;
      for(int i=0;i<=9;i++)
      {
        buff[i]=i;
        MSComm1->Output=buff[i];
      }
        MSComm1->PortOpen=false;
    }


    //---------------------------------------------------------------------------
    运行此程序,当你点击按钮后,会发送数据(你可以在网上下载一个测试串口通讯的软件)
    下面,我来解释一下上边的程序:
      MSComm1->CommPort=1;这句程序是用来确定你将用哪一个串口实行你的通讯传输,我在这里选择是串口1(你也可以选择串口2,不过如果串口2不能用的话,系统会给你提示)

      MSComm1->Settings="9600,N,8,1";这句程序是用来设置污七杂八的东东的,我在程序中设置的波特率为9600,N为无奇偶校验,数据位为8,停止位为1。
      MSComm1->PortOpen=true表示将你设置好的串口1打开(false为关闭串口)接着我用了一个循环语句,也就是i从0到9这十个数分别放到您所定义的缓冲区内(buff[10]),这个缓冲的大小是由你自己来决定,再次提醒,必须为全局变量

      MSComm1->Output=buff[i];就是将数据发送出去。

      MSComm1->PortOpen=false;最后别忘了将串口1关闭就行,这就完成了传的工作,我在这里所讲的都是最简单的应用,不过万变不离其踪,您需要怎么传您就怎么做就可以了:)


      我想说的还有MSComm的Output属性后边要求必须是Olevariant的,用这个控件在传送过程中其实传送的都是AnsiString对于一般的传送要求都可以满足了,但是对于有着特殊要求的传送,VB的这个控件可是爱莫能助的。比如要传送八进制、十六进制的数据,用这个方法传送的数据是错误的。

      因为当你无论是用C语言中的0X还是用BCB中的IntToHex()将数据转化为十六进制的数据,但传送出去的实际数据却是不正确的。那么怎么办呢?我想最有效的方法还是来借助API函数帮助我们,这很有效的。下面我来介绍一下我借助API函数实现十六进制数据的传送。【注意】

    //---------------------------------------------------------------------------
      第二次.用VB的MSComm控件我实现不了对十六进制数据的传送,于是,我就借助了API函数,很多人都知道在API函数中有这么两个函数CreareFile和WriteFile
      至于这两个函数的具体东西,大家在实际应用中去查一下就行,我不多说了。
      首先还是请您创建一个工程(我所做的例子都未对新建的.bpr和.cpp文件名做任何修改),在窗体上放上Button控件,双击,在里边按如下形式加如代码即可。
    void __fastcall TForm1::Button1Click(TObject *Sender)
    {
      HANDLE hCom=CreateFile("COM1",
            GENERIC_READ | GENERIC_WRITE,
            0,
            NULL,
            OPEN_EXISTING,
            0,
            NULL);
          

      if(hCom)
      {
        DCB dcb;
        ZeroMemory(&dcb,sizeof(dcb));
        dcb.DCBlength=sizeof(dcb);
        dcb.BaudRate=9600;
        dcb.ByteSize=8;
        dcb.Parity=NOPARITY;
        dcb.StopBits=ONESTOPBIT;
        if(SetCommState(hCom,&dcb))
        {
          DWORD ByteCount;
          int *msg;
          int a[6]= {'4',4, 'A',A,30, '0'}
          for(msg=a;msg<(a+10);msg++)
          WriteFile(hCom,msg,1,&ByteCount,NULL);
        }
        CloseHandle(hCom);
      }
    }


      关于两个函数的参数到底是怎么用的,大家可以很方便的就能查到,我只想请您注意在定义指针时一定要细心些,否则你可能产生错误上边的程序只是完成了传送了一个十六进制的F0

      如果你要传送字符串,那么你把程序稍加改动即可。例如发送HELLO,我给出程序


    void __fastcall TForm1::Button1Click(TObject *Sender)
    {
      HANDLE hCom = CreateFile("COM1",
                GENERIC_READ | GENERIC_WRITE,
                0,
                NULL,
                OPEN_EXISTING,
                0,
                NULL );
      if(hCom)
      {
        DCB dcb;
        ZeroMemory(&dcb, sizeof(dcb));
        dcb.DCBlength = sizeof(dcb);
        dcb.BaudRate = 9600;
        dcb.ByteSize = 8;
        dcb.Parity = NOPARITY;
        dcb.StopBits = ONESTOPBIT;
        if(SetCommState(hCom,&dcb))
        {
          DWORD ByteCount;
          const char *msg = "HELLO";
          WriteFile(hCom,msg, strlen(msg),&ByteCount,NULL);
        }
        CloseHandle(hCom);
      }
    }
    请同志们把两个程序比较一下,其实很多东西就会明白的。
    好了,关于串口通讯的我就讲这么多,当然这只是个皮毛,而且对于接收数据我没有提到,我想明白了发送,接收程序对于大家也不会是什么困难的事情。具体的应用还要看你们实际中的要求,要求变了,程序当然要变,不变的就是原理。通过这次所做的串口通讯程序,有了以上的一些心得,拿来与大家共同讨论,也是为了感谢象抱雪这样同志,为我们大家创造了交流的机会。希望我的心得能对大家有所帮助。

  • 相关阅读:
    SpringBoot自动装配原理解析
    面试官:你知道Spring中有哪些可以让我们扩展的地方么
    Spring事件监听机制
    Spring扩展点之Aware接口族
    程序员的进阶课-架构师之路(13)-B-树
    程序员的进阶课-架构师之路(12)-2-3-4树
    程序员的进阶课-架构师之路(11)-最容易理解的红黑树
    程序员的进阶课-架构师之路(10)-霍夫曼树
    程序员的进阶课-架构师之路(9)-平衡二叉树(AVL树)
    程序员的进阶课-架构师之路(8)-二叉树
  • 原文地址:https://www.cnblogs.com/gaoquanning/p/3530595.html
Copyright © 2011-2022 走看看