c# - 如果变量更改发生在单独的线程上,Blazor 不会检测到变量更改

标签 c# blazor blazor-server-side

在我的西装外套中,我放了:

@if (cat.IsMeowing)
{
  <div>Cat is meowing!!!</div>
}

在我的 Cat 类中,我放置了以下内容:

public bool IsMeowing {get; set;} = false;
public void Meow()
{
    Task.Run(async () =>
    {
                await Task.Delay(3000); // Cat takes a deep breath
                IsMeowing = true; // MEOW!!!!!!!
    });
}

我想要的行为是,当我调用 Meow 时,有一个延迟,然后它设置导致 Div 出现的变量。但是,当通过另一个线程的闭包更新变量时,blazor 似乎没有注意到变量已更新。

如果我删除任务,然后仅设置延迟和 IsMeowing=true,那么 blazor 会注意到它并正确更新。

有没有办法可以在不实现回调的情况下解决这个问题?

最终,我想创建一个类,当对其调用方法时,会在 blazor 注意到的 3 秒后设置一个变量。想象一下,例如,如果我正在做其他密集工作,如果 3 秒过去了,我想显示一条消息“此操作需要一段时间...”,这样我就可以设置其中一个,开始做我的密集工作,然后当我的密集工作完成后取消它。如果密集工作花费 <3 秒,则不会发生任何事情,如果花费超过 3 秒,则消息将通过 blazor if 显示。

最佳答案

您创建的任务是外部任务,因此 this适用。这是必须调用 StateHasChanged() 的情况之一。为此:

Main.razor:

@implements IDisposable

@if (cat.IsMeowing)
{
  <div>Cat is meowing!!!</div>
}
<button @onclick="() => cat.Meow()" title="Poke the cat">Poke the cat</button>
@code {


    public Feline cat = new Feline();
    protected override void OnInitialized()
    {
        cat.UpdateState += UpdateState;
    }

    public void Dispose()
    {
        cat.UpdateState -= UpdateState;
    }

    private void UpdateState()
    {
        InvokeAsync(StateHasChanged);
    }
}

猫科动物.cs:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

public class Feline
{

    public Action UpdateState = null;

    public bool IsMeowing {get; set;} = false;
    
    public void Meow()
    {
        Task.Run(async () =>
        {
            await Task.Delay(3000); // Cat takes a deep breath
            IsMeowing = true; // MEOW!!!!!!!
            if(UpdateState != null)
                UpdateState();
        });
    }
}

示例: https://blazorrepl.telerik.com/cHOGmxPu44pZTDEm38

如果我错了,请纠正我。

关于c# - 如果变量更改发生在单独的线程上,Blazor 不会检测到变量更改,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/74961417/

相关文章:

c# - XamlCompiler 错误 WMC0055 : Cannot assign text value '10.0' into property 'xx' of type 'Decimal'

c# - 使此 LINQ 语句返回 T 而不是 Task<T>

c# - Blazor、MatBlazor - 如何捕捉 MatSelect 组件的值变化

c# - 使用 Blazor 和 C# 刷新 html 表格数据

c# - Blazor 服务器端的 Asp.Net Core Identity

cookies - 在 Blazor 服务器端创建和读取 Cookie

c# - .NET DateTime 不在 ToShortTimeString() 中返回 AM/PM

c# 在另一个方法结束时调用一个方法?

asp.net - NGINX HTTPS 代理无法使用 Azure AD 重定向 Uri

javascript - Blazor - JavaScript/Bootstrap 动画和脚本在 blazor 组件中不起作用