candlestick sf chart is so slow with just a few thousand data points

Hi,

I have been working with an sfChart and I am trying to give it functionality similar to other stock chart platforms.

However, the performance seems horrendous, and I'm concerned that there is a memory leak somewhere. I'm not sure if my implementation is the cause or if this control is really not as performant as expected.

I added my implementation at the end of this post. In the code I am adding a button and chart to the main window. On clicking the button, I clear the binded observable collection and add 11500 candles to it.


I really hope to get this chart to be much more performant than what I am currently experiencing and would appreciate any help.



The issues that I see listed out are:

1 - the chart takes multiple seconds to render the candles.

2 - The window and control become very slow and delayed when I try to:

     a) scroll along the chart

     b) change the zoom factor with the scroll bar

     c) resize the window.

3 - when loading these 11500 candles into the chart. it takes up almost 600 mb of memory. that seems like a lot, since on other stock platforms I have no problems loading up 5-6 charts with thousands of candles on them. so is that much memory usage correct?

4 - a possibly memory leak somewhere..... In my code I make sure to clear the observable collection that is binded to the chart before reloading it. However, when the chart starts to re-render the candles, I continue to see memory continue to build up every time that I try to repopulate.  I would think that it should stay the same after the initial render. I have attached pictures in memleak.zip


Implementation 

<Window x:Class="WPFSfChartTesting.MainWindow"

        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"

        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"

        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"

        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"

        xmlns:chart="clr-namespace:Syncfusion.UI.Xaml.Charts;assembly=Syncfusion.SfChart.WPF"

        xmlns:local="clr-namespace:WPFSfChartTesting"

        mc:Ignorable="d"

        Title="MainWindow" Height="450" Width="800">

    <Grid>

        <Grid.RowDefinitions>

            <RowDefinition Height="20"/>

            <RowDefinition Height="*"/>

        </Grid.RowDefinitions>


        <Button x:Name="populateBtn" Content="Populate" Click="populateBtn_Click"/>


        <chart:SfChart x:Name="chart"

                       Grid.Row ="1">

            <chart:SfChart.PrimaryAxis>

                <chart:CategoryAxis x:Name="xAxis"

                                    EnableScrollBar="True"

                                    Interval="1"

                                    LabelFormat="ddd d MMM HH:mm"/>

            </chart:SfChart.PrimaryAxis>


            <chart:CandleSeries

                x:Name="candleSeries"

                ItemsSource="{Binding RenderedBars}"

                XBindingPath="Date"

                High="High"

                Low="Low"

                Open="Open"

                Close="Close"

                BearFillColor="Maroon"

                BullFillColor="MidnightBlue"/>

        </chart:SfChart>

    </Grid>

</Window>


using System;

using System.Collections.ObjectModel;

using System.ComponentModel;

using System.Windows;


namespace WPFSfChartTesting

{

    /// <summary>

    /// Interaction logic for MainWindow.xaml

    /// </summary>

    public partial class MainWindow : Window

    {

        ViewModel _vm;

        public MainWindow()

        {

            InitializeComponent();

            _vm = new();

            DataContext = _vm;

        }


        private void populateBtn_Click(object sender, RoutedEventArgs e)

        {

            _vm.Populate();


            int barsToSee = 500;

            double zoomFactor = 0;

            double zoomPosition = 0;


            double pctBars = 1.0 * barsToSee / _vm.RenderedBars.Count;


            zoomFactor = pctBars;

            zoomPosition = 1 - pctBars;


            xAxis.ZoomFactor = zoomFactor;

            xAxis.ZoomPosition = zoomPosition;

        }

    }


    public class ViewModel : INotifyPropertyChanged

    {

        public event PropertyChangedEventHandler? PropertyChanged;


        public ObservableCollection<BarModel> RenderedBars { get; set; } = new();


        public void Populate()

        {

            RenderedBars.Clear();


            Random random = new();

            double min = 0;

            double max = 1;

            DateTime date = new DateTime(2021, 1, 1);


            for (int i = 0; i < 11500; i++)

            {

                double o = random.NextDouble();

                double c = random.NextDouble();

                double h = Math.Max(o, c) + Math.Abs(o - c);

                double l = Math.Min(o, c) - Math.Abs(o - c);


                RenderedBars.Add(new BarModel(date, o, h, l, c));

                date = date.AddMinutes(5);

            }

        }

    }


    public class BarModel

    {

        public DateTime Date { get; private set; }

        public double Open { get; private set; }

        public double High { get; private set; }

        public double Low { get; private set; }

        public double Close { get; private set; }

        public BarModel(DateTime date, double open, double high, double low, double close)

        {

            Date = date;

            Open = open;

            High = high;

            Low = low;

            Close = close;

        }

    }

}



Attachment: memleak_8e4ed559.zip

3 Replies 1 reply marked as answer

YP Yuvaraj Palanisamy Syncfusion Team March 29, 2022 04:34 PM UTC

Hi Lorenzo, 
 
We would like to suggest that use FastCandleBitmapSeries instead of CandleSeries for improving the performance of rendering with huge datapoints.

 
We have attached the sample for your reference. Please find the sample from the below link 
 

For more details, please refer the below link
 
 
Regards, 
Yuvaraj. 


Marked as answer

LO Lorenzo March 30, 2022 10:39 AM UTC

That works so much better, thank you.





YP Yuvaraj Palanisamy Syncfusion Team March 31, 2022 07:56 AM UTC

Hi Lorenzo,


Thanks for your update.


Please let us know if you have any further assistance.


Regards,

Yuvaraj.


Loader.
Up arrow icon