Charts scaling to be smaller when rendered using Windows 10 with 4K Screens (C# .NET)

I’m using these in a program I’m developing to re-render charts:
Aspose.Slides 20.2
Aspose.Cells 20.2
System.Drawing 4.7

For some reason this issue happens ONLY when I’m using a 4K screen (I’m working from home where I have a 4K screen, generally I’ve used a 1080p screen) and rendering charts as EMF images. (The issue doesn’t happen when rendered as PNGs).

When the slideshow renders, for some reason the text becomes about 25% smaller. I’m expecting it to appear the same. This is with using all the same settings as we always have.
I’m using Windows 10 and have previously for all other renders.

Here are the ImageOrPrintOptions I’ve been using. But this issue works fine on a PC with a 1080p screen running the exact same code:

ImageOrPrintOptions options = new ImageOrPrintOptions();
options.OnePagePerSheet = true;
options.SetDesiredSize(width, height);
options.ImageType = Aspose.Cells.Drawing.ImageType.Emf;
options.PageCount = 1;
options.Transparent = true;
options.CheckWorkbookDefaultFont = true;
options.HorizontalResolution = (int)(horizontalRes);
options.VerticalResolution = (int)(verticalRes);
options.TextRenderingHint = System.Drawing.Text.TextRenderingHint.AntiAliasGridFit;
options.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
options.OnlyArea = true;

The height and width and resolution variables should be all the same as the original presentation. This program re-renders the selected charts with new data.

Here are some screenshots. I used a slide with big text that’s part of an embedded excel document as an example. The first screenshot is with EMFs rendered correct (on a 1080p screen) the second is a PNG version (Works the same no matter where you are) and the third is with the images set to EMF on a 4K screen. Besides the screen, the code is exactly the same. (The PNG has ImageType set to PNG).

Do you have any idea what might be causing this? Is there an setting we can set to prevent this?

@pesposito,

Can you please confirm if the scale layout on your end is 100%. It should be 100%. Otherwise, if there is still an issue then please share the source files, sample project and generated output with us.

image.jpg (157.8 KB)

Thanks for responding.
Yes, it’s still 100% on the scale if I go to the Image Format menu in Powerpoint.

I should mention that if I edit any of these charts/embedded excel documents, when they re-render they go back to the normal dimensions.

I’ll see if I can setup a dummy version of this to share that has no private information in it.

Ok here is a sample powerpoint with just one slide (The same one I used in the screenshots). This has the original and the one where the re-rendered version is scaled down.Example Powerpoint With Scale-Down.zip (593.9 KB)

I can’t share the whole project’s source code but this should basically show what’s going on:

using Aspose.Cells;
using Aspose.Cells.Pivot;
using Aspose.Cells.Rendering;
using Aspose.Slides;
using Aspose.Slides.Charts;
using Aspose.Slides.Export;
using Microsoft.EntityFrameworkCore.Internal;
using Cell = Aspose.Cells.Cell;
using SaveFormat = Aspose.Slides.Export.SaveFormat;

private void DoCosmeticRefreshForOleObjectFrame(OleObjectFrame ole, ISlide slide, UpdateResult result)
    {
            string key = $"SLIDE{slide.SlideId}_{ole.Name.ToUpper()}";
            if (result.ChangedObjectList.Contains(key))
            {
                int height = ole.SubstitutePictureFormat.Picture.Image.SystemImage.Height;
                int width = ole.SubstitutePictureFormat.Picture.Image.SystemImage.Width;
                float horizontalRes = ole.SubstitutePictureFormat.Picture.Image.SystemImage.HorizontalResolution;
                float verticalRes = ole.SubstitutePictureFormat.Picture.Image.SystemImage.VerticalResolution;
                ole.AsIGraphicalObject.GraphicalObjectLock.AspectRatioLocked = false;
                int x = ole.SubstitutePictureFormat.Picture.Image.X;
                int y = ole.SubstitutePictureFormat.Picture.Image.Y;
                using (MemoryStream imageStream = new MemoryStream())
                using (MemoryStream ms = new MemoryStream(ole.ObjectData))
                {
                    imageStream.Position = 0;
                    Aspose.Cells.Workbook wb = new Aspose.Cells.Workbook(ms);
                    int activeIndex = wb.Worksheets.ActiveSheetIndex;
                    foreach (Worksheet worksheet1 in wb.Worksheets)
                    {
                        worksheet1.RefreshPivotTables();
                        foreach (PivotTable pTable in worksheet1.PivotTables)
                        {
                            pTable.RefreshDataFlag = true;
                            pTable.RefreshData();
                            pTable.RefreshDataFlag = false;
                            pTable.CalculateData();
                            pTable.RefreshDataOnOpeningFile = true;
                            pTable.CalculateRange();

                        }
                        worksheet1.CalculateFormula(true, false, null);
                        worksheet1.Shapes.UpdateSelectedValue();
                        foreach (Aspose.Cells.Charts.Chart chart1 in worksheet1.Charts)
                        {
                            chart1.RefreshPivotData();
                            chart1.Shapes.UpdateSelectedValue();
                            chart1.Calculate();
                        }

                    }
                    CalculationOptions opts = new CalculationOptions();
                    opts.Recursive = true;
                    opts.IgnoreError = false;
                    wb.CalculateFormula(opts);

                    Worksheet sheet = GetUpdatedWorksheetForOleObjectFrame(wb.Worksheets[activeIndex], result.DataDumpRangeDictionary[key]);          
                
                    ImageOrPrintOptions options = GetImageOrPrintOptionsForOleObjectFrame(width, height, horizontalRes, verticalRes);

                    SheetRender sr = new SheetRender(sheet, options);

                    sr.ToImage(0, imageStream);
                    ole.SubstitutePictureFormat.Picture.Image.ReplaceImage(imageStream.ToArray());
                    ms.Dispose();
                    imageStream.Dispose();
                }
            }

    }

    private void JustifyText(Worksheet sheet)
    {
        foreach (Aspose.Cells.Drawing.Shape shape in sheet.Shapes)
        {
            if (shape is Aspose.Cells.Drawing.TextBox && shape.TextBody.TextParagraphs.Count > 1)
            {
                Aspose.Cells.TextAlignmentType align = shape.TextBody.TextParagraphs[0].AlignmentType;
                for (int i = 1; i < shape.TextBody.TextParagraphs.Count; i++)
                {
                    shape.TextBody.TextParagraphs[i].AlignmentType = align;
                }
            }
        }
    }

    private Worksheet GetUpdatedWorksheetForOleObjectFrame(Worksheet sheet, string printArea)
    {
        sheet.CalculateFormula(true, false, null);
        sheet.Shapes.UpdateSelectedValue();
        if (sheet.Shapes.Count > 0) JustifyText(sheet);
        sheet.PageSetup.PrintArea = printArea;
        sheet.PageSetup.LeftMargin = 0;
        sheet.PageSetup.RightMargin = 0;
        sheet.PageSetup.TopMargin = 0;
        sheet.PageSetup.BottomMargin = 0;
        sheet.PageSetup.Zoom = sheet.Zoom;

        return sheet;
    }

    private ImageOrPrintOptions GetImageOrPrintOptionsForOleObjectFrame(int width, int height, float horizontalRes, float verticalRes)
    {
        ImageOrPrintOptions options = new ImageOrPrintOptions();
        options.OnePagePerSheet = true;
        options.SetDesiredSize(width, height);
        options.ImageType = Aspose.Cells.Drawing.ImageType.Png;
        options.PageCount = 1;
        options.Transparent = true;
        options.CheckWorkbookDefaultFont = true;
        options.HorizontalResolution = (int)(horizontalRes);
        options.VerticalResolution = (int)(verticalRes);
        options.TextRenderingHint = System.Drawing.Text.TextRenderingHint.AntiAliasGridFit;
        options.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
        options.OnlyArea = true;

        return options;
    }

@pesposito,

Thank you for sharing the details with us. I have analyzed the sample code and it doesn’t seem to work as it is in our environment. Can you please be kind enough to share a working example with us.

Moreover after observing your code and your following comments related to rendering to EMF. Using Aspose.Slides, you are only adding image to OLE frame and that image of chart is generated using Aspose.Cells. Am I right?

Also, your second issue is that when you update the OLE frame data and image using Aspose.Cells and save the presentation. Then opening the saved presentation and double clicking OLE frame resize the OLE Object? Am I right?

I also suggest you to please try using latest Aspose.Slides and Cells 20.3 on your end and provide a working sample project reproducing the issue along with generated output that we may use to log issue in our issue tracking system.

I’m not sure if I can give you any more files/code than I’ve already shared, as it’s part of my company’s private system. This is part of a larger application and it may be difficult to make an isolated program out of it.

Yes, this is a specific part of our code for updating OLE frame data. The code I sent is called outside this code looping through the slides and their individual charts.

And yes, if you double click the frame in Powepoint itself, it will resize to the usual size. The desired effect here is for the initial render as well as the re-render when you double click to be the same size (and match the original slide before substituting the old OLE frames with the new updated ones).

This is updating Slides in an Aspose.Slides.Presentation object which later after this code runs for all frames will copy the updated data to a new presentation and save it into our system.

I’ll try upgrading to 20.3 but I think the minor changes between 20.2 and 20.3 won’t change much.

@pesposito,

Thank you for clarification. The issue of EMF being generated requires the access to source file that you are using for creation of EMF image and adding to Slide OLE. Therefore, I request you to please share any dummy information that is actually reproducing the issue and that we may asses and after that log that in our issue tracking system.