簡體   English   中英

將共享參數傳遞給 blazorcomponents

[英]Passing shared parameter to blazorcomponents

我正在構建一個 Blazor 服務器應用程序,它具有側面導航組件和頂部導航組件。

如果用戶從頂部導航菜單中選擇一個項目,我希望清除側邊導航的“已選擇”狀態。

在我的MainLayout.blazor.cs ,我有一個名為ResetSelection的變量:

protected bool ResetSelection { get; set; } = false;

我將其從MainLayout.blazor文件傳遞到頂部和側面導航組件:

<SideNav AuthUser="@navAuth.User.GetAuthUserModel()" ResetSelection="@ResetSelection" />
<TopNav AuthUser="@Auth.User.GetAuthUserModel()" ResetSelection="@ResetSelection" />

TopNav.razor.cs ,我檢查是否選擇了導航項,如果選擇了,我將變量設置為true

private void itemSelected(MenuEventArgs<CategoryModel> args)
{
    // if item selected set the main nav selected item to null
    // breakpoint gets hit-- this method gets fired as expected
    ResetSelection = true;
}

SideNav.razor.cs組件中,我使用OnParameterSet檢查參數是否為true ,如果是,我清除當前選定的導航項並將變量重置為 false:

protected override void OnParametersSet()
{
    base.OnParametersSet();
    
    if (ResetSelection == true)
    {
        // we never get here!
        NavMenu.UnselectAll();
        ResetSelection = false;
    }
}

我從來沒有用OnParametersSet ResetSelection == true條件觸發 OnParametersSet——我不明白為什么。 我似乎無法在兩個子組件之間進行這種交互。

當參數在TopNav.razor.cs中更改其值時,傳入的參數是否被限定為本地組件?

您可以將 Blazor 通知模式應用於您的問題。

當您嘗試在父/子組件之間創建不僅僅是簡單的參數/回調關系時,這種方法避免了不可避免的脆弱的意大利面條管道。

創建一個簡單的 State object 然后級聯。 readonlyIsFixed防止 RenderTree 級聯:渲染由事件驅動。

State Object:

public class MenuState
{
    public event EventHandler<EventArgs>? StateChanged;

    public void NotifyStateCahnged(object? sender)
        => this.StateChanged?.Invoke(sender, EventArgs.Empty);
}

你的布局。

<CascadingValue Value="_state" IsFixed>
    //... layout markup
</CascadingValue>

@code {
    private readonly MenuState _state = new();
}

然后無論你在哪里使用它:

@implements IDisposable

<h3>TopMenu</h3>


@code {
    [CascadingParameter] private MenuState State { get; set; } = new();

    protected override void OnInitialized()
        => this.State.StateChanged += this.OnStateChanged;

    protected async Task MenuClicked()
    {
        // do whatever maybe async
        // emulate an async action
        await Task.Delay(10);
        this.State.NotifyStateCahnged(this);
    }

    private void OnStateChanged(object? sender, EventArgs e)
    {
        // only need to render if it wasn't me who triggered the event
        if (sender != this)
        {
            // Do whatever
            this.StateHasChanged();
        }
    }

    public void Dispose()
        => this.State.StateChanged -= this.OnStateChanged;
}

級聯的替代方法是將MenuState注冊為 Scoped Service,然后將其注入到您需要的位置。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM