我正在尝试使用应用程序的mahaps进度条对话框在任务启动时触发,通常会冻结应用程序几秒钟。
private void Button_Click(object sender, RoutedEventArgs e)
{
LoadingDialog();
SaveAndLoadData.SaveUserData(ApplicationData.UserData);
MainWindowLogic.LogIntoWebsites();
}
private async void LoadingDialog()
{
var controller = await this.ShowProgressAsync("Logging In...", "");
}
在我的LogIntoWebsites()
方法完成之后,实际上不会弹出“加载”对话框。我感觉我并没有理解异步,而且我肯定在这里做错了。
想法?
答案 0 :(得分:1)
您在“火灾中”调用LoadingDialog
并忘记"执行方式。我不确定你想做什么。
如果您希望对话框显示在LogIntoWebsites
之前,则需要将方法签名从async void
更改为async Task
,并使用{{1}异步等待它}}:
await
答案 1 :(得分:0)
我不熟悉Mahaps进度条,但是如果你想使用async-await模式保持你的UI响应,你应该声明你的事件处理程序是异步的。
事件处理程序是唯一可以返回void的异步函数,不必返回任务或任务
<TResult
&gt;
在此异步事件处理程序中,您不必创建新任务。只需调用普通函数,只要您认为函数可能需要一些时间,请将函数声明为异步并等待及时操作。
您的事件处理程序调用三个函数。我不知道哪些需要很长时间才能执行。所以我们假设只有第一个相对较慢。代码如下所示:
private **async** void Button_Click(object sender, ...)
{
await LoadingDialog();
SaveAndLoadData.SaveUserData(ApplicationData.UserData);
MainWindowLogic.LogIntoWebsites();
}
private async void LoadingDialog()
{
var controller = await this.ShowProgressAsync("Logging In...", "");
}
如果SaveUserData和LogIntoWebsites也相当慢,请考虑为它们创建异步版本。如果他们可以调用异步函数,那么异步版本相当容易。如果不是,你将不得不自己创建一个任务并等待它们。例如:
private async void LogIntoWebSitesAsync()
{
// do some processing
// if possible call other async functions
await OtherFunctionAsync(); // use this if return value is Task
TResult result = await YetAnotherAsync(); // use if return Task`<TResult`>
// here you can use result
// or if you want some parallel processing:
var taskA = YetAnotherAsync();
// while taskA is performing, do other things
// after a while you need the result:
TResult taskAResult = await taskA;
// or even start several tasks:
var taskX = functionXAsync(...);
var taskY = functionYAsync(...);
// do some more processing, and after a while you need the results:
await Task.WhenAll( new Task[] {taskX, taskY});
var Xresult = taskX.Result;
var Yresult = taskY.Result;
ProcessResults(XResult, YResult);
}
如果您的事件处理程序需要调用没有同步版本的长函数,请为它创建一个任务并等待它:
private TResult LongFunction()
{
// do something slow
TResult result = ...;
return result;
}
private async Task`<TResult`> LongFunctionAsync(...)
{
// do some processing
// start the task
var longTask = Task.Run( () => LongFunction(...);
// while longTask running, do some more processing
// when the result is needed:
TResult result = await longTask;
// or if you don't have anything else to do you can await immediately
await Task.Run ( () => {...} );
return result;
}
private async void Button_Click(object sender, ...)
{
TResult result = await LongFunctionAsync(...);
ProcessResult(result);
}