Selectable Tables with Blazor

I have recently been writing a web based UI for Windows Virtual Desktop. My POC website was an HTML site generated by PowerShell with a large amount of Javascript, JQuery and AJax to give the required functionality.

Once I migrated the POC into a real site I had a couple of options of how to write it. In the end I went with writing the site as a .NET Core 3 RazorPages app.

I set to work implementing Entity Framework as Code First to my Azure SQL Database. I created the models and views I needed and was easily able to access the data.

I created an HttpClientHelper class that handled all the RESTApi calls to Azure (getting the Access Token, list of Resource Groups/Subscription etc) and all was good. I will look to post about this helper class separately.

I was however having issues with displaying the returned data in the a selected table view. I wanted to say away from JavaScript and instead see if I could use the new Blazor framework.

The issue I had was that there seems to be very little documentation on how to create a selectable table component that would function as I required.

After a while I managed to cobble together code that worked exactly as I needed!

Initialization

The first thing I needed to do was define a relevant data model. In a real world example I would get this from a model or generate from the response from my HTTP request. In this example I simply generated the data as below:

private List<Values> valueList;
private List<string> events = new List<string>();

protected override void OnInitialized()
{
    valueList = new List<Values>();

    valueList.Add( new Value() {
        Name = "James",
        Age = "38"
    });

    valueList.Add( new Value() {
        Name = "John",
        Age = "32"
    });
}

The events List is used for display purposes.

In the required data class we need to ensure it has an additional property for Class as below

class Value
{
    public string Name { get; set; }
    public string Age { get; set; }
    public string Class { get; set; }
}

This additional Class property will be used to set the TR class to selected.

Table Generation

We next need to generate the required table in HTML via code. This is done using a simple for loop. This allows us to keep track of the index for each Value in our valueList.

<table>
    <thead>
        <tr>
            <th>Name</tr>
            <th>Age</tr>
        </tr>
    </thead>
    <tbody>
    @if (valueList != null)
    {
        int count = valueList.Count;
        for (var i = 0; i < count; i++)
        {
            int current = i;
            var values = valueList[current];
            <tr class="@values.Class" @onclick="((e) => SelectItems(current, false))">
                <td>@values.Name</td>
                <td>@values.Age</td>
            </tr>
        }
    } 
    </tbody>
<table>
<div>
    <h4>Show selected table values</h4>
    <button type="button" class"btn btn-info" @onclick="showSelected">Click</button>
</div>

@if (events != null)
{
    <ul>
        @foreach (var evt in events)
        {
            <li>@evt</li>
        }
    </ul>
}

The above create a table and populates the TR if there is data present in the valueList List.

If so it will loop through each value and assign the class to be equal to the Value’s Class parameter. It will also add an @onclick parameter to each value to be used to select the item.

The button is used to trigger the showSelected() functions and with the @if (events != null) loop it is used to display the selected items.

Functions

Finally we need to create the functions in the @code block that will do the main work. The main function SelectItems handles the assignment of the ‘selected’ class to the required TR.

void SelectItems(int index, bool toggle)
{
    var item = valueList[index];

    if (toggle)
    {
        if (item.Class == "selected")
        {
            item.Class = "";
        }
        else
        {
            item.Class = "selected";
        }
    }
    else
    {
        foreach (var value in valueList)
        {
            value.Class = "";
        }
            item.Class = "selected";
    }
}

The function takes 2 parameters. The first is the index of the selected item in the valueList List. It also takes a bool toggle. This allows for multiple item selection.

The function checks if toggle is set. If so it does a simple check to see if the class is equal to ‘selected’ or not. It will change the item.Class to ‘selected’ or “” as required. This will effectively toggle the class.

If you wish to have custom classes on the TR then the code will need tweaking to remove the ‘selected’ text from the existing class, whilst maintaining the existing class string. For my needs this wasn’t required.

Output

The last part was a simple display function to prove the selected items were indeed selected and accessible.

void showSelected()
{
    events.Clear();
    foreach (var value in valueList)
    {
        if (value.Class.Contains("selected")) 
        {
            events.Add($"'{value.Name}' selected. With age: '{value.Age}'");
        }
    }
}

This easy little script check first clears the current events list. Then it checks each value in the valueList list to see if the Class property contains ‘selected’ if so it adds it to the events list that can be displayed on screen.

Conclusion

This piece of code worked perfectly for what I needed and allows for single or multiple selection.

 

Single Selection
Multiple Selection

The finished code can be viewed in the following Blazorfiddle https://blazorfiddle.com/s/0ei5n4iy hopefully it will be useful to someone.

James

 

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s