Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[BUG] XPS DrawBitMap is clipping? #1728

Open
Jonesie opened this issue Jun 24, 2021 · 5 comments
Open

[BUG] XPS DrawBitMap is clipping? #1728

Jonesie opened this issue Jun 24, 2021 · 5 comments

Comments

@Jonesie
Copy link

Jonesie commented Jun 24, 2021

Description

Im using SkiaSharp to create an XPS (and/or PDF) document that includes images for printing. Images in PDF are correctly stretched to fit the required rect, but on XPS they seem to be clipped. My code and sample images are below.

Is this a bug or am I doing something wrong? I would have thought that the code for PDF should be identical for XPS but maybe there's extra trick or hack I need to do?

Code

public void ToDocument(string inputPath, bool pdf = false)
        {

            SKDocument document = null;
            var outputPath = Path.Combine(Path.GetDirectoryName(inputPath), Path.GetFileNameWithoutExtension(inputPath)) + (pdf ? ".pdf" : ".xps");

            using var input = File.OpenRead(inputPath);
            using var inputStream = new SKManagedStream(input);
            using var original = SKBitmap.Decode(inputStream);

            // page a little bigger than source image
            var pageRect = new SKRect(0, 0, original.Width + 20, original.Height + 100);

            var renderRect = new SKRect(0, 0,
                (float)original.Width, (float)original.Height);

            using var outputStream = File.Create(outputPath);
            using var managedStream = new SKManagedWStream(outputStream);

            // null checking removed for readability

            using var canvas = document.BeginPage(pageRect.Width, pageRect.Height);
            canvas.Clear();

            using var p = new SKPaint();

            SKRect picRect;
            float xFactor = 0.25F;
            float yFactor = 0.25F;
            if (pdf)
            {
                // stretch renderRect for pdf
                picRect = new SKRect(renderRect.Left, renderRect.Top, renderRect.Left + renderRect.Width * xFactor, renderRect.Top + renderRect.Height * yFactor);
            }
            else
            {
                // stretch renderRect for xps
                // xFactor = 1.25F;
                // yFactor = 1.25F;
                picRect = new SKRect(renderRect.Left, renderRect.Top, renderRect.Left + renderRect.Width * xFactor, renderRect.Top + renderRect.Height * yFactor);
            }
            canvas.DrawBitmap(original, original.Info.Rect, picRect, p);

            p.StrokeWidth = 2;
            p.Color = SKColors.Red;
            p.Style = SKPaintStyle.Stroke;

            // rect same size as original bitmap
            canvas.DrawRect(renderRect, p);

            p.Color = SKColors.Blue;
            // rect same size as stretched bitmap
            canvas.DrawRect(picRect, p);

            using var tp = new SKPaint();
            tp.TextSize = 10.0f;
            tp.IsAntialias = true;
            tp.IsStroke = false;
            //canvas.DrawText($"Page: {pageRect.Height}w {pageRect.Width}h", 10F, pageRect.Bottom - 55F, tp);
            tp.Color = SKColors.Red;
            canvas.DrawText($"Source: {original.Width}w {original.Height}h", 10F, pageRect.Bottom - 40F, tp);
            tp.Color = SKColors.Blue;
            canvas.DrawText($"Dest: {picRect.Width}w {picRect.Height}h", 10F, pageRect.Bottom - 25F, tp);
            canvas.DrawText($"Stretched: {xFactor}w {yFactor}h", 10F, pageRect.Bottom - 10F, tp);


            // bitmap should fit to the background rect but fails with xps
            //canvas.DrawBitmap(original, renderRect, p);

            document.Close();
        }

Expected Behavior

Actual Behavior

Some images are clipped - it seems like small ones are ok. Maybe there is a buffer size issue or ... ?

Basic Information

  • Version with issue: 2.80.2
  • Last known good version: ??
  • IDE: Visual Studio, Visual Studio Code
  • Platform Target Frameworks:
    • Linux: Ubuntu 16.04 (AWS Linux)
    • Windows Classic: 10
  • Target Devices:
    • n/a - printing the xps
Detailed IDE/OS information (click to expand)

PASTE ANY DETAILED VERSION INFO HERE

Screenshots
Original image:
Original

PDF:
PDF

XPS:
XPS

@AndreaLabeljoy
Copy link

Hi @Jonesie, ran into this exact issue today on version 2.88.8.
Did you ever find a way to make it work?

@JonesieHexcom
Copy link

@AndreaLabeljoy Sorry for the late reply. No, we gave up on XPS and just use PDF. Ive not tried again with later versions.

@oatkins
Copy link

oatkins commented Aug 15, 2024

It turns out that this is a bug in the Google Skia code. It's even commented 😆:

image

The code alludes to SK_ScalarMax, which is large, but for some reason they ended up using 1000 instead. The result is that all images get cropped to a 1000 pixel square centred on the origin. Generally, that means that images get cropped to 500 pixels high and 500 pixels wide.

It looks as though Windows does not consider the VisualBrush.Viewport to be a clipping rectangle, but WPF does. I had, but now can't find, a reference to that in the WPF docs; the XPS spec is vague about it, and doesn't mention clipping at all. The Windows XPS viewer (and probably the printer drivers) render content outside of the viewport, which is probably why the bug has gone unnoticed for so long. So, perhaps the WPF behaviour is wrong.

In any case, my workaround (in my own code) is going to be adding some code to find the Viewbox and Viewport values in XAML:
image

and replace them with a much, much larger box.

In short, I don't think there's much that can be done in this repo, but there is a potential workaround for those hitting this problem.

@Jonesie
Copy link
Author

Jonesie commented Aug 16, 2024

Thats good to know. Thank you !!!

@AndreaLabeljoy
Copy link

Thanks @oatkins for the info.
I've created a bug report on the Skia group referring them to this post, let's see if someone addresses it.
https://issues.skia.org/issues/360641492

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants