#!/usr/bin/perl
# -*- perl -*-
my $version_banner = <<END;
psbook 2.06
Copyright (c) Reuben Thomas 2016-2021.
Released under the GPL version 3, or (at your option) any later version.
END

use warnings;
use strict;

my $bindir;
BEGIN
{
# Relocatable header

if ("no" eq "yes") {
  my $exec_prefix = "/usr/local";
  my $orig_installdir = "/usr/local/bin"; # see Makefile.am's *_SCRIPTS variables
  my ($orig_installprefix, $curr_installprefix) = find_prefixes($orig_installdir, find_curr_installdir());
  sub relocate { # the subroutine is defined whether or not the enclosing block is executed
    my ($dir) = @_;
    if ("no" eq "yes") {
      $dir =~ s%^$orig_installprefix/%$curr_installprefix/%;
      $dir =~ s,/$,,;
    }
    return $dir;
  }
}

# Relocate the directory variables that we use.
my $pkgdatadir = &relocate("/usr/local/share/psutils");
$bindir = &relocate("/usr/local/bin");

# End of relocatable header; "real" Perl starts here.

unshift (@INC, "/usr/local/share/psutils") unless $ENV{PSUTILS_UNINSTALLED};
$bindir = '/home/pea/pobj/psutils-2.06/psutils-2.06' if $ENV{PSUTILS_UNINSTALLED};
}

use File::Spec::Functions 'catfile';
use File::Basename;
use Getopt::Long;

use PSUtils;

our $program_name = basename($0);
my ($help_flag, $version_flag);
my $signature = 0;

sub usage {
  my ($exit_code) = @_;
  print STDERR <<END;
Usage: $program_name [OPTION...] [INFILE [OUTFILE]]
Rearrange pages in a PostScript document into signatures.

  -s, --signature=N    number of pages per signature;
                       0 = all pages in one signature [default];
                       1 = one page per signature;
                       otherwise, a multiple of 4
  -q, --quiet          don't show page numbers being output
      --help           display this help and exit
      --version        display version information and exit
END
  exit $exit_code;
}

# Get arguments
Getopt::Long::Configure("bundling");
# Having configured bundling, must give short options explicitly
my @pstops_args = ();
GetOptions(
  "signature|s=i" => sub { $signature = $_[1];
                           usage(1) if $signature > 1 && $signature % 4 != 0; },
  "quiet|q" => sub { push @pstops_args, "-q"; },
  "help" => \$help_flag,
  "version" => \$version_flag,
 ) or usage(1);
if ($version_flag) {
  print STDERR $version_banner;
  exit 0;
}
usage(0) if $help_flag;
Die("signature must be a multiple of 4") if $signature > 1 && $signature % 4 != 0;

my ($infile, $outfile) = setup_input_and_output(1);
usage(1) if $#ARGV != -1; # Check no more arguments were given

# Get number of pages
my $psinfo = parse_file($infile);
my $input_pages = $psinfo->{pages};

sub page_index_to_real_page {
  my ($maxpage, $signature, $page_number) = @_;
  my $real_page = $page_number - $page_number % $signature;
  my $page_on_sheet = $page_number % 4;
  my $recto_verso = int(($page_number % $signature) / 2);
  if ($page_on_sheet == 0 || $page_on_sheet == 3) {
    $real_page += $signature - 1 - $recto_verso;
  } else {
    $real_page += $recto_verso;
  }
  return $real_page + 1;
}

# Adjust for signature size
my $maxpage;
if ($signature == 0) {
  $signature = $maxpage = $input_pages + (4 - $input_pages % 4) % 4;
} else {
  $maxpage = $input_pages + ($signature - $input_pages % $signature) % $signature;
}

# Compute page list
my @page_list = ();
for (my $page = 0; $page < $maxpage; $page++) {
  my $real_page = page_index_to_real_page($maxpage, $signature, $page);
  push @page_list, $real_page <= $input_pages ? $real_page : "_";
}

# Rearrange pages
exec(catfile($bindir, "pstops"), "-R" . join(',', @page_list), @pstops_args, @ARGV) or Die("error running pstops");
