#!/usr/bin/perl

# This is a script to render a plain text outline file into SVG.
# 
# Copyright (C) 2006 Bryce Harrington.  Available for use under the GPL.
#
# Usage:  outline2svg.pl <presentation.outline> [ --master=template.svg ]
#
use strict;
use Getopt::Long;
use Pod::Usage;
use SVG::Parser;
use vars qw($VERSION);
$VERSION = '1.00';

our $opt_version      = 0;
our $opt_help         = 0;
our $opt_man          = 0;
our $opt_debug        = 1;
our $opt_master       = "template.svg";
our $opt_width        = 300;
our $opt_height       = 200;
our $opt_x_margin     = 100;
our $opt_y_margin     = 150;
our $opt_font         = 'Arial';
our $opt_font_family  = 'Arial';
our $opt_font_size    = 24;

Getopt::Long::Configure ("bundling", "no_ignore_case");
GetOptions(
           "version|V",         # Prints the version and exits
           "help|h",            # Prints a brief help message
           "man",               # Prints a manual page (detailed help)
           "debug|D=i",         # Prints debug messages
           "master|m=s",        # Master template to use
           "width|w=i",         # Page width
           "height|h=i",        # Page height
           "x-margin|x=i",      # Horizontal offset
           "y-margin|y=i",      # Vertical offset
           "font=s",            # Default font name
           "font-family=s",     # Default font family
           "font-size=s",       # Default font size
           );

my $i = 0;
my $page = 0;
my $filename;
my $svg;

sub start_page {
    my $title = shift;
    end_page();

    $filename = sprintf("%02d_$title.svg", $page);
    $filename =~ s/\s+/_/g;
    $filename =~ s#/#-#g;
    $filename =~ s#[^\w\:\.\,\+\-]+#_#g;

    $svg = SVG::Parser->new()->parsefile($opt_master);
    $svg->comment('Generated by outline2svg');
    $page++;
    $i = 0;
}

sub end_page {
    if (defined($svg) && defined($filename)) {
        open(FILE, ">$filename")
            or die "Could not open '$filename' for writing: $!\n";
        my $contents = $svg->xmlify();
        # Work-around bug in SVG::Parser
        $contents =~ s/&#x00;//g;
        print "$filename\n" if $opt_debug>0;
        print FILE $contents;
        close(FILE) || print "Error closing $filename:  $!\n";

        undef $svg;
        undef $filename;
    }
}


my $font = $opt_font;
my $font_family = $opt_font_family;
my $font_size = $opt_font_size;
my $line_spacing = $font_size * 1.5;

while (my $line = <>) {
    chomp($line);
    $line =~ s/\s+$//;  # Trim trailing space
    my $x = 10;
    my $style = { 'font' => $font, 
                  'font-family' => $font_family, 
                  'font-size' => $font_size
              };

    # Convert tabs into spaces, otherwise we get errors about invalid char
    $line =~ s/\t/    /g;

    # If we've encountered a page marker, increment the page number
    if ($line =~ /^\* (.*)$/) {
        my $title = $1;
        start_page($title);

        if ($title !~ /^(title|overview)$/i ) {
            $style->{'font-size'} *= 1.5;
            $svg->text(id    => "title_$i",
                       x     => $opt_x_margin,
                       y     => $opt_y_margin,
                       'xml:space' => 'preserve',
                       style => $style,
                       )
                ->cdata($title);
        }
        $i++;

    } elsif (defined($svg)) {
        my $y = $line_spacing*(1+$i);

        my $num_leading_spaces = 0;
        if ($line =~ /^(\s+)/) {
            $num_leading_spaces = length($1);

        }

        if ($num_leading_spaces > 0 &&
            length($line) > $num_leading_spaces &&
            length($line) + $num_leading_spaces > 70 &&
            length($line) + $num_leading_spaces <76 ) {
            # Looks like user is trying to center this text
            $line =~ s/^\s+//;
            $style->{'align'} = 'centered';
            $style->{'anchor'} = 'middle';
            $x = $opt_width / 2;

        } else {
            while ($line && $line =~ /^\s/) {
                $line =~ s/^\s//;  # Just delete one space at a time
                $x += 5;
            }

            # Create bullets if needed
            if ($line =~ /^-\s+/) {
                $line =~ s/^-\s+//;
                $x += 10;
                $svg->circle(cx=>$opt_x_margin + $x - ($font_size/2), 
                             cy=>$opt_y_margin + $y - ($font_size/3), 
                             r=>($font_size/6.0));
            }
        }

        # Convert markup into appropriate SVG-isms
        $svg->text(id    => "text_line_$i",
                   x     => $opt_x_margin + $x,
                   y     => $opt_y_margin + $y,
                   'xml:space' => 'preserve',
                   style => $style,
                   )
            ->cdata($line);
        $i++;
    }
}
end_page();

#print $svg->xmlify();

