Home > Mobile >  Call method in WPF MainWindow class from another class on a different thread
Call method in WPF MainWindow class from another class on a different thread

Time:07-09

I am trying to edit a main window item by calling a method in the MainWindow class. Where I am trying to call it from is in a separate class on a separate thread.

This is the main window class where I am calling the start method in the server class that create a new thread to execute the server on. You can also see the two methods that I want to call to change the labels in the main window

public partial class MainWindow : Window
    {
        
        public MainWindow()
        {
            InitializeComponent();
            Server server = new Server();
            server.Start();
            
        }
        
        public void UpdateMessage(string message)
        {
            Message.Content = message;
        }

        public void UpdateAddress(string address)
        {
            Address.Content = address;
        }

This is the server class, opens a socket and listens for clients. That all works I just want to update the WPF window with what the socket is doing.

public class Server
{
    public void Start()
    {
        //Create and start threads
        var serverTask = new Task(ExecuteServer);
        serverTask.Start();
    }

    /// <summary>
    /// Start and run TCP IP server/connection
    /// </summary>
    public void ExecuteServer()
    {
        IPHostEntry ipHost = Dns.GetHostEntry(Dns.GetHostName());
        IPAddress ipAddr = ipHost.AddressList[0];
        IPEndPoint localEndPoint = new IPEndPoint(ipAddr, 11111);

        try
        {
            Socket listener = new Socket(ipAddr.AddressFamily,
               SocketType.Stream, ProtocolType.Tcp);
            
// I want to call the methods here

            listener.Bind(localEndPoint);

            listener.Listen(10);
            while (true)
            {
                var clientSocket = listener.AcceptAsync();
                var reciveThread = new Thread(() => ReciveAndEnqueueCommand(clientSocket, listener));
                reciveThread.Start();

            }
        }
        catch (Exception e)
        {
            Console.WriteLine(e.ToString());
        }
    }
}

CodePudding user response:

try the following:

var mw = ((MainWindow)Application.Current.MainWindow);
if(mw!=null)
mw.Dispatcher.Invoke(() =>
{
    mw.UpdateMessage("msg");
});

CodePudding user response:

As commented by @Fildor using IProgress is the way that I was able to get it to work. I did also use the code that @yassinMi posted to make the call to the method in the MainWindow class so thank you both. Below is the code that I used to get my solution.

public class Server
    {
        //Create the progress item outside the second thread
        public Progress<string> _addressProgress = new Progress<string>(a =>
        {
            //get the main window element like yassinMi commented
            var mw = ((MainWindow)Application.Current.MainWindow);
            if (mw != null)
                mw.Dispatcher.Invoke(() =>
                {
                    mw.UpdateAddress(a);
                });
        });

        public void Start()
        {

            //Create and start threads
            //Pass progress item to the execute server method
            var serverTask = new Task(() => ExecuteServer(_addressProgress));
            serverTask.Start();
        }


        /// <summary>
        /// Start and run TCP IP server/connection
        /// </summary>
        public void ExecuteServer(IProgress<string> addressProgress)
        {
            IPHostEntry ipHost = Dns.GetHostEntry(Dns.GetHostName());
            IPAddress ipAddr = ipHost.AddressList[0];
            IPEndPoint localEndPoint = new IPEndPoint(ipAddr, 11111);



            try
            {
                Socket listener = new Socket(ipAddr.AddressFamily,
                   SocketType.Stream, ProtocolType.Tcp);

                //Report the progress to update the ui element
                addressProgress.Report("Test");

                listener.Bind(localEndPoint);

                listener.Listen(10);

                while (true)
                {
                    var clientSocket = listener.AcceptAsync();
                    var reciveThread = new Thread(() => ReciveAndEnqueueCommand(clientSocket, listener));
                    reciveThread.Start();

                }


            }
            catch (Exception e)
            {
                Console.WriteLine(e.ToString());
            }
        }
  • Related