1

I have a device in which if I send a properly formatted string; I get a string back. I would like to use this returned string in a WPF ListView control but I'm having trouble infinitely querying the device on the other end of the serial port. I would like to refresh the data every 3 or so seconds.
Here is the application logic:

            public static void queryDevice()
        {
            SerialPort _serialPort = new SerialPort("COM3", 115200, Parity.None, 8, StopBits.One);
            _serialPort.Handshake = Handshake.None;
            ObservableCollection<string> store= new ObservableCollection<string> { " ", " ", " " };
            string[] query = new string[3] { "t02", "t03", "t04" };
            while (true)
            {
                for (int i = 0; i < 3; i++)
                {
                    string add = SerialCom.returnData(query[i], _serialPort);//returns data depending on which query was sent
                    if (store[i] != add)
                    {
                        store.Add(add);
                    }
                }
                Thread.wait(300);

            }
        }

I'm trying to find the best way to thread this code as putting this code in the UI thread locks the UI thread up. I am planning to use the ObservableCollection as the datasource for the ListView on that note.

Thanks!

bakedpatato
  • 105
  • 5
  • 16

2 Answers2

2

You should separate those code into two methods and using threading in my opinion..

maybe like this

    public static void queryDevice()
    {
        SerialPort _serialPort = new SerialPort("COM3", 115200, Parity.None, 8, StopBits.One);
        _serialPort.Handshake = Handshake.None;
        ObservableCollection<string> store= new ObservableCollection<string> { " ", " ", " " };
        string[] query = new string[3] { "t02", "t03", "t04" };
        Thread thread = new Thread(delegate(){Process(store,query,_serialPort);});
        thread.Start();
    }



     public static void Process(ObservableCollection<string> store, string[] query, SerialPort _serialPort)
     {
         while (true)
         {
             for (int i = 0; i < 3; i++)
             {
                 string add = SerialCom.returnData(query[i], _serialPort);
                 if (store[i] != add)
                 {
                     store.Add(add);
                 }
             }
             Thread.Sleep(300);
         }
     }
0

While this is more than you actually need in this particular case, I usually use the Producer/Consumer Pattern for those kind of things. Just because I know what I'm doing and threading is one of those things where mistakes tend to sneak in easily and are hard to discover.

For an C# implementation have a look at Implementing the Producer/Consumer Pattern in C#

Of all the things I learned while studying this has proven to be the most useful one ;D

Hint: Producer and Consumer get their own thread, the Consumer fills the ObservableCollection.

Disclaimer: There are more efficient / leaner solutions, so if that's an requirement go for another solution, however you'd probably not been using WPF then ;D

Community
  • 1
  • 1
Mene
  • 3,739
  • 21
  • 40
  • 1
    Yeah, I would like to stick to WPF. This data is also filling some wpf dials and gauges controls(and a OpenStreetMap control) that I got commercially. I'm too design deaf to make my own! I was considering the Producer/Consumer pattern but yeah, it's too much work just to get a couple of strings out of a serial port. – bakedpatato Oct 30 '12 at 18:37