I have many checkboxes in my code, but not all are displayed to user.
Only the checkboxes that satisfies condition (if
condition below) are displayed to user.
Assume NavItem contains "fruits" and "nuts". So 5 checkboxes that met condition are displayed when I use my current code.
My current working code:
<div id="checkboxes">
<ul >
@if (NavItem.Contains("fruits"))
<li >
<input type="checkbox" id="checkbox1" data-id=1 checked="true">
<label>apple</label>
</li>
<li >
<input type="checkbox" id="checkbox2" data-id=2>
<label>banana</label>
</li>
<li >
<input type="checkbox" id="checkbox3" data-id=3>
<label>orange/label>
</li>
}
@if (NavItem.Contains("greens"))
{
<li >
<input type="checkbox" id="checkbox4" data-id=4>
<label for="checkbox4">spinach</label>
</li>
<li >
<input type="checkbox" id="checkbox5" data-id=5>
<label for="checkbox5">celery</label>
</li>
}
@if (NavItem.Contains("nuts"))
{
<li >
<input type="checkbox" id="checkbox6" data-id=6>
<label for="checkbox6">almond</label>
</li>
<li >
<input type="checkbox" id="checkbox7" data-id=7>
<label for="checkbox7">walnut</label>
</li>
}
................
</ul>
</div>
I am rewriting the above code, so that it is easier to read and maintain. Below code works fine, except I have trouble incorporating if
condition.
@if (NavItem.Contains("fruits") || NavItem.Contains("greens") || NavItem.Contains("nuts")) // `if` does not work as expected
@for (var i = 1; i < 8; i )
{
var no = i;
<li >
<input type="checkbox" id=@checkboxID[no] data-id=@item>
<label>@ItemName[no]</label>
</li>
}
@code{
List<string> ItemName = new List<string {"dummy", "apple", "banana", "orange", "spinach", "celery", "almond", "walnut"};
List<string> checkboxID = new List<string> {"dummy", "checkbox1", "checkbox2", "checkbox3", "checkbox4", "checkbox5", "checkbox6", "checkbox7"};
}
Same as before, assume NavItem contains "fruits" and "nuts". So, only 5 checkboxes that meets this condition should be displayed. But all 7 are displayed. How do I incorporate if
in my new code. Thank you.
CodePudding user response:
In order to make your system maintainable, you need to key your information somehow, such that you have an arbitrary collection of categories, and you can easily add new members to whatever category you want. Normally, the data would come from a database, but here I built some sample data:
@page "/"
<h3>My Diet</h3>
@foreach (var category in Categories)
{
<input style="margin: 3px;" type="checkbox" @bind="Checklist[category]" /> @category.Name
<br/>
}
<hr />
@foreach (var category in Checklist.Where(c => c.Value == true))
{
foreach (var item in CheckedFoods.Where(cf => cf.Key.CategoryID == category.Key.ID))
{
<input style="margin: 3px;" type="checkbox" @bind="CheckedFoods[item.Key]" /> @item.Key.Name
}
}
@code {
record FoodCategory(int ID, string Name);
record FoodItem(int CategoryID, string Name);
Dictionary<FoodCategory, bool> Checklist = new();
Dictionary<FoodItem, bool> CheckedFoods = new();
List<FoodCategory> Categories = new()
{
new (0,"fruits"), new (1,"greens"), new (2, "nuts")
};
List<FoodItem> FoodItems = new()
{
new (0, "apples"), new (0, "pears"), new (0, "bananas"),
new (1, "beans"), new (1, "cabbage"), new (1, "boogers"),
new (2, "almonds"), new (2, "walnuts"), new (2, "pecans"),
};
protected override void OnInitialized()
{
Checklist = Categories.ToDictionary(c => c, c => false);
CheckedFoods = FoodItems.ToDictionary(f => f, f => false);
}
}
CodePudding user response:
Your new version of the code doesn't evaluate each item. If any of the three options are available in NavItem
than all items are drawn. To replicate the original functionality you'll need to evaluate the range of items to be drawn like you did before.
@for (var i = 1; i < 8; i )
{
bool isAvailable = false;
if (NavItem.Contains("fruits"))
isAvailable = i >= 1 && i <= 3;
if (!isAvailable && NavItem.Contains("greens"))
isAvailable = i >= 4 && i <= 5;
if (!isAvailable && NavItem.Contains("nuts"))
isAvailable = i >= 6 && i <= 7;
if (isAvailable)
{
<li >
<input type="checkbox" [email protected]("checkbox{0}",i) data-id=@i>
<label>@ItemName[i]</label>
</li>
}
}
I personally agree with Bennyboy that that your original solution was not quite sustainable. But if you omit the correlation between the ItemName
and checkboxID
by removing the checkboxID
collection like I've shown you than your solution becomes much simpler.