简体   繁体   中英

Change visibility of nav item in blazor menu based on condition after index load

I have one Menu in Left Navigation, that will be hide/display based on isAdmin Condition. I am getting the value of isAdmin on Index.Razor page. Now I want to re-render the left navigation if isAdmin is true, Below Nav item should be visible

@if (isAdmin)
                {
                 <a class="nav-items" target="_blank">
                        <div style="width:40px;">
                            <i title="Security" class="fab fa-expeditedssl fa-fw" style="color: white; font-size: 30px;"></i>
                        </div>
                        <span class="nav-items-text" style="color:white; visibility:@Visibility">Security</span>
                </a>   
                }

Change visibility of nav item in blazor menu

As suggested by above link, I created the AppStateService in Services. Below is my code for AppStateService

public class AppStateService
    {
        private bool isAdmin;
        public event Action OnChange;
        public bool IsAdmin
        {
            get { return isAdmin; }
            set
            {
                if (isAdmin != value)
                {
                    isAdmin = value;
                    NotifyStateChanged();
                }
            }
        }

        private void NotifyStateChanged() => OnChange?.Invoke();
    }

On Index page, I used and assign the

@inject AppStateService AppStateService
AppStateService.IsAdmin = true;

On Left Navigation Component, I used

@inject AppStateService AppStateService
@implements IDisposable

Left Navigation Component

protected override async Task OnInitializedAsync()
        {
            AppStateService.OnChange += StateHasChanged;
        }


public void Dispose()
        {
            AppStateService.OnChange -= StateHasChanged;
        }

added in Startup class also.

But now how will I get the Value of isAdmin in left Navigation, from Index.Razor page to display / hide the nav item.

Your navigation bar code:

    protected override void OnInitialized()
        => appStateService.OnChange += OnAppStateChanged; 

    private void OnAppStateChanged()
        => InvokeAsync(StateHasChanged);

    public void Dispose()
        => appStateService.OnChange -= OnAppStateChanged; 

And a test page:

@page "/"
@inject AppStateService appStateService; 

<PageTitle>Index</PageTitle>

<h1>Hello, world!</h1>

Welcome to your new app.

<SurveyPrompt Title="How is Blazor working for you?" />

@code{

    protected async override Task OnInitializedAsync()
    {
        this.appStateService.IsAdmin = false;
        await this.GetIsAdmin();
    }

    private async ValueTask GetIsAdmin()
    {
        //emulate an async API call
        await Task.Delay(500);
        var isAdmin = (Random.Shared.Next(0, 2)) == 0;
        this.appStateService.IsAdmin = isAdmin;
    }
}

I think that you are in the right way, but try to add your code in Index page and not in Navigation Component.
Index page

@inject AppStateService AppStateService
@implements IDisposable

protected override void OnAfterRender(bool firstRender)
{
  if (firstRender)
  {
    AppStateService.IsAdmin = true;
    AppStateService.OnChange += StateHasChanged;
  }
}

public void Dispose()
{
   AppStateService.OnChange -= StateHasChanged;
}

Navigation Component, kept the same.

@if (AppStateService.IsAdmin)
 {
    <a class="nav-items" target="_blank">
       <div style="width:40px;">
         <i title="Security" class="fab fa-expeditedssl fa-fw" style="color: white; font-size: 30px;"></i>
       </div>
       <span class="nav-items-text" style="color:white; visibility:@Visibility">Security</span>
    </a>   
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM