看本文前请先看看 http://dev.csdn.net/article/49/49606.shtm
本文只是说明一下之前我看那个网页做工程时理解错的地方,希望对你有帮助.
1:每条短信可以发160个英文字母或者70个中文字
发送160个英文字母的命令是
AT+CMGS=175
175=15+160; 15是信息头长度,160是字符个数
AT+CMGS=175
> 0891683108200005F011000D91683186882635F10000A7a0E170381C0E87C3E1B0582C168BC562B1583C1E8FC7E3F1783C1E93C96432994C2693C9E572B95C2E97CBE5B2D96C369BCD66B3D97C3E9FCFE7F3F97C3EA3D168341A8D46A3D1E9743A9D4EA7D3E9B45AAD56ABD56AB55ABD5EAFD7EBF57ABD5EB3D96C369BCD66B3D9ED76BBDD6EB7DBEDB6DBED76BBDD6EB7DBFD7EBFDFEFF7FBFD7EC3E170381C0E87C3E1
+CMGS: 132 OK
发送70个字符的命令是
AT+CMGS=155
155=15+140 140=70*2
AT+CMGS=155
> 0891683108200005F011000D91683175901813F10008A78c4E004E004E004E004E004E004E004E004E004E004E8C4E8C4E8C4E8C4E8C4E8C4E8C4E8C4E8C4E8C4E094E094E094E094E094E094E094E094E094E0956DB56DB56DB56DB56DB56DB56DB56DB56DB56DB4E944E944E944E944E944E944E944E944E944E94516D516D516D516D516D516D516D516D516D516D4E034E034E034E034E034E034E034E034E034E03
+CMGS: 137 OK
2:0000A7a0 和 0008A78c 中的a0和8c的计算
这个位的计算是未经ENCODE的字符串的长度,而不ENCODE后的长度
当字符为ASCII时,直接用strlen就行了
当字符为UNICODE时,要用strlen*2
之前错误的计算是认为ENCODE后的长度除以2
3: 修改后的send()函数
经过以下修改就可以支持中文了
long CGSMPhone::Send( char *pNo, char *pMsg, BOOL bReport, BOOL bHandFree, BOOL bAsyn )
{
if( IsOpened() == false ) return( -4 );
if( pNo == NULL ) return( -5 );
if( pMsg == NULL ) return( -5 );
if( m_strSMCenter.IsEmpty() ) return( -1 );
char szSendBuf[1024] = {0};
char sztemp[20] = {0};
char* preceivedata = NULL;
int len = 0;
bool isWideChar=true;
isWideChar=isChinese(pMsg);
if(isWideChar && strlen(pMsg)>140)//控制中文的长度
memset(pMsg+140,'/0',1);
memset(szSendBuf,'/0',1024);
char* p = NumberEncode( (char*)(LPCTSTR)m_strSMCenter ); //短信息中心
len=0;
memcpy( szSendBuf, "0891", 4 );// 91代表国际、ISDN/电话号码,没有必要选取其他的值
len += 4;
if( strncmp( p, "68", 2 ) != 0 ) { //不是以86开头
if( strlen( p ) != 12 ) return( -5 ); //短信息中心设置错误
memcpy( szSendBuf+len, "68", 2 ); //加上86
len += 2;
}
else {
if( strlen( p ) != 14 ) return( -5 ); //以86开头
}
memcpy( szSendBuf+len, p, strlen( p ) ); //添加短信息中心
len += strlen( p );
delete [] p;
if(strncmp(pNo,"86",2)!=0) //不是以86开头的
{ memcpy(szSendBuf+len,"11000D9168",10);
len+=10;
}
else
{memcpy(szSendBuf+len,"11000D91",8);
len+=8;
}
p = NumberEncode( pNo );
memcpy( szSendBuf+len, p, strlen( p ) );
len += strlen( p );
delete [] p;
if( bHandFree ) {// 00代表tp_pid值, 18或08代表tp_dcs,a7代表短消息保存24小时
if(isWideChar){memcpy( szSendBuf+len, "0018A7", 6 );}
else{memcpy( szSendBuf+len, "0010A7", 6 );}
}
else {
if(isWideChar){memcpy( szSendBuf+len, "0008A7", 6 );}
else{memcpy( szSendBuf+len, "0000A7", 6 );}
}
len += 6;
DWORD dw;
if(isWideChar){dw = PDUEncodeChn( pMsg, p );}
else{dw = PDUEncodeEng( pMsg, p )/2;}
if(isWideChar) sprintf( sztemp, "%.2x", dw );
else{sprintf( sztemp, "%.2x", strlen(pMsg) );}
memcpy( szSendBuf+len, sztemp, 2 );
len += 2;
memcpy( szSendBuf+len, p, dw * 2 );
len += dw * 2;
delete [] p;
/*
char aa[5];
memset(aa,'/0',5);
sprintf(aa,"%d",dw);
MessageBox(NULL,aa,"dw",MB_OK);
*/
char cmd[20];
memset(cmd,'/0',20);
sprintf( cmd, "AT+CMGS=%d/r/n",15+strlen(pMsg));
isPosting=true;
Submit( cmd, strlen(cmd) );
Sleep(20);
szSendBuf[len] = 0x1a;// 1a代表短消息结束
len += 1;
memcpy( szSendBuf+len, "/r", 1 );
len += 1;
Submit( szSendBuf, len );
isPosting=false;
return 0;
}