开发者

How to invoke Action<> modifying winforms control

I have the following function

    private void UnsubscribeSubscribe(Action action)
    {
        action.BeginInvoke(action.EndInvoke, null);
    }

Whenever I pass in an action that modifies my controls data source nothing happens. I know the action is being invoked because the query I'm running is returning results. I was reading that you can only modify winform controls from the same thread that added them. How can I make this work?

For example, running UnsubscribeSubscribe(() => { Foobar.DataSource = GetResults() });

GetResults() will run properly 开发者_如何转开发but the data source will remain unchanged.


You need to invoke the delegate on the thread that created the control's underlying handle. Control.BeginInvoke is used for just that.


You are using the wrong method. A delegate's BeginInvoke() method always runs the delegate target on a threadpool thread. Poison to the user interface. You need to use Control.BeginInvoke(). Like the form's BeginInvoke method. While similarly named, it has nothing to do with a delegate's BeginInvoke() method. For one, you don't have to (and shouldn't) call EndInvoke().


if you need to make an action on a UI thread from the different thread then GUI thread then you should use Invoke method like this (this example is for text box - from msdn):

private void SetText(string text)
{
   // InvokeRequired required compares the thread ID of the
   // calling thread to the thread ID of the creating thread.
   // If these threads are different, it returns true.
  if (this.textBox1.InvokeRequired)
  { 
    SetTextCallback d = new SetTextCallback(SetText);
    this.Invoke(d, new object[] { text });
  }
  else
  {
    this.textBox1.Text = text;
  }
}

There is also another approach using SynchronizationContext class - you can read about using it here

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜