First, thanks for everyone that posted here.
I have this little script called pdfScale which absorbed parts of the answers posted here. So I decided to post back my 2 cents. I am using a bit of a mix of Kurt's and Tim's answers. More similar to Tim's though. I have played with this for a few days and here is my partial conclusion on the methods posted here:
Set Paper Size by Name with -sPAPERSIZE
- Easy to just pass the paper name (Eg. a4)
- May not produce 100% accurate points size
- May Flip Landscape <> Portrait
Set paper size in PS-points -dDEVICEWIDTHPOINTS
, -dDEVICEHEIGHTPOINTS
- Makes sure you get the size you want in points
- You can Flip WIDTH <> HEIGHT yourself
- You need to know the sizes in Points
- Not so easy to script around it, as you will need the new page size in points and would also need the source's page sizes if you want to detect landscape/portrait.
- You can set custom defined papers as well (any size you want really).
- I was using
-dDEVICEWIDTH
, -dDEVICEHEIGHT
instead of the longer, points version, but they both seem to do the same thing (both get points).
Because my bash script is already capable of getting source page sizes and I liked the idea to be able to set custom page sizes, I decided to focus on setting the page size in points. I had also already included the GS Paper Sizes in my script (with names and sizes). So getting that info was also easy.
Using -dFIXEDMEDIA
seems to be a must on both cases, as pointed out before.
So this is how my approach went (in a scripted way)
- Get Source PDF page sizes (For Flip Detection)
- Get the target's page size in points (Eg. A4 > 595x842)
- Check they have the same orientation or Flip Target if necessary
- Run GS with points or flipped points
When I was trying to fix the auto-rotation problem, I found this other Kurt response.
This is about using -dAutoRotatePages
. Just copying a part of his answer here:
-dAutoRotatePages=/None
-- retains orientation of each page;
-dAutoRotatePages=/All
-- rotates all pages (or none) depending on a kind of "majority decision";
-dAutoRotatePages=/PageByPage
-- auto-rotates pages individually.
My script defaults to PageByPage
but that is adjustable. It worked well in my tests. Using -dAutoRotatePages
also seems to reduce the need for pre-flipping the page size, even though it is not the same thing. I kept both options.
My little app was originally created to scale PDFs (without changing the page size). Then I added now the functionality to do one, the other or both. I still could not do it all in a single GS call though.
This is what I am calling for resizing, changing the variables to real values. This is for A4 Portrait size with PageByPage
auto-rotation:
gs \
-q -dNOPAUSE -dBATCH -sDEVICE=pdfwrite -dSAFER \
-dCompatibilityLevel="1.5" -dPDFSETTINGS="/printer" \
-dColorConversionStrategy=/LeaveColorUnchanged \
-dSubsetFonts=true -dEmbedAllFonts=true \
-dDEVICEWIDTHPOINTS=595 -dDEVICEHEIGHTPOINTS=842 \
-dAutoRotatePages='/PageByPage' \
-dFIXEDMEDIA -dPDFFitPage \
-sOutputFile='../myOutputFile.pdf' \
-f '../input.pdf'
Please note that I am also using -dFIXEDMEDIA
AND -dPDFFitPage
. Because this fits-to-page, the other part of my script may be handy to scale the contents inside the PDF after resizing (specially if the proportion of the PDF changed a lot). And that is one of the reasons I always run the scaling after resizing in my script (in mixed mode).
About the fraction problems when using the Paper Name, I had that happening to me before I rounded the conversions from mm/inches to points. After I started rounding them, they seem to always be the one needed. Seems weird that GS would floor those values though.
So my conclusion is that the hard part is to find a solution that works across the board on different documents with different sizes and orientations. I am still not sure I am using the proper solution. But by letting the user change the Flip Detection and GS Auto-Rotation I hope to have a solution for at least most cases.
I have also rebuilt most of the code in the process and it is pretty easy to read now. May be useful to check it if you want to automate such a task yourself. Also useful to just scale/resize PDFs as well of course:
https://github.com/tavinus/pdfScale
PS: pdfScale has its origins on this StackOverflow thread.
gs -sDEVICE=pdfwrite -sPAPERSIZE=a5 -dFIXEDMEDIA -dPDFFitPage -dCompatibilityLevel=1.4 -o out.pdf in.pdf
– Arroba