即时通讯编程(五)

来源:互联网 发布:ps4gta5淘宝刷钱的店 编辑:程序博客网 时间:2024/05/01 23:23


即时通讯编程(五)

作者:邵盛松  2009-06-02   QQ:346646173

目的:开发基于XMPP(Extensible Messaging and Presence Protocol)协议的即时通讯。
开发工具: Visual C++ 2005
本篇文章主要内容:登录功能的实现

一 界面设计
 两个编辑框,一个用于输入用户名称,一个用户输入密码。
 三个按钮一个登录按钮,一个取消登录按钮,一个用于设置IP(功能暂时未加)的按钮
为登录窗体添加类,类名是CDlgLogin
在登录对话框DlgLogin.h中
public:
CEdit m_Edit_Name;
CEdit m_Edit_Password;
CButton m_Button_Login;
CButton m_Button_Set;
CString m_Edit_strName;
CString m_Edit_strPassword;
为CDlgLogin类添加窗体初始化函数
BOOL CDlgLogin::OnInitDialog(void)
{
CDialog::OnInitDialog();
//取消登录按钮隐藏
m_Buttion_Disconnection.ShowWindow(FALSE);
return 0;

}

用户点击登录按钮
void CDlgLogin::OnBnClickedButtonLogin()
{
 // TODO: 在此添加控件通知处理程序代码
  UpdateData(true);
  //断开连接按钮显示
   m_Buttion_Disconnection.ShowWindow(TRUE);
   m_Button_Login.ShowWindow(FALSE);
   m_Button_Set.ShowWindow(FALSE);
   m_Edit_Name.EnableWindow( false);
   m_Edit_Password.EnableWindow(false);

    //所有控件不可用
  
 g_bLogin=false;
 if (m_Edit_strName.IsEmpty() || m_Edit_strPassword.IsEmpty())
 {
  MessageBox(_T("用户或者密码不能为空"),_T("登录提示"),MB_OK);
 }
 else
 {
   UpdateData(true);
  bLogin=true;//点击登录按钮
  //执行start
  CConnectionManagement *r = new CConnectionManagement();
  r->Start();


 }
 
  UpdateData(false);
 SetTimer(1, 1000, NULL);//用于判断是否连接成功
}

void CDlgLogin::OnTimer(UINT_PTR nIDEvent)
{
 // TODO: 在此添加消息处理程序代码和/或调用默认值
 if(nIDEvent==1)
 {  
  //处理事件 如果登录成功将关闭登录窗体 

  if (g_bLogin==true)
  {
   OnOK();
   KillTimer(1);
  }
 }

 CDialog::OnTimer(nIDEvent);
}

用户点击取消连接按钮,所有控件可用
void CDlgLogin::OnBnClickedButtonDisconnection()
{
 // TODO: 在此添加控件通知处理程序代码
 m_Buttion_Disconnection.ShowWindow(FALSE);
 m_Button_Login.ShowWindow(TRUE);
 m_Button_Set.ShowWindow(TRUE);
 m_Edit_Name.EnableWindow( true);
 m_Edit_Password.EnableWindow(true);
 return;
}
二 登录功能实现
然后在MsgRecvProc 函数中将在界面输入的用户名和密码传递过来即可
ConnectionManagement= new CConnectionManagement();
//在Unicode 下CString 转std:: string解决方案
 ///*****************************************************************************/
 //用户名的转换
 CStringA   strA;
 CString strServer=_T("机器名/gloox");
 CString strJID;
 strJID.Format(_T("%s@%s"),DlgLogin->m_Edit_strName,strServer);
 strA=strJID.GetBuffer(0);
 strJID.ReleaseBuffer(); 
 std::string stdstrJID(strA.GetBuffer(0));
 strA.ReleaseBuffer();
 ///*****************************************************************************/
 //密码的转换
 CString strPWD= DlgLogin->m_Edit_strPassword;
 //AfxMessageBox(strPWD);
 strA=strPWD.GetBuffer(0);
 strPWD.ReleaseBuffer(); 
 std::string stdstrpassword(strA.GetBuffer(0));  
 strA.ReleaseBuffer();
 ///*****************************************************************************/ 
 JID jid(stdstrJID);
 j = new Client( jid,stdstrpassword);
 j->registerConnectionListener(ConnectionManagement);
 j->registerMessageSessionHandler(ConnectionManagement, 0 );

三 编译经验
1 std::string stdstrJID = strJID.operator LPCTSTR();在多字节下转换成功,在Unicode转换失败
错误提示为
error C2440: 'initializing' : cannot convert from 'const wchar_t *' to 'std::basic_string<_Elem,_Traits,_Ax>'
No constructor could take the source type, or constructor overload resolution was ambiguous.
解决方案
类似如下语句
 CString strPWD= DlgLogin->m_Edit_strPassword;
 //AfxMessageBox(strPWD);
 strA=strPWD.GetBuffer(0);
 strPWD.ReleaseBuffer(); 
 std::string stdstrpassword(strA.GetBuffer(0));  
 strA.ReleaseBuffer();

2 调试中出现以下类似警告
gloox.lib(base64.obj) : warning LNK4204: “e:/路径/Debug/vc80.pdb”缺少引用模块的调试信息;正在链接对象,如同没有调

试信息一样
产生原因及解决方案
在添加的gloox.lib的路径中没有包含obj文件,只要将gloox.lib路径设置为编译gloox库debug目录或者将obj文件复制到gloox.lib

的路径

以上在 Visual C++2005 下调试通过