vs2015_MFCSocketClient客户端源码.rar-C++文档类资源-CSDN下载解压密码:blog.csdn.net/txwtech参考:https://blog.csdn.ne更多下载资源、学习资料请访问CSDN下载频道.https://download.csdn.net/download/txwtech/33372547
MFC基于CAsyncSocket套接字客户端代码示范
源文件下载:
创建步骤与调试:
1.stdafx.h中包含 #include
2.
创建CSocketClient类
3.头文件继承CAsyncSocket类
4.项目app文件InitInstance位置添加socket初始化代码
if (!AfxSocketInit())
{
AfxMessageBox(IDP_SOCKETS_INIT_FAILED);
return FALSE;
}
5.添加Init函数
6.定义m_szReceBuf变量
7.宏定义#define MAXSOCKBUF 1024
8.定义长度m_nLength
9.添加OnClose函数
10.添加OnConnect函数
11.添加bool变量m_bConnect
12.定义句柄m_hMsgWnd
13.stdafx.h中添加宏定义:#define WM_SOCKET_LOG WM_USER+200
WM_SOCKET_RECEIVE,并在dlg cpp的对话框消息映射对应两个函数
ON_MESSAGE(WM_SOCKET_LOG,OnLogMsg)
ON_MESSAGE(WM_SOCKET_RECEIVE, OnRecvMsg)
14.CSocketClient类中添加OnReceive函数
15.添加OnSend函数
16.dlg cpp中添加回调函数OnLogMsg,OnRecvMsg
17.添加WriteLog函数
18.添加连接服务器按钮代码
19.dlg cpp.h中添加#include "SocketClient.h"
20.dlg cpp.h中protect添加:CSocketClient* pSocketClient;
21.client类中添加变量m_strHost,m_strIP;
void CMFCSocketClientDlg::OnBnClickedButtonConnect()
{
pSocketClient = new CSocketClient();
UpdateData(TRUE);
pSocketClient->m_strHost = m_Port;
m_IP.GetWindowText(pSocketClient->m_strIP);
pSocketClient->m_hMsgWnd = this->GetSafeHwnd();
int nPort = atoi(pSocketClient->m_strHost);
pSocketClient->Create(0, SOCK_STREAM, FD_READ | FD_WRITE | FD_CONNECT | FD_CLOSE, NULL);
pSocketClient->Connect((LPCTSTR)pSocketClient->m_strIP, nPort);
DWORD nErrno = GetLastError();
//如果onConnect没有触发,调用GetLastError看看 nErrno的值,是不是10093,如果是,那就是app的InitInstance里面
//socket没有初始化,添加如下代码就可以了,
//if (!AfxSocketInit()),如果写成if (!AfxSocketInit),少了一对括号,也会出错啦。
//{
// AfxMessageBox("socket初始化失败");
// return FALSE;
//}
}
---------------------
作者:txwtech
来源:CSDN
原文:https://blog.csdn.net/txwtech/article/details/89820036
版权声明:本文为博主原创文章,转载请附上博文链接!
关键代码:
// MFCSocketClientDlg.cpp : 实现文件
//
#include "stdafx.h"
#include "MFCSocketClient.h"
#include "MFCSocketClientDlg.h"
#include "afxdialogex.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
// 用于应用程序“关于”菜单项的 CAboutDlg 对话框
class CAboutDlg : public CDialogEx
{
public:
CAboutDlg();
// 对话框数据
#ifdef AFX_DESIGN_TIME
enum { IDD = IDD_ABOUTBOX };
#endif
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV 支持
// 实现
protected:
DECLARE_MESSAGE_MAP()
};
CAboutDlg::CAboutDlg() : CDialogEx(IDD_ABOUTBOX)
{
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
CDialogEx::DoDataExchange(pDX);
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)
END_MESSAGE_MAP()
// CMFCSocketClientDlg 对话框
CMFCSocketClientDlg::CMFCSocketClientDlg(CWnd* pParent /*=NULL*/)
: CDialogEx(IDD_MFCSOCKETCLIENT_DIALOG, pParent)
, m_Log(_T(""))
, m_Port(_T("6666"))
, m_editRecv(_T(""))
, m_editSend(_T(""))
{
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
void CMFCSocketClientDlg::DoDataExchange(CDataExchange* pDX)
{
CDialogEx::DoDataExchange(pDX);
DDX_Text(pDX, IDC_EDIT_LOG, m_Log);
DDX_Text(pDX, IDC_EDIT_PORT, m_Port);
DDX_Text(pDX, IDC_EDIT_RECV, m_editRecv);
DDX_Text(pDX, IDC_EDIT_SEND, m_editSend);
DDX_Control(pDX, IDC_IPADDRESS1, m_IP);
}
BEGIN_MESSAGE_MAP(CMFCSocketClientDlg, CDialogEx)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_BN_CLICKED(IDC_BUTTON_CONNECT, &CMFCSocketClientDlg::OnBnClickedButtonConnect)
ON_BN_CLICKED(IDC_BUTTON_SEND, &CMFCSocketClientDlg::OnBnClickedButtonSend)
ON_MESSAGE(WM_SOCKET_LOG,OnLogMsg)
ON_MESSAGE(WM_SOCKET_RECEIVE, OnRecvMsg)
END_MESSAGE_MAP()
// CMFCSocketClientDlg 消息处理程序
BOOL CMFCSocketClientDlg::OnInitDialog()
{
CDialogEx::OnInitDialog();
// 将“关于...”菜单项添加到系统菜单中。
// IDM_ABOUTBOX 必须在系统命令范围内。
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);
CMenu* pSysMenu = GetSystemMenu(FALSE);
if (pSysMenu != NULL)
{
BOOL bNameValid;
CString strAboutMenu;
bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX);
ASSERT(bNameValid);
if (!strAboutMenu.IsEmpty())
{
pSysMenu->AppendMenu(MF_SEPARATOR);
pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
}
}
// 设置此对话框的图标。 当应用程序主窗口不是对话框时,框架将自动
// 执行此操作
SetIcon(m_hIcon, TRUE); // 设置大图标
SetIcon(m_hIcon, FALSE); // 设置小图标
// TODO: 在此添加额外的初始化代码
m_IP.SetWindowText("127.0.0.1");
pSocketClient = NULL;
return TRUE; // 除非将焦点设置到控件,否则返回 TRUE
}
void CMFCSocketClientDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
if ((nID & 0xFFF0) == IDM_ABOUTBOX)
{
CAboutDlg dlgAbout;
dlgAbout.DoModal();
}
else
{
CDialogEx::OnSysCommand(nID, lParam);
}
}
// 如果向对话框添加最小化按钮,则需要下面的代码
// 来绘制该图标。 对于使用文档/视图模型的 MFC 应用程序,
// 这将由框架自动完成。
void CMFCSocketClientDlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // 用于绘制的设备上下文
SendMessage(WM_ICONERASEBKGND, reinterpret_cast(dc.GetSafeHdc()), 0);
// 使图标在工作区矩形中居中
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// 绘制图标
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialogEx::OnPaint();
}
}
//当用户拖动最小化窗口时系统调用此函数取得光标
//显示。
HCURSOR CMFCSocketClientDlg::OnQueryDragIcon()
{
return static_cast(m_hIcon);
}
void CMFCSocketClientDlg::OnBnClickedButtonConnect()
{
pSocketClient = new CSocketClient();
UpdateData(TRUE);
pSocketClient->m_strHost = m_Port;
m_IP.GetWindowText(pSocketClient->m_strIP);
pSocketClient->m_hMsgWnd = this->GetSafeHwnd();
int nPort = atoi(pSocketClient->m_strHost);
pSocketClient->Create(0, SOCK_STREAM, FD_READ | FD_WRITE | FD_CONNECT | FD_CLOSE, NULL);
pSocketClient->Connect((LPCTSTR)pSocketClient->m_strIP, nPort);
DWORD nErrno = GetLastError();
//如过onConnect没有触发,调用GetLastError看看 nErrno的值,是不是10093,如果是,那就是app的InitInstance里面
//socket没有初始化,添加如下代码就可以了,
//if (!AfxSocketInit()),如果写成if (!AfxSocketInit),少了一对括号,也会出错啦。
//{
// AfxMessageBox("socket初始化失败");
// return FALSE;
//}
}
void CMFCSocketClientDlg::OnBnClickedButtonSend()
{
// TODO: 在此添加控件通知处理程序代码
if (pSocketClient == NULL)
{
WriteLog("SOCKET没有初始化");
return;
}
if (!pSocketClient->m_bConnect)
{
WriteLog("SOCKET没有链接服务器");
return;
}
UpdateData(TRUE);
int iLen = m_editSend.GetLength();
BYTE* s = new BYTE[iLen];
memset(s,0x00,iLen);
memcpy(s,(LPCTSTR)m_editSend,iLen);
pSocketClient->Send((unsigned char*)s,iLen);
WriteLog("发送数据中。。。。。");
}
HRESULT CMFCSocketClientDlg::OnLogMsg(WPARAM dwEvent, LPARAM dwLen)
{
if (!dwLen) return 0;
BYTE* temp = new BYTE[dwLen+1];
memset(temp,0x00,dwLen+1);
memcpy(temp,(const void*)dwEvent,dwLen);
WriteLog((LPCTSTR)temp);
//return E_NOTIMPL;
return 0;
}
HRESULT CMFCSocketClientDlg::OnRecvMsg(WPARAM dwEvent, LPARAM dwLen)
{
//return E_NOTIMPL;
if (!dwLen) return 0;
BYTE* temp = new BYTE[dwLen + 1];
memset(temp, 0x00, dwLen + 1);
memcpy(temp, (const void*)dwEvent, dwLen);
CString log;
log.Format("接收到服务器数据=%s\r\n", (LPCTSTR)temp);
if (m_editRecv.GetLength() > 50000) m_editRecv = "";
m_editRecv += log;
UpdateData(FALSE);
return 0;
}
void CMFCSocketClientDlg::WriteLog(CString log)
{
m_Log += log;
m_Log += "\r\n";
UpdateData(FALSE);
}
CSocketClient类:
#include "stdafx.h"
#include "SocketClient.h"
CSocketClient::CSocketClient()
{
m_nLength = 0;
memset(m_szReceBuf, 0, sizeof(m_szReceBuf));
memset(m_szSendBuf, 0, sizeof(m_szSendBuf));
m_bConnect = FALSE;
m_hMsgWnd = NULL;
m_strHost.Empty();
m_strIP.Empty();
}
CSocketClient::~CSocketClient()
{
if (m_hSocket != INVALID_SOCKET)
Close();
}
void CSocketClient::Init()
{
memset(m_szReceBuf,0,sizeof(m_szReceBuf));
m_nLength = MAXSOCKBUF;
}
//void CSocketClient::OnClose()
//{
// CAsyncSocket::OnClose();
//}
void CSocketClient::OnClose(int nErrorCode)
{
CAsyncSocket::OnClose(nErrorCode);
}
void CSocketClient::OnConnect(int nErrorCode)
{
char* pLog = new char[200];
if (nErrorCode == 0)
{
sprintf(pLog, "链接服务器成功");
m_bConnect = TRUE;
}
else
sprintf(pLog,"连接服务器失败,错误代码=%d",nErrorCode);
if (m_hMsgWnd != NULL)
::SendMessage(m_hMsgWnd,WM_SOCKET_LOG,(WPARAM)pLog,strlen(pLog));
}
void CSocketClient::OnReceive(int nErrorCode)
{
m_nLength = Receive((void*)m_szReceBuf,MAXSOCKBUF,0);
m_szReceBuf[m_nLength] = 0;
char* recvBuf = new char[MAXSOCKBUF];
sprintf(recvBuf,(const char*)m_szReceBuf,m_nLength);
if (m_hMsgWnd != NULL)
::SendMessage(m_hMsgWnd,WM_SOCKET_RECEIVE,(WPARAM)recvBuf,strlen(recvBuf));
CAsyncSocket::OnReceive(nErrorCode);
}
void CSocketClient::OnSend(int nErrorCode)
{
int nSendBytes = Send(m_szSendBuf,strlen(m_szSendBuf),0);
char* pLog = new char[200];
sprintf(pLog,"客户端发送%d个数据",nSendBytes);
if (m_hMsgWnd != NULL)
::SendMessage(m_hMsgWnd,WM_SOCKET_LOG,(WPARAM)pLog,strlen(pLog));
AsyncSelect(FD_READ|FD_CLOSE);
}
套接字CAsyncSocket调用connect没有触发onConnect解决方法