一个VC读写刷卡器的例子
2008-10-01 11:42
232 查看
这个程序是2006年编写的,用来读写金诚信刷卡器,提供了IDispatch接口,可以在VB或网页中使中。
由于这是我第一次用VC写程序,所以程序流程和注释不太详细,不过代码很简单,对希望利用VC读写串口的朋友有一定帮助。
一、接口文件:
二、头文件:
三、体文件:
由于这是我第一次用VC写程序,所以程序流程和注释不太详细,不过代码很简单,对希望利用VC读写串口的朋友有一定帮助。
一、接口文件:
import "oaidl.idl"; import "ocidl.idl"; [ object, uuid(9D6A9AC7-9C3E-46A1-859B-B1F2FCFBB320), dual, helpstring("ICard Interface"), pointer_default(unique) ] interface ICard : IDispatch { [id(1), helpstring("method Write")] HRESULT Write([in]long TrackIndex,[in]BSTR bstrValue,[out,retval]BOOL *pbResult); [id(2), helpstring("method Read")] HRESULT Read([in]long TrackIndex,[out,retval]BSTR* pbstrValue); [id(3), helpstring("method SetParameters")] HRESULT SetParameters(long lngComPort,long lngBaudRate); [id(4), helpstring("method Reset")] HRESULT Reset(); [propget, id(5), helpstring("property ComPort")] HRESULT ComPort([out, retval] long *pVal); [propput, id(5), helpstring("property ComPort")] HRESULT ComPort([in] long newVal); }; [ uuid(19CB32FB-3424-48D1-AD65-572DE2BFD9EA), version(1.0), helpstring("MagCard 1.0 Type Library") ] library MAGCARDLib { importlib("stdole32.tlb"); importlib("stdole2.tlb"); [ uuid(05E20EF2-E3A8-4060-8837-8E9966354A1C), helpstring("Card Class") ] coclass Card { [default] interface ICard; }; };
二、头文件:
#ifndef __CARD_H_ #define __CARD_H_ #include "resource.h" // main symbols ///////////////////////////////////////////////////////////////////////////// // CCard class ATL_NO_VTABLE CCard : public CComObjectRootEx<CComSingleThreadModel>, public IObjectSafetyImpl<CCard,INTERFACESAFE_FOR_UNTRUSTED_CALLER | INTERFACESAFE_FOR_UNTRUSTED_DATA>, public CComCoClass<CCard, &CLSID_Card>, public IDispatchImpl<ICard, &IID_ICard, &LIBID_MAGCARDLib> { public: CCard(); ~CCard(); DECLARE_REGISTRY_RESOURCEID(IDR_CARD) DECLARE_PROTECT_FINAL_CONSTRUCT() BEGIN_COM_MAP(CCard) COM_INTERFACE_ENTRY(ICard) COM_INTERFACE_ENTRY(IDispatch) COM_INTERFACE_ENTRY(IObjectSafety) END_COM_MAP() // ICard public: STDMETHOD(get_ComPort)(/*[out, retval]*/ long *pVal); STDMETHOD(put_ComPort)(/*[in]*/ long newVal); STDMETHOD(Reset)(); STDMETHOD(SetParameters)(/*[in]*/long lngComPort,/*[in]*/long lngBaudRate); STDMETHOD(Read)(/*[in]*/long TrackIndex,/*[out,retval]*/BSTR *pbstrValue); STDMETHOD(Write)(/*[in]*/long TrackIndex,/*[in]*/BSTR bstrValue,/*[out,retval]*/BOOL *pbResult); HANDLE hCom; //串口句柄 char m_szComName[15]; //串口名称,即COM1、COM2等。 long m_lComPort; char m_szResetCtl[2]; //复位控制符 char m_szFormatCtl[5]; //数据格式:当第5位为31表示ISO格式,32表示IBM格式 char m_szStartPosCtl[4]; //起始位置:当第4位为36表示16,37表示20,38表示22,39表示25 char m_szDensityCtl[4]; //高密格式:第4位为48表示高密,4C表示低密 }; #endif //__CARD_H_
三、体文件:
#include "stdafx.h" #include "MagCard.h" #include "Card.h" ///////////////////////////////////////////////////////////////////////////// // CCard CCard::CCard() { hCom = NULL; m_lComPort = 0; strcpy(m_szComName,"COM1"); SetParameters(1,9600); } CCard::~CCard() { if(hCom != NULL) CloseHandle(hCom); } STDMETHODIMP CCard::Write(long TrackIndex, BSTR bstrValue, BOOL *pbResult) { if(hCom == NULL) return E_FAIL; //定义写操作控制符 char m_Buff[127]; char m_StartWrite[] = {0x1B,'0',0x1B,'/0','/0','/0'}; //定义写操作头部控制符,随不同磁道而不同 char m_EndWrite[] = {0x1D,0x1B,'//',0x1B,'j','/0'}; //定义写操作尾部(即结束)控制符 switch(TrackIndex) { case 1: m_StartWrite[3] = 'w'; break; case 2: m_StartWrite[3] = 't'; break; default: m_StartWrite[3] = 't'; m_StartWrite[4] = 'A'; } //将头控制符、数据、尾控制符组装到一起 char szTemp[127]; CComBSTR bstrTemp(bstrValue); WideCharToMultiByte(CP_ACP,WC_COMPOSITECHECK,bstrTemp.m_str,-1,szTemp,128,NULL,NULL); memset(m_Buff,0,128); strcat(m_Buff,m_StartWrite); strcat(m_Buff,szTemp); strcat(m_Buff,m_EndWrite); bstrTemp.Empty(); //发送给刷卡器 DWORD dwCount; WriteFile(hCom,m_Buff,strlen(m_Buff),&dwCount,NULL);//将数据写入指定磁道 Sleep(500); //等待500毫秒 //等待刷卡器返回结果 memset(m_Buff,0,127); ReadFile(hCom,m_Buff,127,&dwCount,NULL); FlushFileBuffers(hCom); PurgeComm(hCom,PURGE_TXABORT|PURGE_RXABORT|PURGE_TXCLEAR|PURGE_RXCLEAR); //清空全部缓冲区,PURGE_TXCLEAR发送缓冲区,PURGE_RXCLEAR接收缓冲区 return S_OK; } STDMETHODIMP CCard::Read(long TrackIndex, BSTR *pbstrValue) { if(hCom == NULL) return E_FAIL; if(TrackIndex>3 ||TrackIndex <1) return E_FAIL; //发送读准备操作控制符 DWORD dwCount; char m_szRead[] = {0x1B,'0','/0'}; WriteFile(hCom,m_szRead,2,&dwCount,NULL); //发送读取磁道数控制符 char m_szTrack[]={0x1B,'0',0x1B,'/0','/0','/0'}; switch(TrackIndex) { case 1: //第一磁道 m_szTrack[3] = 'r'; break; case 2: //第二磁道 m_szTrack[3] = ']'; break; default: //默认为第三磁道 m_szTrack[3] = 'T'; m_szTrack[4] = ']'; break; } WriteFile(hCom,m_szTrack,5,&dwCount,NULL); Sleep(20); //读取指定的磁道 char m_Buff[127]; memset(m_Buff,0,128); ReadFile(hCom,m_Buff,127,&dwCount,NULL); //解析读取的结果 if(dwCount>0) { m_Buff[dwCount] = '/0'; if(TrackIndex<3) { memcpy(m_Buff,&m_Buff[2],dwCount-4); m_Buff[dwCount-4] = '/0'; } else{ memcpy(m_Buff,&m_Buff[3],dwCount-5); m_Buff[dwCount-5] = '/0'; } } else m_Buff[0] = '/0'; //将结果返回给用户 CComBSTR bstrTemp; bstrTemp.Append(m_Buff); *pbstrValue = bstrTemp.Copy(); bstrTemp.Empty(); return S_OK; } STDMETHODIMP CCard::SetParameters(long lngComPort,long lngBaudRate) { if(hCom != NULL) CloseHandle(hCom); m_lComPort = lngComPort; wsprintf(m_szComName,"COM%d",lngComPort); hCom=CreateFile(m_szComName,GENERIC_READ|GENERIC_WRITE,0,NULL,OPEN_EXISTING,0,NULL); if(hCom==(HANDLE)-1){ hCom = NULL; return E_FAIL; } //设置串口通讯参数 DCB dcb; GetCommState(hCom,&dcb); dcb.BaudRate = 9600; dcb.ByteSize = 8; dcb.StopBits = 0; dcb.EofChar = 26; dcb.fRtsControl = 0; SetCommState(hCom,&dcb); //设置通讯参数 //设置读写超时参数 COMMTIMEOUTS tagCommTimeOuts ; //定义超时结构,并填写该结构 tagCommTimeOuts.ReadIntervalTimeout = 10; tagCommTimeOuts.ReadTotalTimeoutMultiplier = 200; tagCommTimeOuts.ReadTotalTimeoutConstant = 500; //总的读超时时间为ReadIntervalTimeout*ReadTotalTimeoutMultiplier+ReadTotalTimeoutConstant tagCommTimeOuts.WriteTotalTimeoutConstant = 0; tagCommTimeOuts.WriteTotalTimeoutMultiplier = 0; SetCommTimeouts(hCom,&tagCommTimeOuts ) ;//设置读写操作所允许的超时 SetupComm(hCom,512,512); //设置串口输入和输出缓冲区均为128位 PurgeComm(hCom,PURGE_TXABORT|PURGE_RXABORT|PURGE_TXCLEAR|PURGE_RXCLEAR); //清空全部缓冲区,PURGE_TXCLEAR发送缓冲区,PURGE_RXCLEAR接收缓冲区 //发送刷卡器控制符 DWORD dwCount; char vFormat[] = {0x1B,'0',0x1B,'T','1'}; WriteFile(hCom,vFormat,5,&dwCount,NULL); //数据格式:最后一位1表示ISO,2表示IBM char vDensity[]={0x1B,'0',0x1B,'H'}; WriteFile(hCom,vDensity,4,&dwCount,NULL); //第二磁道高密度:最后一位H表示高,L表示低 char vPos[]={0x1B,'0',0x1B,'6'}; WriteFile(hCom,vPos,4,&dwCount,NULL);//起始位置:最后一位为6表示16,7表示20,8表示22,9表示25 return S_OK; } STDMETHODIMP CCard::Reset() { if(hCom==NULL) return E_FAIL; DWORD dwCount; char m_szControl[]={0x1B,'a','/0'}; WriteFile(hCom,m_szControl,3,&dwCount,NULL); Sleep(200); return S_OK; } STDMETHODIMP CCard::get_ComPort(long *pVal) { *pVal = m_lComPort; return S_OK; } STDMETHODIMP CCard::put_ComPort(long newVal) { if(newVal >8 || newVal <1) return E_FAIL; m_lComPort = newVal; wsprintf(m_szComName,"COM%d",newVal); return S_OK; }
相关文章推荐
- 【MTK】一个寄存器读写的例子
- C# ArrayList用BinaryFormatter序列化和反序列化进行文件读写的一个简单例子
- C# 类用XmlSerializer进行序列化和反序列化进行文件读写的一个简单例子
- java:IO-一个文件读写例子
- 【转载】关于:读写xls文件,提供下载的一个小例子(jxl 的简单运用) - 读取文件
- 关于:读写xls文件,提供下载的一个小例子(jxl 的简单运用) - 创建文件
- 自己写的一个vc操作word的例子
- 一个简单的文件读写、复制的例子
- 【转载】关于:读写xls文件,提供下载的一个小例子(jxl 的简单运用) - 高级操作
- JXL应用(二) 读写excel的一个经典例子
- Java使用JNI调用VC的DLL的一个小例子
- 关于:读写xls文件,提供下载的一个小例子(jxl 的简单运用) - 读取文件
- 一个读写ini文件属性的例子
- VC++ 实战OLEDB编程(七)一个完整的例子 (转)
- 收藏一个好用的C++串口类/RS232/serial port,VC++串口读写归档
- 关于:读写xls文件,提供下载的一个小例子(jxl 的简单运用) - 高级操作
- bcb 读写ini 配置文件的一个例子
- vc2013 中 SystemC一个初级例子时产生错误error:"no RTTI data"
- c语言文件读写的一个例子
- VC使用驱动打印的一个例子