Reputation: 4740
Consider the following requirements:
OnInitializedAsync
when initialized.But here is where the challenge comes in:
OnInitializedAsync
twice).How is this possible in blazor?
Code:
<ul class="nav nav-tabs">
<li class="nav-item">
<a class="nav-link" @onclick="() => tabId == 1">Tab 1</a>
</li>
<li class="nav-item">
<a class="nav-link" @onclick="() => tabId == 2">Tab 2</a>
</li>
<li class="nav-item">
<a class="nav-link" @onclick="() => tabId == 3">Tab 3</a>
</li>
</ul>
@switch(tabId)
{
case 1:
<Tab1Component />
break;
case 2:
<Tab2Component />
break;
case 3:
<Tab3Component />
break;
}
@code {
private int tabId = 1;
}
But this does not work since when I switch tabs, OnInitializedAsync
gets called every time.
What would be helpful is if there is a hidden
blazor attribute where I can just add an attribute to the tab bodies like this:
<Tab1Component @hidden="tabId != 1" />
Upvotes: 1
Views: 1227
Reputation: 4740
One solution I found was to create a Hidable
component:
Hidable.razor.cs
public partial class Hidable
{
[Parameter] public bool? hidden { get; set; }
[Parameter] public bool? show { get; set; }
protected override void OnParametersSet()
{
if (hidden.HasValue && show.HasValue)
{
throw new Exception($"Do not set BOTH {nameof(hidden)} and {nameof(show)}!");
}
}
[Parameter] public RenderFragment ChildContent { get; set; }
private string style
{
get
{
if (hidden.HasValue && !hidden.Value) return "";
if (show.HasValue && show.Value) return "";
return "display: none";
}
}
}
Hidable.razor
<div style="@style">@ChildContent</div>
Example use:
<Hidable hidden="@(tabId == 1)">
<Tab1Component />
</Hidable>
<Hidable hidden="@(tabId == 2)">
<Tab2Component />
</Hidable>
<Hidable hidden="@(tabId == 3)">
<Tab3Component />
</Hidable>
Upvotes: 1
Reputation: 273621
- A tab body should not be initialized twice when it re-appears. (It should not run OnInitializedAsync twice).
Blazor determnines when a Component is Initialized, your problem is actually "how to maintain state". Many ways to do that.
But I can see that a complex control with user input would be hard to restore.
What would be helpful is if there is a hidden blazor attribute
You could make one. Your Tab1-3Component classes can expose a boolean and use CSS to set dispplay=none on the outer tag. I suppose you can't conditiopnaslly render because that would lose state again.
The switch
statement would be replaced by
<Tab1Component Visible=(tabId==1) />
<Tab2Component Visible=(tabId==2) />
<Tab3Component Visible=(tabId==3) />
Upvotes: 3