Pre loader

Slow load of multiple WPF charts

0
0

Hello!

I’m building an application where I need to display quiet a large number of charts next to each other.

In this app the user can select up to 16 devices at the same time, each device having 24 channels of measurement data.
So in the worst case there could be 384 charts visible at the same time.
Usually it’s more likely to be around 24 or 48.

The user will also be switching between different views to monitor the devices he’s working with so UI elements need to be reloaded and repopulated more than once.

I have realized that this might not be possible to do with SciChart as loading 24 charts on their own already takes about a second or two.

I already have placed a call to “SciChart2DInitializer.LoadLibrariesAndLicenseAsync().Wait();” in my startup part of my software.
The chart itself is quiet simple and it is placed within an ItemsControl to be populated as many times as required.:

<ItemsControl Grid.Row="1" ItemsSource="{Binding Path=Data}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<s:SciChartSurface
x:Name="sciChartSurface"
Margin="10"
s:ThemeManager.Theme="BrightSpark"
Background="White"
Style="{x:Null}">
<s:SciChartSurface.RenderSurface>
<s:XamlRenderSurface />
</s:SciChartSurface.RenderSurface>
<s:SciChartSurface.YAxes>
<s:NumericAxis
x:Name="reflectanceAxis"
AxisAlignment="Left"
Id="reflectanceAxis"
IsPrimaryAxis="True" />
</s:SciChartSurface.YAxes>
<s:SciChartSurface.XAxis>
<s:DateTimeAxis x:Name="timeAxis" Id="timeAxis" />
</s:SciChartSurface.XAxis>
<s:SciChartSurface.RenderableSeries>
<s:FastLineRenderableSeries XAxisId="timeAxis" YAxisId="reflectanceAxis" />
</s:SciChartSurface.RenderableSeries>
</s:SciChartSurface>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>

Is there any way that I can improve the loading performance even further?

Attached you can find a stripped down sample project which demonstrates the slow load times I’m experiencing.
There is also a picture attached where you can see that loading 24 charts blocks the UI thread for about 1.5 seconds.

I am using the latest SciChart version currently available (6.2.1.13304)

Version
6.2.1.13304
Attachments
Images
  • Andrew Burnett-Thompson
    Hi Michael! Team has been made aware of this, apologies for no follow-up so far. I will chase. Best regards, Andrew
  • You must to post comments
1
0

Hi Michael,

I’ve looked at your example and I’ve got a few suggestions.
First of all, it’s important to say that SciChartSurface is inherently expensive entity with several child UI elements so creating lots of those is going to be slow. We are aware of the problem and have some long term improvement plans but I don’t think that quickly creating 350 surfaces will be possible even after those are implemented.
So, primary suggestion to fix slow creation would be to avoid creation at all where possible. Basically, you shouldn’t create a surface unless it’s visible to user, and to achieve this you can use techniques such as paging and virtualization which can be further improved by instance pooling. Finally, you may want to consider having multiple series on single surface with some color coding or checkboxes/dropdown to select active device(s) – these usage scenarios are well supported and fast.
As an example I’ve added virtualization to ShellView and it does noticeably improve performance, that improvement will be even larger when increasing number of surfaces.

Finally, XamlRenderSurface is the slowest possible option, in general it’s recommended to use VisualXcceleratorRenderSurface which is hardware accelerated and add some way for user to opt-out of it to HighSpeedRenderSurface in case of GPU-related glitches.

Yours,
Alex

Attachments
  • You must to post comments
0
0

Hello Alexander,

thanks for your help!

I have found another way of improving the performance in my software.

As I realized the slow down consists of two parts, parsing and layout.

By implementing a very simple control cache mechanism I was able to offload the “parsing” bit into the application startup so that, when changing views, the charts only need to be put in place and layouted.

public class ChartWellCacheControl : UserControl
{
    private static List<ChartWellControl> _cache;
    static ChartWellCacheControl()
    {
        _cache = new List<ChartWellControl>();
    }
    public ChartWellCacheControl()
    {
        Loaded += ChartWellCacheControl_Loaded;
        Unloaded += ChartWellCacheControl_Unloaded;
    }
    public static void PreloadCache(int items)
    {
        for (int i = 0; i < items; i++)
        {
            var itemToInit = new ChartWellControl();
            itemToInit.ApplyTemplate();
            _cache.Add(itemToInit);
        }
    }

    private void ChartWellCacheControl_Unloaded(object sender, System.Windows.RoutedEventArgs e)
    {
        if (Content != null && Content is ChartWellControl chartWellControl)
        {
            Content = null;
            _cache.Add(chartWellControl);
        }
    }
    private void ChartWellCacheControl_Loaded(object sender, System.Windows.RoutedEventArgs e)
    {
        if (Content == null)
        {
            var itemToLoad = _cache.LastOrDefault();
            if (itemToLoad != null)
            {
                _cache.Remove(itemToLoad);
                Content = itemToLoad;
            }
            else
            {
                Content = new TextBlock() {  Text = "Cache empty" };
            }
        }
    }
}

This might not be a solution for everyone but it works quiet well in my case.
I think I could improve the performance even more by simplifying my layout even further.
So far I am quiet happy with it.

Thanks again, keep up the good work, SciChart is great and a delight to use! 🙂

Ceers

  • You must to post comments
Showing 2 results
Your Answer

Please first to submit.

Try SciChart Today

Start a trial and discover why we are the choice
of demanding developers worldwide

Start TrialCase Studies