C# 在Blazor中维护嵌套(不是第一个或最后一个)方法的SynchronizationContext 使用VisualStudio 2019加载的默认项目,当在磊科3.1中创建新的BLAZOR服务器端项目时,请考虑下面的示例(对自己的反例页稍作更改):

C# 在Blazor中维护嵌套(不是第一个或最后一个)方法的SynchronizationContext 使用VisualStudio 2019加载的默认项目,当在磊科3.1中创建新的BLAZOR服务器端项目时,请考虑下面的示例(对自己的反例页稍作更改):,c#,blazor,blazor-server-side,C#,Blazor,Blazor Server Side,第一个按钮和标签很简单,只要按一个按钮,用户界面上的计数就会按预期更新。但是,第二个按钮更复杂 中间的wait-NestedUpdate(++nestedCounter)调用不会反映在UI上。第一个调用和最后一个调用(第一个和最后一个嵌套方法调用)都实时反映在UI上,因此您看到的是: Update from nested method: 1 *2 seconds go by Update from nested method: 3 我意识到这是因为SynchronizationContext的

第一个按钮和标签很简单,只要按一个按钮,用户界面上的计数就会按预期更新。但是,第二个按钮更复杂

中间的
wait-NestedUpdate(++nestedCounter)
调用不会反映在UI上。第一个调用和最后一个调用(第一个和最后一个嵌套方法调用)都实时反映在UI上,因此您看到的是:

Update from nested method: 1
*2 seconds go by
Update from nested method: 3
我意识到这是因为
SynchronizationContext
的警告,但我更好奇的是如何捕获和维护该上下文,以便在我的按钮按下事件中调用的每个等待的
方法都使用相同的上下文,以便UI在代码执行时实时更新。有没有一个好的/漂亮的方法可以做到这一点

我意识到这是因为SynchronizationContext的警告

不,不是真的。所有这些代码都应该在主线程上异步但按顺序运行。
这里的SyncContext没有错误或需要修复

您看到的是StateHasChanged()逻辑,它实际上是关于一个状态的,可能只是一个布尔标志

BLAZOR框架会在调用EvEnthANDER之前和之后设置这个标志,但是在中间,你必须这样做。 快速修复和解释:

protected async Task NestedMethodUpdate()
{
    // the flag is pre-set here
    await NestedUpdate(++nestedCounter);
    // the thread is available and Blazor will render '1' and reset the flag
    await Task.Delay(1000);  

    await NestedUpdate(++nestedCounter);
    // the thread is available but the flag is down: the '2' is not shown
    await Task.Delay(1000);

    await NestedUpdate(++nestedCounter);
    StatehasChanged();  // <<-- add this
    // the thread is available and the flag is up: the '3' is shown
    await Task.Delay(1000);

    // you can add more steps
    await NestedUpdate(++nestedCounter);
    StatehasChanged();  // <<-- set the flag
    await Task.Delay(1000);  // show '4'

    // this result will show '5' after the method has completed
    await NestedUpdate(++nestedCounter);
}
NestedMethodUpdate()受保护的异步任务
{
//此标志在此处预设
等待NesteUpdate(++nestedCounter);
//线程可用,Blazor将呈现“1”并重置标志
等待任务。延迟(1000);
等待NesteUpdate(++nestedCounter);
//线程可用,但标志已关闭:“2”未显示
等待任务。延迟(1000);
等待NesteUpdate(++nestedCounter);

StatehasChanged();//
ConfigureAwait(true)
也许吧?@Henkholtman你是什么意思?啊,我明白了!我注意到前后的方法都呈现得很好,但现在这很有意义!StatehasChanged的行为是否只会在任何地方记录的方法的开头和结尾自动应用?
Update from nested method: 1
*2 seconds go by
Update from nested method: 3
protected async Task NestedMethodUpdate()
{
    // the flag is pre-set here
    await NestedUpdate(++nestedCounter);
    // the thread is available and Blazor will render '1' and reset the flag
    await Task.Delay(1000);  

    await NestedUpdate(++nestedCounter);
    // the thread is available but the flag is down: the '2' is not shown
    await Task.Delay(1000);

    await NestedUpdate(++nestedCounter);
    StatehasChanged();  // <<-- add this
    // the thread is available and the flag is up: the '3' is shown
    await Task.Delay(1000);

    // you can add more steps
    await NestedUpdate(++nestedCounter);
    StatehasChanged();  // <<-- set the flag
    await Task.Delay(1000);  // show '4'

    // this result will show '5' after the method has completed
    await NestedUpdate(++nestedCounter);
}