Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems.. It's 100% free, no registration required.

I have a pdf file that was made into a booklet format. It is meant to print on A4 paper in landscape orientation; here are two pages in the pdf, which should correspond to four pages in the actual book.

 -------------------------------
|              |                |
|              |                |
|              |                |
|    (1)       |      (3)       |
|              |                |
|              |                |
|              |                |
 ------------------------------- 

 -------------------------------
|              |                |
|              |                |
|              |                |
|    (4)       |      (2)       |
|              |                |
|              |                |
|              |                |
 -------------------------------

The bracketed numbers correspond to the order of the individual pages.

I know that there are all sorts of commands (pdfbook, pdfnup, etc.) on linux (which was probably used to make this booklet in the first place). How do I 'unbook' it---that is, I'd like to make a pdf document from this where each individual page of the final product is an individual page of the pdf, ordered in the usual way.

Edit

Thanks to Gilles, I managed to use the following code:

import copy, sys
from pyPdf import PdfFileWriter, PdfFileReader
input = PdfFileReader(sys.stdin)
output = PdfFileWriter()
second_half = []
for i in range(0,input.getNumPages()):
    p = input.getPage(i)
    q = copy.copy(p)

    print >> sys.stderr, 'splitting page',i
    print >> sys.stderr, '\tlowerLeft:',p.mediaBox.lowerLeft
    print >> sys.stderr, '\tupperRight:',p.mediaBox.upperRight

    p.mediaBox.upperRight = (ur[0], (bl[1]+ur[1])/2)
    p.mediaBox.lowerLeft = bl

    q.mediaBox.upperRight = ur
    q.mediaBox.lowerLeft = (bl[0], (bl[1]+ur[1])/2)

    if i % 2 == 0:
        output.addPage(p)
        qold = q
    else:
        output.addPage(q)
        output.addPage(qold)
        output.addPage(p)
output.write(sys.stdout)
share|improve this question
1  
I think this should go to superuser.com –  Adam Zalcman Jan 20 '12 at 22:08
    
@AdamZalcman Why? He's looking for a Linux program –  Michael Mrozek Jan 20 '12 at 22:25
2  
You could adapt this questions answer (by Gilles) to your problem, i.e. create a PyPdf script. –  sr_ Jan 21 '12 at 10:14
add comment

1 Answer 1

up vote 4 down vote accepted

Here's a small Python script using the PyPdf library that does the job. (Derived from un2up.) Save it in a script called unbook, make it executable (chmod +x un2up), and run it as a filter (unbook <book.pdf >1up.pdf).

I tested this script on the output of pdfbook --signature=N. For another method, you may not need to reverse every other input page, and the page order may be different (it depends on the orientation of the landscape pages). The page disposition doesn't match up with your question; the 13,42 doesn't make sense to me (in a 4-page book, 3 should be next to 2, not next to 1).

#!/usr/bin/env python
import copy, sys
from pyPdf import PdfFileWriter, PdfFileReader
input = PdfFileReader(sys.stdin)
output = PdfFileWriter()
second_half = []
for i in range(0,input.getNumPages()):
    p = input.getPage(i)
    q = copy.copy(p)
    (w, h) = p.mediaBox.upperRight
    p.mediaBox.upperRight = (w/2, h)
    q.mediaBox.upperLeft = (w/2, h)
    if i % 2 == 0:
        p.rotateClockwise(180)
        q.rotateClockwise(180)
        output.addPage(p)
        second_half.append(q)
    else:
        output.addPage(p)
        second_half.append(q)
second_half.reverse()
for q in second_half: output.addPage(q)
output.write(sys.stdout)

Ignore any deprecation warning; only the PyPdf maintainers need be concerned with these.

share|improve this answer
    
This was asked some time ago, but I'm having trouble implementing your solution. I'm running OSX, have installed python and py27-pypdf via MacPorts. I created an unbook file and copied and pasted the script. Running the command as instructed creates a new 1up.pdf file with 0 bytes. No error or anything is listed in my terminal, but upon executing the command, nothing happens (I have to CTRL-C out); the system does not hang and does not appear to be doing anything. How can I track down the problem? @Gilles –  TSGM Jun 6 '12 at 21:53
    
@TSGM The most probable explanation is that you forgot the < before the input file. If you're really absolutely sure that you wrote the command correctly, it could be a bug in the PyPdf library (it hasn't failed me yet, but it could happen). –  Gilles Jun 6 '12 at 22:01
    
The problem was that I was supposed to call python via "python unbook <in.pdf >out.pdf". Silly me. Also, your code was a bit strange (it was sticking the second_half pages all at the end. I seem to have corrected it for the format that I wrote in the original post). I've edited my original response to contain the code I eventually used. Also, the page size commands seem to be wrong. I corrected that as well. @Gilles –  TSGM Jun 7 '12 at 1:24
    
@TSGM The code assumes a layout of 1|4 obverse, 2|3 reverse, which is the usual book layout. You may need to tweak it if your pages are laid out differently. It was field-tested in that setting. Your having to explicitly call python was my mistake: I should have put a shebang line, added. –  Gilles Jun 7 '12 at 8:34
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.