Consider the following code :
In MyPage.razor :
<ul>
@foreach (var item in myList)
{
var theBool = false;
<li>
<span>For @item, theBool is @theBool</span>
(<a href="" @onclick="@(e => theBool = !theBool)">Reverse bool for @item</a>)
</li>
}
</ul>
@code {
List<string> myList = new() { "item1", "item2", "item3", "item4", "item5", };
}
... which produce the following output :

I expect that clicking on a link will switch the preceding bool value, so it shows "True" instead of "False". It's not working at all, the variable seems to be changed but the UI (the <span>) is not refreshed. What is the good way to implement this in Blazor Webassembly ?
(I hope not to be forced to use the @code section : it would be a major code overhead in term of maintainability).
This is what I'm trying to achieve : A click on a link (which is outside of a component) has to change the parameter of the component (to change the component behavior) :
<ul>
@foreach (var item in myList)
{
var theBool = false;
<li>
<a href="" @onclick="@(e => theBool = !theBool)">Show/Hide details</a>
<MyCoolComponent DisplayDetails="@theBool"></MyCoolComponent>
</li>
}
</ul>
As theBool is captured by the lambda, I expected it still exists after le loop.
That is true...
@PanagiotisKanavos : Do you mean that Blazor only subscribe for Ui refresh on fields and not variables ?
Each time you click on an anchor element, the StateHasChanged method is automatically called by the framework, and the UI is re-rendered, but you can't see it changed, as at the start of the loop you've got var theBool = false;
And thus, <span>For @item, theBool is @theBool</span> is re-rendered to:
<span>For item2, theBool is false</span>
if you've clicked on the second item.
Your code will never work as at each iteration of the loop the local variable theBool is set to false; that is you can't see the changes on the UI...
You can solve it like this:
<ul>
@foreach (var item in Items)
{
<li>
<span>For @item.Name, item.IsSelected is @item.IsSelected</span>
(<a href="" @onclick="@(e => { item.IsSelected = !item.IsSelected; })">Reverse bool for @item.Name</a>)
</li>
}
</ul>
@code {
private List<Item> Items = Enumerable.Range(1, 5).Select(i => new Item { Name = $"item{i}" }).ToList();
public class Item
{
public string Name { get; set; }
public bool IsSelected { get; set; }
}
}
Copy and test...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With