BlazorT2_1200x303

The Chart component in Telerik UI for Blazor gives you two modes for binding data. Both give you the ability to let the user customize the chart at runtime – including choosing which data they want to display.

In an earlier post, Creating Charts with the Telerik Chart Component for Blazor, I showed how to graph data that wasn’t coming from your data source in the format that you wanted. My component was retrieving a set of Data Transfer Objects that I had to filter and transform to get the data that I wanted to graph. Essentially, I had to generate two matching collections: one with the “data to be graphed” (the vertical or Y-axis), and one with the categories for that data (the horizontal labels or X-axis).

However, if the data objects that you want to graph contain both the “data to be graphed” and the category label to use – in other words, if each object provides all the data for a point on the graph – well, suddenly everything gets much easier.

Independent Series vs. Data with Labels

My case study in that previous column used what Telerik calls “Independent Series” binding. For a line graph, it means that the Telerik Chart is bound to two separate collections: one that holds the data to be graphed (the vertical or Y-axis), and another collection that holds the categories (the labels that run along the horizontal X-axis).

With Independent Series binding, I tie the field holding my “data to be graphed” collection (quantitiesSold, a collection of integers) to the ChartSeries element using its Data attribute; I bind the field holding my category labels collection (months, a collection of strings) to the ChartCategoryAxis element using its Categories attribute.

Here’s the markup that leverages Independent Series binding:

<TelerikChart Width="75%">
    <ChartSeriesItems>
        <ChartSeries Type="@selectedType" Data="@quantitiesSold"></ChartSeries>
    </ChartSeriesItems>
    <ChartCategoryAxes>
        <ChartCategoryAxis Categories="@months"></ChartCategoryAxis>
    </ChartCategoryAxes>
</TelerikChart>
@code {
    private IEnumerable<object> quantitiesSold;
    private string[] months;

However, if the collection that you’re retrieving consists of objects that hold both the data to be graphed and the category data… well, in that case, things get simpler: You just pass that collection to the chart to have the results graphed. In Telerik UI for Blazor this is called “Attach Series to Their Categories” binding.

For example, the SalesDTO objects that I want to graph have a QuantitySold property (the data to be graphed) and a Month property (the name of the month for the sales). There’s no reason that I couldn’t use the Month property as the label for the QuantitySold data. In that case, because each SalesDTO object holds both the data and the label for one point on the graph, I can just pass my SalesDTO collection to the Telerik Chart component and everything will work out fine.

With the “Attach Series to Their Categories” binding, inside the TelerikChart element I just need the ChartSeries element. I still bind the ChartSeries’ Data attribute, but, this time, I bind it to a collection of objects rather than values – in this case, a collection of my SalesDTO objects.

I do have to add two more attributes to the ChartSeries element:

  • The Field attribute (which I set to the name of the property on the SalesDTO object that holds the “data to be graphed”)
  • The CategoryField attribute (which I set to the name of the property that holds the category label)

In my case, the data to be graphed is in the QuantitySold property and the label for that data is in the Month property. As a result, I can create a graph of all of my SalesDTO objects with just this markup and the field that holds my SalesDTO objects:

<TelerikChart Width="75%">
    <ChartSeriesItems>
        <ChartSeries Data="@graphSales" Field="QuantitySold" CategoryField="Month"> </ChartSeries>
    </ChartSeriesItems>
</TelerikChart>
@code {
    private IEnumerable<SalesDTO> graphSales;

Supporting Customization

Plainly, Independent Series gives you more flexibility in mixing and matching data and labels. With Independent Series, I can massage my input data in any way I want to create the points on the chart, summarizing or transforming the data as needed. There’s no necessary connection between the incoming data and the points on my chart.

With Attaching Series Data to Their Categories, though, each object in my collection has to have a one-to-one relationship with a point on the chart. On top of that, every object in the collection has to hold both its data and its “official label” – and that label must be something that I’m willing to put in my UI.

With Independent Series, the data and labels can come from completely different sources. In my case study, for example, where I was charting sales numbers against month names, my month names (“January” through “December”) could easily have been hardcoded into my application.

But I don’t lose much else in the way of flexibility when I use Attach Series Data to Their Categories. For example, in another post, Creating Customizable Charts with the Telerik Chart Component for Blazor, I can let the user both select what data to display and the kind of chart they wanted (bar, line, area, etc.). Some customization options actually become easier if I’m using Attach Series Items to Their Categories.

For example, let’s say I want to give the user the ability to choose between seeing the number of units sold and the total amount they were sold for. Those are two different properties on my SalesDTO object: QuantitySold and ValueSold. I can do that with both binding mechanisms.

Regardless of which binding method I choose, I start the same way: By giving the user a tool to choose what data they want. For this, I’ll provide a dropdown list showing the two options that’s bound to a field that will hold the user’s choice:

Data: <select @bind="propertyName">
    <option value="QuantitySold">Amount</option>
    <option value="ValueSold">Value</option>
</select>
@code {
    private string propertyName;

Changing the Data with Independent Series

If I’m using Independent Series, I will have already set up a field of IEnumerable to hold the data to be graphed. In my previous post that field looked like this:

private IEnumerable<object> quantitiesSold;

Because the quantitiesSold field is a list of type object, I can load the field with any data I want. That works out well for me because QuantitySold is type int, while ValueSold is type decimal.

Having said that, though, I’m going to either need some “clever” (by which I mean: “unreadable and unmaintainable”) LINQ to switch between the two properties, or I’m going to need two LINQ statements. I prefer the solution with two LINQ statements… which also means that I’ll have to rewrite my propertyName field into a full-fledged property.

As an example of how that would work, this code gives the user the ability to switch between QuantitySold and ValueSold on the fly:

private string propertyname;
    private string propertyName
    {
        get { return propertyname; }
        set
        {
            propertyname = value;
            switch (propertyname)
            {
                case "QuantitySold":
                    quantitiesSold = from s in graphSales
                                     where s.Year == selectedYear
                                     orderby s.Month
                                     select (object)s.QuantitySold;
                    break;
                case "ValueSold":
                    quantitiesSold = from s in graphSales
                                     where s.Year == selectedYear
                                     orderby s.Month
                                     select (object)s.ValueSold;
                    break;
            }
        }
    }

(As a side note, now that my “data to be graphed” field holds two different kinds of data, I should probably rename it to something more neutral than ‘quantitiesSold’ – perhaps ‘dataToBeGraphed’).

Changing the Data with Attach Data Series to Their Labels

With Attach Series Items to Their Categories, the solution is much simpler: It just requires a layer of indirection. Instead of setting the ChartSeries’ Field attribute to the name of a property, I set the attribute to a field that holds the name of the property.

I’ve already bound my dropdown list to a field called propertyName so I’ll use that propertyName field in my ChartSeries’ Field attribute, like this:

<ChartSeries Data="@graphSales" Field="@propertyName"
                                                              CategoryField="Month">

And, because my dropdown list will automatically update my propertyName field, it can go back to being just a field:

private string propertyName;

Now, when the user picks a property name from my dropdown list, my propertyName field will automatically be updated with the name of the property, and the Chart will regenerate itself with the new data.

As you probably expect, every silver lining has a cloud wrapped around it. Attach Items to Their Categories can make generating your chart considerably simpler – even making it easier to provide your user with customization options. If your incoming data doesn’t meet the criteria for Attach Items to Their Categories, it might make sense to massage your incoming data into a format where each object represents a point on the chart holding both the data and label. Where that isn’t possible (or requires too much effort to be worthwhile), Independent Series binding will meet your needs with some loss of flexibility.

Or, as I tell my clients: “You do have a choice: Do you want your arm cut off or ripped off?”

Try it Today

To learn more about Telerik UI for Blazor components and what they can do, check out the Blazor demo page or download a trial to start developing right away.


Peter Vogel
About the Author

Peter Vogel

Peter Vogel is a system architect and principal in PH&V Information Services. PH&V provides full-stack consulting from UX design through object modeling to database design. Peter also writes courses and teaches for Learning Tree International.

Related Posts

Comments

Comments are disabled in preview mode.