16
votes

I have a module whith an event for serial port sygnal

serialPort.DataReceived.AddHandler(SerialDataReceivedEventHandler(DataReceived));

where DataReceived is

let DataReceived a b =
    rxstring <- serialPort.ReadExisting()
    arrayRead <- System.Text.Encoding.UTF8.GetBytes(rxstring)
    if arrayRead.[0] = 0x0Auy then
        ProcessData(a, null)

and ProcessData is invoking WinForms method

let ProcessData(a, b) =
    dataProcessor.Invoke(a, b) |> ignore

which is

private void ProcessData(object sender, EventArgs e) {
   byte[] m = Core.ncon.ArrayRead;
   switch (m[1]) {
      case 0x01: {
          if (m.Length > 5) {
             int myval = BitConverter.ToInt32(m, 3);
             textBox1.Text += " val: " + myval.ToString() + " ";

but when it's trying to access textBox1 I'm getting:

Cross-thread operation not valid: Control 'textBox1' accessed from a thread other than the thread it was created on.

So the question is How to access WinForm elements from another module events?

2

2 Answers

29
votes

You need to use the forms dispatcher.

FormContaingTheTextbox.Invoke(new MethodInvoker(delegate(){
    textBox1.Text += " val: " + myval.ToString() + " ";
}));

This makes that code run in the forms thread instead of yours.

18
votes

Try Using below Code:

this.Invoke(new MethodInvoker(delegate() 
{ 
//Access your controls
}));

hope this helps