locked
Delegate for serial port receive event to .Net controls RRS feed

  • Question

  •           
          How/where do put a delegate to  place the data in "indata" into a control on the main thread/form,,,
           private void OutputPort1_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
            {
                System.IO.Ports.SerialPort sp = (System.IO.Ports.SerialPort)sender;
                string indata = sp.ReadExisting();
               
                
            }

    Monday, October 26, 2020 4:36 PM

All replies

  • The documentation indicates that this event is raised on a secondary thread. Therefore any UI updates have to be marshalled to the main thread. From within the handler itself the easiest way to do that is to call Invoke (or BeginInvoke) on the control you want to update. This marshals the data.

    Typically what we do is create a helper method that uses InvokeRequired to determine if Invoke is needed and marshals the data directly otherwise it performs the update.

    private delegate void UpdateData ( string data );
    
    private void UpdateData ( string data )
    {
       if (myControl.InvokeRequired)
          myControl.Invoke(UpdateData, new [] { data });
       else
       {
          //On UI thread, update it...
       };
    }
    
    void OnDataReceived ( object sender, SerialDataReceivedEventArgs e )
    {
       ...
       var indata = sp.ReadExisting();
    
       UpdateData(indata);  
    }

    Note that this event handler really needs to return quickly otherwise you run the risk of the port buffer filling up if a large amount of data is sent in quick succession and the handler is not processing fast enough. Since any marshaling to the UI thread could potentially stall if the UI is busy this would be bad.

    At a minimum you should probably consider using BeginInvoke instead which doesn't block. Alternatively push the data to a queue and then have the data retrieved from the queue using a UI timer (from Winforms). The timer is running on the UI thread so it doesn't have to marshal anything. The queue (with locking) is shared between the 2 threads so the port thread adds data and the UI thread reads whatever is available.


    Michael Taylor http://www.michaeltaylorp3.net

    Monday, October 26, 2020 4:53 PM
  • Hi JKSCooper,

    Thank you for posting here.

    The same function can also be achieved using BackgroundWorker.

    This is described in the Microsoft documentation, you can take a look.

    How to: Make thread-safe calls to Windows Forms controls

    Best Regards,

    Timon


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Tuesday, October 27, 2020 3:12 AM
  • Hi,

    Has your issue been resolved?

    If so, please click on the "Mark as answer" option of the reply that solved your question, so that it will help other members to find the solution quickly if they face a similar issue.

    Best Regards,

    Timon


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Tuesday, November 3, 2020 7:06 AM
  • https://stackoverflow.com/questions/11590945/how-to-display-the-data-read-in-datareceived-event-handler-of-serialport

    I hope answer the question

    Tuesday, November 3, 2020 9:18 AM