-
Notifications
You must be signed in to change notification settings - Fork 1k
Simplify Invoke
and BeginInvoke
signature and accept Action
#4608
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
@MadsTorgersen @jaredpar @KathleenDollard can you see any issues with this change? |
LGTM |
#1347 😁 |
Will this also works?
|
Yes but its currently slightly more inefficient because the delegate is not cached (for historic reasons). There's a roslyn issue for changing this and making it behave like the other delegate syntax variants. |
@weltkante, do you think if we introduced this, we would break a terribly awful lot of people with regards to what you wrote here? (And let's all keep in mind, we always said, given the nature of .NET in contrast to Framework, we don't want to, but if the benefit outweighs the risk, we would introduce breaking changes. I'd say it would do here, so I am very much in favor to take this.) |
Not really, no, people who wrote an extension method will compile against the new overload now (has higher priority than the extension method), but I really doubt someone would make an I expect existing extension methods are doing the same you are going to do in your overload so that should not be breaking. Users who don't recompile will still be calling their extension method regardless of what you introduce here, so at most its affecting source code, and you can be expected to update your code when you compile against a new framework version. (Though I don't think its necessary in this case to update anything for most users.) The comment in the other thread was just saying that having this method inbox is "nice to have" and people are already doing it manually via extension, but it wasn't an argument against introducing it. |
Sorry for the digression; but I completely forgot about this, and I remember how I was shocked, because I was always thinking that this form was more efficient that the other one (instead of allocating a delegate, just point directly to the method). Thanks for the reminder 😅 |
Updated with |
I think you missed that the old
You'd either cast the boxed value or return it through a variable captured in the closure: float area = 0;
listView1.Invoke(new Action(() => { area = CalculateArea(); }));
// consume "area" or var area = (float)listView1.Invoke(new Func<float>(() => CalculateArea()));
myControl.Invoke(new Action(() => { UpdateUI(); })); or myControl.Invoke((Action)(() => { UpdateUI(); })); in fact you can pass (almost) arbitrary delegates, taking parameters or returning values. Thats why there is an overload taking a params-array. For what its worth its not necessary to add an |
Thank you @weltkante, I indeed totally overlooked it. |
namespace System.Windows.Forms
{
public partial class Control
{
public IAsyncResult BeginInvoke(Action method);
// public IAsyncResult BeginInvoke(Delegate method);
// public IAsyncResult BeginInvoke(Delegate method, params object[] args);
public T Invoke<T>(Func<T> method);
public void Invoke(Action method);
// public object Invoke(Delegate method);
// public object Invoke(Delegate method, params object[] args);
}
} |
@weltkante made a great comment in #4631 (comment)
This could be addressed by dotnet/runtime#47525 that's looking at adding support for timeout and cancellation token support. |
Actually I don't think so, that will only allowing the consumer of the WPF has had the ability from the start, their I mean its not a big deal that WinForms doesn't have it, whenever I need to cancel a |
I think we should go forward with this. Sorry again for the delay. |
Setting as up for grabs. |
Add overloads that takes `Action` and `Func<T>` as a parameter: * `IAsyncResult BeginInvoke(Action method)` * `void Invoke(Action method)` * `T Invoke<T>(Func<T> method)` Closes dotnet#4608
Proposed API:
Add an overload that takes
Action
as a parameter for bothInvoke(Action method)
andBeginInvoke(Action method)
.I don't think it is necessary to create overloads for methods that take
params object[] args
as it is possible to pass necessary parameters via a closure.Background
There are two golden rules for Windows Forms:
InvokeRequired
,Invoke
,BeginInvoke
, etc.Invoke
andBeginInvoke
takeDelegate
as their input parameters, which requires rather cumbersome boilerplate code, and frankly look dated by todays standard.E.g.
The cumbersome bit is this:
which can also be written as
However it can not be written as this:
despite the factThank you @weltkante for pointing it out.Action
is of a delegate type, just likeMethodInvoker
But now it will be possible to write something like this:
Perf considerations
The added benefit of the new API is that we will be creating smaller code footprint:
InvokeDelegateFunc
vs
InvokeFunc
Other considerations
I have checked emitted IL, and it appears to be of the same size, with the only difference use of
Action
instead ofMethodInvoker
.@KlausLoeffelmann has highlighted to me that the issue appears to be C# specific, as VB understand the following right now:
I have verified the proposal does not appear to have any negative impacts on VB.
The text was updated successfully, but these errors were encountered: