CartesianChartPoint issue

Hi,

I'm using SfCartesianChart with DateTimeCategoryAxis in primaryXAxis.

After upgrading to the latest Syncfusion version, I'm getting an error:

======== Exception caught by rendering library =====================================================

type 'CartesianChartPoint<dynamic>' is not a subtype of type 'CartesianChartPoint<DateTime>' of 'point'


The issue is in the following code:

onActualRangeChanged: (args) {
if (args.orientation ==
AxisOrientation.horizontal) {
// You can get the x axis maximum value pixel point here. This is the x axis right side pixel value. So, opposed y-axis started from this position.
final double visibleMaxX = candleController!
.pointToPixel(CartesianChartPoint(
x:args.visibleMax, y:0))
.dx;

// You can get the x axis minimum value pixel point here.
final double visibleMinX = candleController!
.pointToPixel(CartesianChartPoint(
x:args.visibleMin, y:0))
.dx;

// You can get the x axis width here.
xAxisWidth = visibleMaxX - visibleMinX;
}

13 Replies

PS Preethika Selvam Syncfusion Team January 12, 2024 12:51 PM UTC

Hi Bar IIan,


We can able to replicate the reported issue at our end. Currently, we have fixed the reported issue with a workaround solution in which we have achieved your requirement using addPostFrameCallback, where we have done a pointToPixel conversion. We have attached the sample below for reference.


We will fix the reported issue in source level and let you know.


Regards,

Preethika Selvam.



BI Bar Ilan January 21, 2024 03:46 PM UTC

Where is the sample ?



PS Preethika Selvam Syncfusion Team January 22, 2024 06:41 AM UTC

Hi Bar IIan,


Sorry for inconvenience. Here we have attached the sample for your reference, you can modify the sample based on your needs. Please let us know if you need any further assistance.


Regards,

Preethika Selvam.


Attachment: fr186186_400f01ca.zip


BI Bar Ilan January 22, 2024 09:06 AM UTC

Thank you for your quick response.

When the changed will be released?




BI Bar Ilan January 22, 2024 09:28 AM UTC

I still getting the same error.



PS Preethika Selvam Syncfusion Team January 24, 2024 12:38 PM UTC

Hi Bar llan,


We have validated the reported details with the development team, and they have provided the following information.


According to the new Charts architecture flow change, the axis size is now calculated based on the axis range obtained from the onActualRangeChanged callback. This behavior is correct because the axis size is determined using the final axis range. If we were to modify the axis range in the onActualRangeChanged callback, the pointToPixel method would yield an incorrect position. Previously it was working wrongly, hence we have corrected this behavior in our volume 4 release.


Please specify the exact requirements, and we will provide a possible solution on our end.


Regards,

Preethika Selvam.



BI Bar Ilan January 29, 2024 07:41 AM UTC

I need calculate width of the chart.



PS Preethika Selvam Syncfusion Team February 6, 2024 02:03 PM UTC

Hi Bar,


Query 1: To calculate plot area width.


We have achieved your requirement regarding ‘To calculate plot area width’ by using the onCreateRenderer property in the ColumnSeries. By using this, you can get the ColumnSeries size in the performLayout method. Additionally, we have displayed ColumnSeries size by using TextField Widget. We have provided a code snippet and a sample for your reference. You can customize the sample according to your requirements. Also, you can refer the sample we provided on January 22, 2024, to calculate the plot area width using the axis visible range in a addPostFrameCallback.


Code Snippet:


TextEditingController _controller = TextEditingController();

 

class _MyHomePageState extends State<_MyHomePage> {

  List<_SalesData> data = [

    _SalesData(DateTime(2000, 01, 01), 35),

    _SalesData(DateTime(2000, 01, 05), 28),

    _SalesData(DateTime(2000, 01, 10), 34),

    _SalesData(DateTime(2000, 01, 15), 32),

    _SalesData(DateTime(2000, 01, 20), 40)

  ];

 

  _CustomColumnSeriesRenderer<_SalesData, DateTime>? _seriesRenderer;

 

  @override

  void initState() {

    _seriesRenderer = _CustomColumnSeriesRenderer(updateTextField: updateText);

    super.initState();

  }

 

  @override

  Widget build(BuildContext context) {

    return Scaffold(

      appBar: AppBar(

        title: const Text('Syncfusion Flutter chart'),

      ),

      body: Column(

        children: [

          SfCartesianChart(

            primaryXAxis: const DateTimeAxis(),

            primaryYAxis: const NumericAxis(),

            series: <CartesianSeries<_SalesData, DateTime>>[

              ColumnSeries<_SalesData, DateTime>(

                dataSource: data,

                xValueMapper: (_SalesData sales, _) => sales.x,

                yValueMapper: (_SalesData sales, _) => sales.y,

                name: 'Sales',

                animationDuration: 0,

                onCreateRenderer: (ChartSeries<dynamic, dynamic> series) {

                  return _seriesRenderer!;

                },

              )

            ],

          ),

          TextField(

            controller: _controller,

          )

        ],

      ),

    );

  }

 

  void updateText(String newText) {

    SchedulerBinding.instance.addPostFrameCallback(

      (timeStamp) {

        _controller.text = newText;

      },

    );

  }

}

 

class _CustomColumnSeriesRenderer<ChartData, DateTime>

    extends ColumnSeriesRenderer<ChartData, DateTime> {

  num? plotAreaWidth;

  num? plotAreaHeight;

  Function(String) updateTextField;

 

  _CustomColumnSeriesRenderer({

    required this.updateTextField,

  });

 

  @override

  void performLayout() {

    super.performLayout();

    plotAreaHeight = size.height;

    plotAreaWidth = size.width;

    updateTextField('Plot Area Width: $plotAreaWidth, Height: $plotAreaHeight');

  }

}


Screenshot:


Query 2: To calculate chart area width.


We have achieved your requirement regarding ‘To calculate chart area width’ by using the ‘_updateChartSize’ method, where we retrieve the size of the chart area by accessing its render box through the global key. It then extracts the width and height from this size and updates a text field. We have provided a code snippet and a sample for your reference. You can customize the sample according to your requirements.


Code Snippet:


 TextEditingController _controller = TextEditingController();

 

class _MyHomePageState extends State<_MyHomePage> {

  final GlobalKey<SfCartesianChartState> _chartKey = GlobalKey();

 

  @override

  Widget build(BuildContext context) {

    return Scaffold(

      appBar: AppBar(

        title: const Text('Syncfusion Flutter chart'),

      ),

      body: Column(

        children: [

          Expanded(

            child: SfCartesianChart(

              key: _chartKey,

              primaryXAxis: const DateTimeAxis(),

              primaryYAxis: const NumericAxis(),

              series: <CartesianSeries<_SalesData, DateTime>>[

                ColumnSeries<_SalesData, DateTime>(

                  dataSource: data,

                  xValueMapper: (_SalesData sales, _) => sales.x,

                  yValueMapper: (_SalesData sales, _) => sales.y,

                  name: 'Sales',

                  animationDuration: 0,

                )

              ],

            ),

          ),

          TextField(

            controller: _controller,

            readOnly: true,

            decoration: const InputDecoration(

              labelText: 'Chart Size',

              border: OutlineInputBorder(),

            ),

          )

        ],

      ),

    );

  }

 

  @override

  void initState() {

    super.initState();

    WidgetsBinding.instance.addPostFrameCallback((_) {

      _updateChartSize();

    });

  }

 

  void _updateChartSize() {

    final RenderBox renderBox =

        _chartKey.currentContext!.findRenderObject() as RenderBox;

    final chartSize = renderBox.size;

    final width = chartSize.width;

    final height = chartSize.height;

    _controller.text = 'Chart Width: $width, Height: $height';

  }

}


Screenshot:


Please let us know if you need any further assistance.


Regards,

Preethika Selvam.


Attachment: 186186_8d5ae3c5.zip


BI Bar Ilan replied to Preethika Selvam February 12, 2024 12:03 PM UTC

I'm using CandleSeries and want to get the pixel point based on a specific value in the y-component. How can I do this with the new version?



BI Bar Ilan February 12, 2024 03:23 PM UTC

I have problem with _seriesRenderer, i have 3 _seriesRenderer according to specific series (AreaSeries, CandleSeries, LineSeries).

when i change the chart for example candle to line using setstate, and then going back to candle chart is display the following error:


I'm having problem with _seriesRenderer. I use three different _seriesRenderer for different chart types (Area, Candle, Line). When I switch from Candle to Line using setState, going back to the Candle chart shows an error.

======== Exception caught by widgets library =======================================================

The following assertion was thrown building KeyedSubtree-[GlobalKey#7823a]:

'package:flutter/src/widgets/framework.dart': Failed assertion: line 6426 pos 12: '!_renderObject!.debugDisposed!': is not true.





PS Preethika Selvam Syncfusion Team February 13, 2024 01:59 PM UTC

Hi Bar,


Query 1: When switching from one chart to another using set state, an exception occurs when using different series with different series renderers.


We can be able to replicate the reported issue. Currently, we are validating the issue. We will fix the issue and it will be rolled out in the upcoming weekly patch release on February 20, 2024. We appreciate your patience until then.


Query 2: I need to get the pixel point based on a specific value in the y-axis for the candle series.


We would like to let you know, to get the pixel point of specific value, we can use the pixelToPoint method. We have shared a user guide documentation for your reference.


UG: https://help.syncfusion.com/flutter/cartesian-charts/methods#pixeltopoint


Please let us know if you need any further assistance.


Regards,

Preethika Selvam.



PS Preethika Selvam Syncfusion Team February 21, 2024 02:33 PM UTC

Hi Bar,


Sorry for the inconvenience. We are looking into the issue and reported issue occurs when using a custom series renderer and it is working fine when using a default series. We are working on this, and the patch will be released on February 22, 2024. We appreciate your patience until then.


Regards,

Preethika Selvam.



YG Yuvaraj Gajaraj Syncfusion Team February 22, 2024 02:20 PM UTC

Hi Bar,


Sorry for the inconvenience. While further investigating the reported issue, we found that it is a sample-level issue caused by storing the CustomSeriesRenderer in a field and accessing the disposed series renderer while calling setState.

Therefore, we have modified the sample by returning the CustomSeriesRenderer in the onCreateRender callback without storing it in a field. This ensures that the series renderer will not get disposed while switching between series.

We have attached the sample below for your reference. We hope it will help you to resolve the issue.


Regards,

Yuvaraj.


Attachment: f186186_7a850ae2.zip

Loader.
Up arrow icon