www.gusucode.com > VC写的短信串口发送程序源码程序 > VC写的短信串口发送程序源码程序/SMSDemo/ShortMessage.cpp

    // ShortMessage.cpp: implementation of the CShortMessage class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "ShortMessage.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CShortMessage::CShortMessage()
{
	m_nPos		=	0;		//初始化为开始位置
	m_bBOF		=	TRUE;	//为开始位置时,此为TRUE
	m_bEOF		=	FALSE;	//为末尾位置时,此为FALSE
}

CShortMessage::~CShortMessage()
{
	for(int i=0; i<GetSize();i++)
	{
		CSMSItem * pItem = GetAt(i);

		if(pItem)
			delete pItem;
	}
	RemoveAll();
}

void CShortMessage::Open(LPCTSTR szSmsInfo)
{
	//
	m_szContent	=	szSmsInfo;

	//解析SMS信息列表
	ResolveSMSInfoList(m_szContent);
}

char CShortMessage::BinStringToChar(LPCTSTR szbuff)
{
	char Table[16][5] = 
	{
		"0000","0001","0010","0011",
		"0100","0101","0110","0111",
		"1000","1001","1010","1011",
		"1100","1101","1110","1111"
	};

	char szBuffer1[5] = {0};
	char szBuffer2[5] = {0};
	char ch;

	strncpy(szBuffer1, szbuff, 4);
	strncpy(szBuffer2, &szbuff[4], 4);

	int bExist = -1;
	for(int i=0;i<16;i++)
	{
		if( strncmp(szBuffer1, Table[i], 4) ==0 )
		{
			bExist = i;
			break;
		}
	}

	if ( bExist == -1 )
		return 0;
	else
		ch = i * 16;

	bExist = -1;
	for(i=0;i<16;i++)
	{
		if( strncmp(szBuffer2, Table[i], 4) ==0 )
		{
			bExist = i;
			break;
		}
	}

	if ( bExist == -1 )
		return 0;
	else
		ch += i;

	return ch;
}

CString CShortMessage::Convert7BitString(LPCTSTR szBuffer)
{
	CString szBuf = szBuffer;
	CString szBinStr = _T("");
	for(int i=0;i<szBuf.GetLength();i+=2)
	{
		CString szChar = szBuf.Mid(i,2);
		szBinStr += HexStringToBinString(szChar);
	}

	CString szStr  = _T("");
	CString szPrev = _T("");
	CString szNext = _T("");
	int nCount = 1;
	for(int j=0;j<szBinStr.GetLength();j+=8,nCount++)
	{
		CString szBuf = szBinStr.Mid(j,8);

		szNext = szBuf.Left(nCount);
		szBuf.Delete(0,nCount);

		if (szBuf.GetLength() < 7 )
			szBuf = szBuf + szPrev;

		if (szBuf.GetLength() == 7 )
		{
			szBuf.Insert(0,'0');
			szStr += BinStringToChar(szBuf);
		}

		szPrev = szNext;

		if (nCount==7) 
		{
			szBuf = szPrev;
			szBuf.Insert(0,'0');
			szStr += BinStringToChar(szBuf);

			nCount = 0;
		}
	}

	return (LPCTSTR)szStr;
}

char * CShortMessage::HexStringToBinString(LPCTSTR szbuff)
{
	char Table[16][5] = 
	{
		"0000","0001","0010","0011",
		"0100","0101","0110","0111",
		"1000","1001","1010","1011",
		"1100","1101","1110","1111"
	};
	char * szbuf = new char[9];
	memset(szbuf, 0, 9);

	for(unsigned int i=0;i<strlen(szbuff);i++)
	{
		if (::isdigit(szbuff[i]))
		{
			strcat(szbuf, Table[szbuff[i]-48]);
		}
		else
		{
			if (::islower(szbuff[i]))
				strcat(szbuf, Table[szbuff[i]-87]);
			else
			{
				if (::isupper(szbuff[i]))
					strcat(szbuf, Table[szbuff[i]-55]);
			}
		}
	}
	
	return szbuf;
}

BOOL CShortMessage::ResolveSMSInfo(CSMSItem & pItem, CString bstrInfo)
{
	CString strSource = bstrInfo;

	//保存原有信息
	pItem.bstrSMSInfomation = bstrInfo;

	CString	strCallCenter;		//短信中心
	CString	strCallNumber;		//发送号码
	CString	strDateTime;		//日期时间
	CString	strSMSContent;		//短信内容

	//短信中心
	CString strSMSCLength(strSource.Left(2));
	int intSMSCLength = HexString2Int((LPCTSTR)strSMSCLength) * 2 - 2;
	int iPos = 2;
	CString strMobileType(strSource.Mid(iPos, 2));

	iPos += 2;
	CString strMobileLength(strSource.Mid(iPos, 2));
	int intMobileLength = HexString2Int((LPCTSTR)strMobileLength);
	int iTemp = intSMSCLength % 2 == 0 ? intSMSCLength: intSMSCLength + 1;
	strCallCenter = strSource.Mid(iPos, iTemp);
	strCallCenter = ConvertSemiOctet((LPCTSTR)strCallCenter);

	if (strCallCenter.Right(1).Compare("F") == 0)
		strCallCenter = strCallCenter.Left(intSMSCLength-1);

	if (strMobileType.Compare("91") == 0)
		strCallCenter = "+" + strCallCenter;

	//发送号码
	iPos += ( intSMSCLength + 2 );
	strMobileLength = strSource.Mid(iPos, 2);
	intMobileLength = HexString2Int((LPCTSTR)strMobileLength);

	if(intMobileLength > 20)	//电话号码将来会达到20位???
		return FALSE;
	
	iPos += 2;
	strMobileType = strSource.Mid(iPos, 2);
	
	iPos += 2;
	iTemp = intMobileLength % 2 == 0 ? intMobileLength: intMobileLength + 1;
	strCallNumber = strSource.Mid(iPos, iTemp);
	strCallNumber = ConvertSemiOctet((LPCTSTR)strCallNumber);

	if (strCallNumber.Right(1).Compare("F") == 0)
		strCallNumber = strCallNumber.Left(intMobileLength);

	if (strMobileType.Compare("91") == 0)
		strCallNumber = "+" + strCallNumber;

	//消息发送段


	//编码类型(Unicode or ASCii)
	iPos += iTemp + 2;
	CString strTPDCS(strSource.Mid(iPos, 2));
	int intDataType;
	if (strTPDCS.Compare("08") == 0)
		intDataType = 1;		//Unicode
	else
		intDataType = 0;		//ASCii

	//日期时间
	CString strYear, strMonth, strDay;
	CString strHour, strMinute, strSecond;

	char strYearTemp[5];
	iPos += 2;
	CString strTemp(strSource.Mid(iPos, 14));
	strTemp = ConvertSemiOctet((LPCTSTR)strTemp);
	int iYear = OctString2Int((LPCTSTR)strTemp.Left(2));
	if (iYear < 50)
	{
		iYear += 2000;
	}
	else
	{
		iYear += 1990;
	}
	_itoa(iYear, strYearTemp, 10);
	strYear = strYearTemp;

	strMonth = strTemp.Mid(2, 2);
	strDay = strTemp.Mid(4, 2);
	strHour = strTemp.Mid(6, 2);
	strMinute = strTemp.Mid(8, 2);
	strSecond = strTemp.Mid(10, 2);
	strDateTime = strYear + "-" + strMonth + "-" + strDay + " " + strHour + ":" + strMinute + ":" + strSecond;
	
	//短信内容
	iPos += 14;
	CString strDataLength(strSource.Mid(iPos, 2));
	int intDataLength = HexString2Int((LPCTSTR)strDataLength);
	iPos += 2;
	CString strDataSrc(strSource.Mid(iPos));
	if (intDataType == 1)		//processing unicode
	{
		// Unicode 编码
		intDataLength /= 2;
		strSMSContent = ConvertUnicode2String(strDataSrc);
	}
	else
	{
		// ASCII 编码
		strSMSContent = Convert7BitString(strDataSrc);
	}

	strcpy(pItem.szCallCenter, strCallCenter);
	strcpy(pItem.szCallNumber, strCallNumber);
	strcpy(pItem.szDateTime,   strDateTime);
	strcpy(pItem.szSMSContent, strSMSContent);
	/*
	pItem.bstrCallcenter	=	strCallCenter;
	pItem.bstrCallNumber	=	strCallNumber;
	pItem.bstrDateTime		=	strDateTime;
	pItem.bstrSMSContent	=	strSMSContent;
	*/

	char szBuffer[5]		=	{0};

	//月
	int nMonth	= atoi(strMonth);
	//日
	int nDay	= atoi(strDay);
	//时
	int nHour	= atoi(strHour);
	//分
	int nMinute	= atoi(strMinute);
	//秒
	int nSecond	= atoi(strSecond);

	pItem.dtSMSDateTime		=	COleDateTime(iYear,nMonth,nDay,nHour,nMinute,nSecond);

	return TRUE;
}

void CShortMessage::ResolveSMSInfoList(CString bstrInfo)
{
	CString szInfo = bstrInfo;

	m_szContent = _T("");

	//去掉AT+CMGL=4等命令信息
	int nPos = szInfo.Find("\r\n");
	if ( nPos != -1 )
		szInfo = szInfo.Right( szInfo.GetLength() - nPos - 2 );

	nPos = szInfo.Find("\r\n");
	while(nPos!=-1)
	{
		CString szLine = szInfo.Left(nPos);
		if ( szLine.Find("OK") != -1 )
			break;	//退出循环

		//除去+CMGL信息
		if ( szLine.Find("+CMGL") != -1 )
		{
			szInfo = szInfo.Right( szInfo.GetLength() - nPos - 2 );
			nPos = szInfo.Find("\r\n");
			szLine = szInfo.Left(nPos);
		}

		//是消息体,进行解码
		if ( szLine.GetLength() > 10 )
		{
			CSMSItem * pItem = new CSMSItem;
			
			if(ResolveSMSInfo(*pItem,szLine))
				Add(pItem);
		}

		//继续查找
		szInfo = szInfo.Right( szInfo.GetLength() - nPos - 2 );
		nPos = szInfo.Find("\r\n");
	}

	if (GetSize()==0)
		m_bEOF = TRUE;
}

DATE CShortMessage::GetDateTime()
{
	// TODO: Add your implementation code here
	CSMSItem * pItem = GetAt(m_nPos);
	if ( pItem )
		return (DATE)pItem->dtSMSDateTime;
	else
		return 0;
}

LPCTSTR CShortMessage::GetCallCenter()
{
	CSMSItem * pItem = GetAt(m_nPos);
	if ( pItem )
		return pItem->szCallCenter;
	else
		return _T("");
}

LPCTSTR CShortMessage::GetCallNumber()
{
	CSMSItem * pItem = GetAt(m_nPos);
	if ( pItem )
		return pItem->szCallNumber;
	else
		return _T("");
}

LPCTSTR CShortMessage::GetSMSContent()
{
	CSMSItem * pItem = GetAt(m_nPos);
	if ( pItem )
		return pItem->szSMSContent;
	else
		return _T("");
}

LPCTSTR CShortMessage::GetDateString()
{
	AFX_MANAGE_STATE(AfxGetStaticModuleState())

	// TODO: Add your implementation code here
	CSMSItem * pItem = GetAt(m_nPos);
	if ( pItem )
		return pItem->szDateTime;
	else
		return _T("");
}

void CShortMessage::MoveFirst()
{
	//移动游标到最前位置
	m_nPos = 0;
	m_bBOF = TRUE;
	m_bEOF = FALSE;
}

void CShortMessage::MoveLast()
{
	//移动游标到最后位置
	m_nPos = GetSize() - 1;

	m_bEOF = TRUE;
	m_bBOF = FALSE;
}

void CShortMessage::MoveNext()
{
	//移动游标到后一位置
	if ( m_nPos <= GetSize() - 1 )
	{
		m_nPos ++;
		m_bBOF = FALSE;

		if ( m_nPos == GetSize() )
		{
			m_bEOF = TRUE;
			m_nPos --;
		}
	}
}

void CShortMessage::MovePrev()
{
	//移动游标到前一位置
	if ( m_nPos >= 0 )
	{
		m_nPos --;
		m_bEOF = FALSE;

		if ( m_nPos == -1 )
		{
			m_bBOF = TRUE;
			m_nPos ++;
		}
	}
}