📄 filetransfersdlg.cpp
字号:
m_nTimer = SetTimer(1, 50000, NULL);
}
}
void CFileTransfersDlg::OnStopTransfers()
{
if(m_bIsWait)
{
if(MessageBox(_T("真的要停止等待吗?"), _T("警告"), MB_ICONEXCLAMATION|MB_YESNO) == IDYES)
{
m_bIsWait = FALSE;
if(!m_bIsClient)
{
//停止ID为2的计时器
if(KillTimer(2))
{
//结束监听
CSocket sockClient;
sockClient.Create();
sockClient.Connect(_T("127.0.0.1"), m_wPort + PORT);
sockClient.Close();
}
}
else
{
//停止ID为1的计时器
if(KillTimer(1))
{
//告诉对方发送等待被取消
CMessage* pMsg = new CMessage(CANCEL);
m_psockClient->SendMsg(pMsg);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(TRUE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(FALSE);
}
}
}
return ;
}
if(MessageBox(_T("真的要停止文件传输吗?"), _T("警告"), MB_ICONEXCLAMATION|MB_YESNO) == IDYES)
{
m_bIsStop = TRUE;
return ;
}
}
int CFileTransfersDlg::GetLocalHostInfo(CString &strHostName, CString &strIPAddress)
{
char szHostName[256];
if(gethostname(szHostName, sizeof(szHostName)))
{
strHostName = _T("");
MessageBox(GetError(GetLastError()), _T("错误"), MB_ICONHAND|MB_OK);
return -1;
}
PHOSTENT hostinfo;
if((hostinfo = gethostbyname(szHostName)) == NULL)
return GetLastError();
LPCSTR ip = inet_ntoa (*(struct in_addr *)*hostinfo->h_addr_list);
strIPAddress = ip;
strHostName = szHostName;
return 0;
}
CString CFileTransfersDlg::GetError(DWORD error)
{
CString strError;
switch(error)
{
case WSANOTINITIALISED:
strError="初始化错误";
break;
case WSAENOTCONN:
strError="对方没有启动";
break;
case WSAEWOULDBLOCK :
strError="对方已经关闭";
break;
case WSAECONNREFUSED:
strError="连接的尝试被拒绝";
break;
case WSAENOTSOCK:
strError="在一个非套接字上尝试了一个操作";
break;
case WSAEADDRINUSE:
strError="特定的地址已在使用中";
break;
case WSAECONNRESET:
strError="与主机的连接被关闭";
break;
default:
strError="一般性错误";
}
return strError;
}
void CFileTransfersDlg::ProcessAccept()
{
CClientSocket* pSocket = new CClientSocket(this);
//将请求接收下来,得到一个新的套接字pSocket
if(m_psockServer->Accept(*pSocket))
{
//初始化套接字pSocket
pSocket->Init();
CMessage* pMsg;
//如果m_psockClient套接字为空,则表示还没有和任何客户端建立连接
if(m_psockClient == NULL)
{
//向客户端发送一个消息,表示连接被接受
pMsg = new CMessage(CONNECT_BE_ACCEPT);
pSocket->SendMsg(pMsg);
m_psockClient = pSocket;
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
}
else
{
//否则向客户端发一个信息,服务器已经存在连接
pMsg = new CMessage(CONNECT_BE_REFUSE);
pSocket->SendMsg(pMsg);
}
}
}
void CFileTransfersDlg::ProcessReceive(CClientSocket* pSocket)
{
//获取信息
CMessage* pMsg = new CMessage();
pSocket->ReceiveMsg(pMsg);
//当消息类型为连接被接受时执行该if语句里面的内容
if(pMsg->m_nType == CONNECT_BE_ACCEPT)
{
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
return;
}
//当消息类型为连接被拒绝时执行该if语句里面的内容
if(pMsg->m_nType == CONNECT_BE_REFUSE)
{
MessageBox(_T("服务器已经和另外的客户端建立连接,请等一下再连接。"), _T("错误"), MB_ICONHAND);
delete m_psockClient;
m_psockClient = NULL;
GetDlgItem(IDC_RADIO_SERVER)->EnableWindow(TRUE);
GetDlgItem(IDC_RADIO_CLIENT)->EnableWindow(TRUE);
GetDlgItem(IDC_IPADDRESS)->EnableWindow(TRUE);
GetDlgItem(IDC_PORT)->EnableWindow(TRUE);
GetDlgItem(IDC_BEGIN)->EnableWindow(TRUE);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(FALSE);
return ;
}
//当消息类型为连接被断开时执行该if语句里面的内容
if(pMsg->m_nType == DISCONNECT)
{
// MessageBox(_T("对方已经关闭"), _T("警告"), MB_ICONHAND);
if(m_psockClient != NULL)
{
delete m_psockClient;
m_psockClient = NULL;
}
if(m_nServerType == CLIENT)
{
GetDlgItem(IDC_RADIO_SERVER)->EnableWindow(TRUE);
GetDlgItem(IDC_RADIO_CLIENT)->EnableWindow(TRUE);
GetDlgItem(IDC_PORT)->EnableWindow(TRUE);
GetDlgItem(IDC_BEGIN)->EnableWindow(TRUE);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(FALSE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(FALSE);
GetDlgItem(IDC_IPADDRESS)->EnableWindow(TRUE);
}
else
{
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(FALSE);
}
return ;
}
//当收到传输文件请求时执行该if语句里面的内容
if(pMsg->m_nType == REQUEST)
{
m_bIsWait = TRUE;
m_strFileName = pMsg->m_strFileName;
m_dwFileSize = pMsg->m_dwFileSize;
//CFileDialog dlg(FALSE, NULL, NULL, OFN_HIDEREADONLY|OFN_OVERWRITEPROMPT, "所有文件 (*.*)|*.*||", this);
//dlg.m_ofn.lpstrTitle = _T("另存为");
//strcpy(dlg.m_ofn.lpstrFile, m_strFileName.GetBuffer(m_strFileName.GetLength()));
CString a;
a=m_strFileName;
// if(dlg.DoModal() == IDOK)
// {
if(m_bIsWait == FALSE)
{
MessageBox(_T("对方已经取消文件发送"), _T("警告"), MB_ICONEXCLAMATION);
return ;
}
m_bIsClient = FALSE;
//m_strPath = dlg.GetPathName();
m_strPath="d:\\file\\"+a;
GetDlgItem(IDC_DISCONNECT)->EnableWindow(FALSE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(FALSE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(TRUE);
m_strFileSize.Format("%ld 字节", m_dwFileSize);
// GetDlgItem(IDC_FILE_NAME)->SetWindowText(dlg.GetFileName());
GetDlgItem(IDC_FILE_NAME)->SetWindowText(a);
GetDlgItem(IDC_FILE_SIZE)->SetWindowText(m_strFileSize);
GetDlgItem(IDC_TRANSFERS_TIP)->SetWindowText(_T("已收到:"));
//启动接收文件的线程
pThreadListen = ::AfxBeginThread(_ListenThread, this);
return ;
// }
if(m_bIsWait == TRUE)
{
//告诉对方文件发送请求被拒绝
CMessage* pMsg = new CMessage(REFUSE);
m_psockClient->SendMsg(pMsg);
}
m_bIsWait = FALSE;
return ;
}
//当对方同意且准备好接收文件时执行该if语句里面的内容
if(pMsg->m_nType == ACCEPT)
{
KillTimer(1);
m_bIsWait = FALSE;
//启动文件发送线程
pThreadSend = ::AfxBeginThread(_SendThread, this);
return ;
}
//当发送文件请求被拒绝时执行该if语句里面的内容
if(pMsg->m_nType == REFUSE)
{
m_bIsWait = FALSE;
MessageBox(_T("请求被拒绝"), _T("警告"), MB_ICONEXCLAMATION);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(TRUE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(FALSE);
return ;
}
//当对方取消文件传输时执行该if语句里面的内容
if(pMsg->m_nType == CANCEL)
{
m_bIsWait = FALSE;
return ;
}
return ;
}
void CFileTransfersDlg::SendFile(CSocket &senSo)
{
m_bIsTransmitting = TRUE;
//打开要发送的文件
CFile file;
if(!file.Open(m_strPath, CFile::modeRead | CFile::typeBinary))
{
AfxMessageBox(_T("文件打开失败"));
GetDlgItem(IDC_DISCONNECT)->EnableWindow(TRUE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(FALSE);
senSo.Close();
return ;
}
m_ctrlProgress.SetRange32(0, m_dwFileSize);
int nSize = 0, nLen = 0;
DWORD dwCount = 0;
char buf[BLOCKSIZE] = {0};
file.Seek(0, CFile::begin);
//开始传送文件
for(;;)
{
//一次读取BLOCKSIZE大小的文件内容
nLen = file.Read(buf, BLOCKSIZE);
if(nLen == 0)
break;
//发送文件内容
nSize = senSo.Send(buf, nLen);
dwCount += nSize;
m_ctrlProgress.SetPos(dwCount);
CString strTransfersSize;
strTransfersSize.Format("%ld 字节", dwCount);
GetDlgItem(IDC_RECEIVE_SIZE)->SetWindowText(strTransfersSize);
if(m_bIsStop)
{
m_bIsStop = FALSE;
break;
}
if(nSize == SOCKET_ERROR)
break;
}
//关闭文件
file.Close();
//关闭套接字
senSo.Close();
if(m_dwFileSize == dwCount)
AfxMessageBox(_T("文件发送成功"));
else
AfxMessageBox(_T("文件发送失败"));
m_ctrlProgress.SetPos(0);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(TRUE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(FALSE);
m_bIsTransmitting = FALSE;
}
void CFileTransfersDlg::ReceiveFile(CSocket &recSo)
{
//停止等待超时计时器
KillTimer(2);
m_bIsWait = FALSE;
m_bIsTransmitting = TRUE;
m_ctrlProgress.SetRange32(0, m_dwFileSize);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(FALSE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(FALSE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(TRUE);
int nSize = 0;
DWORD dwCount = 0;
char buf[BLOCKSIZE] = {0};
//创建一个文件
CFile file(m_strPath, CFile::modeCreate|CFile::modeWrite);
//开始接收文件
for(;;)
{
//每次接收BLOCKSIZE大小的文件内容
nSize = recSo.Receive(buf, BLOCKSIZE);
if(nSize == 0)
break;
//将接收到的文件写到新建的文件中去
file.Write(buf, nSize);
dwCount += nSize;
m_ctrlProgress.SetPos(dwCount);
CString strTransfersSize;
strTransfersSize.Format("%ld 字节", dwCount);
GetDlgItem(IDC_RECEIVE_SIZE)->SetWindowText(strTransfersSize);
//用户是否要停止接收
if(m_bIsStop)
{
m_bIsStop = FALSE;
break;
}
}
//关闭文件
file.Close();
//关闭套接字
recSo.Close();
// if(m_dwFileSize == dwCount)
// AfxMessageBox(_T("文件接收成功"));
// else
// AfxMessageBox(_T("文件接收失败"));
m_ctrlProgress.SetPos(0);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(TRUE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(FALSE);
m_bIsTransmitting = FALSE;
}
void CFileTransfersDlg::TransfersFailed()
{
GetDlgItem(IDC_DISCONNECT)->EnableWindow(TRUE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(FALSE);
}
LRESULT CFileTransfersDlg::OnAcceptTransfers(WPARAM wParam, LPARAM lParam)
{
//告诉对方文件请求被接受且准备好接收
CMessage* pMsg = new CMessage(ACCEPT);
m_psockClient->SendMsg(pMsg);
//设置一个ID为2的超时计时器
m_nTimer = SetTimer(2, 5000, NULL);
return 0;
}
void CFileTransfersDlg::OnTimer(UINT nIDEvent)
{
switch(nIDEvent)
{
//ID为1的计时器
case 1:
{
//结束ID为1的计时器
KillTimer(1);
m_bIsWait = FALSE;
//告诉对方发送等待被取消
CMessage* pMsg = new CMessage(CANCEL);
m_psockClient->SendMsg(pMsg);
MessageBox(_T("等待超时"), _T(" 警告"), MB_ICONEXCLAMATION);
GetDlgItem(IDC_DISCONNECT)->EnableWindow(TRUE);
GetDlgItem(IDC_SELECT_FILE)->EnableWindow(TRUE);
GetDlgItem(IDC_STOP_TRANSFERS)->EnableWindow(FALSE);
break;
}
//ID为2的计时器
case 2:
{
//结束ID为2的计时器
KillTimer(2);
//结束监听
CSocket sockClient;
sockClient.Create();
sockClient.Connect(_T("127.0.0.1"), m_wPort + PORT);
sockClient.Close();
break;
}
}
CDialog::OnTimer(nIDEvent);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -