After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 683984 - "Shrink to printable area" fails
"Shrink to printable area" fails
Status: RESOLVED OBSOLETE
Product: evince
Classification: Core
Component: printing
3.4.x
Other Linux
: Normal normal
: ---
Assigned To: Evince Maintainers
Evince Maintainers
Depends on: 686109
Blocks:
 
 
Reported: 2012-09-13 19:40 UTC by Panayiotis
Modified: 2018-05-22 14:42 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
proposed fix (1.84 KB, patch)
2012-10-08 19:11 UTC, Panayiotis
rejected Details | Review
additional patch (804 bytes, patch)
2012-10-09 08:35 UTC, Panayiotis
rejected Details | Review
additional patch (804 bytes, patch)
2012-10-09 08:42 UTC, Panayiotis
none Details | Review

Description Panayiotis 2012-09-13 19:40:16 UTC
Printing a large-sized document with the option "Shrink to printable area" results in the top of the document being cropped, while there seems to be unneeded bottom margin.

Printing with "shrink to printable area" enabled should *never* result in cropping.

My printer backend is hpcups. This is the original bug:

https://bugs.launchpad.net/hplip/+bug/1045486

And this may be related:

https://bugs.launchpad.net/ubuntu/+source/gimp/+bug/998156
Comment 1 Panayiotis 2012-10-08 19:11:27 UTC
Created attachment 226065 [details] [review]
proposed fix

Please review the attached patch.

Scaling seemed to take into account only the hardware margins of the printer, and ignore the page size margins. These are not necessarily the same.

This patch switches to calculation of the effective margins of the paper, defined as the maximum of the hard and page margins.
Comment 2 Panayiotis 2012-10-09 08:35:01 UTC
Created attachment 226102 [details] [review]
additional patch

Another issue.

Scaling of the document happens after translation. Does this not scale the margins as well?

The attached patch reverses the order of these two operations, to preserve the margins from being modified due to scaling. This seems to be correct logically; however, I have not noticed any significant observable difference on my test document.
Comment 3 Panayiotis 2012-10-09 08:42:21 UTC
Created attachment 226103 [details] [review]
additional patch

Another issue.

Scaling of the document happens after translation. Does this not scale the margins as well?

The attached patch reverses the order of these two operations, to preserve the margins from being modified due to scaling. This seems to be correct logically; however, I have not noticed any significant observable difference on my test document.

This patch is to be applied after the first one.
Comment 4 Panayiotis 2012-10-09 08:44:06 UTC
Sorry for the double post. The server seems to be facing some technical issues (internal server error).
Comment 5 Adrian Johnson 2012-10-09 09:14:44 UTC
From looking at your launchpad bug report it looks like the problem is your PPD file does not specify *HWMargins. It appears that the gtk+ function gtk_print_context_get_hard_margins() should use *ImageableArea for predefined page sizes and *HWMargins for custom pages sizes as defined in 

partners.adobe.com/public/developer/en/.../5003.PPD_Spec_v4.3.pdf

Currently gtk_print_context_get_hard_margins() is only using *HWMargins.
Comment 6 Adrian Johnson 2012-10-09 09:16:20 UTC
Review of attachment 226065 [details] [review]:

This is incorrect. The scaling is meant to be using only the hard margins. As mention in the previous comment the problem is gtk+ returning the wrong hard margins.
Comment 7 Adrian Johnson 2012-10-09 09:19:17 UTC
Review of attachment 226102 [details] [review]:

Translation occurs first to move the origin of the printable area to the origin of the page. If the scaling occurred first we would need to multiple the margin by the scale when translating. So translating first is easier.
Comment 8 Panayiotis 2012-10-09 09:47:04 UTC
Indeed, by looking at the function cups_printer_get_hard_margins, apparently an implementation, the hard margins are simply the ppd file's custom_margins, the minimum margins that the hardware leaves.

My ppd file does define HWMargins. All four are set to 9 points. However the ImageableArea top and bottom margins are in excess of 30 points.

Certainly the printer is, on some occasions, capable to print as low as 9 points of margin space. But I think, because the ImageableArea disallows it, that's why clipping occurs.

So I do not think the problem is gtk+ returning wrong values (this could be happening too, I have not checked). The problem is that the hard_margins = custom_margins (the minimum margins each custom size must respect) are different from the PaperSize margins, and the printer driver is enforcing the latter, as well as the first.

Even if evince could bypass the PaperSize margins, is it desirable for it to do so? The user has specified that she wants e.g. 30 points of top margin, so why should evince second-guess her?

For what it's worth, incorporating PaperSize margins in the calculations produces prints similar to those produced by passing the 'fitplot' option to lpr, and no clipping occurs.
Comment 9 Panayiotis 2012-10-09 10:02:08 UTC
Regarding, the second patch you are correct. Looking at some examples in Cairo's documentation, I understand it. Thanks and sorry.
Comment 10 Panayiotis 2012-10-09 10:12:45 UTC
Unfortunately the link:

partners.adobe.com/public/developer/en/.../5003.PPD_Spec_v4.3.pdf

gives a 404.
Comment 11 Adrian Johnson 2012-10-09 10:41:25 UTC
(In reply to comment #10)
> Unfortunately the link:
> 
> partners.adobe.com/public/developer/en/.../5003.PPD_Spec_v4.3.pdf
> 
> gives a 404.

I didn't notice google had shorted the link. Just google "ppd specification".
Comment 12 Adrian Johnson 2012-10-09 11:07:32 UTC
(In reply to comment #8)
> Indeed, by looking at the function cups_printer_get_hard_margins, apparently an
> implementation, the hard margins are simply the ppd file's custom_margins, the
> minimum margins that the hardware leaves.
> 
> My ppd file does define HWMargins. All four are set to 9 points. However the
> ImageableArea top and bottom margins are in excess of 30 points.

I see it now. I must have mistyped it when I searched for it.

> Certainly the printer is, on some occasions, capable to print as low as 9
> points of margin space. But I think, because the ImageableArea disallows it,
> that's why clipping occurs.
> 
> So I do not think the problem is gtk+ returning wrong values (this could be
> happening too, I have not checked). The problem is that the hard_margins =
> custom_margins (the minimum margins each custom size must respect) are
> different from the PaperSize margins, and the printer driver is enforcing the
> latter, as well as the first.

While the name of the gtk_print_context_get_hard_margins() function may suggest it should only return HWMargins (as it does now), the intent is to return the unprintable margins which for predefined pages is ImageableArea and for custom margins it is HWMargins.

The user defined margins have no relation to the printable area. It is just whatever the user defines.
 
> 
> Even if evince could bypass the PaperSize margins, is it desirable for it to do
> so? The user has specified that she wants e.g. 30 points of top margin, so why
> should evince second-guess her?

User margins are for applications that generate their own layout. These applications can reflow text to fit the user specified margins. Evince prints documents that already have a fixed layout. The intent of "shrink to fit" is that ideally evince would print at 100% scale but because the printer has an unprintable area the document is scaled down just enough to avoid cropping any content.

> 
> For what it's worth, incorporating PaperSize margins in the calculations
> produces prints similar to those produced by passing the 'fitplot' option to
> lpr, and no clipping occurs.

It just happens that your user defined margins are large enough to exclude the unprintable area on your printer. As the user defined margins are not derived from the ImageableArea in the PPD file this will not work in all cases. It is also undesirable to shrink the document any more than necessary. Hence the need to obtain the correct unprintable area from the PPD file.

I'll work on creating a patch for gtk+ to fix the bug in gtk_print_context_get_hard_margins() when I get some time. For now the workaround is to increase the size of HWMargins in your PPD.
Comment 13 Panayiotis 2012-10-09 11:53:26 UTC
I am sorry, some confusion has arisen. I was not referring at all to user-defined margins such as those defined in LibreOffice.

The GtkPaperSize margins, I believe, are exactly the ImageableArea margins. For all purposes they should be considered hardware margins. The driver will simply refuse to print past them, even if the hardware is capable of doing so. At least on my system.

My understanding is that the hard margins are 4 printer-global constants. When a developer adds a new predefined paper size, or a user adds a custom paper size, (s)he specifies the margins of this paper size within the range allowed by the hard margins.

For example, many printers are capable of borderless (full-bleed) photo printing. We can say that the hard margins of the printer are close to zero. Regardless, the driver also provides bordered photo printing. To achieve this, the ImageableArea of the paper size is set to some appropriate value. This is not a user margin at all, it is a driver margin. A user application cannot and should not try to go past it.

My point is that what you called "user defined margin" is in fact the same thing as the unprintable area. Truly user-defined margins are added on top of that by e.g. PDF generators such a Latex.

Ideally, for the goal of producing as close a print as the document on-screen, the application should detect the user margins (exterior whitespace) present in the document, and only should these be less than the GtkPaperSize margins, must the application add space, and scale, to make them equal. But I imagine this to be difficult.

As a final note, although I have not checked, the margins of each predefined PaperSize (=ImageableArea) should fall within the HWMargins.

The above is supported by the PPD specification which states that "HWMargins and ImageableArea should provide the same information". So I really think they should both be taken into account.

And, if you do implement the behavior in gtk_print_context_get_margins:
1) You will need to find the current GtkPageSetup and associated GtkPaperSize from the context.
2) Regardless of whether the size is predefined or custom you should take into account its margins.
3) I do not think the hard margins are intended for anything more that validating custom sizes.

I am not sure if any of this is correct, but I thought it was worth writing.

Thanks and good time of day. :-)
Comment 14 Panayiotis 2012-10-09 12:01:19 UTC
Also my user defined margins (white space in test document) are NOT large enough to accommodate the ImageableArea-induced margins. Because of this clipping occurs, this is my point.

I think the whole point is: how should the unprintable area be discovered? The current implementation says: "just use the HWMargins". I say: "take the max of HWMargins and ImageableArea-induced margins". I think that's all.
Comment 15 Adrian Johnson 2012-10-09 12:11:10 UTC
I'm currently reading the gtk+ printing code. Do you know where the imageable area is obtained? It has been 2 or 3 years since I last looked at this code.
Comment 16 Panayiotis 2012-10-09 12:23:42 UTC
Yes, thank you, I believe it is obtained in the file gtkprintbackendcups.c in the function cups_printer_get_hard_margins. (where is the PPD file parsed, I have no idea.) After that is is available in the PageSetup structure through the usual acessors.
Comment 17 Panayiotis 2012-10-09 12:34:50 UTC
Oh I am very sorry, I meant to write cups_printer_list_papers. It is just above the other one.
Comment 18 Adrian Johnson 2012-10-09 12:51:32 UTC
I see how it works now. ppd_size_t contains the imageable area. This is used to initialise the margins.

The problem is this only works for the CUPS backend. When printing to a PDF file the margins are set to a hard coded value of 0.5". There isn't any way for evince to know if the margins are the imageable area or something else. Printing to a PDF file should not shrink the page because PDF files do not have an unprintable area.

On windows gtk_print_context_get_hard_margins will return the correct imageable area based on the paper size. This is why the get hard margins function was added to the print context since each page can be a different size. So on Linux it should work the same way and return the imageable area for the page size selected for the context.
Comment 19 Panayiotis 2012-10-09 13:06:34 UTC
Hmm, perhaps the hard-coded value could be simply zero? Then scaling would not occur.

Anyway, you have convinced me that the fix belongs to gtk+. After all the function refers to hard margins, not hardware margins.

I think that the only place where the changes can go is GtkPrintContext, and specifically gtk_print_context_get_hard_margins, because we need to know the selected paper size.

What does windows do, in case of a PDF backend?
Comment 20 Adrian Johnson 2012-10-09 13:16:46 UTC
(In reply to comment #19)
> Hmm, perhaps the hard-coded value could be simply zero? Then scaling would not
> occur.

That is currently the case for gtk_print_context_get_hard_margins when printing to pdf.

> What does windows do, in case of a PDF backend?

It would depend on the PDF printing software you are using since windows does not have a built in PDF printer driver. It has been a long time since I last tested this but I'm fairly sure the hard margins were zero when I tried it.
Comment 21 Panayiotis 2012-10-09 13:47:31 UTC
[how do you quote? :-)]

No, I meant, is there any particular reason for the GtkPageSetup (ImageableArea) of a PDF paper size to be set to 0.5" (this is what you said, right?), rather than zero?

Perhaps we can set the PDF paper sizes to be marginless, and then all we would have to do is modify finish_print (this name is a little worrying) in gtkprintoperation-unix.c to update the GtkPrintContext hard margins (by a call to gtk_print_context_set_hard_margins) according to the GtkPageSetup, which I think is available in that function.

There is a design question: if the PDF backend says "I shall leave 0.5 inch margins", then who are we to disrespect that? Out of curiosity, what would happen if we tried to print a fully black page to PDF? Evince would not scale, so would the PDF backend leave 0.5" white margins? Unless there is some limitation in the PDF specification, then it seems the PDF backend is at fault, for claiming its imageable area is not borderless.

Just my opinion.
Comment 22 Adrian Johnson 2012-10-09 14:06:40 UTC
(In reply to comment #21)
> [how do you quote? :-)]

Click the reply link next to the comment.
 
> No, I meant, is there any particular reason for the GtkPageSetup
> (ImageableArea) of a PDF paper size to be set to 0.5" (this is what you said,
> right?), rather than zero?

GtkPage margins are initialised to the GtkPaper default margins. Later the CUPS back overwrites the margins with it's own values.

> 
> Perhaps we can set the PDF paper sizes to be marginless,

The depends on what the margins are supposed to represent. I don't know whether the margins were meant to mean printable area or some other meaning. You would have to the gtk+ developers. When I wrote the patch for gtk_print_context_get_hard_margins no one said the function is not required because the GtkPage margins are meant to be the hard margins.

> There is a design question: if the PDF backend says "I shall leave 0.5 inch
> margins", then who are we to disrespect that? Out of curiosity, what would

Again that depends on what gtk+ intends the margins to mean. As I said earlier the shrink to fit feature is not intended to fit to some arbitrary margin. It is intended to fit to the printer's printable area. It is meant to work the same way as the shrink to fit feature in Adobe Reader.
Comment 23 Panayiotis 2012-10-09 18:06:58 UTC
> The depends on what the margins are supposed to represent. I don't know whether
> the margins were meant to mean printable area or some other meaning. You would
> have to the gtk+ developers.

The first meaning was my assumption. I have sent an email to the gtk-devel-list list, with a link back here.

Thanks, good night.
Comment 24 Adrian Johnson 2012-10-14 11:22:12 UTC
I've created gtk+ bug 686109 with a patch to fix this issue.
Comment 25 Panayiotis 2012-10-14 18:11:08 UTC
Great, thanks.

I will back home in 10 days and I'll test it.
Comment 26 Germán Poo-Caamaño 2018-04-04 12:30:33 UTC
Shall we move this issue to Gtk+?
Comment 27 GNOME Infrastructure Team 2018-05-22 14:42:53 UTC
-- GitLab Migration Automatic Message --

This bug has been migrated to GNOME's GitLab instance and has been closed from further activity.

You can subscribe and participate further through the new bug through this link to our GitLab instance: https://gitlab.gnome.org/GNOME/evince/issues/299.