小弟最近学习 想做一个聊天的小程序当客户端A 和 客户端B 通讯的时候A 接受到 B 的消息A在事件处理中new 一个Form FormMsg  并Show()然后 调用 FormMsg 的方法(显示消息)
程序运行后,可以看到在B发出消息后,A弹出了Form,并且Form上也显示了数据,但是显示完数据后,Form就无法响应了因为A和B接受发送数据都是多线程的 我想这可能和多线程与Form有关吧 网上看了几篇都不是很懂 请大侠们指教!
A 中处理接受消息的事件:(大意如此)private void StringInputHandler(String Data)
{
    FormMSG newForm = new FormMSG();
    newForm.Show();
    newForm.ShowText(Data);
}小弟先谢谢大家了!!

解决方案 »

  1.   

    i think you should attach a thread to "newForm", to let it deal with messages and commands such as mouse click. Otherwise it will not respond to anything...
      

  2.   

    form只是一个显示的介质,你应该自己写一个接受的client socket程序,
    由这个client socket和你的server进行通讯,然后在client socket中把
    接受到的东西往你的form上显示
      

  3.   

    关注一下,4年前就快2星了,可是后来不搞.net了,现在回来接点分,争取再升一星!
      

  4.   


    gambolgs(Gambol) 
    Bote_China() 两位说的对 但是我不太清楚怎么改我试着改为(大意如此,我用的ParameterizedThreadStart传参数)private void StringInputHandler(String Data)
    {
        Thread th = new Thread()
        th.start
    }void NewForm()
    {
        FormMSG newForm = new FormMSG();
        newForm.Show();
        newForm.ShowText(Data);   
    }但是这个newForm一显示 瞬间又关闭了 怎样给这个Form一个独立的线程又能接受到父窗体的消息和调用呢??
      

  5.   

    回 zhenglf(问路人)因为设想着可以和多个人聊天 所以Socket是在一个父窗体中监听的根据发来消息中带有的用户信息 再建立不同的子窗体来显示现在问题就是子窗体建立显示后就没有响应了 或者就是子窗体有响应但是子窗体的方法接受不到父窗体的调用了请大家指教
      

  6.   

    在父窗口监听没有问题,
    父窗体接收到连接请求后,
    就创建一个子窗体,同时生成一个通讯子线程,
    把这个通讯子线程通过窗口的构造函数传过去,
    接下去有这个通讯子线程和server进行通讯。
    子线程收到数据后,通过委托方式让数据显示在子窗体中
      

  7.   

    回上面:就创建一个子窗体,同时生成一个通讯子线程,这个意思是每个子窗体就要有一个Socket监听了?但是这样子每个窗体都要占用一个端口啊?我只想要父窗体与其它节点通讯,父窗体通过调用子窗体的方法把结果传给子窗体
      

  8.   

    如果像你那么做的话,怎么实现实时多人对话。
    如果理解FTP的处理方式,你就会知道应该用什么方式去做。
      

  9.   

    还是没有解决 一个Form Show了之后没有响应是怎么回事啊
      

  10.   

    只要StringInputHandler 的程序段一运行完不管是直接Show的Form 还是用新线程Show的Form  还是用Application.Run()的Form都变成无法响应的状态了
      

  11.   

    看一下这文章,也许有帮助
    http://www.devarticles.com/c/a/C-Sharp/Socket-Programming-in-C-sharp-Part-II/1/
      

  12.   

    回上面:文章看了 但是好像帮助不上啊
    文章中好像只是讲Socket的异步传输数据 但没有Form的问题啊我这里用的codeproject上有个人写的一个类 XYNetSocket.XYNetServer  server
    这个XYNetServer 是多线程的在父窗体中 server.StartServer() 后 如果有消息传来 就会响应StringInputHandler
    我是想新建一个子窗体 并显示数据在上面 但是现在子窗体显示数据后 就无法响应了 就是鼠标点击没有 窗体也补重画了 private void StringInputHandler(String Data)
    {
        FormMSG newForm = new FormMSG();
        newForm.Show();
        newForm.ShowText(Data);
    }这多线程和WinForm我比较糊涂了 请大家指教啊!!
      

  13.   

    问题的原因可能是事件由多线程抛出,窗体由该线程创建,在事件处理完成之后,线程进入下一次消息接收循环,线程一直处于等待接受消息的状态,导致显示的窗体处于假死状态========================肯定的,一个消息过来你就new一个窗体 显然不符合常理阿
      

  14.   

    回楼上:对某一个远程用户来的消息 我是第一次是New一个窗体 并把这个窗体加入了个List<Form> list每次接受消息 都会查找对应的窗体是否已经存在于list  如果存在就不New了 而直接显示如果不存在 就进行第一次的new并加入list我是这么写的程序 但现在问题就是这样子 现在就只是测试接受一条消息 就无法响应了窗体是假死 但是怎么能让窗体正常呢?
      

  15.   

    public delegate void ShowMessage(string s);//定义委托
    //用委托调用显示窗体的方法
    ShowMessage showMsg = new ShowMessage(StringInputHandler);
    Object[] obj = {Data};//Data是传入方法的参数
    this.Invoke(showMsg,obj);
      

  16.   

    楼上大哥 能否详细说说 private void StringInputHandler(String Data)
    {
        FormMSG newForm = new FormMSG();
        newForm.Show();
        newForm.ShowText(Data);
    }这段代码用你所说使用委托怎么修改呢??要改 Show() 和 ShowText()吗?谢谢阿
      

  17.   

    你真快啊我已经试过用这个了 我这样子写if (newForm.InvokeRequired)
    {
        newForm.Invoke(new ShowHandler(newForm.Show));
        newForm.Invoke(new AppendTextHandler(newForm.AppendText), new object[] { temp.Name, ss[1], false });
    }如果这样子 直接看不到窗体了 但是能接受到数据
      

  18.   

    我认为你的StringInputHandler是一个带参数的方法
    在窗体加上我定义的委托,再在你要调用StringInputHandler方法的地方改为我下面那几行代码就行了..
      

  19.   

    回楼上:
    “再在你要调用StringInputHandler方法的地方”StringInputHandler 是处理事件的方法啊private void StringInputHandler(String sRemoteAddress, int nRemotePort, String sData)我只是把它加上而已啊 ??
      

  20.   

    StringInputHandler 不是我调用的方法是处理事件的 接受到字符串的事件我测试中
    if (newForm.InvokeRequired) 一直是false
    但是newForm.Show() 就又会没响应
      

  21.   

    又:每次窗体 是在StringInputHandler方法 执行完之后才出现的
      

  22.   

    你再定义一个方法,例如fun(String Data),将
        FormMSG newForm = new FormMSG();
        newForm.Show();
        newForm.ShowText(Data);
    代码放在fun方法里面
    然后在StringInputHandler方法里面将原来代码注释,加上
    ShowMessage showMsg = new ShowMessage(fun);
    Object[] obj = {Data};
    this.Invoke(showMsg,obj);
    再试试看
      

  23.   

    嗯 但是 StringInputHandler方法 的类并不是继承Control的 他是一个普通的类 叫做MSGServer没有this.Invoke()在父窗体中实例化的MSGServer 并调用它的Start() 开始监听 照你这么说 应该在哪里Invoke啊 ??
      

  24.   

    用异步委托来show窗口,就是beginInvoke。
      

  25.   

    终于搞定了 眼泪哗哗的~~~~~~~~~~~谢谢问路人 zhenglf(问路人) JoneG(琼琼) 等等以上各位兄弟最后解决的方法 是把父窗体和子窗体 中间间隔的那个类去掉了 因为其实也没有什么作用 然后父窗体中要用Invoke() 就好了再次谢谢大家 马上给分~~~