Chart image export no longer working in 2024 Q4

1 Answer 121 Views
Charts
Adam
Top achievements
Rank 1
Adam asked on 19 Nov 2024, 09:37 PM

After upgrading to 2024 Q4, the function to export charts to images no longer works.

var chart = $("#chart").getKendoChart();
    chart.exportImage().done(function(data) {
        kendo.saveAs({
            dataURI: data,
            fileName: "chart.png"
        });
    });

The error received is: Uncaught TypeError: chart.exportImage(...).done is not a function.

This can also been seen in the API examples.
https://docs.telerik.com/kendo-ui/api/javascript/dataviz/ui/chart/methods/exportimage

Ben
Top achievements
Rank 1
commented on 20 Nov 2024, 01:39 PM

I am also interested in the answer to this question. We have just updated jQuery and our chart exports are no longer working. I'm considering upgrading kendo ui, but I need to know if it will solve our problems.
James Shelton Agar
Top achievements
Rank 2
commented on 11 Dec 2024, 01:29 AM

Same with us , latest version chart export no longer working ...
Morten
Top achievements
Rank 2
Iron
Iron
Iron
commented on 14 Jan 2025, 01:02 PM | edited


                                    // TODO 20250114: remove code block when fixed https://www.telerik.com/forums/chart-image-export-no-longer-working-in-2024-q4
                                    //#region block to remove
                                    let oldImage = kendo.drawing.exportImage;
                                    kendo.drawing.exportImage = function (group, options) {
                                        let promise = oldImage(group, options);
                                        return kendo.convertPromiseToDeferred(promise);
                                    };
                                    //#endregion

                                    let $qrCode = $("#qrcode").data("kendoQRCode");
                                    $qrCode.exportImage().done(function(data) {
                                        kendo.saveAs({
                                            dataURI: data,
                                            fileName: "QR-Code.png"
                                        });
                                    });

I have the same issue with QRCode, this works for me:

                                    // TODO 20250114: remove code block when fixed https://www.telerik.com/forums/chart-image-export-no-longer-working-in-2024-q4
                                    //#region block to remove
                                    let oldImage = kendo.drawing.exportImage;
                                    kendo.drawing.exportImage = function (group, options) {
                                        let promise = oldImage(group, options);
                                        return kendo.convertPromiseToDeferred(promise);
                                    };
                                    //#endregion

                                    let $qrCode = $("#qrcode").data("kendoQRCode");
                                    $qrCode.exportImage().done(function(data) {
                                        kendo.saveAs({
                                            dataURI: data,
                                            fileName: "QR-Code.png"
                                        });
                                    });

 

1 Answer, 1 is accepted

Sort by
0
Nikolay
Telerik team
answered on 22 Nov 2024, 10:25 AM

Hi Adam, Ben,

This is a regression bug that has been already addressed. The fix is in testing and you can track its progress at the below link:

https://github.com/telerik/kendo-ui-core/issues/8054

Regards,
Nikolay
Progress Telerik

Love the Telerik and Kendo UI products and believe more people should try them? Invite a fellow developer to become a Progress customer and each of you can get a $50 Amazon gift voucher.

Ben
Top achievements
Rank 1
commented on 09 Dec 2024, 11:58 AM

Can we have an ETA on this? Looking at the github, it doesn't appear to have moved in 3 weeks.
James Shelton Agar
Top achievements
Rank 2
commented on 11 Dec 2024, 01:38 AM

This is a critical function for us, export the image and then import into telerik report...is there an alternative work around?
Nikolay
Telerik team
commented on 12 Dec 2024, 09:49 AM

Hello, Ben, James,

The fix will be available with the upcoming release scheduled for February.

Meanwhile, I am sharing a workaround that you can use. 

     let oldImage = kendo.drawing.exportImage;
      kendo.drawing.exportImage = function(group, options) {
        let promise = oldImage(group, options);
        return kendo.convertPromiseToDeferred(promise);
      };

      let oldSvg = kendo.drawing.exportSVG
      kendo.drawing.exportSVG = function(group, options) {
        let promise = oldSvg(group, options);
        return kendo.convertPromiseToDeferred(promise);
      };

Dojo demo: https://dojo.telerik.com/YOYDeDlB

Regards,

Nikolay

James Shelton Agar
Top achievements
Rank 2
commented on 13 Dec 2024, 04:20 AM

Thanks alot Nikolay

That worked for Line chart :-)

Could you also provide for Bar & Pie

  • Bar (no series or color)
  • Pie missing color

Thanks
James

Nikolay
Telerik team
commented on 17 Dec 2024, 11:05 AM

Hi James,

The solution I shared must be valid for the Diagram and all types of Charts.

Here is a Dojo demo I used to test and the export looks good:

https://dojo.telerik.com/aCkAJPie

Feel free to modify it to showcase the problem so I can investigate.

Regards,

Nikolay

Ben
Top achievements
Rank 1
commented on 21 Jan 2025, 02:50 PM | edited

I'm struggling to make this work in our solution. We create a dynamic script file with js like so:


let oldImage = kendo.drawing.exportImage;
		kendo.drawing.exportImage = function (group, options) {
			let promise = oldImage(group, options);
			return kendo.convertPromiseToDeferred(promise);
		};
		let oldSvg = kendo.drawing.exportSVG;
		kendo.drawing.exportSVG = function (group, options) {
			let promise = oldSvg(group, options);
			return kendo.convertPromiseToDeferred(promise);
		};
		function getBase64() {
			createChart();
			var chart = $('#<ChartIdentifier>').getKendoChart();
			chart.exportImage().done(function (data) {
				return data;
			});
		}
		window.getBase64 = getBase64;

createChart() is defined earlier in the script. It uses: 

$('#<ChartIdentifier>').kendoChart({ ...

Then the getBase64() function is called in C# using a headless browser. 


EO.Base.Runtime.EnableEOWP = true;
ThreadRunner threadRunner = new ThreadRunner();
WebView webView = threadRunner.CreateWebView();
string image_b64 = "";
threadRunner.Send(() =>
{
    webView.LoadUrlAndWait(new Uri(htmlFilePath.ToString()).ToString());
    var jsResult = webView.EvalScript("getBase64()");
    image_b64 = jsResult.ToString();
});

webView.Destroy();
threadRunner.Stop();

With this code jsResult is coming back as {undefined}.
I have tried many variations on this code and have not been able to get the image. Any help you can offer would be appreciated.
Ben
Top achievements
Rank 1
commented on 22 Jan 2025, 12:36 PM

I think I found the solution. It has to do with the new js being asynchronous. 
I was able to make it work by assigning the result of exportImage() to a variable in the js. Then in the C#, I evaluate the value of the variable in a while loop, waiting for it to be populated.


threadRunner.Send(() =>
{
    webView.LoadUrlAndWait(new Uri(htmlFilePath.ToString()).ToString());
    webView.EvalScript("getBase64()");
    while (string.IsNullOrEmpty(image_b64))
    {
        image_b64 = (string)webView.EvalScript("imageBase64");
        Thread.Sleep(50);//delay
    }
    
});

Although this is working to render the image of the chart, I now have another problem with the pdf export regarding page breaks. It seems every line of the report is on its own page of the export. This was not an issue with our previous version of Kendo UI (v2023.3.1114), even with the latest version of jQuery, but it is an issue with Kendo UI v2024.4.1112. Is this a known issue. Has it been addressed with the new version set to come out next month?
v2024.4.1112
Nikolay
Telerik team
commented on 24 Jan 2025, 11:13 AM

Hi Ben,

Thank you for the update!

Is it possible to share a Dojo demo where the page breaks problem is replicated? I need this so I can investigate further.

Regards,

Nikolay

Ben
Top achievements
Rank 1
commented on 13 Feb 2025, 02:49 PM

I figured out the page breaks. It was a problem on our end. It is not easy for me to share a demo of our code as it contains proprietary information and sensitive data. 
Now that the new version is out, how do I make it work? This is the getBase64() function that we use in our dynamic js script file:


function getBase64(){
createChart();
var result = '';
var chart = $('#Chart065696ed-1d2f-4ba3-8a94-acba3507960b').getKendoChart();
chart.exportImage().done(function(data) { result = data; });
return result;} 

then it is called in C#, using EO Webbrowser like so:


            EO.Base.Runtime.EnableEOWP = true;
            ThreadRunner threadRunner = new ThreadRunner();
            WebView webView = threadRunner.CreateWebView();
            string image_b64 = "";
            threadRunner.Send(() =>
            {
                webView.LoadUrlAndWait(new Uri(htmlFilePath.ToString()).ToString());
                image_b64 = (string)webView.EvalScript("getBase64()");
            });

            webView.Destroy();
            threadRunner.Stop();

image_b64 is resolving to an empty string. Any idea how I can make this work with the new version of Kendo UI?
Nikolay
Telerik team
commented on 18 Feb 2025, 10:37 AM

Hi Ben,

It looks like you're on the right track with handling the asynchronous nature of the exportImage function in Kendo UI. The key issue is that the exportImage function returns a promise, and you need to handle this promise correctly to get the base64 image data.

Here's a revised approach to ensure the base64 image data is correctly retrieved and passed back to your C# code:

1.Update the getBase64 Function:

Modify the getBase64 function to store the base64 image data in a global variable that can be accessed later.

var imageBase64 = '';

function getBase64() {
    createChart();
    var chart = $('#Chart065696ed-1d2f-4ba3-8a94-acba3507960b').getKendoChart();
    chart.exportImage().done(function(data) {
        imageBase64 = data;
    });
}

2. 

Ensure the C# Code Waits for the Image Data:

Use a while loop in your C# code to wait until the imageBase64 variable is populated.

EO.Base.Runtime.EnableEOWP = true;
ThreadRunner threadRunner = new ThreadRunner();
WebView webView = threadRunner.CreateWebView();
string image_b64 = "";
threadRunner.Send(() =>
{
    webView.LoadUrlAndWait(new Uri(htmlFilePath.ToString()).ToString());
    webView.EvalScript("getBase64()");
    while (string.IsNullOrEmpty(image_b64))
    {
        image_b64 = (string)webView.EvalScript("imageBase64");
        Thread.Sleep(50); // delay
    }
});

webView.Destroy();
threadRunner.Stop();

3. Handle Asynchronous Execution:

Ensure that the JavaScript code is executed in the correct order and that the imageBase64 variable is updated before the C# code tries to access it.

Regards,

Nikolay

Tags
Charts
Asked by
Adam
Top achievements
Rank 1
Answers by
Nikolay
Telerik team
Share this question
or