texinfo-commits
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

texinfo/tp/Texinfo Parser.pm Structuring.pm Con...


From: Patrice Dumas
Subject: texinfo/tp/Texinfo Parser.pm Structuring.pm Con...
Date: Sun, 10 Apr 2011 17:43:17 +0000

CVSROOT:        /sources/texinfo
Module name:    texinfo
Changes by:     Patrice Dumas <pertusus>        11/04/10 17:43:17

Modified files:
        tp/Texinfo     : Parser.pm Structuring.pm 
        tp/Texinfo/Convert: HTML.pm 

Log message:
        Handle directions as external nodes and references to externa nodes.
        Do links at the file beginning.

CVSWeb URLs:
http://cvs.savannah.gnu.org/viewcvs/texinfo/tp/Texinfo/Parser.pm?cvsroot=texinfo&r1=1.237&r2=1.238
http://cvs.savannah.gnu.org/viewcvs/texinfo/tp/Texinfo/Structuring.pm?cvsroot=texinfo&r1=1.50&r2=1.51
http://cvs.savannah.gnu.org/viewcvs/texinfo/tp/Texinfo/Convert/HTML.pm?cvsroot=texinfo&r1=1.13&r2=1.14

Patches:
Index: Parser.pm
===================================================================
RCS file: /sources/texinfo/texinfo/tp/Texinfo/Parser.pm,v
retrieving revision 1.237
retrieving revision 1.238
diff -u -b -r1.237 -r1.238
--- Parser.pm   9 Apr 2011 17:00:45 -0000       1.237
+++ Parser.pm   10 Apr 2011 17:43:16 -0000      1.238
@@ -897,7 +897,7 @@
   return "$cmd$type : $args $text $contents\n$parent_string";
 }
 
-# For debugging
+# For debugging
 my @kept_keys = ('contents', 'cmdname', 'type', 'text', 'args');
 my %kept_keys;
 foreach my $key (@kept_keys) {

Index: Structuring.pm
===================================================================
RCS file: /sources/texinfo/texinfo/tp/Texinfo/Structuring.pm,v
retrieving revision 1.50
retrieving revision 1.51
diff -u -b -r1.50 -r1.51
--- Structuring.pm      9 Apr 2011 09:25:44 -0000       1.50
+++ Structuring.pm      10 Apr 2011 17:43:16 -0000      1.51
@@ -650,6 +650,37 @@
   return address@hidden;
 }
 
+sub _new_external_node($;$$)
+{
+  my $node_content = shift;
+  my $manual_content = shift;
+
+  my $external_node = { 'type' => 'external_node',
+                'extra' => {'manual_content' => $manual_content}};
+  
+  if ($node_content) {
+    $external_node->{'extra'}->{'node_content'} = $node_content;
+    $external_node->{'extra'}->{'normalized'} = 
+       Texinfo::Convert::NodeNameNormalization::normalize_node(
+          {'contents' => $node_content}); 
+  }
+  return $external_node;
+}
+
+# FIXME node not existing
+sub _node_element($)
+{
+  my $node = shift;
+  if ($node->{'extra'} and $node->{'extra'}->{'manual_content'}) {
+    return _new_external_node($node->{'extra'}->{'node_content'},
+                              $node->{'extra'}->{'manual_content'});
+  } else {
+    return $node->{'parent'};
+  }
+}
+
+# Do element directions (like in texi2html) and store them 
+# in 'extra'->'directions'.
 sub element_directions($$)
 {
   my $self = shift;
@@ -660,28 +691,29 @@
   foreach my $element (@$elements) {
     my $directions;
     $directions->{'This'} = $element;
-    $directions->{'Forward'} = $element->{'extra'}->{'element_next'}
-      if ($element->{'extra'}->{'element_next'});
-    $directions->{'Back'} = $element->{'extra'}->{'element_prev'}
-      if ($element->{'extra'}->{'element_prev'});
-    if ($element->{'node'}) {
-      my $node = $element->{'node'};
+    $directions->{'Forward'} = $element->{'element_next'}
+      if ($element->{'element_next'});
+    $directions->{'Back'} = $element->{'element_prev'}
+      if ($element->{'element_prev'});
+    if ($element->{'extra'}->{'node'}) {
+      my $node = $element->{'extra'}->{'node'};
       foreach my $direction(['NodeUp', 'node_up'], ['NodeNext', 'node_next'],
                             ['NodePrev', 'node_prev']) {
-        $directions->{$direction->[0]} = $node->{$direction->[1]}->{'parent'}
+        $directions->{$direction->[0]} = 
_node_element($node->{$direction->[1]})
           if ($node->{$direction->[1]});
       }
+      # Now do NodeForward which is something like the following node.
       my $automatic_directions = 
         (scalar(@{$node->{'extra'}->{'nodes_manuals'}}) == 1);
       if ($node->{'menu_child'}) {
-        $directions->{'NodeForward'} = $node->{'menu_child'}->{'parent'};
+        $directions->{'NodeForward'} = _node_element($node->{'menu_child'});
       } elsif ($automatic_directions and $node->{'associated_section'}
                and $node->{'associated_section'}->{'section_childs'}
                and $node->{'associated_section'}->{'section_childs'}->[0]) {
         $directions->{'NodeForward'} 
           = $node->{'associated_section'}->{'section_childs'}->[0]->{'parent'};
       } elsif ($node->{'node_next'}) {
-        $directions->{'NodeForward'} = $node->{'node_next'}->{'parent'};
+        $directions->{'NodeForward'} = _node_element($node->{'node_next'});
       } else {
         my $up = $node->{'node_up'};
         my @up_list = ($node);
@@ -691,7 +723,7 @@
                and not (grep {$up eq $_} @up_list  
                         or ($node_top and $up eq $node_top))) {
           if (defined($up->{'node_next'})) {
-            $directions->{'NodeForward'} = $up->{'node_next'}->{'parent'};
+            $directions->{'NodeForward'} = _node_element($up->{'node_next'});
             last;
           }
           push @up_list, $up;
@@ -701,10 +733,11 @@
       
       $directions->{'NodeForward'}->{'extra'}->{'directions'}->{'NodeBack'} = 
$element
         if ($directions->{'NodeForward'} 
+            and $directions->{'NodeForward'}->{'type'} eq 'element'
             and 
!$directions->{'NodeForward'}->{'extra'}->{'directions'}->{'NodeBack'});
     }
-    if ($element->{'section'}) {
-      my $section = $element->{'section'};
+    if ($element->{'extra'}->{'section'}) {
+      my $section = $element->{'extra'}->{'section'};
       foreach my $direction(['Up', 'section_up'], ['Next', 'section_next'],
                             ['Prev', 'section_prev']) {
         $directions->{$direction->[0]} = 
$section->{$direction->[1]}->{'parent'}
@@ -737,6 +770,13 @@
           = $section if ($directions->{'FastForward'});
       }
     }
+    # Use node up if there is no section up.
+    # FIXME is it really right?
+    if (!$directions->{'Up'} and $element->{'extra'}->{'node'}
+        and $element->{'extra'}->{'node'}->{'node_up'} 
+        and (!$node_top or ($element->{'extra'}->{'node'} ne $node_top))) {
+      $directions->{'Up'} = 
_node_element($element->{'extra'}->{'node'}->{'node_up'});
+    }
     if ($element->{'extra'}->{'directions'}) {
       %{$element->{'extra'}->{'directions'}} = 
(%{$element->{'extra'}->{'directions'}}, 
                                                 %$directions)
@@ -744,6 +784,56 @@
       $element->{'extra'}->{'directions'} = $directions;
     }
   }
+  if ($self->get_conf('DEBUG')) {
+    foreach my $element (@$elements) {
+      print STDERR "Directions($element): 
".Texinfo::Structuring::_print_directions($element)."\n";
+    }
+  }
+}
+
+sub _print_element_command_texi($)
+{
+  my $element = shift;
+  if ($element->{'type'} eq 'external_node') {
+    my $command = {'contents' => [{'text' => '('}, 
+                        @{$element->{'extra'}->{'manual_content'}},
+                               {'text' => ')'}]};
+    if ($element->{'extra'}->{'node_content'}) {
+      unshift @{$command->{'contents'}}, 
@{$element->{'extra'}->{'node_content'}};
+    }
+    return Texinfo::Convert::Texinfo::convert ($command);
+  }
+  
+  my $command = $element->{'extra'}->{'element_command'};
+  if (!defined($command)) {
+    my $result = "BUG: no associated command ";
+    $result .= "(type $element->{'type'})" if (defined($element->{'type'}));
+    return $result;
+  }
+  my $tree;
+  if ($command->{'cmdname'} eq 'node') {
+    $tree = $command->{'extra'}->{'node_content'};
+  } else {
+    $tree = $command->{'extra'}->{'misc_content'};
+  }
+  return '@'.$command->{'cmdname'}. ' '
+       .Texinfo::Convert::Texinfo::convert ({'contents' => $tree});
+}
+
+sub _print_directions($)
+{
+  my $element = shift;
+  my $result = _print_element_command_texi($element)."\n";
+
+  if ($element->{'extra'} and $element->{'extra'}->{'directions'}) {
+    foreach my $direction (keys(%{$element->{'extra'}->{'directions'}})) {
+      $result .= "  $direction: ".
+       
_print_element_command_texi($element->{'extra'}->{'directions'}->{$direction})."\n";
+    }
+  } else {
+    $result .= "  NO DIRECTION";
+  }
+  return $result;
 }
 
 # this is used in the test suite, but not likely to be useful in real life.

Index: Convert/HTML.pm
===================================================================
RCS file: /sources/texinfo/texinfo/tp/Texinfo/Convert/HTML.pm,v
retrieving revision 1.13
retrieving revision 1.14
diff -u -b -r1.13 -r1.14
--- Convert/HTML.pm     9 Apr 2011 17:00:46 -0000       1.13
+++ Convert/HTML.pm     10 Apr 2011 17:43:17 -0000      1.14
@@ -149,6 +149,32 @@
   return $self->{'context'}->[-1]->{'align'}->[-1];
 }
 
+# see http://www.w3.org/TR/REC-html40/types.html#type-links
+my %BUTTONS_REL =
+(
+ 'Top',         'start',
+ 'Contents',    'contents',
+ 'Overview',    '',
+ 'Index',       'index',
+ 'This',        '',
+ 'Back',        'previous',
+ 'FastBack',    '',
+ 'Prev',        'previous',
+ 'Up',          'up',
+ 'Next',        'next',
+ 'NodeUp',      'up',
+ 'NodeNext',    'next',
+ 'NodePrev',    'previous',
+ 'NodeForward', '',
+ 'NodeBack',    '',
+ 'Forward',     'next',
+ 'FastForward', '',
+ 'About' ,      'help',
+ 'First',       '',
+ 'Last',        '',
+ 'NextFile',    'next',
+ 'PrevFile',    'previous',
+);
 
 
 my %defaults = (
@@ -182,11 +208,13 @@
   'TOP_NODE_FILE'        => 'index',
   'NODE_FILE_EXTENSION'  => 'html',
   'EXTENSION'            => 'html',
+  'TOP_NODE_FILE_TARGET' => 'index',
   'TRANSLITERATE_FILE_NAMES' => 1,
   'USE_LINKS'            => 1,
   'DATE_IN_HEADER'       => 0,
   'LINKS_BUTTONS'        => ['Top', 'Index', 'Contents', 'About', 
                               'Up', 'NextFile', 'PrevFile'],
+  'BUTTONS_REL'          => \%BUTTONS_REL,
   'DOCTYPE'              => '<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 
Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd";>',
   'BODYTEXT'             => undef,
   'documentlanguage'     => 'en',
@@ -843,24 +871,20 @@
   # T2H_DEFAULT_css_lines in texi2html.init
 }
 
-# FIXME also convert to html, to use name in cross-refs or do it on demand?
-# This set 2 unrelated things.  
-#  * The targets and id of sectioning elements
-#  * the target, id and normalized filename of 'labels', ie everything that 
-#    may be the target of a ref, like @node, @float, @anchor...
-sub _set_root_commands_targets_node_files($$)
+sub _node_id_file($$)
 {
   my $self = shift;
-  my $elements = shift;
+  my $root_command = shift;
 
   my $no_unidecode;
   $no_unidecode = 1 if (defined($self->get_conf('USE_UNIDECODE')) 
                         and !$self->get_conf('USE_UNIDECODE'));
 
-  if ($self->{'labels'}) {
-    foreach my $root_command (values(%{$self->{'labels'}})) {
       my $target = _normalized_to_id($root_command->{'extra'}->{'normalized'});
-      my $id = $target;
+  my $id;
+  if (!$root_command->{'extra'}->{'manual_content'}) {
+    $id = $target;
+  }
       # FIXME something special for Top node ?
       if (defined($Texinfo::Config::node_target_name)) {
         ($target, $id) = &$Texinfo::Config::node_target_name($root_command,
@@ -874,6 +898,26 @@
       } else {
         $filename = $root_command->{'extra'}->{'normalized'};
       }
+  return ($filename, $target, $id);
+}
+
+# FIXME also convert to html, to use name in cross-refs or do it on demand?
+# This set 2 unrelated things.  
+#  * The targets and id of sectioning elements
+#  * the target, id and normalized filename of 'labels', ie everything that 
+#    may be the target of a ref, like @node, @float, @anchor...
+sub _set_root_commands_targets_node_files($$)
+{
+  my $self = shift;
+  my $elements = shift;
+
+  my $no_unidecode;
+  $no_unidecode = 1 if (defined($self->get_conf('USE_UNIDECODE')) 
+                        and !$self->get_conf('USE_UNIDECODE'));
+
+  if ($self->{'labels'}) {
+    foreach my $root_command (values(%{$self->{'labels'}})) {
+      my ($filename, $target, $id) = $self->_node_id_file($root_command);
       $filename .= '.'.$self->get_conf('NODE_FILE_EXTENSION') 
         if (defined($self->get_conf('NODE_FILE_EXTENSION')) 
             and $self->get_conf('NODE_FILE_EXTENSION') ne '');
@@ -1094,6 +1138,119 @@
   return $elements;
 }
 
+sub htmlxref($$)
+{
+  my $self = shift;
+  my $file = shift;
+
+  return undef;
+}
+
+my %htmlxref_entries = (
+ 'node' => [ 'node', 'section', 'chapter', 'mono' ],
+ 'section' => [ 'section', 'chapter','node', 'mono' ],
+ 'chapter' => [ 'chapter', 'section', 'node', 'mono' ],
+ 'mono' => [ 'mono', 'chapter', 'section', 'node' ],
+);
+
+sub default_external_href($$$)
+{
+  my $self = shift;
+  my $external_node = shift;
+  my $target = shift;
+  my $target_filebase = shift;
+
+  my $xml_target = _normalized_to_id($target);
+
+  my $default_target_split = $self->get_conf('EXTERNAL_CROSSREF_SPLIT');
+
+  my $extension = '';
+  $extension = "." . $self->get_conf('NODE_FILE_EXTENSION')
+          if (defined($self->get_conf('NODE_FILE_EXTENSION')) 
+              and $self->get_conf('NODE_FILE_EXTENSION') ne '');
+
+  my $target_split;
+  my $file;
+  if ($external_node->{'extra'}->{'manual_content'}) {
+    my $manual_name = Texinfo::Convert::Text::convert(
+       {'contents' => $external_node->{'extra'}->{'manual_content'}});
+    my $manual_base = $manual_name;
+    $manual_base =~ s/\.[^\.]*$//;
+    $manual_base =~ s/^.*\///;
+    my $document_split = $self->get_conf('SPLIT');
+    $document_split = 'mono' if (!$document_split);
+    my $split_found;
+    my $href;
+    my $htmlxref_info = $self->htmlxref($manual_base);
+    if ($htmlxref_info) {
+      foreach my $split_ordered (@{$htmlxref_entries{$document_split}}) {
+        if (defined($htmlxref_info->{$split_ordered})) {
+          $split_found = $split_ordered;
+          $href = $htmlxref_info->{$split_ordered};
+          last;
+        }
+      }
+    }
+    if (defined($split_found)) {
+      $target_split = 1 unless ($split_found eq 'mono');
+    } else { # nothing specified for that manual, use default
+      $target_split = $default_target_split;
+    }
+
+    if ($target_split) {
+      if (defined($href)) {
+        $file = $href;
+      } elsif (defined($self->get_conf('EXTERNAL_DIR'))) {
+        $file = $self->get_conf('EXTERNAL_DIR')."/$manual_base";
+      } elsif ($self->get_conf('SPLIT')) {
+        $file = "../$manual_base";
+      }
+      $file .= "/";
+    } else {# target not split
+      if (defined($href)) {
+        $file = $href;
+      } else {
+        if (defined($self->get_conf('EXTERNAL_DIR'))) {
+          $file = $self->get_conf('EXTERNAL_DIR')."/$manual_base";
+        } elsif ($self->get_conf('SPLIT')) {
+          $file = "../$manual_base";
+        } else {
+          $file = $manual_base;
+        }
+        $file .= $extension;
+      }
+    }
+  } else {
+    $target_split = $default_target_split;
+  }
+
+  # FIXME use $external_node->{'extra'}->{'node_content'}?
+  if ($target eq '') {
+    if ($target_split) {
+      if (defined($self->get_conf('TOP_NODE_FILE_TARGET'))) {
+        return $file . $self->get_conf('TOP_NODE_FILE_TARGET') 
+           . $extension . '#Top';
+      } else {
+        return $file . '#Top';
+      }
+    } else {
+      return $file . '#Top';
+    }
+  }
+
+  if (! $target_split) {
+    return $file . '#' . $xml_target;
+  } else {
+    my $file_basename;
+    if ($target eq 'Top' and defined($self->get_conf('TOP_NODE_FILE_TARGET'))) 
{
+      $file_basename = $self->get_conf('TOP_NODE_FILE_TARGET');
+    } else {
+      $file_basename = $target_filebase;
+    }
+    return $file . $file_basename . $extension . '#' . $xml_target;
+  }
+}
+
 my %valid_types = (
   'href' => 1,
   'string' => 1,
@@ -1101,6 +1258,24 @@
   'tree' => 1,
 );
 
+sub _external_node_reference($$$;$)
+{
+  my $self = shift;
+  my $external_node = shift;
+  my $type = shift;
+  my $filename = shift;
+
+  my ($target_filebase, $target, $id) = $self->_node_id_file($external_node);
+  
+  if ($type eq 'href') {
+    return &{$self->{'external_node_target'}}($self, $external_node, 
+                                              $target, $target_filebase);
+  } else {
+    return 'TEXT TODO';
+  }
+}
+
+
 # FIXME global targets
 sub _element_direction($$$$;$)
 {
@@ -1123,8 +1298,12 @@
       and $element->{'extra'}->{'directions'}->{$direction}) {
     $element_target 
      = $element->{'extra'}->{'directions'}->{$direction};
+    if ($element_target->{'type'} eq 'external_node') {
+      return $self->_external_node_reference($element_target, $type, 
$filename);
+    } else {
     $command = $element_target->{'extra'}->{'element_command'};
     $target = $self->{'targets'}->{$command};
+    }
   } else {
     return undef;
   }
@@ -1138,6 +1317,7 @@
     }
     $href .= '#' . $target->{'target'} 
       if (defined($target->{'target'}));
+    return $href;
   } elsif (exists($target->{$type})) {
     return $target->{$type};
   } elsif ($command) {
@@ -1164,7 +1344,7 @@
     }
     print STDERR "DO $target->{'id'}($type)\n" if ($self->get_conf('DEBUG'));
     $target->{$type} = $self->_convert($tree);
-    pop @{$self->{'context'}}, 
+    pop @{$self->{'context'}};
     return $target->{$type};
   }
 }
@@ -1224,15 +1404,19 @@
   if ($self->get_conf('USE_LINKS')) {
     my $link_buttons = $self->get_conf('LINKS_BUTTONS');
     foreach my $link (@$link_buttons) {
-      # TODO
-#            if (defined($Texi2HTML::HREF{$link}) and $Texi2HTML::HREF{$link} 
ne '')
-#            {
-#                my $title = '';
-#                $title = " title=\"$Texi2HTML::SIMPLE_TEXT{$link}\"" if 
(defined($Texi2HTML::SIMPLE_TEXT{$link}));
-#                my $rel = '';
-#                $rel = " rel=\"$BUTTONS_REL{$link}\"" if 
(defined($BUTTONS_REL{$link}));
-#                $links .= "<link 
href=\"$Texi2HTML::HREF{$link}\"${rel}${title}>\n";
-#            }
+      my $link_href = $self->_element_direction($page->{'extra'}->{'element'},
+                                          $link, 'href', $page->{'filename'});
+      #print STDERR "$title: $link -> $link_href \n";
+      if ($link_href and $link_href ne '') {
+        my $link_string = 
$self->_element_direction($page->{'extra'}->{'element'},
+                                          $link, 'string');
+        my $title = '';
+        $title = " title=\"$link_string\"" if (defined($link_string));
+        my $rel = '';
+        $rel = " rel=\"$self->{'BUTTONS_REL'}->{$link}\"" 
+           if (defined($self->{'BUTTONS_REL'}->{$link}));
+        $links .= "<link href=\"$link_href\"${rel}${title}>\n";
+      }
     }
   }
   my $css_lines;
@@ -1334,6 +1518,7 @@
   if ($self->get_conf('NODE_FILES') or $self->get_conf('SPLIT') eq 'node') {
     $self->set_conf('NODE_FILENAMES', 1);
   }
+  $self->set_conf('EXTERNAL_CROSSREF_SPLIT', $self->get_conf('SPLIT'));
                                                    
   $self->_prepare_css();
 
@@ -1356,7 +1541,7 @@
   $self->_set_page_files($pages);
 
   # Add element directions.  FIXME do it here or before?  Here it means that
-  # PrevFil eand NextFile can be set.
+  # PrevFile and NextFile can be set.
   Texinfo::Structuring::element_directions($self, $elements);
 
   # FIXME Before that, set multiple commands
@@ -1372,7 +1557,7 @@
       next if (!$command->{'extra'}
                or (!$command->{'extra'}->{'misc_contents'}
                    or $command->{'extra'}->{'missing_argument'}));
-      # FIXME remove the virtual type?
+      # FIXME remove the virtual type?
       print STDERR "Using $fulltitle_command as title\n"
         if ($self->get_conf('DEBUG'));
       $fulltitle = {'contents' => $command->{'extra'}->{'misc_contents'},
@@ -1914,11 +2099,12 @@
     } elsif ($root->{'type'} eq '_string') {
       $self->{'context'}->[-1]->{'string'}--;
     }
-    print STDERR "DO type ($root->{'type'}) => `$result'\n";
+    print STDERR "DO type ($root->{'type'}) => `$result'\n"
+      if ($self->get_conf('DEBUG'));
     return $result;
-    # no type, no cmdname, but contents.
+    # no type, no cmdname, but contents.
   } elsif ($root->{'contents'}) {
-    # FIXME what does this corresponds to?
+    # FIXME document situations where that happens? Use virtual types?
     my $content_formatted = '';
     foreach my $content (@{$root->{'contents'}}) {
       $content_formatted .= $self->_convert($content);



reply via email to

[Prev in Thread] Current Thread [Next in Thread]