I'm working on an interface that receives data from the serial ports and once it gets an specific value it shows another form, but when this is shown the window freezes Could you help me to find a solution to this?
public string[] data=new string[14]; public SerialPort port = new SerialPort("COM17",2400, Parity.None,8,StopBits.One); private Queue recievedData = new Queue();
public MainForm()
{
InitializeComponent();
port.Open();
port.DataReceived = new SerialDataReceivedEventHandler(serialPort1_DataReceived);
int count = port.BytesToRead;
byte[] ByteArray = new byte[count];
}
public void serialPort1_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
byte[] data = new byte[port.BytesToRead];
port.Read(data, 0, data.Length);
data.ToList().ForEach(b => recievedData.Enqueue(b));
processData();
}
public void processData()
{
byte[] byteArray = new byte[14];
if (recievedData.Count > 13)
{
for (int i = 0; i < byteArray.Length; i )
{
byteArray[i] = recievedData.Dequeue();
}
}
for (int i = 0; i < 14; i )
{
data[i] = byteArray[i].ToString();
}
int value0 = Convert.ToInt16(data[0]);
BitArray b0 = new BitArray(new int[] { value0 });
bool[] bits0 = new bool[b0.Count];
b0.CopyTo(bits0, 0);
int value1 = Convert.ToInt16(data[1]);
BitArray b1 = new BitArray(new int[] { value1 });
bool[] bits1 = new bool[b1.Count];
b1.CopyTo(bits1, 0);
int value2 = Convert.ToInt16(data[2]);
BitArray b2 = new BitArray(new int[] { value2 });
bool[] bits2 = new bool[b2.Count];
b2.CopyTo(bits2, 0);
int value3 = Convert.ToInt16(data[3]);
BitArray b3 = new BitArray(new int[] { value3 });
bool[] bits3 = new bool[b3.Count];
b3.CopyTo(bits3, 0);
int value4 = Convert.ToInt16(data[4]);
BitArray b4 = new BitArray(new int[] { value4 });
bool[] bits4 = new bool[b4.Count];
b4.CopyTo(bits4, 0);
int value5 = Convert.ToInt16(data[5]);
BitArray b5 = new BitArray(new int[] {value5});
bool[] bits5 = new bool[b5.Count];
b5.CopyTo(bits5, 0);
int value6 = Convert.ToInt16(data[6]);
BitArray b6 = new BitArray(new int[] { value6 });
bool[] bits6 = new bool[b6.Count];
b6.CopyTo(bits6, 0);
int value7 = Convert.ToInt16(data[7]);
BitArray b7 = new BitArray(new int[] { value7 });
bool[] bits7 = new bool[b7.Count];
b7.CopyTo(bits7, 0);
int value8 = Convert.ToInt16(data[8]);
BitArray b8 = new BitArray(new int[] { value8 });
bool[] bits8 = new bool[b8.Count];
b8.CopyTo(bits8, 0);
int value9 = Convert.ToInt16(data[9]);
BitArray b9 = new BitArray(new int[] { value9});
bool[] bits9 = new bool[b9.Count];
b9.CopyTo(bits9, 0);
int value10 = Convert.ToInt16(data[10]);
BitArray b10 = new BitArray(new int[] { value10 });
bool[] bits10 = new bool[b10.Count];
b10.CopyTo(bits10, 0);
int value11 = Convert.ToInt16(data[11]);
BitArray b11 = new BitArray(new int[] { value11 });
bool[] bits11 = new bool[b11.Count];
b11.CopyTo(bits11, 0);
int value12 = Convert.ToInt16(data[12]);
BitArray b12 = new BitArray(new int[] { value12 });
bool[] bits12 = new bool[b12.Count];
b12.CopyTo(bits12, 0);
int value13 = Convert.ToInt16(data[13]);
BitArray b13 = new BitArray(new int[] { value13 });
bool[] bits13 = new bool[b13.Count];
b13.CopyTo(bits13, 0);
if (bits13[2]&&reentrant==0)
{
reentrant = 1;
Form1 formita = new Form1(this);
formita.Show();
}
string direction = "";
if (bits1[3]==true)
{
direction = "-";
}
string firstdigital = bittobcd(bits1[2], bits1[1], bits1[0], bits2[3], bits2[2], bits2[1], bits2[0]);
string seconddigital = bittobcd(bits3[2], bits3[1], bits3[0], bits4[3], bits4[2], bits4[1], bits4[0]);
string thirddigital = bittobcd(bits5[2], bits5[1], bits5[0], bits6[3], bits6[2], bits6[1], bits6[0]);
string fourthdigital = bittobcd(bits7[2], bits7[1], bits7[0], bits8[3], bits8[2], bits8[1], bits8[0]);
Writing(direction firstdigital seconddigital thirddigital fourthdigital);
}
string bittobcd(bool a, bool b, bool c, bool d, bool e, bool f, bool g)
{
string number="";
if (a == false && b == false && c == false && d == false && e == true && f == false && g == true)
{
number = "1";
}
else if(a == true && b == false && c == true && d == true && e == false && f == true && g == true)
{
number = "2";
}
else if(a == false && b == false && c == true && d == true && e == true && f == true && g == true)
{
number = "3";
}
else if(a == false && b == true && c == false && d == false && e == true && f == true && g == true)
{
number = "4";
}
else if(a == false && b == true && c == true && d == true && e == true && f == true && g == false)
{
number = "5";
}
else if(a == true && b == true && c == true && d ==true && e == true && f == true && g == false)
{
number = "6";
}
else if(a == false && b == false && c == true && d == false && e == true && f == false && g == true)
{
number = "7";
}
else if(a == true && b == true && c == true && d == true && e == true && f == true && g == true)
{
number = "8";
}
else if(a == false && b == true && c == true && d == true && e == true && f == true && g == true)
{
number = "9";
}
else if(a == true && b == true && c == true && d == true && e == true && f == false && g == true)
{
number = "0";
}
else if(a == true && b == true && c == false && d == true && e == false && f == false && g == false)
{
number = "L";
}
else if(a == false && b == false && c == false && d == false && e == false && f == false && g == false)
{
number = " ";
}
return number;
}
public void Writing(string text)
{
if (textBox2.InvokeRequired)
{
Action safeWrite = delegate { Writing($"{text}"); };
textBox2.Invoke(safeWrite);
}
else
textBox2.Text = text;
}
}
public MainForm mainy2; public Form1(MainForm mainy) { InitializeComponent(); mainy2 = mainy; }
private void Form1_Load(object sender, EventArgs e)
{
this.Invoke((MethodInvoker)delegate
{
mainy2.Hide();
});
}
CodePudding user response:
As Ralf mentions, serialPort1_DataReceived
will most probably be raised on a background thread. But then you call
Form1 formita = new Form1(this);
formita.Show();
While this is not strictly disallowed, it is most probably not a good idea since you will not have multiple forms associated with different UI threads.
I would assume the reason for the freeze would the blocking invoke call. And it might also cause various kinds of synchronization issues:
if (textBox2.InvokeRequired)
{
Action safeWrite = delegate { Writing($"{text}"); };
textBox2.Invoke(safeWrite);
}
Meaning the background thread will block until the UI thread have done its update. And there will probably be a bunch of other synchronization issues.
I would suggest to only ever access any UI classes from the UI thread. I would assume that should at least help. I.e. change the code above to
textBox2.BeginInvoke(() => {
Form1 formita = new Form1(this);
formita.Show();
});