#!/usr/bin/env perl
use v5.22;
use File::Basename;
use Getopt::Long qw(:config bundling_override require_order);
use autodie;
use File::Temp qw(tempdir);
use File::Copy;
#--------------------------- Constantes -------------------------------#
my $BPL = '\begin{postscript}';
my $EPL = '\end{postscript}';
my $sipgf = 'pgfpicture';
my $nopgf = 'pgfinterruptpicture';
my $BP = '\\\\begin\{postscript\}';
my $EP = '\\\\end\{postscript\}';
my $tempDir = tempdir( CLEANUP => 1); # temporary directory
#-------------------------- Getopt::Long ------------------------------#
my $other = "other"; # other environment for search
my $imageDir = "images"; # dir for images (images default)
my $ignore = "ignore"; # ignore verbatim environment
my $clear = 0; # 1->clear all temporary files
my $source = 0; # 1->extrae codigo de las imágenes
my $nopreview = 0; # 1->activa el modo nopreview
my $subfile = 0; # 1->activa el modo nopreview
my $latex = 0; # 1->create all images using latex
my $xetex = 0; # 1->create all images using xelatex
my $luatex = 0; # 1->create all images using lualatex
my $png = 0; # 1->create .png using Ghoscript
my $jpg = 0; # 1->create .jpg using Ghoscript
my $eps = 0; # 1->create .eps using pdftops
my $svg = 0; # 1->create .svg using pdf2svg
my $ppm = 0; # 1->create .ppm using pdftoppm
my $all = 0; # 1->create all images type
my $miktex = 0; # 1->enable write 18 for miktex system
my $Verbose = 0; # 0 or 1, logfile
#------------------------ Opciones y ayuda ----------------------------#
my $usage = <<"END_OF_USAGE";
Uso: script [opciones] entrada.tex [salida]
END_OF_USAGE
### error
sub errorUsage { die "@_ (use script --help)\n"; }
### Getopt::Long
my $result=GetOptions (
'imgdir=s' => \$imageDir, # images
'ignore=s' => \$ignore, # ignore, ignore*
'other=s' => \$other, # other, other*
'e|eps' => \$eps, # pdftops
'j|jpg' => \$jpg, # gs
'p|png' => \$png, # gs
'P|ppm' => \$ppm, # pdftoppm
's|svg' => \$svg, # pdf2svg
'a|all' => \$all, # all
'c|clear' => \$clear, # clear
'h|help' => \$::opt_help, # help
'subfile' => \$subfile, # subfile
'source' => \$source, # src
'np|nopreview' => \$nopreview, #
'xetex' => \$xetex, #
'latex' => \$latex, #
'luatex' => \$luatex,#
'miktex' => \$miktex, #
'Verbose' => \$Verbose, # verbose
) or die "use script --help para ver las opciones\n";
### help
if ($::opt_help) {
print $usage;
exit(0);
}
#--------------- Chequeamos los argumentos de entrada -----------------#
@ARGV > 0 or errorUsage "Falta ingresar el nombre del archivo de entrada";
@ARGV < 3 or errorUsage "Opción desconocida o varios archivos de entrada";
#--------------------- Arreglo de la extensión ------------------------#
my @SuffixList = ('.tex', '', '.ltx'); # posibles
my ($name, $path, $ext) = fileparse($ARGV[0], @SuffixList);
$ext = '.tex' if not $ext;
### El nombre del archivo de salida se guarda en $ARGV[1]
my $output = $ARGV[1];
#---------------------- Abrimos el archivo ----------------------------#
open my $ENTRADA, '<', "$name$ext";
my $archivo;
{
local $/;
$archivo = <$ENTRADA>;
}
close $ENTRADA;
### Creamos el directorio para las imágenes
-e $imageDir or mkdir($imageDir,0744) or die "No puedo crear $imageDir: $!\n";
### Dividimos el archivo de entrada
my($cabeza,$cuerpo,$final) = $archivo =~ m/\A (.+?) (\\begin\{document\} .+?)(\\end\{document\}.*)\z/msx;
### Verbatim environments
my $VERBATIM = qr/(?: (v|V)erbatim\*?| PSTexample | aling)/xi;
### postscript environment
my $POSTSCRIPT = qr/(?: postscript)/xi;
### tikzpicture environment
my $ENVIRONMENT = qr/(?: tikzpicture | pspicture\*?)/xi;
#------------------ Expresiones regulares en $cuerpo ------------------#
### \pspicture to \begin{pspicture}
$cuerpo =~ s/\\pspicture(\*)?(.+?)\\endpspicture/\\begin{pspicture$1}$2\\end{pspicture$1}/gmsx;
### tikz/pst to Postscript
$cuerpo =~ s/\\begin\{$POSTSCRIPT\}.+?\\end\{$POSTSCRIPT\}(*SKIP)(*F)|
(
(?:\\(psset|tikzset)(\{(?:\{.*?\}|[^\{])*\}).*?)? # si está lo guardo
(\\begin\{($ENVIRONMENT)\} (.*?) \\end\{\g{-2}\})
)
/$BPL\n$1\n$EPL/gmsx;
### pgfpicture to Postscript
$cuerpo =~ s/\\begin\{$POSTSCRIPT\}.+?\\end\{$POSTSCRIPT\}(*SKIP)(*F)|
(
\\begin\{$sipgf\}
.*?
(
\\begin\{$nopgf\}
.+?
\\end\{$nopgf\}
.*?
)*?
\\end\{$sipgf\}
)
/$BPL\n$1\n$EPL/gmsx;
### other to PostScript
my $EXPORT = qr/(forest|ganttchart|tikzcd|circuitikz|dependency|$other\*?)/x;
$cuerpo =~ s/\\begin\{$POSTSCRIPT\}.+?\\end\{$POSTSCRIPT\}(*SKIP)(*F)|
(\\begin\{($EXPORT)\} (.*?) \\end\{\g{-2}\})
/$BPL\n$1\n$EPL/gmsx;
#----------------- Creación del fichero de imágenes -------------------#
### $nopreview mode
if ($nopreview) {
my @env_extract;
while ( $cuerpo =~ m/(?<=$BP)(?<env_src>.+?)(?=$EP)/gms ) { # recorremos $cuerpo
push @env_extract, $+{env_src}."\n\\newpage\n";
}
open my $SALIDA, '>', "$imageDir/$name-fig$ext";
print $SALIDA $cabeza."\\pagestyle{empty}\n\\begin{document}\n"."@env_extract\n"."\\end{document}";
close $SALIDA;
} # close $nopreview
### preview mode (default)
else {
my $opcion = $xetex ? 'xetex,'
: $latex ? ''
: 'pdftex,'
;
my $preview = <<"EXTRA";
\\AtBeginDocument\{%
\\RequirePackage\[${opcion}active,tightpage\]\{preview\}%
\\renewcommand\\PreviewBbAdjust\{-60pt -60pt 60pt 60pt\}%
\\newenvironment\{postscript\}\{\}\{\}%
\\PreviewEnvironment\{postscript\}\}%
EXTRA
# write
open my $SALIDA, '>', "$imageDir/$name-fig$ext";
print $SALIDA $preview.$cabeza.$cuerpo."\\end{document}";
close $SALIDA;
} # close preview
#-------------------- Extracción de ficheros fuente -------------------#
if ($source) {
my $src_file = "$name-src-"; # nombre del archivo de salida
my $srcNo = 1; # contador para los ficheros fuente
while ($cuerpo =~ m/(?<=$BP)(?<env_src>.+?)(?=$EP)/gms) { # recorremos $cuerpo
open my $SALIDA, '>', "$imageDir/$src_file$srcNo$ext";
print $SALIDA $+{env_src};
close $SALIDA;
}
continue {
$srcNo++; # auto incremento del contador
}
} # close $source
#-------------------- Extracción de subficheros -----------------------#
if ($subfile) {
my $sub_file = "$name-fig-"; # nombre del archivo de salida
my $subNo = 1; # subfile number
while ($cuerpo =~ m/(?<=$BP)(?<env_src>.+?)(?=$EP)/gms) { # recorremos $cuerpo
open my $SALIDA, '>', "$imageDir/$sub_file$subNo$ext";
print $SALIDA <<"EOC";
$cabeza\\pagestyle\{empty\}\n\\begin\{document\}$+{'env_src'}\\end\{document\}
EOC
close $SALIDA;
} # close while
continue {
$subNo++; # auto incremento del contador
}
} # close $subfile
#------------------ Creación del archivo de salida --------------------#
if (defined $output) {
if ($output =~ /(^\-|^\.).*?/){ # No comienze por -, -- o .
die "$output no es un nombre valido para el archivo de salida\n";
}
if ($output eq "$ARGV[0]" or $output eq "$name") { # $output = $input
$output = "$name-out$ext";
}
if ($output =~ /.*?$ext/){ # Si $output termina en .ltx o .tex la quitamos
$output =~ s/(.+?)$ext/$1/gms;
}
### Convertimos Postscript a includegraphics
my $grap="\\includegraphics[scale=1]{$name-fig-";
my $close = '}';
my $imgNo = 1; # contador para las imágenes
$cuerpo =~ s/$BP.+?$EP/$grap@{[$imgNo++]}$close/msg; # cambiamos
# print "Creamos $output$ext\n" if $verbose;
open my $SALIDA, '>', "$tempDir/$output$ext";
print $SALIDA <<"EOC";
$cabeza$cuerpo$final
EOC
close $SALIDA;
copy "$tempDir/$output$ext", "$tempDir/mojo";
} # cerramos defined
move "$tempDir/$output$ext", "$output$ext";
__END__