0

I make a winform program to read data from serial port and display it in textbox. The data will be sent from external device at every 5 sec interval. The first data is "1 followed by "2" and then "3" and repeat the same pattern forever.
I will make pictureBox1, pictureBox2, pictureBox3 visisble and play gif when data "1", "2" and "3" received respectively. The problem is sometime the pictureBox does not switch to the next respective one even though the next data has arrived. I am not sure whether I am using the invoke function correctly?

public Form1()
{
    InitializeComponent();
    SerialPortProgram();
    pictureBox1.Image=
    Image.FromFile(@"C:\Users\user\Downloads\Gif#1.gif");
    pictureBox2.Image = 
    Image.FromFile(@"C:\Users\user\Downloads\Gif#2.gif");
    pictureBox3.Image = 
    Image.FromFile(@"C:\Users\user\Downloads\Gif#3.gif");
}

// Create the serial port with basic settings
private SerialPort port = new SerialPort("COM17", 9600, Parity.None, 8, StopBits.One);

private void SerialPortProgram()
{
    // Attach a method to be called when there
    // is data waiting in the port's buffer
    port.DataReceived += new SerialDataReceivedEventHandler(port_DataReceived);

    // Begin communications
    port.Open();

    // Enter an application loop to keep this thread alive
    // Application.Run();        // if this Application.Run() is not commented out, Form1 will not be displayed
}

private void port_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
    // Show all the incoming data in the port's buffer
    string data = (port.ReadExisting());
    Log(data);
    if (data == "1")
    {
        gif1Showl();
    }

    if (data == "2")
    {
        gif2Show();
    }

    if (data == "3")
    {
        gif3Show();
    }
}


private void Log(string msg)
{
    textBox1.Invoke(new EventHandler(delegate
    {
        textBox1.AppendText(msg);
    }));
}

private void gif1Showl()
{
    this.Invoke(new ThreadStart(() =>
    {
        pictureBox1.Visible = true;
        pictureBox1.Enabled = true;
        pictureBox2.Visible = false;
        pictureBox2.Enabled = false;
        pictureBox3.Visible = false;
        pictureBox3.Enabled = false;
    }));
}

private void gif2Show()
{
    this.Invoke(new ThreadStart(() =>
    {
        pictureBox1.Visible = false;
        pictureBox1.Enabled = false;
        pictureBox2.Visible = true;
        pictureBox2.Enabled = true;
        pictureBox3.Visible = false;
        pictureBox3.Enabled = false;
    }));
}

private void gif3Show()
{
    this.Invoke(new ThreadStart(() =>
    {
        pictureBox1.Visible = false;
        pictureBox1.Enabled = false;
        pictureBox2.Visible = false;
        pictureBox2.Enabled = false;
        pictureBox3.Visible = true;
        pictureBox3.Enabled = true;
    }));
}
Baddack
  • 1,947
  • 1
  • 24
  • 33
Syscomer
  • 1
  • 1
  • If you think that the problem lies in something other than the serial I/O itself, then your code example is not a [mcve] as long as it still has serial I/O code in it. If you think that the problem _is_ in the serial I/O, you're going to have a very difficult time finding anyone who can reproduce the problem, because your specific hardware is not available to the rest of us. In either case, you should have done enough debugging, isolating the individual pieces of the problem, so that you _know_ whether the problem is related to the serial I/O or not. – Peter Duniho Dec 08 '17 at 06:39
  • This program has a Log(data) method to display the data arrived into the textbox for my verification purpose. The thing is data has been logged to textbox consistently in the pattern I mentioned above, but picturebox has not been switch to the respective one occassionally. – Syscomer Dec 08 '17 at 06:59

1 Answers1

0

You should check if invoking is needed and call your delegate. Creating a new thread to update the UI itself is wrong.

MethodInvoker methodInvokerDelegate = delegate() 
{ 
    pictureBox1.Visible = false;
    pictureBox1.Enabled = false;
    pictureBox2.Visible = false;
    pictureBox2.Enabled = false;
    pictureBox3.Visible = true;
    pictureBox3.Enabled = true; 
};

//This will be true if Current thread is not UI thread.
if (this.InvokeRequired)
    this.Invoke(methodInvokerDelegate);
else
    methodInvokerDelegate();
jegtugado
  • 5,081
  • 1
  • 12
  • 35