]> www.wagner.pp.ru Git - fiction/Kate-the-Empress.git/commitdiff
added Tex2fb2 script
authorVictor Wagner <wagner@atlas-card.ru>
Tue, 12 Nov 2013 14:15:22 +0000 (18:15 +0400)
committerVictor Wagner <wagner@atlas-card.ru>
Tue, 12 Nov 2013 14:15:22 +0000 (18:15 +0400)
Tex2fb2 [new file with mode: 0644]

diff --git a/Tex2fb2 b/Tex2fb2
new file mode 100644 (file)
index 0000000..2fe0580
--- /dev/null
+++ b/Tex2fb2
@@ -0,0 +1,132 @@
+#!/usr/bin/perl
+# char-level modes
+my $poetry = 0;
+my $verbatim = 0;
+my @sections;
+my $buffer;
+#
+# TODO italic paragaphs
+# footnotes
+# epigraphs
+#
+# print fictionbook header
+print "<?xml version=\"1.0\" encoding=\"UTF-8\">\n";
+print "<FictionBook xmlns=\"http://www.gribuser.ru/xml/fictionbook/2.0\"
+xmlns:l=\"http://www.w3.org/1999/xlink\">\n";
+my $metadata = shift @ARGV;
+open F,"<",$metadata;
+while (<F>) {
+       print $_;
+}
+close F;
+
+my $header =1;
+while (<>) {
+$environ = undef;
+if (/\\(begin|end){(\w+)}/) {
+       $environ = $2;
+       $begin=$1 eq "begin";
+       if ($environ eq 'verbatim') {
+               $verbatim=$begin;
+       } elsif ($environ eq 'verse') {
+               if ($begin) {
+               pushsection("poem",undef);
+               } else {
+               flushsection('poem');
+               }
+               $poetry = $begin;
+       } elsif($environ = 'document' && $begin) {
+               $header=0;
+       }
+}
+next LINE if $header;
+if (/^$/ && $environ && $buffer) {
+#output on empty line (p or stanza) depending on poetry mode
+       add_to_section(tag($buffer,$poetry?"stanza":"p"));
+       $buffer="";
+}
+next LINE if $environ;
+# Section headings
+if (/\\(part|chapter|section|subsection|subsubsection){(.*)}/) {
+       pushsection($1,$2);
+}
+#normal mode: 
+if (!$verbatim) {
+#strip TeX comments 
+s/([^\\])%.*$/$1/;
+#replace TeX ligatures ~ --- << >> \% with appropriate unicode symbols
+s/~/\xA0/g;
+s/---/-/g;
+s/<</«/g;
+s/>>/»/g;
+}
+#replace ' and " with entities
+s/&/&amp;/g;
+s/'/&apos;/g;
+s/"/&quot;/g;
+s/</&lt;/g;
+s/>/&gt;/g;
+
+if ($poetry) {
+       chomp;
+  $buffer.=tag($_,'v');
+} elsif ($verbatim) {
+       add_to_section(tag(tag($_,"code"),"p"));
+} else {
+  $buffer.=$_;
+}
+}
+if ($buffer) {
+       add_to_section(tag($buffer,"p"));
+}
+
+while (@sections) {
+       flushsection();
+}
+print "</body>\n";
+## FIXME print footnotes
+print "</FictionBook>";
+
+sub add_to_section {
+       my $data = shift;
+       return if ($#sections<0) ;
+       $sections[$#sections]->{data}.=$data;
+}
+
+sub flushsection {
+       my $tag= shift || 'section';
+       my $str = pop @sections;
+       my $content="";
+       if ($str->{title}) {
+               $content = tag($str->{title},"title");
+       }
+       $content .=  $str->{data};
+       if ($#sections >=0) {
+               add_to_section(tag($content,$tag));
+       } else {
+               print tag($content,$tag);
+       }
+}
+
+sub pushsection {
+       my ($level,$title)=@_;
+       # Find section of $level in the current stack
+       my $found=scalar(@sections);
+       LEVEL:
+       for (my $i=0;$i<=$#sections;$i++) {
+               if ($sections[$i]->{level} eq $level) {
+                       $found=$i;
+                       last LEVEL;
+               }
+       }
+       # if found, flush everything below
+       while (scalar(@sections) > $found) {
+               flushsection;
+       }
+       push @sections,{level=>$level,title=>$title,data=>""};
+}
+
+sub tag {
+       my ($content,$name) = @_;
+       return "<$name>$content</$name>";
+}