The calling thread cannot access this object because another thread belongs to it.

Ok, my current code is working, and I will probably try to do the same with Async CTP. But I still want to understand what is happening.

I have a function like below

// In MainWindow.xaml.cs Task.Factory.StartNew(() => helper.Send()); // In class HttpHelper public void Send() { // ... try { Status = Statuses.Uploading; // write to request stream Status = Statuses.Downloading; // write to response stream Status = Statuses.Idle; // the exception is thrown here // ... } catch (Exception e) { // ... } } 

Full code for HttpHelper @pastebin . Send() on line 76

I wonder why I get an exception? Maybe I did something wrong with streaming processing, but why does the exception only occur after I have successfully set the Status property 2 times?

UPDATE: Reason ...

I had an event handler listening to the StatusChanged event, in condition 1 if I forgot to use the UI thread to update the UI

 helper.StatusChanged += (s, evt) => { _dispatcher.Invoke(new Action(() => txtStatus.Text = helper.Status.ToString())); // I used _dispatcher here correctly if (helper.Status == HttpHelper.Statuses.Idle || helper.Status == HttpHelper.Statuses.Error) progBar.IsIndeterminate = false; // but not here }; 
+4
source share
3 answers

Refresh . I missed (in my defense, a small) comment in your code, which made it clear that you are using WPF / Silverlight and not Windows Forms.

However, it looks like you were able to take the main point of what I said and apply it correctly to your own script (using Dispatcher.Invoke rather than Control.Invoke ) - well done;)


I assume the event handler attached to your StatusChanged event updates the StatusLabel control in your user interface? If this is the case, then you need Invoke that call from the UI thread; eg:.

 void HttpHelper_StatusChanged(object sender, EventArgs e) { var httpHelper = (HttpHelper)sender; UpdateStatus(httpHelper.Status); } void UpdateStatus(HttpHelper.Statuses status) { if (InvokeRequired) { Invoke(new Action<HttpHelper.Statuses>(UpdateStatus), status); } else { // Your code probably doesn't look like this; // it just an example. statusLabel.Text = status.ToString(); } } 

The reason you can see two successes followed by failure is slightly higher than me; but I know that managing StatusLabel in particular can be a bit evasive when it comes to StatusLabel issues. I saw code where it is updated directly from background threads (usually due to forgetfulness of developers) without any exceptions; It seems to me that you were just lucky twice and once unlucky.

+3
source

Does Status the user interface? Because it looks like this.

I can only guess, but I believe that Status is changing something in the user interface, which needs to be done through Dispatcher.Invoke() .

0
source

if Status is a global variable, you will get this exception because several threads are accessing them and updating at the same time. I suggest using a lock around it

-1
source

All Articles