Articles in this section
Category / Section

How to export the cartesian chart as a pdf document (SfCartesianChart) ?

In this article, we explain how to export the cartesian chart as a PDF using the Flutter cartesian chart.

The SfCartesianChart widget provides an option to export the chart in PDF format. The following steps explain how to accomplish this exporting functionality.

Step 1: To access the path from mobile and other platforms, add the path_provider package as a dependency in the application. And add syncfusion_flutter_pdf package as a dependency to create and access PDF files.

  path_provider: ^2.0.9
  syncfusion_flutter_charts: ^20.1.48
  syncfusion_flutter_pdf: ^20.1.48-beta

Step 2: It is necessary to include the platform-specific file generating codes to save the file as a PDF document. So, we have created two dart files (save_file_mobile and save_file_web) to save and launch the file on different platforms. On that two dart files, we have provided the common method called saveAndLaunchFile to save the exported content as a file.

To download the PDF file in the web platform, we should add AnchorElement from dart:html in this save_file_web file.

save_file_web.dart

import 'dart:async';
import 'dart:convert';
import 'dart:html';
 
class FileSaveHelper {
  static Future<void> saveAndLaunchFile(
      List<int> bytes, String fileName) async {
    AnchorElement(
        href:
            'data:application/octet-stream;charset=utf-16le;base64,${base64.encode(bytes)}')
      ..setAttribute('download', fileName)
      ..click();
  }
}

To download the PDF file on the mobile and other platforms, we use this save_file_mobile file.

save_file_mobile.dart

import 'dart:io';
import 'package:flutter/services.dart';
import 'package:path_provider/path_provider.dart';
import 'package:path_provider_platform_interface/path_provider_platform_interface.dart';
 
class FileSaveHelper {
  static const MethodChannel _platformCall = MethodChannel('launchFile');
 
  static Future<void> saveAndLaunchFile(
      List<int> bytes, String fileName) async {
    String? path;
    if (Platform.isAndroid ||
        Platform.isIOS ||
        Platform.isLinux ||
        Platform.isWindows) {
      final Directory directory = await getApplicationSupportDirectory();
      path = directory.path;
    } else {
      path = await PathProviderPlatform.instance.getApplicationSupportPath();
    }
    final File file =
        File(Platform.isWindows ? '$path\\$fileName' : '$path/$fileName');
    await file.writeAsBytes(bytes, flush: true);
    if (Platform.isAndroid || Platform.isIOS) {
      final Map<String, String> argument = <String, String> {
        'file_path': '$path/$fileName'
      };
      try {
        final Future<Map<String, String>?> result =
            _platformCall.invokeMethod('viewPdf', argument);
      } catch (e) {
        throw Exception(e);
      }
    } else if (Platform.isWindows) {
      await Process.run('start', <String>['$path\\$fileName'],
          runInShell: true);
    } else if (Platform.isMacOS) {
      await Process.run('open', <String>['$path/$fileName'], runInShell: true);
    } else if (Platform.isLinux) {
      await Process.run('xdg-open', <String>['$path/$fileName'],
          runInShell: true);
    }
  }
}

Step 3: Initialize the variable _chartData which stores the data source and initialize the variable _cartesianChartKey which stores the global key of rendering the cartesian chart. This key is used to convert the chart into an image and we will use that image to create a PDF file.

And create the SfCartesianChart widget with the necessary properties.

//Add the necessary imports
import 'dart:typed_data';
import 'dart:ui' as ui;
import 'package:flutter/material.dart';
import '../save_file_mobile.dart'
    if (dart.library.html) '../save_file_web.dart';
import 'dart:async';
import 'package:syncfusion_flutter_charts/charts.dart';
import 'package:syncfusion_flutter_pdf/pdf.dart';
 
late GlobalKey<SfCartesianChartState> _cartesianChartKey;
late List<ChartSampleData> _chartData;
 
@override
void initState() {
  _cartesianChartKey = GlobalKey();
  _chartData = < ChartSampleData >[
      ChartSampleData ('Jan', 12),
      ChartSampleData ('Feb', 28),
      ChartSampleData ('Mar', 35),
      ChartSampleData ('Apr', 27),
      ChartSampleData ('Jun', 42),
      ChartSampleData ('Jul', 33)
  ];
  super.initState();
}
 
@override
Widget build(BuildContext context) {
  return SfCartesianChart(
    key: _cartesianChartKey,
    primaryXAxis: CategoryAxis(), 
    series: <ColumnSeries< ChartSampleData, String>>[
      ColumnSeries< ChartSampleData, String>(
        dataSource: _chartData,
        xValueMapper: (ChartSampleData data, _) => data.x,
        yValueMapper: (ChartSampleData data, _) => data.y
      )
    ]
  )
}
 
class ChartSampleData {
  ChartSampleData ({this.x, this.y});
  final String? x;
  final num? y;
}

Step 4: Create a separate method called _renderPdf  where we export the chart as a PDF. Added a snack bar to notify the chart is exported as a PDF document.

Future<void> _ renderPdf () async {
  final ui.Image data = await  _ cartesianChartKey.currentState!.toImage(pixelRatio : 3.0);
  final ByteData? bytes = await data.toByteData(format : ui.ImageByteFormat.png);
  final Uint8List imageBytes = bytes!.buffer.asUint8List(bytes.offsetInBytes, bytes.lengthInBytes);
  final PdfBitmap bitmap = PdfBitmap(imageBytes);
  final PdfDocument document = PdfDocument();
  document.pageSettings.size = Size(bitmap.width.toDouble(), bitmap.height.toDouble());
  final PdfPage page = document.pages.add();
  final Size pageSize = page.getClientSize();
  page.graphics.drawImage(bitmap, Rect.fromLTWH(0, 0, pageSize.width, pageSize.height));
  await FileSaveHelper.saveAndLaunchFile(document.save(), 'cartesian_chart.pdf');
  ScaffoldMessenger.of(context).showSnackBar(
    const SnackBar(
      behavior: SnackBarBehavior.floating,
      shape: RoundedRectangleBorder(
        borderRadius: BorderRadius.all(Radius.circular(5))
      ),
      duration: Duration(milliseconds: 200),
      content: Text('Chart has been exported as PDF document.'),
    )
  );

Step 5: Add the TextButton widget and call the _renderPdf method to convert the rendered chart as PDF.

@override
Widget build(BuildContext context) {
  return Column(
    mainAxisAlignment: MainAxisAlignment.spaceEvenly,
    children: <Widget>[
      SfCartesianChart(
        key: _ cartesianChartKey,
        primaryXAxis: CategoryAxis(),
        series: <ColumnSeries<ChartSampleData, String>>[
          ColumnSeries<ChartSampleData, String>(
            dataSource: _chartData,
            xValueMapper: (ChartSampleData data, _) => data.x,
            yValueMapper: (ChartSampleData data, _) => data.y,
          )
        ]
      ),
      TextButton(
        child: const Text('Export as PDF),
        onPressed: () {
          _renderPdf();
        },
      )
    ]
  );
}

Now when you tap the TextButton ,the cartesian chart will be exported and downloaded as a PDF file.

flutter chart - pdf export

View the Github Sample here.

 
Did you find this information helpful?
Yes
No
Help us improve this page
Please provide feedback or comments
Comments (0)
Access denied
Access denied