#!/bin/perl -w use strict; use XML::Twig; my $h2_nb=0; my $h3_nb=0; my $h4_nb=0; my $title; my $info; my @toc; my %example; my $t= XML::Twig->new( twig_roots => { h2 => \&h2_first_pass },); if( $ARGV[0]) { $t->parsefile( $ARGV[0]); } # process the twig else { $t->parse( \*STDIN); } $t= XML::Twig->new ( twig_handlers => { h1 => \&h1, author => sub { $info = "

by " . $_->text . ""; }, date => sub { $info .= "
updated ".$_->text."

"; }, h2 => \&h2, h3 => \&h3, h4 => \&h4, example => \&example, br => \&process_empty, hr => \&process_empty, td => \&td, section => \§ion, tutorial => \&tutorial, method => \&method, pre => \&pre, }, ); if( $ARGV[0]) { $t->parsefile( $ARGV[0]); } # process the twig else { $t->parse( \*STDIN); } sub h2_first_pass { my( $t, $h2)= @_; $h2_nb++; my $filename= filename( $h2_nb); my $section_title= "$h2_nb. " . $h2->text; push @toc, { file => $filename, title => $section_title}; } sub h1 { my( $t, $h1)= @_; $h2_nb=0; $title= $h1->text; } sub h2 { my( $t, $h2)= @_; $h2_nb++; $h3_nb=0; $h2->prefix( "$h2_nb. "); } sub h3 { my( $t, $h3)= @_; $h3_nb++; $h4_nb=0; $h3->prefix( "$h2_nb.$h3_nb "); } sub h4 { my( $t, $h4)= @_; $h4_nb++; $h4->prefix( "$h2_nb.$h3_nb.$h4_nb "); } sub pre { my( $t, $pre)= @_; $pre->remove_cdata; } sub example { my( $t, $example)= @_; # first get the included file my $file= $example->text; open( EXAMPLE, "<$file") or die "cannot open file $file: $!"; local undef $/; my $text= ; my $parser= $t->{twig_parser}; my $table= XML::Twig::Elt->new( 'table', $text); my $p= $example->parent; $table->paste( 'after', $p); $table->insert( 'tr', 'td', 'pre'); $table->set_att( border => 1); $table->set_att( width => "100%"); $table->set_att( bgcolor => "#00FFFF"); $example->set_gi( 'a'); $example->set_att( href => $file); if( $example->att( 'class') && ($example->att( 'class') eq 'code') ) { $example{$file}= $example->att( 'desc'); $example->del_att( 'desc'); $example->del_att( 'class'); } } sub process_empty { my( $t, $empty)= @_; my $html_empty= XML::Twig::Elt->new( PCDATA, "<" . $empty->gi . ">"); $html_empty->paste( 'before', $empty); $empty->cut; } sub td { my( $t, $td)= @_; $td->set_text( ' ') unless( $td->text); } sub method { my( $t, $method)= @_; $method->set_gi( 'tt'); my $a= $method->insert( 'a'); my $class= $method->att( 'class'); if( $class=~ /^twig/) { $class= ucfirst $class; } elsif( $class=~ /^elt/) { $class= 'Twig_' . ucfirst $class; } my $item= $method->text; $method->del_att( 'class'); $a->set_att( href => "../twig_dev.html#METHODS_XML_$class\_$item"); } sub section { my( $t, $section)= @_; my $filename="yapc_twig_s$h2_nb.html"; warn "creating section $h2_nb\n"; open( SECTION, ">$filename") or die "cannot open $filename: $!"; select SECTION; my $body= $section->insert( 'body'); $body->set_att( bgcolor => "#FFFFFF"); my $head= XML::Twig::Elt->new( 'head'); $head->paste( $section); my $title= XML::Twig::Elt->new( 'title', "Processing XMl efficiently with XML::Twig - Section $h2_nb"); $title->paste( $head); $head->insert_new_elt( last_child => meta => { content => "main", name => "template"}); my $top_links= links( $h2_nb); my $bottom_links= $top_links->copy; $top_links->paste( $body); my $hr= XML::Twig::Elt->new( hr => '#EMPTY'); $hr->paste( after => $top_links); $bottom_links->paste( 'last_child', $body); $hr= XML::Twig::Elt->new( hr => '#EMPTY'); $hr->paste( before => $bottom_links); $section->set_gi( 'html'); $section->print; $t->purge; close SECTION; } sub tutorial { my $filename="index.html"; open( INDEX, ">$filename") or die "cannot open $filename: $!"; select INDEX; print "\n$title\n"; print "

$title

\n"; print $info; print "
\n"; print "

Table of Content

\n\n"; print "

Code Examples

\n

"; foreach my $file ( sort keys %example) { print "$file: $example{$file}
\n"; } print "

\n"; print ""; close INDEX; } sub filename { my $section= shift; return "yapc_twig_s$section.html"; } sub links { my $section = shift; my $current = $section-1; my $previous = $current-1; my $next = $current+1; my $table= XML::Twig::Elt->new( 'table'); $table->set_att( width => "100%" ); my $tr= $table->insert( 'tr'); my $td= $tr->insert( 'td'); $td->set_atts( { align => "left", width => "33%" }); unless( $previous == -1) { my $a= $td->insert( 'a'); $a->set_att( href => $toc[$previous]->{file}); my $img= $a->insert( 'img'); $img->set_atts( { src => "previous.gif", alt => "Previous", border => "0" }); my $text= XML::Twig::Elt->new( PCDATA, { '#ASIS' => 1}, "
" . $toc[$previous]->{title}); $text->paste( 'last_child', $a); } else { my $nbsp= XML::Twig::Elt->new( PCDATA, ""); $nbsp->paste( $td); } $td= XML::Twig::Elt->new( 'td', { '#ASIS' => 1}, ''. 'Table of Content' . '
Table of Content
'); $td->set_asis; $td->set_atts( { align => "center", width => "34%" }); $td->paste( 'last_child', $tr); $td= XML::Twig::Elt->new( 'td'); $td->set_atts( { align => "right", width => "33%" }); unless( $next > $#toc) { my $a= $td->insert( 'a'); $a->set_att( href => $toc[$next]->{file}); my $img= $a->insert( 'img'); $img->set_atts( { src => "next.gif", alt => "Next", border => "0"}); my $text= XML::Twig::Elt->new( '#PCDATA' => {'#ASIS' => 1}, "
" . $toc[$next]->{title}); $text->paste( 'last_child', $a); } else { my $nbsp= XML::Twig::Elt->new( PCDATA, {'#ASIS' => 1}, ""); $nbsp->paste( $td); } $td->paste( 'last_child', $tr); return $table; }