关于孙鑫vc++深入详解的第16章聊天工具的疑问

thefutureisour 2012-11-09 09:06:12
这个聊天工具的编写思路大概是这样:

使用非阻塞的套接字,在初始化套接字时,使用

if(SOCKET_ERROR == WSAAsyncSelect(m_socket,m_hWnd,UM_SOCK,FD_READ))
{
MessageBox("注册网络读取事件失败!");
return FALSE;
}


将UM_SOCK与读事件绑定起来,在消息响应函数中显示接收的消息。
我想做的事情,是如何能够在发送消息时,将发送的消息也显示出来。我有一个笨办法可以使用:
发送消息时,再发送一条自定义消息,消息的参数是要发送的字符串,然后在消息响应函数中,先获取原来的内容,再加上发送的内容,一起SetDlgItemText上去。

我的问题是,有没有其他的方法,最好是利用了WSAAsyncSelect。
说白了,就是我不会用这个函数,具体的说,是两个问题:
1.MSDN上说:Issuing a WSAAsyncSelect for a socket cancels any previous WSAAsyncSelect or WSAEventSelect for the same socket. For example, to receive notification for both reading and writing, the application must call WSAAsyncSelect with both FD_READ and FD_WRITE, as follows:

rc = WSAAsyncSelect(s, hWnd, wMsg, FD_READ|FD_WRITE);

那我是不是应该在初始化的时候就改成这样呢?然后在消息响应函数中,switch case一下看是哪个消息。
2.如何设置将要发送的数据传递给UM_SOCK的参数?

或者,我这个想法完全就是错的,根本错误的理解了这个函数。
...全文
189 6 打赏 收藏 转发到动态 举报
写回复
用AI写文章
6 条回复
切换为时间正序
请发表友善的回复…
发表回复
转角天边 2012-11-10
  • 打赏
  • 举报
回复
引用 5 楼 thefutureisour 的回复:
引用 4 楼 anhuizhuanjiao 的回复:引用 3 楼 thefutureisour 的回复:引用 2 楼 anhuizhuanjiao 的回复:将发送的消息显示出来直接再send完之后用SetDlgItemText()函数就可以了啊 C/C++ code12345678910111213141516171819202122232425262728293031……
共同学习
thefutureisour 2012-11-10
  • 打赏
  • 举报
回复
引用 4 楼 anhuizhuanjiao 的回复:
引用 3 楼 thefutureisour 的回复:引用 2 楼 anhuizhuanjiao 的回复:将发送的消息显示出来直接再send完之后用SetDlgItemText()函数就可以了啊 C/C++ code1234567891011121314151617181920212223242526272829303132333435363738394041424344……
这不算骗,至少给了我一个可行的思路么,我已近搞定了。多谢多谢啊!
转角天边 2012-11-09
  • 打赏
  • 举报
回复
引用 3 楼 thefutureisour 的回复:
引用 2 楼 anhuizhuanjiao 的回复:将发送的消息显示出来直接再send完之后用SetDlgItemText()函数就可以了啊 C/C++ code1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950void CChatDlg:……
上次骗了你1分,这次骗了30分
thefutureisour 2012-11-09
  • 打赏
  • 举报
回复
引用 2 楼 anhuizhuanjiao 的回复:
将发送的消息显示出来直接再send完之后用SetDlgItemText()函数就可以了啊 C/C++ code1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950void CChatDlg::OnBtnSend() { // TODO:……
我瞬间觉得自己很笨!
转角天边 2012-11-09
  • 打赏
  • 举报
回复
将发送的消息显示出来直接再send完之后用SetDlgItemText()函数就可以了啊

void CChatDlg::OnBtnSend() 
{
	// TODO: Add your control notification handler code here
	DWORD  dwIP;
	((CIPAddressCtrl*)GetDlgItem(IDC_IPADDRESS1))->GetAddress(dwIP);
	
	SOCKADDR_IN  addrto;
	addrto.sin_family=AF_INET;
	addrto.sin_port=htons(6000);
	addrto.sin_addr.S_un.S_addr=htonl(dwIP);
	
	CString  strSend;
	GetDlgItemText(IDC_EDIT_SEND,strSend);
	
	sendto(m_socket,strSend,strSend.GetLength()+1,0,(SOCKADDR*)&addrto,sizeof(SOCKADDR));
	
	/*
	CString  st;
	GetDlgItemText(IDC_EDIT_RECV,st);
	strSend+="\r\n";
	st+="你说 : ";
	st+=strSend;
	SetDlgItemText(IDC_EDIT_RECV,st);
	SetDlgItemText(IDC_EDIT_SEND,"");
	*/
	//获取本机名
	char  name[255];
	HOSTENT*  hostent;
	if(SOCKET_ERROR==gethostname(name,sizeof(name)))
	{
		MessageBox("获取主机名失败!");
		return;
	}
	//获取本机IP
	hostent=gethostbyname(name);	
	CString  st;
	GetDlgItemText(IDC_EDIT_RECV,st);
	strSend+="\r\n";
	st+=inet_ntoa(*(in_addr *)hostent->h_addr_list[0]);
	st+="  说:  ";
	st+=strSend;
	SetDlgItemText(IDC_EDIT_RECV,st);
	SetDlgItemText(IDC_EDIT_SEND,"");
	//让滚动条始终处在底端
	CEdit *pedit=(CEdit*)GetDlgItem(IDC_EDIT_RECV); 
	int   nline=pedit-> GetLineCount(); 
	pedit-> LineScroll(nline-1);

}
这是我以前写的
Eleven 2012-11-09
  • 打赏
  • 举报
回复
if(SOCKET_ERROR == WSAAsyncSelect(m_socket,m_hWnd,UM_SOCK,FD_READ)) ------------ 简单的说就是你注册了FD_READ事件,如果有数据到达,你就会收到一个UM_SOCK消息,然后你就可以调用阻塞函数recv,将数据从系统缓冲区copy到用户缓冲区。

16,471

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC相关问题讨论
社区管理员
  • 基础类社区
  • Web++
  • encoderlee
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

        VC/MFC社区版块或许是CSDN最“古老”的版块了,记忆之中,与CSDN的年龄几乎差不多。随着时间的推移,MFC技术渐渐的偏离了开发主流,若干年之后的今天,当我们面对着微软的这个经典之笔,内心充满着敬意,那些曾经的记忆,可以说代表着二十年前曾经的辉煌……
        向经典致敬,或许是老一代程序员内心里面难以释怀的感受。互联网大行其道的今天,我们期待着MFC技术能够恢复其曾经的辉煌,或许这个期待会永远成为一种“梦想”,或许一切皆有可能……
        我们希望这个版块可以很好的适配Web时代,期待更好的互联网技术能够使得MFC技术框架得以重现活力,……

试试用AI创作助手写篇文章吧