juser
juser

Reputation: 13

Calling UI-thread from another thread C#

I'm creating a chat application in which multiple users can enter their messages and send them to the server over tcp (networkstream).

I have the following code for receiving messages:

private void ReceiveData()
    {
        Task.Run(() =>
        {
            int bufferSize = 1024;
            string message = "";

            byte[] buffer = new byte[bufferSize];
            _NetworkStream = _TcpClient.GetStream();
            AddMessage("Connected!");

            while (true)
            {
                int readBytes = _NetworkStream.Read(buffer, 0, bufferSize);
                message = Encoding.ASCII.GetString(buffer, 0, readBytes);
                Console.WriteLine("I received a message: " + message);

                if (message.Equals("bye"))
                {
                    break;
                }

                AddMessage(message);
            }

            buffer = Encoding.ASCII.GetBytes("bye");
            _NetworkStream.Write(buffer, 0, buffer.Length);

            _NetworkStream.Close();
            _TcpClient.Close();

            AddMessage("Connection closed!");
        });
    }

Now when I call AddMessage (which I call from a different Thread, thus a different context) My application crashes. Which is quite logical given my AddMessage code:

private void AddMessage(string message)
    {
        this.ListBox_Messages.Items.Add(message);
    }

My question is, is the addmessage function responsible for executing this on the ui thread or the function caller, in this case ReceiveData() and what would be the best and most modern way to implement it?

Thank you in advance!

Upvotes: 0

Views: 178

Answers (1)

Idle_Mind
Idle_Mind

Reputation: 39122

Did your teacher actually TEACH you any of these "modern methods"?!

Tell him or her there is nothing wrong with going back to basics:

private void AddMessage(string message)
{
    if (this.ListBox_Messages.InvokeRequired)
    {
        this.ListBox_Messages.Invoke((MethodInvoker)delegate {
            this.ListBox_Messages.Items.Add(message);
        });
    }
    else
    {
        this.ListBox_Messages.Items.Add(message);
    }          
}

It's simple, and it just works.

As a computer science teacher myself, I hate seeing these types of questions. Makes me wonder what the teachers are doing.

Teacher: "You must use this magical stuff that I haven't taught you yet!"

Giving your teacher the benefit of the doubt, are there any requirements for this application that you haven't shared with us?

Upvotes: 2

Related Questions