1#! /usr/bin/perl 2'di '; 3'ig 00 '; 4#+############################################################################## 5# 6# texi2html: Program to transform Texinfo documents to HTML 7# 8# Copyright (C) 1999, 2000 Free Software Foundation, Inc. 9# 10# This program is free software: you can redistribute it and/or modify 11# it under the terms of the GNU General Public License as published by 12# the Free Software Foundation, either version 3 of the License, or 13# (at your option) any later version. 14# 15# This program is distributed in the hope that it will be useful, 16# but WITHOUT ANY WARRANTY; without even the implied warranty of 17# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18# GNU General Public License for more details. 19# 20# You should have received a copy of the GNU General Public License 21# along with this program. If not, see <http://www.gnu.org/licenses/>. 22# 23#-############################################################################## 24 25# This requires perl version 5 or higher 26require 5.0; 27 28#++############################################################################## 29# 30# NOTE FOR DEBUGGING THIS SCRIPT: 31# You can run 'perl texi2html.pl' directly, provided you have 32# the environment variable T2H_HOME set to the directory containing 33# the texi2html.init file 34# 35#--############################################################################## 36 37# CVS version: 38# $Id: texi2html 7792 2004-06-07 09:07:27Z korli $ 39 40# Homepage: 41$T2H_HOMEPAGE = <<EOT; 42http://www.mathematik.uni-kl.de/~obachman/Texi2html 43EOT 44 45# Authors: 46$T2H_AUTHORS = <<EOT; 47Written by: Lionel Cons <Lionel.Cons\@cern.ch> (original author) 48 Karl Berry <karl\@freefriends.org> 49 Olaf Bachmann <obachman\@mathematik.uni-kl.de> 50 and many others. 51Maintained by: Olaf Bachmann <obachman\@mathematik.uni-kl.de> 52Send bugs and suggestions to <texi2html\@mathematik.uni-kl.de> 53EOT 54 55# Version: set in configure.in 56$THISVERSION = '1.64'; 57$THISPROG = "texi2html $THISVERSION"; # program name and version 58 59# The man page for this program is included at the end of this file and can be 60# viewed using the command 'nroff -man texi2html'. 61 62# Identity: 63 64$T2H_TODAY = &pretty_date; # like "20 September 1993" 65# the eval prevents this from breaking on system which do not have 66# a proper getpwuid implemented 67eval { ($T2H_USER = (getpwuid ($<))[6]) =~ s/,.*//;}; # Who am i 68 69#+++############################################################################ 70# # 71# Initialization # 72# Pasted content of File $(srcdir)/texi2html.init: Default initializations # 73# # 74#---############################################################################ 75 76# leave this within comments, and keep the require statement 77# This way, you can directly run texi2html.pl, if $ENV{T2H_HOME}/texi2html.init 78# exists. 79 80# 81# -*-perl-*- 82###################################################################### 83# File: texi2html.init 84# 85# Sets default values for command-line arguments and for various customizable 86# procedures 87# 88# A copy of this file is pasted into the beginning of texi2html by 89# 'make texi2html' 90# 91# Copy this file and make changes to it, if you like. 92# Afterwards, either, load it with command-line option -init_file <your_init_file> 93# 94# $Id: texi2html 7792 2004-06-07 09:07:27Z korli $ 95 96###################################################################### 97# stuff which can also be set by command-line options 98# 99# 100# Note: values set here, overwrite values set by the command-line 101# options before -init_file and might still be overwritten by 102# command-line arguments following the -init_file option 103# 104 105# T2H_OPTIONS is a hash whose keys are the (long) names of valid 106# command-line options and whose values are a hash with the following keys: 107# type ==> one of !|=i|:i|=s|:s (see GetOpt::Long for more info) 108# linkage ==> ref to scalar, array, or subroutine (see GetOpt::Long for more info) 109# verbose ==> short description of option (displayed by -h) 110# noHelp ==> if 1 -> for "not so important options": only print description on -h 1 111# 2 -> for obsolete options: only print description on -h 2 112 113$T2H_DEBUG = 0; 114$T2H_OPTIONS -> {debug} = 115{ 116 type => '=i', 117 linkage => \$main::T2H_DEBUG, 118 verbose => 'output HTML with debuging information', 119}; 120 121$T2H_DOCTYPE = '<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">'; 122$T2H_OPTIONS -> {doctype} = 123{ 124 type => '=s', 125 linkage => \$main::T2H_DOCTYPE, 126 verbose => 'document type which is output in header of HTML files', 127 noHelp => 1 128}; 129 130$T2H_CHECK = 0; 131$T2H_OPTIONS -> {check} = 132{ 133 type => '!', 134 linkage => \$main::T2H_CHECK, 135 verbose => 'if set, only check files and output all things that may be Texinfo commands', 136 noHelp => 1 137}; 138 139# -expand 140# if set to "tex" (or, "info") expand @iftex and @tex (or, @ifinfo) sections 141# else, neither expand @iftex, @tex, nor @ifinfo sections 142$T2H_EXPAND = "info"; 143$T2H_OPTIONS -> {expand} = 144{ 145 type => '=s', 146 linkage => \$T2H_EXPAND, 147 verbose => 'Expand info|tex|none section of texinfo source', 148}; 149 150# - glossary 151#if set, uses section named `Footnotes' for glossary 152$T2H_USE_GLOSSARY = 0; 153T2H_OPTIONS -> {glossary} = 154{ 155 type => '!', 156 linkage => \$T2H_USE_GLOSSARY, 157 verbose => "if set, uses section named `Footnotes' for glossary", 158 noHelp => 1, 159}; 160 161 162# -invisible 163# $T2H_INVISIBLE_MARK is the text used to create invisible destination 164# anchors for index links (you can for instance use the invisible.xbm 165# file shipped with this program). This is a workaround for a known 166# bug of many WWW browsers, including netscape. 167# For me, it works fine without it -- on the contrary: if there, it 168# inserts space between headers and start of text (obachman 3/99) 169$T2H_INVISIBLE_MARK = ''; 170# $T2H_INVISIBLE_MARK = ' '; 171$T2H_OPTIONS -> {invisible} = 172{ 173 type => '=s', 174 linkage => \$T2H_INVISIBLE_MARK, 175 verbose => 'use text in invisble anchot', 176 noHelp => 1, 177}; 178 179# -iso 180# if set, ISO8879 characters are used for special symbols (like copyright, etc) 181$T2H_USE_ISO = 0; 182$T2H_OPTIONS -> {iso} = 183{ 184 type => 'iso', 185 linkage => \$T2H_USE_ISO, 186 verbose => 'if set, ISO8879 characters are used for special symbols (like copyright, etc)', 187 noHelp => 1, 188}; 189 190# -I 191# list directories where @include files are searched for (besides the 192# directory of the doc file) additional '-I' args add to this list 193@T2H_INCLUDE_DIRS = ("."); 194$T2H_OPTIONS -> {I} = 195{ 196 type => '=s', 197 linkage => \@T2H_INCLUDE_DIRS, 198 verbose => 'append $s to the @include search path', 199}; 200 201# -top_file 202# uses file of this name for top-level file 203# extension is manipulated appropriately, if necessary. 204# If empty, <basename of document>.html is used 205# Typically, you would set this to "index.html". 206$T2H_TOP_FILE = ''; 207$T2H_OPTIONS -> {top_file} = 208{ 209 type => '=s', 210 linkage => \$T2H_TOP_FILE, 211 verbose => 'use $s as top file, instead of <docname>.html', 212}; 213 214 215# -toc_file 216# uses file of this name for table of contents file 217# extension is manipulated appropriately, if necessary. 218# If empty, <basename of document>_toc.html is used 219$T2H_TOC_FILE = ''; 220$T2H_OPTIONS -> {toc_file} = 221{ 222 type => '=s', 223 linkage => \$T2H_TOC_FILE, 224 verbose => 'use $s as ToC file, instead of <docname>_toc.html', 225}; 226 227# -frames 228# if set, output two additional files which use HTML 4.0 "frames". 229$T2H_FRAMES = 0; 230$T2H_OPTIONS -> {frames} = 231{ 232 type => '!', 233 linkage => \$T2H_FRAMES, 234 verbose => 'output files which use HTML 4.0 frames (experimental)', 235 noHelp => 1, 236}; 237 238 239# -menu | -nomenu 240# if set, show the Texinfo menus 241$T2H_SHOW_MENU = 1; 242$T2H_OPTIONS -> {menu} = 243{ 244 type => '!', 245 linkage => \$T2H_SHOW_MENU, 246 verbose => 'ouput Texinfo menus', 247}; 248 249# -number | -nonumber 250# if set, number sections and show section names and numbers in references 251# and menus 252$T2H_NUMBER_SECTIONS = 1; 253$T2H_OPTIONS -> {number} = 254{ 255 type => '!', 256 linkage => \$T2H_NUMBER_SECTIONS, 257 verbose => 'use numbered sections' 258}; 259 260# if set, and T2H_NUMBER_SECTIONS is set, then use node names in menu 261# entries, instead of section names 262$T2H_NODE_NAME_IN_MENU = 0; 263 264# if set and menu entry equals menu descr, then do not print menu descr. 265# Likewise, if node name equals entry name, do not print entry name. 266$T2H_AVOID_MENU_REDUNDANCY = 1; 267 268# -split section|chapter|none 269# if set to 'section' (resp. 'chapter') create one html file per (sub)section 270# (resp. chapter) and separate pages for Top, ToC, Overview, Index, 271# Glossary, About. 272# otherwise, create monolithic html file which contains whole document 273#$T2H_SPLIT = 'section'; 274$T2H_SPLIT = ''; 275$T2H_OPTIONS -> {split} = 276{ 277 type => '=s', 278 linkage => \$T2H_SPLIT, 279 verbose => 'split document on section|chapter else no splitting', 280}; 281 282# -section_navigation|-no-section_navigation 283# if set, then navigation panels are printed at the beginning of each section 284# and, possibly at the end (depending on whether or not there were more than 285# $T2H_WORDS_IN_PAGE words on page 286# This is most useful if you do not want to have section navigation 287# on -split chapter 288$T2H_SECTION_NAVIGATION = 1; 289$T2H_OPTIONS -> {sec_nav} = 290{ 291 type => '!', 292 linkage => \$T2H_SECTION_NAVIGATION, 293 verbose => 'output navigation panels for each section', 294}; 295 296# -subdir 297# if set put result files in this directory 298# if not set result files are put into current directory 299#$T2H_SUBDIR = 'html'; 300$T2H_SUBDIR = ''; 301$T2H_OPTIONS -> {subdir} = 302{ 303 type => '=s', 304 linkage => \$T2H_SUBDIR, 305 verbose => 'put HTML files in directory $s, instead of $cwd', 306}; 307 308# -short_extn 309# If this is set all HTML file will have extension ".htm" instead of 310# ".html". This is helpful when shipping the document to PC systems. 311$T2H_SHORTEXTN = 0; 312$T2H_OPTIONS -> {short_ext} = 313{ 314 type => '!', 315 linkage => \$T2H_SHORTEXTN, 316 verbose => 'use "htm" extension for output HTML files', 317}; 318 319 320# -prefix 321# Set the output file prefix, prepended to all .html, .gif and .pl files. 322# By default, this is the basename of the document 323$T2H_PREFIX = ''; 324$T2H_OPTIONS -> {prefix} = 325{ 326 type => '=s', 327 linkage => \$T2H_PREFIX, 328 verbose => 'use as prefix for output files, instead of <docname>', 329}; 330 331# -o filename 332# If set, generate monolithic document output html into $filename 333$T2H_OUT = ''; 334$T2H_OPTIONS -> {out_file} = 335{ 336 type => '=s', 337 linkage => sub {$main::T2H_OUT = @_[1]; $T2H_SPLIT = '';}, 338 verbose => 'if set, all HTML output goes into file $s', 339}; 340 341# -short_ref 342#if set cross-references are given without section numbers 343$T2H_SHORT_REF = ''; 344$T2H_OPTIONS -> {short_ref} = 345{ 346 type => '!', 347 linkage => \$T2H_SHORT_REF, 348 verbose => 'if set, references are without section numbers', 349}; 350 351# -idx_sum 352# if value is set, then for each @prinindex $what 353# $docu_name_$what.idx is created which contains lines of the form 354# $key\t$ref sorted alphabetically (case matters) 355$T2H_IDX_SUMMARY = 0; 356$T2H_OPTIONS -> {idx_sum} = 357{ 358 type => '!', 359 linkage => \$T2H_IDX_SUMMARY, 360 verbose => 'if set, also output index summary', 361 noHelp => 1, 362}; 363 364# -verbose 365# if set, chatter about what we are doing 366$T2H_VERBOSE = ''; 367$T2H_OPTIONS -> {Verbose} = 368{ 369 type => '!', 370 linkage => \$T2H_VERBOSE, 371 verbose => 'print progress info to stdout', 372}; 373 374# -lang 375# For page titles use $T2H_WORDS->{$T2H_LANG}->{...} as title. 376# To add a new language, supply list of titles (see $T2H_WORDS below). 377# and use ISO 639 language codes (see e.g. perl module Locale-Codes-1.02 378# for definitions) 379# Default's to 'en' if not set or no @documentlanguage is specified 380$T2H_LANG = ''; 381$T2H_OPTIONS -> {lang} = 382{ 383 type => '=s', 384 linkage => sub {SetDocumentLanguage($_[1])}, 385 verbose => 'use $s as document language (ISO 639 encoding)', 386}; 387 388# -l2h 389# if set, uses latex2html for generation of math content 390$T2H_L2H = ''; 391$T2H_OPTIONS -> {l2h} = 392{ 393 type => '!', 394 linkage => \$T2H_L2H, 395 verbose => 'if set, uses latex2html for @math and @tex', 396}; 397 398###################### 399# The following options are only relevant if $T2H_L2H is set 400# 401# -l2h_l2h 402# name/location of latex2html progam 403$T2H_L2H_L2H = "latex2html"; 404$T2H_OPTIONS -> {l2h_l2h} = 405{ 406 type => '=s', 407 linkage => \$T2H_L2H_L2H, 408 verbose => 'program to use for latex2html translation', 409 noHelp => 1, 410}; 411 412# -l2h_skip 413# if set, skips actual call to latex2html tries to reuse previously generated 414# content, instead 415$T2H_L2H_SKIP = ''; 416$T2H_OPTIONS -> {l2h_skip} = 417{ 418 type => '!', 419 linkage => \$T2H_L2H_SKIP, 420 verbose => 'if set, tries to reuse previously latex2html output', 421 noHelp => 1, 422}; 423 424# -l2h_tmp 425# if set, l2h uses this directory for temporarary files. The path 426# leading to this directory may not contain a dot (i.e., a "."), 427# otherwise, l2h will fail 428$T2H_L2H_TMP = ''; 429$T2H_OPTIONS -> {l2h_tmp} = 430{ 431 type => '=s', 432 linkage => \$T2H_L2H_TMP, 433 verbose => 'if set, uses $s as temporary latex2html directory', 434 noHelp => 1, 435}; 436 437# if set, cleans intermediate files (they all have the prefix $doc_l2h_) 438# of l2h 439$T2H_L2H_CLEAN = 1; 440$T2H_OPTIONS -> {l2h_clean} = 441{ 442 type => '!', 443 linkage => \$T2H_L2H_CLEAN, 444 verbose => 'if set, do not keep intermediate latex2html files for later reuse', 445 noHelp => 1, 446}; 447 448$T2H_OPTIONS -> {D} = 449{ 450 type => '=s', 451 linkage => sub {$main::value{@_[1]} = 1;}, 452 verbose => 'equivalent to Texinfo "@set $s 1"', 453 noHelp => 1, 454}; 455 456$T2H_OPTIONS -> {init_file} = 457{ 458 type => '=s', 459 linkage => \&LoadInitFile, 460 verbose => 'load init file $s' 461}; 462 463 464############################################################################## 465# 466# The following can only be set in the init file 467# 468############################################################################## 469 470# if set, center @image by default 471# otherwise, do not center by default 472$T2H_CENTER_IMAGE = 1; 473 474# used as identation for block enclosing command @example, etc 475# If not empty, must be enclosed in <td></td> 476$T2H_EXAMPLE_INDENT_CELL = '<td> </td>'; 477# same as above, only for @small 478$T2H_SMALL_EXAMPLE_INDENT_CELL = '<td> </td>'; 479# font size for @small 480$T2H_SMALL_FONT_SIZE = '-1'; 481 482# if non-empty, and no @..heading appeared in Top node, then 483# use this as header for top node/section, otherwise use value of 484# @settitle or @shorttitle (in that order) 485$T2H_TOP_HEADING = ''; 486 487# if set, use this chapter for 'Index' button, else 488# use first chapter whose name matches 'index' (case insensitive) 489$T2H_INDEX_CHAPTER = ''; 490 491# if set and $T2H_SPLIT is set, then split index pages at the next letter 492# after they have more than that many entries 493$T2H_SPLIT_INDEX = 100; 494 495# if set (e.g., to index.html) replace hrefs to this file 496# (i.e., to index.html) by ./ 497$T2H_HREF_DIR_INSTEAD_FILE = ''; 498 499######################################################################## 500# Language dependencies: 501# To add a new language extend T2H_WORDS hash and create $T2H_<...>_WORDS hash 502# To redefine one word, simply do: 503# $T2H_WORDS->{<language>}->{<word>} = 'whatever' in your personal init file. 504# 505$T2H_WORDS_EN = 506{ 507 # titles of pages 508 'ToC_Title' => 'Table of Contents', 509 'Overview_Title' => 'Short Table of Contents', 510 'Index_Title' => 'Index', 511 'About_Title' => 'About this document', 512 'Footnotes_Title' => 'Footnotes', 513 'See' => 'See', 514 'see' => 'see', 515 'section' => 'section', 516# If necessary, we could extend this as follows: 517# # text for buttons 518# 'Top_Button' => 'Top', 519# 'ToC_Button' => 'Contents', 520# 'Overview_Button' => 'Overview', 521# 'Index_button' => 'Index', 522# 'Back_Button' => 'Back', 523# 'FastBack_Button' => 'FastBack', 524# 'Prev_Button' => 'Prev', 525# 'Up_Button' => 'Up', 526# 'Next_Button' => 'Next', 527# 'Forward_Button' =>'Forward', 528# 'FastWorward_Button' => 'FastForward', 529# 'First_Button' => 'First', 530# 'Last_Button' => 'Last', 531# 'About_Button' => 'About' 532}; 533 534$T2H_WORD_DE = 535{ 536 'ToC_Title' => 'Inhaltsverzeichniss', 537 'Overview_Title' => 'Kurzes Inhaltsverzeichniss', 538 'Index_Title' => 'Index', 539 'About_Title' => 'Über dieses Dokument', 540 'Footnotes_Title' => 'Fußnoten', 541 'See' => 'Siehe', 542 'see' => 'siehe', 543 'section' => 'Abschnitt', 544}; 545 546$T2H_WORD_NL = 547{ 548 'ToC_Title' => 'Inhoudsopgave', 549 'Overview_Title' => 'Korte inhoudsopgave', 550 'Index_Title' => 'Index', #Not sure ;-) 551 'About_Title' => 'No translation available!', #No translation available! 552 'Footnotes_Title' => 'No translation available!', #No translation available! 553 'See' => 'Zie', 554 'see' => 'zie', 555 'section' => 'sectie', 556}; 557 558$T2H_WORD_ES = 559{ 560 'ToC_Title' => 'índice General', 561 'Overview_Title' => 'Resumen del Contenido', 562 'Index_Title' => 'Index', #Not sure ;-) 563 'About_Title' => 'No translation available!', #No translation available! 564 'Footnotes_Title' => 'Fußnoten', 565 'See' => 'Véase', 566 'see' => 'véase', 567 'section' => 'sección', 568}; 569 570$T2H_WORD_NO = 571{ 572 'ToC_Title' => 'Innholdsfortegnelse', 573 'Overview_Title' => 'Kort innholdsfortegnelse', 574 'Index_Title' => 'Indeks', #Not sure ;-) 575 'About_Title' => 'No translation available!', #No translation available! 576 'Footnotes_Title' => 'No translation available!', 577 'See' => 'Se', 578 'see' => 'se', 579 'section' => 'avsnitt', 580}; 581 582$T2H_WORD_PT = 583{ 584 'ToC_Title' => 'Sumário', 585 'Overview_Title' => 'Breve Sumário', 586 'Index_Title' => 'Índice', #Not sure ;-) 587 'About_Title' => 'No translation available!', #No translation available! 588 'Footnotes_Title' => 'No translation available!', 589 'See' => 'Veja', 590 'see' => 'veja', 591 'section' => 'Seção', 592}; 593 594$T2H_WORDS = 595{ 596 'en' => $T2H_WORDS_EN, 597 'de' => $T2H_WORDS_DE, 598 'nl' => $T2H_WORDS_NL, 599 'es' => $T2H_WORDS_ES, 600 'no' => $T2H_WORDS_NO, 601 'pt' => $T2H_WORDS_PT 602}; 603 604@MONTH_NAMES_EN = 605( 606 'January', 'February', 'March', 'April', 'May', 607 'June', 'July', 'August', 'September', 'October', 608 'November', 'December' 609); 610 611@MONTH_NAMES_DE = 612( 613 'Januar', 'Februar', 'März', 'April', 'Mai', 614 'Juni', 'Juli', 'August', 'September', 'Oktober', 615 'November', 'Dezember' 616); 617 618@MONTH_NAMES_NL = 619( 620 'Januari', 'Februari', 'Maart', 'April', 'Mei', 621 'Juni', 'Juli', 'Augustus', 'September', 'Oktober', 622 'November', 'December' 623); 624 625@MONTH_NAMES_ES = 626( 627 'enero', 'febrero', 'marzo', 'abril', 'mayo', 628 'junio', 'julio', 'agosto', 'septiembre', 'octubre', 629 'noviembre', 'diciembre' 630); 631 632@MONTH_NAMES_NO = 633( 634 635 'januar', 'februar', 'mars', 'april', 'mai', 636 'juni', 'juli', 'august', 'september', 'oktober', 637 'november', 'desember' 638); 639 640@MONTH_NAMES_PT = 641( 642 'Janeiro', 'Fevereiro', 'Março', 'Abril', 'Maio', 643 'Junho', 'Julho', 'Agosto', 'Setembro', 'Outubro', 644 'Novembro', 'Dezembro' 645); 646 647 648$MONTH_NAMES = 649{ 650 'en' => \@MONTH_NAMES_EN, 651 'de' => \@MONTH_NAMES_DE, 652 'es' => \@MONTH_NAMES_ES, 653 'nl' => \@MONTH_NAMES_NL, 654 'no' => \@MONTH_NAMES_NO, 655 'pt' => \@MONTH_NAMES_PT 656}; 657######################################################################## 658# Control of Page layout: 659# You can make changes of the Page layout at two levels: 660# 1.) For small changes, it is often enough to change the value of 661# some global string/hash/array variables 662# 2.) For larger changes, reimplement one of the T2H_DEFAULT_<fnc>* routines, 663# give them another name, and assign them to the respective 664# $T2H_<fnc> variable. 665 666# As a general interface, the hashes T2H_HREF, T2H_NAME, T2H_NODE hold 667# href, html-name, node-name of 668# This -- current section (resp. html page) 669# Top -- top page ($T2H_TOP_FILE) 670# Contents -- Table of contents 671# Overview -- Short table of contents 672# Index -- Index page 673# About -- page which explain "navigation buttons" 674# First -- first node 675# Last -- last node 676# 677# Whether or not the following hash values are set, depends on the context 678# (all values are w.r.t. 'This' section) 679# Next -- next node of texinfo 680# Prev -- previous node of texinfo 681# Up -- up node of texinfo 682# Forward -- next node in reading order 683# Back -- previous node in reading order 684# FastForward -- if leave node, up and next, else next node 685# FastBackward-- if leave node, up and prev, else prev node 686# 687# Furthermore, the following global variabels are set: 688# $T2H_THISDOC{title} -- title as set by @setttile 689# $T2H_THISDOC{fulltitle} -- full title as set by @title... 690# $T2H_THISDOC{subtitle} -- subtitle as set by @subtitle 691# $T2H_THISDOC{author} -- author as set by @author 692# 693# and pointer to arrays of lines which need to be printed by t2h_print_lines 694# $T2H_OVERVIEW -- lines of short table of contents 695# $T2H_TOC -- lines of table of contents 696# $T2H_TOP -- lines of Top texinfo node 697# $T2H_THIS_SECTION -- lines of 'This' section 698 699# 700# There are the following subs which control the layout: 701# 702$T2H_print_section = \&T2H_DEFAULT_print_section; 703$T2H_print_Top_header = \&T2H_DEFAULT_print_Top_header; 704$T2H_print_Top_footer = \&T2H_DEFAULT_print_Top_footer; 705$T2H_print_Top = \&T2H_DEFAULT_print_Top; 706$T2H_print_Toc = \&T2H_DEFAULT_print_Toc; 707$T2H_print_Overview = \&T2H_DEFAULT_print_Overview; 708$T2H_print_Footnotes = \&T2H_DEFAULT_print_Footnotes; 709$T2H_print_About = \&T2H_DEFAULT_print_About; 710$T2H_print_misc_header = \&T2H_DEFAULT_print_misc_header; 711$T2H_print_misc_footer = \&T2H_DEFAULT_print_misc_footer; 712$T2H_print_misc = \&T2H_DEFAULT_print_misc; 713$T2H_print_chapter_header = \&T2H_DEFAULT_print_chapter_header; 714$T2H_print_chapter_footer = \&T2H_DEFAULT_print_chapter_footer; 715$T2H_print_page_head = \&T2H_DEFAULT_print_page_head; 716$T2H_print_page_foot = \&T2H_DEFAULT_print_page_foot; 717$T2H_print_head_navigation = \&T2H_DEFAULT_print_head_navigation; 718$T2H_print_foot_navigation = \&T2H_DEFAULT_print_foot_navigation; 719$T2H_button_icon_img = \&T2H_DEFAULT_button_icon_img; 720$T2H_print_navigation = \&T2H_DEFAULT_print_navigation; 721$T2H_about_body = \&T2H_DEFAULT_about_body; 722$T2H_print_frame = \&T2H_DEFAULT_print_frame; 723$T2H_print_toc_frame = \&T2H_DEFAULT_print_toc_frame; 724 725######################################################################## 726# Layout for html for every sections 727# 728sub T2H_DEFAULT_print_section 729{ 730 my $fh = shift; 731 local $T2H_BUTTONS = \@T2H_SECTION_BUTTONS; 732 &$T2H_print_head_navigation($fh) if $T2H_SECTION_NAVIGATION; 733 my $nw = t2h_print_lines($fh); 734 if ($T2H_SPLIT eq 'section' && $T2H_SECTION_NAVIGATION) 735 { 736 &$T2H_print_foot_navigation($fh, $nw); 737 } 738 else 739 { 740 print $fh '<HR SIZE="6">' . "\n"; 741 } 742} 743 744################################################################### 745# Layout of top-page I recommend that you use @ifnothtml, @ifhtml, 746# @html within the Top texinfo node to specify content of top-level 747# page. 748# 749# If you enclose everything in @ifnothtml, then title, subtitle, 750# author and overview is printed 751# T2H_HREF of Next, Prev, Up, Forward, Back are not defined 752# if $T2H_SPLIT then Top page is in its own html file 753sub T2H_DEFAULT_print_Top_header 754{ 755 &$T2H_print_page_head(@_) if $T2H_SPLIT; 756 t2h_print_label(@_); # this needs to be called, otherwise no label set 757 &$T2H_print_head_navigation(@_); 758} 759sub T2H_DEFAULT_print_Top_footer 760{ 761 &$T2H_print_foot_navigation(@_); 762 &$T2H_print_page_foot(@_) if $T2H_SPLIT; 763} 764sub T2H_DEFAULT_print_Top 765{ 766 my $fh = shift; 767 768 # for redefining navigation buttons use: 769 # local $T2H_BUTTONS = [...]; 770 # as it is, 'Top', 'Contents', 'Index', 'About' are printed 771 local $T2H_BUTTONS = \@T2H_MISC_BUTTONS; 772 &$T2H_print_Top_header($fh); 773 if ($T2H_THIS_SECTION) 774 { 775 # if top-level node has content, then print it with extra header 776 print $fh "<H1>$T2H_NAME{Top}</H1>" 777 unless ($T2H_HAS_TOP_HEADING); 778 t2h_print_lines($fh, $T2H_THIS_SECTION) 779 } 780 else 781 { 782 # top-level node is fully enclosed in @ifnothtml 783 # print fulltitle, subtitle, author, Overview 784 print $fh 785 "<CENTER>\n<H1>" . 786 join("</H1>\n<H1>", split(/\n/, $T2H_THISDOC{fulltitle})) . 787 "</H1>\n"; 788 print $fh "<H2>$T2H_THISDOC{subtitle}</H2>\n" if $T2H_THISDOC{subtitle}; 789 print $fh "$T2H_THISDOC{author}\n" if $T2H_THISDOC{author}; 790 print $fh <<EOT; 791</CENTER> 792<HR> 793<P></P> 794<H2> Overview: </H2> 795<BLOCKQUOTE> 796EOT 797 t2h_print_lines($fh, $T2H_OVERVIEW); 798 print $fh "</BLOCKQUOTE>\n"; 799 } 800 &$T2H_print_Top_footer($fh); 801} 802 803################################################################### 804# Layout of Toc, Overview, and Footnotes pages 805# By default, we use "normal" layout 806# T2H_HREF of Next, Prev, Up, Forward, Back, etc are not defined 807# use: local $T2H_BUTTONS = [...] to redefine navigation buttons 808sub T2H_DEFAULT_print_Toc 809{ 810 return &$T2H_print_misc(@_); 811} 812sub T2H_DEFAULT_print_Overview 813{ 814 return &$T2H_print_misc(@_); 815} 816sub T2H_DEFAULT_print_Footnotes 817{ 818 return &$T2H_print_misc(@_); 819} 820sub T2H_DEFAULT_print_About 821{ 822 return &$T2H_print_misc(@_); 823} 824 825sub T2H_DEFAULT_print_misc_header 826{ 827 &$T2H_print_page_head(@_) if $T2H_SPLIT; 828 # this needs to be called, otherwise, no labels are set 829 t2h_print_label(@_); 830 &$T2H_print_head_navigation(@_); 831} 832sub T2H_DEFAULT_print_misc_footer 833{ 834 &$T2H_print_foot_navigation(@_); 835 &$T2H_print_page_foot(@_) if $T2H_SPLIT; 836} 837sub T2H_DEFAULT_print_misc 838{ 839 my $fh = shift; 840 local $T2H_BUTTONS = \@T2H_MISC_BUTTONS; 841 &$T2H_print_misc_header($fh); 842 print $fh "<H1>$T2H_NAME{This}</H1>\n"; 843 t2h_print_lines($fh); 844 &$T2H_print_misc_footer($fh); 845} 846 847################################################################### 848# chapter_header and chapter_footer are only called if 849# T2H_SPLIT eq 'chapter' 850# chapter_header: after print_page_header, before print_section 851# chapter_footer: after print_section of last section, before print_page_footer 852# 853# If you want to get rid of navigation stuff after each section, 854# redefine print_section such that it does not call print_navigation, 855# and put print_navigation into print_chapter_header 856@T2H_CHAPTER_BUTTONS = 857 ( 858 'FastBack', 'FastForward', ' ', 859 ' ', ' ', ' ', ' ', 860 'Top', 'Contents', 'Index', 'About', 861 ); 862 863sub T2H_DEFAULT_print_chapter_header 864{ 865 # nothing to do there, by default 866 if (! $T2H_SECTION_NAVIGATION) 867 { 868 my $fh = shift; 869 local $T2H_BUTTONS = \@T2H_CHAPTER_BUTTONS; 870 &$T2H_print_navigation($fh); 871 print $fh "\n<HR SIZE=2>\n"; 872 } 873} 874 875sub T2H_DEFAULT_print_chapter_footer 876{ 877 local $T2H_BUTTONS = \@T2H_CHAPTER_BUTTONS; 878 &$T2H_print_navigation(@_); 879} 880################################################################### 881$T2H_TODAY = &pretty_date; # like "20 September 1993" 882 883sub pretty_date { 884 local($sec, $min, $hour, $mday, $mon, $year, $wday, $yday, $isdst); 885 886 ($sec, $min, $hour, $mday, $mon, $year, $wday, $yday, $isdst) = localtime(time); 887 $year += ($year < 70) ? 2000 : 1900; 888 # obachman: Let's do it as the Americans do 889 return($MONTH_NAMES->{$T2H_LANG}[$mon] . ", " . $mday . " " . $year); 890} 891 892 893################################################################### 894# Layout of standard header and footer 895# 896 897# Set the default body text, inserted between <BODY ... > 898###$T2H_BODYTEXT = 'LANG="EN" BGCOLOR="#FFFFFF" TEXT="#000000" LINK="#0000FF" VLINK="#800080" ALINK="#FF0000"'; 899$T2H_BODYTEXT = 'LANG="' . $T2H_LANG . '" BGCOLOR="#FFFFFF" TEXT="#000000" LINK="#0000FF" VLINK="#800080" ALINK="#FF0000"'; 900# text inserted after <BODY ...> 901$T2H_AFTER_BODY_OPEN = ''; 902#text inserted before </BODY> 903$T2H_PRE_BODY_CLOSE = ''; 904# this is used in footer 905$T2H_ADDRESS = "by <I>$T2H_USER</I> " if $T2H_USER; 906$T2H_ADDRESS .= "on <I>$T2H_TODAY</I>"; 907# this is added inside <HEAD></HEAD> after <TITLE> and some META NAME stuff 908# can be used for <style> <script>, <meta> tags 909$T2H_EXTRA_HEAD = ''; 910 911sub T2H_DEFAULT_print_page_head 912{ 913 my $fh = shift; 914 my $longtitle = "$T2H_THISDOC{title}: $T2H_NAME{This}"; 915 print $fh <<EOT; 916<HTML> 917$T2H_DOCTYPE 918<!-- Created on $T2H_TODAY by $THISPROG --> 919<!-- 920$T2H_AUTHORS 921--> 922<HEAD> 923<TITLE>$longtitle</TITLE> 924 925<META NAME="description" CONTENT="$longtitle"> 926<META NAME="keywords" CONTENT="$longtitle"> 927<META NAME="resource-type" CONTENT="document"> 928<META NAME="distribution" CONTENT="global"> 929<META NAME="Generator" CONTENT="$THISPROG"> 930$T2H_EXTRA_HEAD 931</HEAD> 932 933<BODY $T2H_BODYTEXT> 934$T2H_AFTER_BODY_OPEN 935EOT 936} 937 938sub T2H_DEFAULT_print_page_foot 939{ 940 my $fh = shift; 941 print $fh <<EOT; 942<BR> 943<FONT SIZE="-1"> 944This document was generated 945$T2H_ADDRESS 946using <A HREF="$T2H_HOMEPAGE"><I>texi2html</I></A> 947$T2H_PRE_BODY_CLOSE 948</BODY> 949</HTML> 950EOT 951} 952 953################################################################### 954# Layout of navigation panel 955 956# if this is set, then a vertical navigation panel is used 957$T2H_VERTICAL_HEAD_NAVIGATION = 0; 958sub T2H_DEFAULT_print_head_navigation 959{ 960 my $fh = shift; 961 if ($T2H_VERTICAL_HEAD_NAVIGATION) 962 { 963 print $fh <<EOT; 964<TABLE BORDER="0" CELLPADDING="0" CELLSPACING="0"> 965<TR VALIGN="TOP"> 966<TD ALIGN="LEFT"> 967EOT 968 } 969 &$T2H_print_navigation($fh, $T2H_VERTICAL_HEAD_NAVIGATION); 970 if ($T2H_VERTICAL_HEAD_NAVIGATION) 971 { 972 print $fh <<EOT; 973</TD> 974<TD ALIGN="LEFT"> 975EOT 976 } 977 elsif ($T2H_SPLIT eq 'section') 978 { 979 print $fh "<HR SIZE=1>\n"; 980 } 981} 982 983# Specifies the minimum page length required before a navigation panel 984# is placed at the bottom of a page (the default is that of latex2html) 985# T2H_THIS_WORDS_IN_PAGE holds number of words of current page 986$T2H_WORDS_IN_PAGE = 300; 987sub T2H_DEFAULT_print_foot_navigation 988{ 989 my $fh = shift; 990 my $nwords = shift; 991 if ($T2H_VERTICAL_HEAD_NAVIGATION) 992 { 993 print $fh <<EOT; 994</TD> 995</TR> 996</TABLE> 997EOT 998 } 999 print $fh "<HR SIZE=1>\n"; 1000 &$T2H_print_navigation($fh) if ($nwords >= $T2H_WORDS_IN_PAGE) 1001} 1002 1003###################################################################### 1004# navigation panel 1005# 1006# specify in this array which "buttons" should appear in which order 1007# in the navigation panel for sections; use ' ' for empty buttons (space) 1008@T2H_SECTION_BUTTONS = 1009 ( 1010 'Back', 'Forward', ' ', 'FastBack', 'Up', 'FastForward', 1011 ' ', ' ', ' ', ' ', 1012 'Top', 'Contents', 'Index', 'About', 1013 ); 1014 1015# buttons for misc stuff 1016@T2H_MISC_BUTTONS = ('Top', 'Contents', 'Index', 'About'); 1017 1018# insert here name of icon images for buttons 1019# Icons are used, if $T2H_ICONS and resp. value are set 1020%T2H_ACTIVE_ICONS = 1021 ( 1022 'Top', '', 1023 'Contents', '', 1024 'Overview', '', 1025 'Index', '', 1026 'Back', '', 1027 'FastBack', '', 1028 'Prev', '', 1029 'Up', '', 1030 'Next', '', 1031 'Forward', '', 1032 'FastForward', '', 1033 'About' , '', 1034 'First', '', 1035 'Last', '', 1036 ' ', '' 1037 ); 1038 1039# insert here name of icon images for these, if button is inactive 1040%T2H_PASSIVE_ICONS = 1041 ( 1042 'Top', '', 1043 'Contents', '', 1044 'Overview', '', 1045 'Index', '', 1046 'Back', '', 1047 'FastBack', '', 1048 'Prev', '', 1049 'Up', '', 1050 'Next', '', 1051 'Forward', '', 1052 'FastForward', '', 1053 'About', '', 1054 'First', '', 1055 'Last', '', 1056 ); 1057 1058# how to create IMG tag 1059sub T2H_DEFAULT_button_icon_img 1060{ 1061 my $button = shift; 1062 my $icon = shift; 1063 my $name = shift; 1064 return qq{<IMG SRC="$icon" BORDER="0" ALT="$button: $name" ALIGN="MIDDLE">}; 1065} 1066 1067# Names of text as alternative for icons 1068%T2H_NAVIGATION_TEXT = 1069 ( 1070 'Top', 'Top', 1071 'Contents', 'Contents', 1072 'Overview', 'Overview', 1073 'Index', 'Index', 1074 ' ', ' ', 1075 'Back', ' < ', 1076 'FastBack', ' << ', 1077 'Prev', 'Prev', 1078 'Up', ' Up ', 1079 'Next', 'Next', 1080 'Forward', ' > ', 1081 'FastForward', ' >> ', 1082 'About', ' ? ', 1083 'First', ' |< ', 1084 'Last', ' >| ' 1085 ); 1086 1087sub T2H_DEFAULT_print_navigation 1088{ 1089 my $fh = shift; 1090 my $vertical = shift; 1091 my $spacing = 1; 1092 print $fh "<TABLE CELLPADDING=$spacing CELLSPACING=$spacing BORDER=0>\n"; 1093 1094 print $fh "<TR>" unless $vertical; 1095 for $button (@$T2H_BUTTONS) 1096 { 1097 print $fh qq{<TR VALIGN="TOP" ALIGN="LEFT">\n} if $vertical; 1098 print $fh qq{<TD VALIGN="MIDDLE" ALIGN="LEFT">}; 1099 1100 if (ref($button) eq 'CODE') 1101 { 1102 &$button($fh, $vertical); 1103 } 1104 elsif ($button eq ' ') 1105 { # handle space button 1106 print $fh 1107 $T2H_ICONS && $T2H_ACTIVE_ICONS{' '} ? 1108 &$T2H_button_icon_img($button, $T2H_ACTIVE_ICONS{' '}) : 1109 $T2H_NAVIGATION_TEXT{' '}; 1110 next; 1111 } 1112 elsif ($T2H_HREF{$button}) 1113 { # button is active 1114 print $fh 1115 $T2H_ICONS && $T2H_ACTIVE_ICONS{$button} ? # use icon ? 1116 t2h_anchor('', $T2H_HREF{$button}, # yes 1117 &$T2H_button_icon_img($button, 1118 $T2H_ACTIVE_ICONS{$button}, 1119 $T2H_NAME{$button})) 1120 : # use text 1121 "[" . 1122 t2h_anchor('', $T2H_HREF{$button}, $T2H_NAVIGATION_TEXT{$button}) . 1123 "]"; 1124 } 1125 else 1126 { # button is passive 1127 print $fh 1128 $T2H_ICONS && $T2H_PASSIVE_ICONS{$button} ? 1129 &$T2H_button_icon_img($button, 1130 $T2H_PASSIVE_ICONS{$button}, 1131 $T2H_NAME{$button}) : 1132 1133 "[" . $T2H_NAVIGATION_TEXT{$button} . "]"; 1134 } 1135 print $fh "</TD>\n"; 1136 print $fh "</TR>\n" if $vertical; 1137 } 1138 print $fh "</TR>" unless $vertical; 1139 print $fh "</TABLE>\n"; 1140} 1141 1142###################################################################### 1143# Frames: this is from "Richard Y. Kim" <ryk@coho.net> 1144# Should be improved to be more conforming to other _print* functions 1145 1146sub T2H_DEFAULT_print_frame 1147{ 1148 my $fh = shift; 1149 print $fh <<EOT; 1150<HTML> 1151<HEAD><TITLE>$T2H_THISDOC{title}</TITLE></HEAD> 1152<FRAMESET cols="140,*"> 1153 <FRAME name=toc src="$docu_toc_frame_file"> 1154 <FRAME name=main src="$docu_doc"> 1155</FRAMESET> 1156</HTML> 1157EOT 1158} 1159 1160sub T2H_DEFAULT_print_toc_frame 1161{ 1162 my $fh = shift; 1163 &$T2H_print_page_head($fh); 1164 print $fh <<EOT; 1165<H2>Content</H2> 1166EOT 1167 print $fh map {s/HREF=/target=\"main\" HREF=/; $_;} @stoc_lines; 1168 print $fh "</BODY></HTML>\n"; 1169} 1170 1171###################################################################### 1172# About page 1173# 1174 1175# T2H_PRE_ABOUT might be a function 1176$T2H_PRE_ABOUT = <<EOT; 1177This document was generated $T2H_ADDRESS 1178using <A HREF="$T2H_HOMEPAGE"><I>texi2html</I></A> 1179<P></P> 1180EOT 1181$T2H_AFTER_ABOUT = ''; 1182 1183sub T2H_DEFAULT_about_body 1184{ 1185 my $about; 1186 if (ref($T2H_PRE_ABOUT) eq 'CODE') 1187 { 1188 $about = &$T2H_PRE_ABOUT(); 1189 } 1190 else 1191 { 1192 $about = $T2H_PRE_ABOUT; 1193 } 1194 $about .= <<EOT; 1195The buttons in the navigation panels have the following meaning: 1196<P></P> 1197<table border = "1"> 1198<TR> 1199<TH> Button </TH> 1200<TH> Name </TH> 1201<TH> Go to </TH> 1202<TH> From 1.2.3 go to</TH> 1203</TR> 1204EOT 1205 1206 for $button (@T2H_SECTION_BUTTONS) 1207 { 1208 next if $button eq ' ' || ref($button) eq 'CODE'; 1209 $about .= <<EOT; 1210<TR> 1211<TD ALIGN="CENTER"> 1212EOT 1213 $about .= 1214 ($T2H_ICONS && $T2H_ACTIVE_ICONS{$button} ? 1215 &$T2H_button_icon_img($button, $T2H_ACTIVE_ICONS{$button}) : 1216 " [" . $T2H_NAVIGATION_TEXT{$button} . "] "); 1217 $about .= <<EOT; 1218</TD> 1219<TD ALIGN="CENTER"> 1220$button 1221</TD> 1222<TD> 1223$T2H_BUTTONS_GOTO{$button} 1224</TD> 1225<TD> 1226$T2H_BUTTONS_EXAMPLE{$button} 1227</TD> 1228</TR> 1229EOT 1230 } 1231 1232 $about .= <<EOT; 1233</TABLE> 1234<P></P> 1235where the <STRONG> Example </STRONG> assumes that the current position 1236is at <STRONG> Subsubsection One-Two-Three </STRONG> of a document of 1237the following structure: 1238<UL> 1239<LI> 1. Section One </LI> 1240<UL> 1241<LI>1.1 Subsection One-One</LI> 1242<UL> 1243<LI> ... </LI> 1244</UL> 1245<LI>1.2 Subsection One-Two</LI> 1246<UL> 1247<LI>1.2.1 Subsubsection One-Two-One 1248</LI><LI>1.2.2 Subsubsection One-Two-Two 1249</LI><LI>1.2.3 Subsubsection One-Two-Three <STRONG> 1250<== Current Position </STRONG> 1251</LI><LI>1.2.4 Subsubsection One-Two-Four 1252</LI></UL> 1253<LI>1.3 Subsection One-Three</LI> 1254<UL> 1255<LI> ... </LI> 1256</UL> 1257<LI>1.4 Subsection One-Four</LI> 1258</UL> 1259</UL> 1260$T2H_AFTER_ABOUT 1261EOT 1262 return $about; 1263} 1264 1265 1266%T2H_BUTTONS_GOTO = 1267 ( 1268 'Top', 'cover (top) of document', 1269 'Contents', 'table of contents', 1270 'Overview', 'short table of contents', 1271 'Index', 'concept index', 1272 'Back', 'previous section in reading order', 1273 'FastBack', 'previous or up-and-previous section ', 1274 'Prev', 'previous section same level', 1275 'Up', 'up section', 1276 'Next', 'next section same level', 1277 'Forward', 'next section in reading order', 1278 'FastForward', 'next or up-and-next section', 1279 'About' , 'this page', 1280 'First', 'first section in reading order', 1281 'Last', 'last section in reading order', 1282 ); 1283 1284%T2H_BUTTONS_EXAMPLE = 1285( 1286 'Top', ' ', 1287 'Contents', ' ', 1288 'Overview', ' ', 1289 'Index', ' ', 1290 'Back', '1.2.2', 1291 'FastBack', '1.1', 1292 'Prev', '1.2.2', 1293 'Up', '1.2', 1294 'Next', '1.2.4', 1295 'Forward', '1.2.4', 1296 'FastForward', '1.3', 1297 'About', ' ', 1298 'First', '1.', 1299 'Last', '1.2.4', 1300); 1301 1302 1303###################################################################### 1304# from here on, its l2h init stuff 1305# 1306 1307## initialization for latex2html as for Singular manual generation 1308## obachman 3/99 1309 1310# 1311# Options controlling Titles, File-Names, Tracing and Sectioning 1312# 1313$TITLE = ''; 1314 1315$SHORTEXTN = 0; 1316 1317$LONG_TITLES = 0; 1318 1319$DESTDIR = ''; # should be overwritten by cmd-line argument 1320 1321$NO_SUBDIR = 0;# should be overwritten by cmd-line argument 1322 1323$PREFIX = ''; # should be overwritten by cmd-line argument 1324 1325$AUTO_PREFIX = 0; # this is needed, so that prefix settings are used 1326 1327$AUTO_LINK = 0; 1328 1329$SPLIT = 0; 1330 1331$MAX_LINK_DEPTH = 0; 1332 1333$TMP = ''; # should be overwritten by cmd-line argument 1334 1335$DEBUG = 0; 1336 1337$VERBOSE = 1; 1338 1339# 1340# Options controlling Extensions and Special Features 1341# 1342$HTML_VERSION = "3.2"; 1343 1344$TEXDEFS = 1; # we absolutely need that 1345 1346$EXTERNAL_FILE = ''; 1347 1348$SCALABLE_FONTS = 1; 1349 1350$NO_SIMPLE_MATH = 1; 1351 1352$LOCAL_ICONS = 1; 1353 1354$SHORT_INDEX = 0; 1355 1356$NO_FOOTNODE = 1; 1357 1358$ADDRESS = ''; 1359 1360$INFO = ''; 1361 1362# 1363# Switches controlling Image Generation 1364# 1365$ASCII_MODE = 0; 1366 1367$NOLATEX = 0; 1368 1369$EXTERNAL_IMAGES = 0; 1370 1371$PS_IMAGES = 0; 1372 1373$NO_IMAGES = 0; 1374 1375$IMAGES_ONLY = 0; 1376 1377$REUSE = 2; 1378 1379$ANTI_ALIAS = 1; 1380 1381$ANTI_ALIAS_TEXT = 1; 1382 1383# 1384#Switches controlling Navigation Panels 1385# 1386$NO_NAVIGATION = 1; 1387$ADDRESS = ''; 1388$INFO = 0; # 0 = do not make a "About this document..." section 1389 1390# 1391#Switches for Linking to other documents 1392# 1393# actuall -- we don't care 1394 1395$MAX_SPLIT_DEPTH = 0; # Stop making separate files at this depth 1396 1397$MAX_LINK_DEPTH = 0; # Stop showing child nodes at this depth 1398 1399$NOLATEX = 0; # 1 = do not pass unknown environments to Latex 1400 1401$EXTERNAL_IMAGES = 0; # 1 = leave the images outside the document 1402 1403$ASCII_MODE = 0; # 1 = do not use any icons or internal images 1404 1405# 1 = use links to external postscript images rather than inlined bitmap 1406# images. 1407$PS_IMAGES = 0; 1408$SHOW_SECTION_NUMBERS = 0; 1409 1410### Other global variables ############################################### 1411$CHILDLINE = ""; 1412 1413# This is the line width measured in pixels and it is used to right justify 1414# equations and equation arrays; 1415$LINE_WIDTH = 500; 1416 1417# Used in conjunction with AUTO_NAVIGATION 1418$WORDS_IN_PAGE = 300; 1419 1420# Affects ONLY the way accents are processed 1421$default_language = 'english'; 1422 1423# The value of this variable determines how many words to use in each 1424# title that is added to the navigation panel (see below) 1425# 1426$WORDS_IN_NAVIGATION_PANEL_TITLES = 0; 1427 1428# This number will determine the size of the equations, special characters, 1429# and anything which will be converted into an inlined image 1430# *except* "image generating environments" such as "figure", "table" 1431# or "minipage". 1432# Effective values are those greater than 0. 1433# Sensible values are between 0.1 - 4. 1434$MATH_SCALE_FACTOR = 1.5; 1435 1436# This number will determine the size of 1437# image generating environments such as "figure", "table" or "minipage". 1438# Effective values are those greater than 0. 1439# Sensible values are between 0.1 - 4. 1440$FIGURE_SCALE_FACTOR = 1.6; 1441 1442 1443# If both of the following two variables are set then the "Up" button 1444# of the navigation panel in the first node/page of a converted document 1445# will point to $EXTERNAL_UP_LINK. $EXTERNAL_UP_TITLE should be set 1446# to some text which describes this external link. 1447$EXTERNAL_UP_LINK = ""; 1448$EXTERNAL_UP_TITLE = ""; 1449 1450# If this is set then the resulting HTML will look marginally better if viewed 1451# with Netscape. 1452$NETSCAPE_HTML = 1; 1453 1454# Valid paper sizes are "letter", "legal", "a4","a3","a2" and "a0" 1455# Paper sizes has no effect other than in the time it takes to create inlined 1456# images and in whether large images can be created at all ie 1457# - larger paper sizes *MAY* help with large image problems 1458# - smaller paper sizes are quicker to handle 1459$PAPERSIZE = "a4"; 1460 1461# Replace "english" with another language in order to tell LaTeX2HTML that you 1462# want some generated section titles (eg "Table of Contents" or "References") 1463# to appear in a different language. Currently only "english" and "french" 1464# is supported but it is very easy to add your own. See the example in the 1465# file "latex2html.config" 1466$TITLES_LANGUAGE = "english"; 1467 14681; # This must be the last non-comment line 1469 1470# End File texi2html.init 1471###################################################################### 1472 1473 1474require "$ENV{T2H_HOME}/texi2html.init" 1475 if ($0 =~ /\.pl$/ && 1476 -e "$ENV{T2H_HOME}/texi2html.init" && -r "$ENV{T2H_HOME}/texi2html.init"); 1477 1478#+++############################################################################ 1479# # 1480# Initialization # 1481# Pasted content of File $(srcdir)/MySimple.pm: Command-line processing # 1482# # 1483#---############################################################################ 1484 1485# leave this within comments, and keep the require statement 1486# This way, you can directly run texi2html.pl, if $ENV{T2H_HOME}/texi2html.init 1487# exists. 1488 1489# 1490package Getopt::MySimple; 1491 1492# Name: 1493# Getopt::MySimple. 1494# 1495# Documentation: 1496# POD-style (incomplete) documentation is in file MySimple.pod 1497# 1498# Tabs: 1499# 4 spaces || die. 1500# 1501# Author: 1502# Ron Savage rpsavage@ozemail.com.au. 1503# 1.00 19-Aug-97 Initial version. 1504# 1.10 13-Oct-97 Add arrays of switches (eg '=s@'). 1505# 1.20 3-Dec-97 Add 'Help' on a per-switch basis. 1506# 1.30 11-Dec-97 Change 'Help' to 'verbose'. Make all hash keys lowercase. 1507# 1.40 10-Nov-98 Change width of help report. Restructure tests. 1508# 1-Jul-00 Modifications for Texi2html 1509 1510# -------------------------------------------------------------------------- 1511# Locally modified by obachman (Display type instead of env, order by cmp) 1512# $Id: texi2html 7792 2004-06-07 09:07:27Z korli $ 1513 1514# use strict; 1515# no strict 'refs'; 1516 1517use vars qw(@EXPORT @EXPORT_OK @ISA); 1518use vars qw($fieldWidth $opt $VERSION); 1519 1520use Exporter(); 1521use Getopt::Long; 1522 1523@ISA = qw(Exporter); 1524@EXPORT = qw(); 1525@EXPORT_OK = qw($opt); # An alias for $self -> {'opt'}. 1526 1527# -------------------------------------------------------------------------- 1528 1529$fieldWidth = 20; 1530$VERSION = '1.41'; 1531 1532# -------------------------------------------------------------------------- 1533 1534sub byOrder 1535{ 1536 my($self) = @_; 1537 1538 return uc($a) cmp (uc($b)); 1539} 1540 1541# -------------------------------------------------------------------------- 1542 1543sub dumpOptions 1544{ 1545 my($self) = @_; 1546 1547 print 'Option', ' ' x ($fieldWidth - length('Option') ), "Value\n"; 1548 1549 for (sort byOrder keys(%{$self -> {'opt'} }) ) 1550 { 1551 print "-$_", ' ' x ($fieldWidth - (1 + length) ), "${$self->{'opt'} }{$_}\n"; 1552 } 1553 1554 print "\n"; 1555 1556} # End of dumpOptions. 1557 1558# -------------------------------------------------------------------------- 1559# Return: 1560# 0 -> Error. 1561# 1 -> Ok. 1562 1563sub getOptions 1564{ 1565 push(@_, 0) if ($#_ == 2); # Default for $ignoreCase is 0. 1566 push(@_, 1) if ($#_ == 3); # Default for $helpThenExit is 1. 1567 1568 my($self, $default, $helpText, $versionText, 1569 $helpThenExit, $versionThenExit, $ignoreCase) = @_; 1570 1571 $helpThenExit = 1 unless (defined($helpThenExit)); 1572 $versionThenExit = 1 unless (defined($versionThenExit)); 1573 $ignoreCase = 0 unless (defined($ignoreCase)); 1574 1575 $self -> {'default'} = $default; 1576 $self -> {'helpText'} = $helpText; 1577 $self -> {'versionText'} = $versionText; 1578 $Getopt::Long::ignorecase = $ignoreCase; 1579 1580 unless (defined($self -> {'default'}{'help'})) 1581 { 1582 $self -> {'default'}{'help'} = 1583 { 1584 type => ':i', 1585 default => '', 1586 linkage => sub {$self->helpOptions($_[1]); exit (0) if $helpThenExit;}, 1587 verbose => "print help and exit" 1588 }; 1589 } 1590 1591 unless (defined($self -> {'default'}{'version'})) 1592 { 1593 $self -> {'default'}{'version'} = 1594 { 1595 type => '', 1596 default => '', 1597 linkage => sub {print $self->{'versionText'}; exit (0) if versionTheExit;}, 1598 verbose => "print version and exit" 1599 }; 1600 } 1601 1602 for (keys(%{$self -> {'default'} }) ) 1603 { 1604 my $type = ${$self -> {'default'} }{$_}{'type'}; 1605 push(@{$self -> {'type'} }, "$_$type"); 1606 $self->{'opt'}->{$_} = ${$self -> {'default'} }{$_}{'linkage'} 1607 if ${$self -> {'default'} }{$_}{'linkage'}; 1608 } 1609 1610 my($result) = &GetOptions($self -> {'opt'}, @{$self -> {'type'} }); 1611 1612 return $result unless $result; 1613 1614 for (keys(%{$self -> {'default'} }) ) 1615 { 1616 if (! defined(${$self -> {'opt'} }{$_})) #{ 1617 { 1618 ${$self -> {'opt'} }{$_} = ${$self -> {'default'} }{$_}{'default'}; 1619 } 1620 } 1621 1622 $result; 1623} # End of getOptions. 1624 1625# -------------------------------------------------------------------------- 1626 1627sub helpOptions 1628{ 1629 my($self) = shift; 1630 my($noHelp) = shift; 1631 $noHelp = 0 unless $noHelp; 1632 my($optwidth, $typewidth, $defaultwidth, $maxlinewidth, $valind, $valwidth) 1633 = (10, 5, 9, 78, 4, 11); 1634 1635 print "$self->{'helpText'}" if ($self -> {'helpText'}); 1636 1637 print ' Option', ' ' x ($optwidth - length('Option') -1 ), 1638 'Type', ' ' x ($typewidth - length('Type') + 1), 1639 'Default', ' ' x ($defaultwidth - length('Default') ), 1640 "Description\n"; 1641 1642 for (sort byOrder keys(%{$self -> {'default'} }) ) 1643 { 1644 my($line, $help, $option, $val); 1645 $option = $_; 1646 next if ${$self->{'default'} }{$_}{'noHelp'} && ${$self->{'default'} }{$_}{'noHelp'} > $noHelp; 1647 $line = " -$_ " . ' ' x ($optwidth - (2 + length) ) . 1648 "${$self->{'default'} }{$_}{'type'} ". 1649 ' ' x ($typewidth - (1+length(${$self -> {'default'} }{$_}{'type'}) )); 1650 1651 $val = ${$self->{'default'} }{$_}{'linkage'}; 1652 if ($val) 1653 { 1654 if (ref($val) eq 'SCALAR') 1655 { 1656 $val = $$val; 1657 } 1658 else 1659 { 1660 $val = ''; 1661 } 1662 } 1663 else 1664 { 1665 $val = ${$self->{'default'} }{$_}{'default'}; 1666 } 1667 $line .= "$val "; 1668 $line .= ' ' x ($optwidth + $typewidth + $defaultwidth + 1 - length($line)); 1669 1670 if (defined(${$self -> {'default'} }{$_}{'verbose'}) && 1671 ${$self -> {'default'} }{$_}{'verbose'} ne '') 1672 { 1673 $help = "${$self->{'default'} }{$_}{'verbose'}"; 1674 } 1675 else 1676 { 1677 $help = ' '; 1678 } 1679 if ((length("$line") + length($help)) < $maxlinewidth) 1680 { 1681 print $line , $help, "\n"; 1682 } 1683 else 1684 { 1685 print $line, "\n", ' ' x $valind, $help, "\n"; 1686 } 1687 for $val (sort byOrder keys(%{${$self->{'default'}}{$option}{'values'}})) 1688 { 1689 print ' ' x ($valind + 2); 1690 print $val, ' ', ' ' x ($valwidth - length($val) - 2); 1691 print ${$self->{'default'}}{$option}{'values'}{$val}, "\n"; 1692 } 1693 } 1694 1695 print <<EOT; 1696Note: 'Options' may be abbreviated. 'Type' specifications mean: 1697 <none>| ! no argument: variable is set to 1 on -foo (or, to 0 on -nofoo) 1698 =s | :s mandatory (or, optional) string argument 1699 =i | :i mandatory (or, optional) integer argument 1700EOT 1701} # End of helpOptions. 1702 1703#------------------------------------------------------------------- 1704 1705sub new 1706{ 1707 my($class) = @_; 1708 my($self) = {}; 1709 $self -> {'default'} = {}; 1710 $self -> {'helpText'} = ''; 1711 $self -> {'opt'} = {}; 1712 $opt = $self -> {'opt'}; # An alias for $self -> {'opt'}. 1713 $self -> {'type'} = (); 1714 1715 return bless $self, $class; 1716 1717} # End of new. 1718 1719# -------------------------------------------------------------------------- 1720 17211; 1722 1723# End MySimple.pm 1724 1725require "$ENV{T2H_HOME}/MySimple.pm" 1726 if ($0 =~ /\.pl$/ && 1727 -e "$ENV{T2H_HOME}/texi2html.init" && -r "$ENV{T2H_HOME}/texi2html.init"); 1728 1729package main; 1730 1731#+++############################################################################ 1732# # 1733# Constants # 1734# # 1735#---############################################################################ 1736 1737$DEBUG_TOC = 1; 1738$DEBUG_INDEX = 2; 1739$DEBUG_BIB = 4; 1740$DEBUG_GLOSS = 8; 1741$DEBUG_DEF = 16; 1742$DEBUG_HTML = 32; 1743$DEBUG_USER = 64; 1744$DEBUG_L2H = 128; 1745 1746 1747$BIBRE = '\[[\w\/-]+\]'; # RE for a bibliography reference 1748$FILERE = '[\/\w.+-]+'; # RE for a file name 1749$VARRE = '[^\s\{\}]+'; # RE for a variable name 1750$NODERE = '[^,:]+'; # RE for a node name 1751$NODESRE = '[^:]+'; # RE for a list of node names 1752 1753$ERROR = "***"; # prefix for errors 1754$WARN = "**"; # prefix for warnings 1755 1756 # program home page 1757$PROTECTTAG = "_ThisIsProtected_"; # tag to recognize protected sections 1758 1759$CHAPTEREND = "<!-- End chapter -->\n"; # to know where a chpater ends 1760$SECTIONEND = "<!-- End section -->\n"; # to know where section ends 1761$TOPEND = "<!-- End top -->\n"; # to know where top ends 1762 1763 1764 1765# 1766# pre-defined indices 1767# 1768$index_properties = 1769{ 1770 'c' => { name => 'cp'}, 1771 'f' => { name => 'fn', code => 1}, 1772 'v' => { name => 'vr', code => 1}, 1773 'k' => { name => 'ky', code => 1}, 1774 'p' => { name => 'pg', code => 1}, 1775 't' => { name => 'tp', code => 1} 1776}; 1777 1778 1779%predefined_index = ( 1780 'cp', 'c', 1781 'fn', 'f', 1782 'vr', 'v', 1783 'ky', 'k', 1784 'pg', 'p', 1785 'tp', 't', 1786 ); 1787 1788# 1789# valid indices 1790# 1791%valid_index = ( 1792 'c', 1, 1793 'f', 1, 1794 'v', 1, 1795 'k', 1, 1796 'p', 1, 1797 't', 1, 1798 ); 1799 1800# 1801# texinfo section names to level 1802# 1803%sec2level = ( 1804 'top', 0, 1805 'chapter', 1, 1806 'unnumbered', 1, 1807 'majorheading', 1, 1808 'chapheading', 1, 1809 'appendix', 1, 1810 'section', 2, 1811 'unnumberedsec', 2, 1812 'heading', 2, 1813 'appendixsec', 2, 1814 'appendixsection', 2, 1815 'subsection', 3, 1816 'unnumberedsubsec', 3, 1817 'subheading', 3, 1818 'appendixsubsec', 3, 1819 'subsubsection', 4, 1820 'unnumberedsubsubsec', 4, 1821 'subsubheading', 4, 1822 'appendixsubsubsec', 4, 1823 ); 1824 1825# 1826# accent map, TeX command to ISO name 1827# 1828%accent_map = ( 1829 '"', 'uml', 1830 '~', 'tilde', 1831 '^', 'circ', 1832 '`', 'grave', 1833 '\'', 'acute', 1834 ); 1835 1836# 1837# texinfo "simple things" (@foo) to HTML ones 1838# 1839%simple_map = ( 1840 # cf. makeinfo.c 1841 "*", "<BR>", # HTML+ 1842 " ", " ", 1843 "\t", " ", 1844 "-", "­", # soft hyphen 1845 "\n", "\n", 1846 "|", "", 1847 'tab', '<\/TD><TD>', 1848 # spacing commands 1849 ":", "", 1850 "!", "!", 1851 "?", "?", 1852 ".", ".", 1853 "-", "", 1854 ); 1855 1856# 1857# texinfo "things" (@foo{}) to HTML ones 1858# 1859%things_map = ( 1860 'TeX', 'TeX', 1861 'br', '<P>', # paragraph break 1862 'bullet', '*', 1863 'copyright', '(C)', 1864 'dots', '<small>...<\/small>', 1865 'enddots', '<small>....<\/small>', 1866 'equiv', '==', 1867 'error', 'error-->', 1868 'expansion', '==>', 1869 'minus', '-', 1870 'point', '-!-', 1871 'print', '-|', 1872 'result', '=>', 1873 'today', $T2H_TODAY, 1874 'aa', 'å', 1875 'AA', 'Å', 1876 'ae', 'æ', 1877 'oe', 'œ', 1878 'AE', 'Æ', 1879 'OE', 'Œ', 1880 'o', 'ø', 1881 'O', 'Ø', 1882 'ss', 'ß', 1883 'l', '\/l', 1884 'L', '\/L', 1885 'exclamdown', '¡', 1886 'questiondown', '¿', 1887 'pounds', '£' 1888 ); 1889 1890# 1891# texinfo styles (@foo{bar}) to HTML ones 1892# 1893%style_map = ( 1894 'acronym', '&do_acronym', 1895 'asis', '', 1896 'b', 'B', 1897 'cite', 'CITE', 1898 'code', 'CODE', 1899 'command', 'CODE', 1900 'ctrl', '&do_ctrl', # special case 1901 'dfn', 'EM', # DFN tag is illegal in the standard 1902 'dmn', '', # useless 1903 'email', '&do_email', # insert a clickable email address 1904 'emph', 'EM', 1905 'env', 'CODE', 1906 'file', '"TT', # will put quotes, cf. &apply_style 1907 'i', 'I', 1908 'kbd', 'KBD', 1909 'key', 'KBD', 1910 'math', '&do_math', 1911 'option', '"SAMP', # will put quotes, cf. &apply_style 1912 'r', '', # unsupported 1913 'samp', '"SAMP', # will put quotes, cf. &apply_style 1914 'sc', '&do_sc', # special case 1915 'strong', 'STRONG', 1916 't', 'TT', 1917 'titlefont', '', # useless 1918 'uref', '&do_uref', # insert a clickable URL 1919 'url', '&do_url', # insert a clickable URL 1920 'var', 'VAR', 1921 'w', '', # unsupported 1922 'H', '&do_accent', 1923 'dotaccent', '&do_accent', 1924 'ringaccent','&do_accent', 1925 'tieaccent', '&do_accent', 1926 'u','&do_accent', 1927 'ubaraccent','&do_accent', 1928 'udotaccent','&do_accent', 1929 'v', '&do_accent', 1930 ',', '&do_accent', 1931 'dotless', '&do_accent' 1932 ); 1933 1934# 1935# texinfo format (@foo/@end foo) to HTML ones 1936# 1937%format_map = ( 1938 'quotation', 'BLOCKQUOTE', 1939 # lists 1940 'itemize', 'UL', 1941 'enumerate', 'OL', 1942 # poorly supported 1943 'flushleft', 'PRE', 1944 'flushright', 'PRE', 1945 ); 1946 1947# 1948# an eval of these $complex_format_map->{what}->[0] yields beginning 1949# an eval of these $complex_format_map->{what}->[1] yieleds end 1950$complex_format_map = 1951{ 1952 example => 1953 [ 1954 q{"<TABLE><tr>$T2H_EXAMPLE_INDENT_CELL<td class=example><pre>"}, 1955 q{'</pre></td></tr></table>'} 1956 ], 1957 smallexample => 1958 [ 1959 q{"<TABLE><tr>$T2H_SMALL_EXAMPLE_INDENT_CELL<td class=smallexample><FONT SIZE=$T2H_SMALL_FONT_SIZE><pre>"}, 1960 q{'</FONT></pre></td></tr></table>'} 1961 ], 1962 display => 1963 [ 1964 q{"<TABLE><tr>$T2H_EXAMPLE_INDENT_CELL<td class=display><pre " . 'style="font-family: serif">'}, 1965 q{'</pre></td></tr></table>'} 1966 ], 1967 smalldisplay => 1968 [ 1969 q{"<TABLE><tr>$T2H_SMALL_EXAMPLE_INDENT_CELL<td class=smalldisplay><FONT SIZE=$T2H_SMALL_FONT_SIZE><pre " . 'style="font-family: serif">'}, 1970 q{'</pre></FONT></td></tr></table>'} 1971 ] 1972}; 1973 1974$complex_format_map->{lisp} = $complex_format_map->{example}; 1975$complex_format_map->{smalllisp} = $complex_format_map->{smallexample}; 1976$complex_format_map->{format} = $complex_format_map->{display}; 1977$complex_format_map->{smallformat} = $complex_format_map->{smalldisplay}; 1978 1979# 1980# texinfo definition shortcuts to real ones 1981# 1982%def_map = ( 1983 # basic commands 1984 'deffn', 0, 1985 'defvr', 0, 1986 'deftypefn', 0, 1987 'deftypevr', 0, 1988 'defcv', 0, 1989 'defop', 0, 1990 'deftp', 0, 1991 # basic x commands 1992 'deffnx', 0, 1993 'defvrx', 0, 1994 'deftypefnx', 0, 1995 'deftypevrx', 0, 1996 'defcvx', 0, 1997 'defopx', 0, 1998 'deftpx', 0, 1999 # shortcuts 2000 'defun', 'deffn Function', 2001 'defmac', 'deffn Macro', 2002 'defspec', 'deffn {Special Form}', 2003 'defvar', 'defvr Variable', 2004 'defopt', 'defvr {User Option}', 2005 'deftypefun', 'deftypefn Function', 2006 'deftypevar', 'deftypevr Variable', 2007 'defivar', 'defcv {Instance Variable}', 2008 'deftypeivar', 'defcv {Instance Variable}', # NEW: FIXME 2009 'defmethod', 'defop Method', 2010 'deftypemethod', 'defop Method', # NEW:FIXME 2011 # x shortcuts 2012 'defunx', 'deffnx Function', 2013 'defmacx', 'deffnx Macro', 2014 'defspecx', 'deffnx {Special Form}', 2015 'defvarx', 'defvrx Variable', 2016 'defoptx', 'defvrx {User Option}', 2017 'deftypefunx', 'deftypefnx Function', 2018 'deftypevarx', 'deftypevrx Variable', 2019 'defivarx', 'defcvx {Instance Variable}', 2020 'defmethodx', 'defopx Method', 2021 ); 2022 2023# 2024# things to skip 2025# 2026%to_skip = ( 2027 # comments 2028 'c', 1, 2029 'comment', 1, 2030 'ifnotinfo', 1, 2031 'ifnottex', 1, 2032 'ifhtml', 1, 2033 'end ifhtml', 1, 2034 'end ifnotinfo', 1, 2035 'end ifnottex', 1, 2036 # useless 2037 'detailmenu', 1, 2038 'direntry', 1, 2039 'contents', 1, 2040 'shortcontents', 1, 2041 'summarycontents', 1, 2042 'footnotestyle', 1, 2043 'end ifclear', 1, 2044 'end ifset', 1, 2045 'titlepage', 1, 2046 'end titlepage', 1, 2047 # unsupported commands (formatting) 2048 'afourpaper', 1, 2049 'cropmarks', 1, 2050 'finalout', 1, 2051 'headings', 1, 2052 'sp', 1, 2053 'need', 1, 2054 'page', 1, 2055 'setchapternewpage', 1, 2056 'everyheading', 1, 2057 'everyfooting', 1, 2058 'evenheading', 1, 2059 'evenfooting', 1, 2060 'oddheading', 1, 2061 'oddfooting', 1, 2062 'smallbook', 1, 2063 'vskip', 1, 2064 'filbreak', 1, 2065 'paragraphindent', 1, 2066 # unsupported formats 2067 'cartouche', 1, 2068 'end cartouche', 1, 2069 'group', 1, 2070 'end group', 1, 2071 ); 2072 2073#+++############################################################################ 2074# # 2075# Argument parsing, initialisation # 2076# # 2077#---############################################################################ 2078 2079# 2080# flush stdout and stderr after every write 2081# 2082select(STDERR); 2083$| = 1; 2084select(STDOUT); 2085$| = 1; 2086 2087 2088%value = (); # hold texinfo variables, see also -D 2089$use_bibliography = 1; 2090$use_acc = 1; 2091 2092# 2093# called on -init-file 2094sub LoadInitFile 2095{ 2096 my $init_file = shift; 2097 # second argument is value of options 2098 $init_file = shift; 2099 if (-f $init_file) 2100 { 2101 print "# reading initialization file from $init_file\n" 2102 if ($T2H_VERBOSE); 2103 require($init_file); 2104 } 2105 else 2106 { 2107 print "$ERROR Error: can't read init file $int_file\n"; 2108 $init_file = ''; 2109 } 2110} 2111 2112# 2113# called on -lang 2114sub SetDocumentLanguage 2115{ 2116 my $lang = shift; 2117 if (! exists($T2H_WORDS->{$lang})) 2118 { 2119 warn "$ERROR: Language specs for '$lang' do not exists. Reverting to '" . 2120 ($T2H_LANG ? T2H_LANG : "en") . "'\n"; 2121 } 2122 else 2123 { 2124 print "# using '$lang' as document language\n" if ($T2H_VERBOSE); 2125 $T2H_LANG = $lang; 2126 } 2127} 2128 2129## 2130## obsolete cmd line options 2131## 2132$T2H_OBSOLETE_OPTIONS -> {'no-section_navigation'} = 2133{ 2134 type => '!', 2135 linkage => sub {$main::T2H_SECTION_NAVIGATION = 0;}, 2136 verbose => 'obsolete, use -nosec_nav', 2137 noHelp => 2, 2138}; 2139$T2H_OBSOLETE_OPTIONS -> {use_acc} = 2140{ 2141 type => '!', 2142 linkage => \$use_acc, 2143 verbose => 'obsolete', 2144 noHelp => 2 2145}; 2146$T2H_OBSOLETE_OPTIONS -> {expandinfo} = 2147{ 2148 type => '!', 2149 linkage => sub {$main::T2H_EXPAND = 'info';}, 2150 verbose => 'obsolete, use "-expand info" instead', 2151 noHelp => 2, 2152}; 2153$T2H_OBSOLETE_OPTIONS -> {expandtex} = 2154{ 2155 type => '!', 2156 linkage => sub {$main::T2H_EXPAND = 'tex';}, 2157 verbose => 'obsolete, use "-expand tex" instead', 2158 noHelp => 2, 2159}; 2160$T2H_OBSOLETE_OPTIONS -> {monolithic} = 2161{ 2162 type => '!', 2163 linkage => sub {$main::T2H_SPLIT = '';}, 2164 verbose => 'obsolete, use "-split no" instead', 2165 noHelp => 2 2166}; 2167$T2H_OBSOLETE_OPTIONS -> {split_node} = 2168{ 2169 type => '!', 2170 linkage => sub{$main::T2H_SPLIT = 'section';}, 2171 verbose => 'obsolete, use "-split section" instead', 2172 noHelp => 2, 2173}; 2174$T2H_OBSOLETE_OPTIONS -> {split_chapter} = 2175{ 2176 type => '!', 2177 linkage => sub{$main::T2H_SPLIT = 'chapter';}, 2178 verbose => 'obsolete, use "-split chapter" instead', 2179 noHelp => 2, 2180}; 2181$T2H_OBSOLETE_OPTIONS -> {no_verbose} = 2182{ 2183 type => '!', 2184 linkage => sub {$main::T2H_VERBOSE = 0;}, 2185 verbose => 'obsolete, use -noverbose instead', 2186 noHelp => 2, 2187}; 2188$T2H_OBSOLETE_OPTIONS -> {output_file} = 2189{ 2190 type => '=s', 2191 linkage => sub {$main::T2H_OUT = @_[1]; $T2H_SPLIT = '';}, 2192 verbose => 'obsolete, use -out_file instead', 2193 noHelp => 2 2194}; 2195 2196$T2H_OBSOLETE_OPTIONS -> {section_navigation} = 2197{ 2198 type => '!', 2199 linkage => \$T2H_SECTION_NAVIGATION, 2200 verbose => 'obsolete, use -sec_nav instead', 2201 noHelp => 2, 2202}; 2203 2204$T2H_OBSOLETE_OPTIONS -> {verbose} = 2205{ 2206 type => '!', 2207 linkage => \$T2H_VERBOSE, 2208 verbose => 'obsolete, use -Verbose instead', 2209 noHelp => 2 2210}; 2211 2212# read initialzation from $sysconfdir/texi2htmlrc or $HOME/.texi2htmlrc 2213my $home = $ENV{HOME}; 2214defined($home) or $home = ''; 2215foreach $i ('/usr/local/etc/texi2htmlrc', "$home/.texi2htmlrc") { 2216 if (-f $i) { 2217 print "# reading initialization file from $i\n" 2218 if ($T2H_VERBOSE); 2219 require($i); 2220 } 2221} 2222 2223 2224#+++############################################################################ 2225# # 2226# parse command-line options 2227# # 2228#---############################################################################ 2229$T2H_USAGE_TEXT = <<EOT; 2230Usage: texi2html [OPTIONS] TEXINFO-FILE 2231Translates Texinfo source documentation to HTML. 2232EOT 2233$T2H_FAILURE_TEXT = <<EOT; 2234Try 'texi2html -help' for usage instructions. 2235EOT 2236$options = new Getopt::MySimple; 2237 2238# some older version of GetOpt::Long don't have 2239# Getopt::Long::Configure("pass_through") 2240eval {Getopt::Long::Configure("pass_through");}; 2241$Configure_failed = $@ && <<EOT; 2242**WARNING: Parsing of obsolete command-line options could have failed. 2243 Consider to use only documented command-line options (run 2244 'texi2html -help 2' for a complete list) or upgrade to perl 2245 version 5.005 or higher. 2246EOT 2247 2248if (! $options->getOptions($T2H_OPTIONS, $T2H_USAGE_TEXT, "$THISVERSION\n")) 2249{ 2250 print $Configure_failed if $Configure_failed; 2251 die $T2H_FAILURE_TEXT; 2252} 2253 2254if (@ARGV > 1) 2255{ 2256 eval {Getopt::Long::Configure("no_pass_through");}; 2257 if (! $options->getOptions($T2H_OBSOLETE_OPTIONS, $T2H_USAGE_TEXT, "$THISVERSION\n")) 2258 { 2259 print $Configure_failed if $Configure_failed; 2260 die $T2H_FAILURE_TEXT; 2261 } 2262} 2263 2264if ($T2H_CHECK) { 2265 die "Need file to check\n$T2H_FAILURE_TEXT" unless @ARGV > 0; 2266 ✓ 2267 exit; 2268} 2269 2270#+++############################################################################ 2271# # 2272# evaluation of cmd line options 2273# # 2274#---############################################################################ 2275 2276if ($T2H_EXPAND eq 'info') 2277{ 2278 $to_skip{'ifinfo'} = 1; 2279 $to_skip{'end ifinfo'} = 1; 2280} 2281elsif ($T2H_EXPAND eq 'tex') 2282{ 2283 $to_skip{'iftex'} = 1; 2284 $to_skip{'end iftex'} = 1; 2285 2286} 2287 2288$T2H_INVISIBLE_MARK = '<IMG SRC="invisible.xbm">' if $T2H_INVISIBLE_MARK eq 'xbm'; 2289 2290# 2291# file name buisness 2292# 2293die "Need exactly one file to translate\n$T2H_FAILURE_TEXT" unless @ARGV == 1; 2294$docu = shift(@ARGV); 2295if ($docu =~ /.*\//) { 2296 chop($docu_dir = $&); 2297 $docu_name = $'; 2298} else { 2299 $docu_dir = '.'; 2300 $docu_name = $docu; 2301} 2302unshift(@T2H_INCLUDE_DIRS, $docu_dir); 2303$docu_name =~ s/\.te?x(i|info)?$//; # basename of the document 2304$docu_name = $T2H_PREFIX if ($T2H_PREFIX); 2305 2306# subdir 2307if ($T2H_SUBDIR && ! $T2H_OUT) 2308{ 2309 $T2H_SUBDIR =~ s|/*$||; 2310 unless (-d "$T2H_SUBDIR" && -w "$T2H_SUBDIR") 2311 { 2312 if ( mkdir($T2H_SUBDIR, oct(755))) 2313 { 2314 print "# created directory $T2H_SUBDIR\n" if ($T2H_VERBOSE); 2315 } 2316 else 2317 { 2318 warn "$ERROR can't create directory $T2H_SUBDIR. Put results into current directory\n"; 2319 $T2H_SUBDIR = ''; 2320 } 2321 } 2322} 2323 2324if ($T2H_SUBDIR && ! $T2H_OUT) 2325{ 2326 $docu_rdir = "$T2H_SUBDIR/"; 2327 print "# putting result files into directory $docu_rdir\n" if ($T2H_VERBOSE); 2328} 2329else 2330{ 2331 if ($T2H_OUT && $T2H_OUT =~ m|(.*)/|) 2332 { 2333 $docu_rdir = "$1/"; 2334 print "# putting result files into directory $docu_rdir\n" if ($T2H_VERBOSE); 2335 } 2336 else 2337 { 2338 print "# putting result files into current directory \n" if ($T2H_VERBOSE); 2339 $docu_rdir = ''; 2340 } 2341} 2342 2343# extension 2344if ($T2H_SHORTEXTN) 2345{ 2346 $docu_ext = "htm"; 2347} 2348else 2349{ 2350 $docu_ext = "html"; 2351} 2352if ($T2H_TOP_FILE =~ /\..*$/) 2353{ 2354 $T2H_TOP_FILE = $`.".$docu_ext"; 2355} 2356 2357# result files 2358if (! $T2H_OUT && ($T2H_SPLIT =~ /section/i || $T2H_SPLIT =~ /node/i)) 2359{ 2360 $T2H_SPLIT = 'section'; 2361} 2362elsif (! $T2H_OUT && $T2H_SPLIT =~ /chapter/i) 2363{ 2364 $T2H_SPLIT = 'chapter' 2365} 2366else 2367{ 2368 undef $T2H_SPLIT; 2369} 2370 2371$docu_doc = "$docu_name.$docu_ext"; # document's contents 2372$docu_doc_file = "$docu_rdir$docu_doc"; 2373if ($T2H_SPLIT) 2374{ 2375 $docu_toc = $T2H_TOC_FILE || "${docu_name}_toc.$docu_ext"; # document's table of contents 2376 $docu_stoc = "${docu_name}_ovr.$docu_ext"; # document's short toc 2377 $docu_foot = "${docu_name}_fot.$docu_ext"; # document's footnotes 2378 $docu_about = "${docu_name}_abt.$docu_ext"; # about this document 2379 $docu_top = $T2H_TOP_FILE || $docu_doc; 2380} 2381else 2382{ 2383 if ($T2H_OUT) 2384 { 2385 $docu_doc = $T2H_OUT; 2386 $docu_doc =~ s|.*/||; 2387 } 2388 $docu_toc = $docu_foot = $docu_stoc = $docu_about = $docu_top = $docu_doc; 2389} 2390 2391$docu_toc_file = "$docu_rdir$docu_toc"; 2392$docu_stoc_file = "$docu_rdir$docu_stoc"; 2393$docu_foot_file = "$docu_rdir$docu_foot"; 2394$docu_about_file = "$docu_rdir$docu_about"; 2395$docu_top_file = "$docu_rdir$docu_top"; 2396 2397$docu_frame_file = "$docu_rdir${docu_name}_frame.$docu_ext"; 2398$docu_toc_frame_file = "$docu_rdir${docu_name}_toc_frame.$docu_ext"; 2399 2400# 2401# variables 2402# 2403$value{'html'} = 1; # predefine html (the output format) 2404$value{'texi2html'} = $THISVERSION; # predefine texi2html (the translator) 2405# _foo: internal to track @foo 2406foreach ('_author', '_title', '_subtitle', 2407 '_settitle', '_setfilename', '_shorttitle') { 2408 $value{$_} = ''; # prevent -w warnings 2409} 2410%node2sec = (); # node to section name 2411%sec2node = (); # section to node name 2412%sec2number = (); # section to number 2413%number2sec = (); # number to section 2414%idx2node = (); # index keys to node 2415%node2href = (); # node to HREF 2416%node2next = (); # node to next 2417%node2prev = (); # node to prev 2418%node2up = (); # node to up 2419%bib2href = (); # bibliography reference to HREF 2420%gloss2href = (); # glossary term to HREF 2421@sections = (); # list of sections 2422%tag2pro = (); # protected sections 2423 2424# 2425# initial indexes 2426# 2427$bib_num = 0; 2428$foot_num = 0; 2429$gloss_num = 0; 2430$idx_num = 0; 2431$sec_num = 0; 2432$doc_num = 0; 2433$html_num = 0; 2434 2435# 2436# can I use ISO8879 characters? (HTML+) 2437# 2438if ($T2H_USE_ISO) { 2439 $things_map{'bullet'} = "•"; 2440 $things_map{'copyright'} = "©"; 2441 $things_map{'dots'} = "…"; 2442 $things_map{'equiv'} = "≡"; 2443 $things_map{'expansion'} = "→"; 2444 $things_map{'point'} = "∗"; 2445 $things_map{'result'} = "⇒"; 2446} 2447 2448# 2449# read texi2html extensions (if any) 2450# 2451$extensions = 'texi2html.ext'; # extensions in working directory 2452if (-f $extensions) { 2453 print "# reading extensions from $extensions\n" if $T2H_VERBOSE; 2454 require($extensions); 2455} 2456($progdir = $0) =~ s/[^\/]+$//; 2457if ($progdir && ($progdir ne './')) { 2458 $extensions = "${progdir}texi2html.ext"; # extensions in texi2html directory 2459 if (-f $extensions) { 2460 print "# reading extensions from $extensions\n" if $T2H_VERBOSE; 2461 require($extensions); 2462 } 2463} 2464 2465 2466print "# reading from $docu\n" if $T2H_VERBOSE; 2467 2468######################################################################### 2469# 2470# latex2html stuff 2471# 2472# latex2html conversions consist of three stages: 2473# 1) ToLatex: Put "latex" code into a latex file 2474# 2) ToHtml: Use latex2html to generate corresponding html code and images 2475# 3) FromHtml: Extract generated code and images from latex2html run 2476# 2477 2478########################## 2479# default settings 2480# 2481 2482# defaults for files and names 2483 2484sub l2h_Init 2485{ 2486 local($root) = @_; 2487 2488 return 0 unless ($root); 2489 2490 $l2h_name = "${root}_l2h"; 2491 2492 $l2h_latex_file = "$docu_rdir${l2h_name}.tex"; 2493 $l2h_cache_file = "${docu_rdir}l2h_cache.pm"; 2494 $T2H_L2H_L2H = "latex2html" unless ($T2H_L2H_L2H); 2495 2496 # destination dir -- generated images are put there, should be the same 2497 # as dir of enclosing html document -- 2498 $l2h_html_file = "$docu_rdir${l2h_name}.html"; 2499 $l2h_prefix = "${l2h_name}_"; 2500 return 1; 2501} 2502 2503 2504########################## 2505# 2506# First stage: Generation of Latex file 2507# Initialize with: l2h_InitToLatex 2508# Add content with: l2h_ToLatex($text) --> HTML placeholder comment 2509# Finish with: l2h_FinishToLatex 2510# 2511 2512$l2h_latex_preample = <<EOT; 2513% This document was automatically generated by the l2h extenstion of texi2html 2514% DO NOT EDIT !!! 2515\\documentclass{article} 2516\\usepackage{html} 2517\\begin{document} 2518EOT 2519 2520$l2h_latex_closing = <<EOT; 2521\\end{document} 2522EOT 2523 2524# return used latex 1, if l2h could be initalized properly, 0 otherwise 2525sub l2h_InitToLatex 2526{ 2527 %l2h_to_latex = (); 2528 unless ($T2H_L2H_SKIP) 2529 { 2530 unless (open(L2H_LATEX, ">$l2h_latex_file")) 2531 { 2532 warn "$ERROR Error l2h: Can't open latex file '$latex_file' for writing\n"; 2533 return 0; 2534 } 2535 print "# l2h: use ${l2h_latex_file} as latex file\n" if ($T2H_VERBOSE); 2536 print L2H_LATEX $l2h_latex_preample; 2537 } 2538 # open database for caching 2539 l2h_InitCache(); 2540 $l2h_latex_count = 0; 2541 $l2h_to_latex_count = 0; 2542 $l2h_cached_count = 0; 2543 return 1; 2544} 2545 2546# print text (1st arg) into latex file (if not already there), return 2547# HTML commentary which can be later on replaced by the latex2html 2548# generated text 2549sub l2h_ToLatex 2550{ 2551 my($text) = @_; 2552 my($count); 2553 2554 $l2h_to_latex_count++; 2555 $text =~ s/(\s*)$//; 2556 2557 # try whether we can cache it 2558 my $cached_text = l2h_FromCache($text); 2559 if ($cached_text) 2560 { 2561 $l2h_cached_count++; 2562 return $cached_text; 2563 } 2564 2565 # try whether we have text already on things to do 2566 unless ($count = $l2h_to_latex{$text}) 2567 { 2568 $count = $l2h_latex_count; 2569 $l2h_latex_count++; 2570 $l2h_to_latex{$text} = $count; 2571 $l2h_to_latex[$count] = $text; 2572 unless ($T2H_L2H_SKIP) 2573 { 2574 print L2H_LATEX "\\begin{rawhtml}\n"; 2575 print L2H_LATEX "<!-- l2h_begin ${l2h_name} ${count} -->\n"; 2576 print L2H_LATEX "\\end{rawhtml}\n"; 2577 2578 print L2H_LATEX "$text\n"; 2579 2580 print L2H_LATEX "\\begin{rawhtml}\n"; 2581 print L2H_LATEX "<!-- l2h_end ${l2h_name} ${count} -->\n"; 2582 print L2H_LATEX "\\end{rawhtml}\n"; 2583 } 2584 } 2585 return "<!-- l2h_replace ${l2h_name} ${count} -->"; 2586} 2587 2588# print closing into latex file and close it 2589sub l2h_FinishToLatex 2590{ 2591 local ($reused); 2592 2593 $reused = $l2h_to_latex_count - $l2h_latex_count - $l2h_cached_count; 2594 unless ($T2H_L2H_SKIP) 2595 { 2596 print L2H_LATEX $l2h_latex_closing; 2597 close(L2H_LATEX); 2598 } 2599 print "# l2h: finished to latex ($l2h_cached_count cached, $reused reused, $l2h_latex_count contents)\n" if ($T2H_VERBOSE); 2600 unless ($l2h_latex_count) 2601 { 2602 l2h_Finish(); 2603 return 0; 2604 } 2605 return 1; 2606} 2607 2608################################### 2609# Second stage: Use latex2html to generate corresponding html code and images 2610# 2611# l2h_ToHtml([$l2h_latex_file, [$l2h_html_dir]]): 2612# Call latex2html on $l2h_latex_file 2613# Put images (prefixed with $l2h_name."_") and html file(s) in $l2h_html_dir 2614# Return 1, on success 2615# 0, otherwise 2616# 2617sub l2h_ToHtml 2618{ 2619 local($call, $ext, $root, $dotbug); 2620 2621 if ($T2H_L2H_SKIP) 2622 { 2623 print "# l2h: skipping latex2html run\n" if ($T2H_VERBOSE); 2624 return 1; 2625 } 2626 2627 # Check for dot in directory where dvips will work 2628 if ($T2H_L2H_TMP) 2629 { 2630 if ($T2H_L2H_TMP =~ /\./) 2631 { 2632 warn "$ERROR Warning l2h: l2h_tmp dir contains a dot. Use /tmp, instead\n"; 2633 $dotbug = 1; 2634 } 2635 } 2636 else 2637 { 2638 if (&getcwd =~ /\./) 2639 { 2640 warn "$ERROR Warning l2h: current dir contains a dot. Use /tmp as l2h_tmp dir \n"; 2641 $dotbug = 1; 2642 } 2643 } 2644 # fix it, if necessary and hope that it works 2645 $T2H_L2H_TMP = "/tmp" if ($dotbug); 2646 2647 $call = $T2H_L2H_L2H; 2648 # use init file, if specified 2649 $call = $call . " -init_file " . $init_file if ($init_file && -f $init_file); 2650 # set output dir 2651 $call .= ($docu_rdir ? " -dir $docu_rdir" : " -no_subdir"); 2652 # use l2h_tmp, if specified 2653 $call = $call . " -tmp $T2H_L2H_TMP" if ($T2H_L2H_TMP); 2654 # options we want to be sure of 2655 $call = $call ." -address 0 -info 0 -split 0 -no_navigation -no_auto_link"; 2656 $call = $call ." -prefix ${l2h_prefix} $l2h_latex_file"; 2657 2658 print "# l2h: executing '$call'\n" if ($T2H_VERBOSE); 2659 if (system($call)) 2660 { 2661 warn "l2h ***Error: '${call}' did not succeed\n"; 2662 return 0; 2663 } 2664 else 2665 { 2666 print "# l2h: latex2html finished successfully\n" if ($T2H_VERBOSE); 2667 return 1; 2668 } 2669} 2670 2671# this is directly pasted over from latex2html 2672sub getcwd { 2673 local($_) = `pwd`; 2674 2675 die "'pwd' failed (out of memory?)\n" 2676 unless length; 2677 chop; 2678 $_; 2679} 2680 2681 2682########################## 2683# Third stage: Extract generated contents from latex2html run 2684# Initialize with: l2h_InitFromHtml 2685# open $l2h_html_file for reading 2686# reads in contents into array indexed by numbers 2687# return 1, on success -- 0, otherwise 2688# Extract Html code with: l2h_FromHtml($text) 2689# replaces in $text all previosuly inserted comments by generated html code 2690# returns (possibly changed) $text 2691# Finish with: l2h_FinishFromHtml 2692# closes $l2h_html_dir/$l2h_name.".$docu_ext" 2693 2694sub l2h_InitFromHtml 2695{ 2696 local($h_line, $h_content, $count, %l2h_img); 2697 2698 if (! open(L2H_HTML, "<${l2h_html_file}")) 2699 { 2700 print "$ERROR Error l2h: Can't open ${l2h_html_file} for reading\n"; 2701 return 0; 2702 } 2703 print "# l2h: use ${l2h_html_file} as html file\n" if ($T2H_VERBOSE); 2704 2705 $l2h_html_count = 0; 2706 2707 while ($h_line = <L2H_HTML>) 2708 { 2709 if ($h_line =~ /^<!-- l2h_begin $l2h_name ([0-9]+) -->/) 2710 { 2711 $count = $1; 2712 $h_content = ""; 2713 while ($h_line = <L2H_HTML>) 2714 { 2715 if ($h_line =~ /^<!-- l2h_end $l2h_name $count -->/) 2716 { 2717 chomp $h_content; 2718 chomp $h_content; 2719 $l2h_html_count++; 2720 $h_content = l2h_ToCache($count, $h_content); 2721 $l2h_from_html[$count] = $h_content; 2722 $h_content = ''; 2723 last; 2724 } 2725 $h_content = $h_content.$h_line; 2726 } 2727 if ($hcontent) 2728 { 2729 print "$ERROR Warning l2h: l2h_end $l2h_name $count not found\n" 2730 if ($T2H_VERBOSE); 2731 close(L2H_HTML); 2732 return 0; 2733 } 2734 } 2735 } 2736 print "# l2h: Got $l2h_html_count of $l2h_latex_count html contents\n" 2737 if ($T2H_VERBOSE); 2738 2739 close(L2H_HTML); 2740 return 1; 2741} 2742 2743sub l2h_FromHtml 2744{ 2745 local($text) = @_; 2746 local($done, $to_do, $count); 2747 2748 $to_do = $text; 2749 2750 while ($to_do =~ /([^\000]*)<!-- l2h_replace $l2h_name ([0-9]+) -->([^\000]*)/) 2751 { 2752 $to_do = $1; 2753 $count = $2; 2754 $done = $3.$done; 2755 2756 $done = "<!-- l2h_end $l2h_name $count -->".$done 2757 if ($T2H_DEBUG & $DEBUG_L2H); 2758 2759 $done = &l2h_ExtractFromHtml($count) . $done; 2760 2761 $done = "<!-- l2h_begin $l2h_name $count -->".$done 2762 if ($T2H_DEBUG & $DEBUG_L2H); 2763 } 2764 return $to_do.$done; 2765} 2766 2767 2768sub l2h_ExtractFromHtml 2769{ 2770 local($count) = @_; 2771 2772 return $l2h_from_html[$count] if ($l2h_from_html[$count]); 2773 2774 if ($count >= 0 && $count < $l2h_latex_count) 2775 { 2776 # now we are in trouble 2777 local($l_l2h, $_); 2778 2779 $l2h_extract_error++; 2780 print "$ERROR l2h: can't extract content $count from html\n" 2781 if ($T2H_VERBOSE); 2782 # try simple (ordinary) substition (without l2h) 2783 $l_l2h = $T2H_L2H; 2784 $T2H_L2H = 0; 2785 $_ = $l2h_to_latex{$count}; 2786 $_ = &substitute_style($_); 2787 &unprotect_texi; 2788 $_ = "<!-- l2h: ". __LINE__ . " use texi2html -->" . $_ 2789 if ($T2H_DEBUG & $DEBUG_L2H); 2790 $T2H_L2H = $l_l2h; 2791 return $_; 2792 } 2793 else 2794 { 2795 # now we have been incorrectly called 2796 $l2h_range_error++; 2797 print "$ERROR l2h: Request of $count content which is out of valide range [0,$l2h_latex_count)\n"; 2798 return "<!-- l2h: ". __LINE__ . " out of range count $count -->" 2799 if ($T2H_DEBUG & $DEBUG_L2H); 2800 return "<!-- l2h: out of range count $count -->"; 2801 } 2802} 2803 2804sub l2h_FinishFromHtml 2805{ 2806 if ($T2H_VERBOSE) 2807 { 2808 if ($l2h_extract_error + $l2h_range_error) 2809 { 2810 print "# l2h: finished from html ($l2h_extract_error extract and $l2h_range_error errors)\n"; 2811 } 2812 else 2813 { 2814 print "# l2h: finished from html (no errors)\n"; 2815 } 2816 } 2817} 2818 2819sub l2h_Finish 2820{ 2821 l2h_StoreCache(); 2822 if ($T2H_L2H_CLEAN) 2823 { 2824 print "# l2h: removing temporary files generated by l2h extension\n" 2825 if $T2H_VERBOSE; 2826 while (<"$docu_rdir$l2h_name"*>) 2827 { 2828 unlink $_; 2829 } 2830 } 2831 print "# l2h: Finished\n" if $T2H_VERBOSE; 2832 return 1; 2833} 2834 2835############################## 2836# stuff for l2h caching 2837# 2838 2839# I tried doing this with a dbm data base, but it did not store all 2840# keys/values. Hence, I did as latex2html does it 2841sub l2h_InitCache 2842{ 2843 if (-r "$l2h_cache_file") 2844 { 2845 my $rdo = do "$l2h_cache_file"; 2846 warn("$ERROR l2h Error: could not load $docu_rdir$l2h_cache_file: $@\n") 2847 unless ($rdo); 2848 } 2849} 2850 2851sub l2h_StoreCache 2852{ 2853 return unless $l2h_latex_count; 2854 2855 my ($key, $value); 2856 open(FH, ">$l2h_cache_file") || return warn"$ERROR l2h Error: could not open $docu_rdir$l2h_cache_file for writing: $!\n"; 2857 2858 2859 while (($key, $value) = each %l2h_cache) 2860 { 2861 # escape stuff 2862 $key =~ s|/|\\/|g; 2863 $key =~ s|\\\\/|\\/|g; 2864 # weird, a \ at the end of the key results in an error 2865 # maybe this also broke the dbm database stuff 2866 $key =~ s|\\$|\\\\|; 2867 $value =~ s/\|/\\\|/g; 2868 $value =~ s/\\\\\|/\\\|/g; 2869 $value =~ s|\\\\|\\\\\\\\|g; 2870 print FH "\n\$l2h_cache_key = q/$key/;\n"; 2871 print FH "\$l2h_cache{\$l2h_cache_key} = q|$value|;\n"; 2872 } 2873 print FH "1;"; 2874 close(FH); 2875} 2876 2877# return cached html, if it exists for text, and if all pictures 2878# are there, as well 2879sub l2h_FromCache 2880{ 2881 my $text = shift; 2882 my $cached = $l2h_cache{$text}; 2883 if ($cached) 2884 { 2885 while ($cached =~ m/SRC="(.*?)"/g) 2886 { 2887 unless (-e "$docu_rdir$1") 2888 { 2889 return undef; 2890 } 2891 } 2892 return $cached; 2893 } 2894 return undef; 2895} 2896 2897# insert generated html into cache, move away images, 2898# return transformed html 2899$maximage = 1; 2900sub l2h_ToCache 2901{ 2902 my $count = shift; 2903 my $content = shift; 2904 my @images = ($content =~ /SRC="(.*?)"/g); 2905 my ($src, $dest); 2906 2907 for $src (@images) 2908 { 2909 $dest = $l2h_img{$src}; 2910 unless ($dest) 2911 { 2912 my $ext; 2913 if ($src =~ /.*\.(.*)$/ && $1 ne $docu_ext) 2914 { 2915 $ext = $1; 2916 } 2917 else 2918 { 2919 warn "$ERROR: L2h image $src has invalid extension\n"; 2920 next; 2921 } 2922 while (-e "$docu_rdir${docu_name}_$maximage.$ext") { $maximage++;} 2923 $dest = "${docu_name}_$maximage.$ext"; 2924 system("cp -f $docu_rdir$src $docu_rdir$dest"); 2925 $l2h_img{$src} = $dest; 2926 unlink "$docu_rdir$src" unless ($DEBUG & DEBUG_L2H); 2927 } 2928 $content =~ s/$src/$dest/g; 2929 } 2930 $l2h_cache{$l2h_to_latex[$count]} = $content; 2931 return $content; 2932} 2933 2934 2935#+++############################################################################ 2936# # 2937# Pass 1: read source, handle command, variable, simple substitution # 2938# # 2939#---############################################################################ 2940 2941@lines = (); # whole document 2942@toc_lines = (); # table of contents 2943@stoc_lines = (); # table of contents 2944$curlevel = 0; # current level in TOC 2945$node = ''; # current node name 2946$node_next = ''; # current node next name 2947$node_prev = ''; # current node prev name 2948$node_up = ''; # current node up name 2949$in_table = 0; # am I inside a table 2950$table_type = ''; # type of table ('', 'f', 'v', 'multi') 2951@tables = (); # nested table support 2952$in_bibliography = 0; # am I inside a bibliography 2953$in_glossary = 0; # am I inside a glossary 2954$in_top = 0; # am I inside the top node 2955$has_top = 0; # did I see a top node? 2956$has_top_command = 0; # did I see @top for automatic pointers? 2957$in_pre = 0; # am I inside a preformatted section 2958$in_list = 0; # am I inside a list 2959$in_html = 0; # am I inside an HTML section 2960$first_line = 1; # is it the first line 2961$dont_html = 0; # don't protect HTML on this line 2962$deferred_ref = ''; # deferred reference for indexes 2963@html_stack = (); # HTML elements stack 2964$html_element = ''; # current HTML element 2965&html_reset; 2966%macros = (); # macros 2967 2968# init l2h 2969$T2H_L2H = &l2h_Init($docu_name) if ($T2H_L2H); 2970$T2H_L2H = &l2h_InitToLatex if ($T2H_L2H); 2971 2972# build code for simple substitutions 2973# the maps used (%simple_map and %things_map) MUST be aware of this 2974# watch out for regexps, / and escaped characters! 2975$subst_code = ''; 2976foreach (keys(%simple_map)) { 2977 ($re = $_) =~ s/(\W)/\\$1/g; # protect regexp chars 2978 $subst_code .= "s/\\\@$re/$simple_map{$_}/g;\n"; 2979} 2980foreach (keys(%things_map)) { 2981 $subst_code .= "s/\\\@$_\\{\\}/$things_map{$_}/g;\n"; 2982} 2983if ($use_acc) { 2984 # accentuated characters 2985 foreach (keys(%accent_map)) { 2986 if ($_ eq "`") { 2987 $subst_code .= "s/$;3"; 2988 } elsif ($_ eq "'") { 2989 $subst_code .= "s/$;4"; 2990 } else { 2991 $subst_code .= "s/\\\@\\$_"; 2992 } 2993 $subst_code .= "([a-z])/&\${1}$accent_map{$_};/gi;\n"; 2994 } 2995} 2996eval("sub simple_substitutions { $subst_code }"); 2997 2998&init_input; 2999INPUT_LINE: while ($_ = &next_line) { 3000 # 3001 # remove \input on the first lines only 3002 # 3003 if ($first_line) { 3004 next if /^\\input/; 3005 $first_line = 0; 3006 } 3007 # non-@ substitutions cf. texinfmt.el 3008 # 3009 # parse texinfo tags 3010 # 3011 $tag = ''; 3012 $end_tag = ''; 3013 if (/^\s*\@end\s+(\w+)\b/) { 3014 $end_tag = $1; 3015 } elsif (/^\s*\@(\w+)\b/) { 3016 $tag = $1; 3017 } 3018 # 3019 # handle @html / @end html 3020 # 3021 if ($in_html) { 3022 if ($end_tag eq 'html') { 3023 $in_html = 0; 3024 } else { 3025 $tag2pro{$in_html} .= $_; 3026 } 3027 next; 3028 } elsif ($tag eq 'html') { 3029 $in_html = $PROTECTTAG . ++$html_num; 3030 push(@lines, $in_html); 3031 next; 3032 } 3033 3034 # 3035 # try to remove inlined comments 3036 # syntax from tex-mode.el comment-start-skip 3037 # 3038 s/((^|[^\@])(\@\@)*)\@c(omment | |\{|$).*/$1/; 3039 3040# Sometimes I use @c right at the end of a line ( to suppress the line feed ) 3041# s/((^|[^\@])(\@\@)*)\@c(omment)?$/$1/; 3042# s/((^|[^\@])(\@\@)*)\@c(omment)? .*/$1/; 3043# s/(.*)\@c{.*?}(.*)/$1$2/; 3044# s/(.*)\@comment{.*?}(.*)/$1$2/; 3045# s/^(.*)\@c /$1/; 3046# s/^(.*)\@comment /$1/; 3047 3048 ############################################################# 3049 # value substitution before macro expansion, so that 3050 # it works in macro arguments 3051 s/\@value{($VARRE)}/$value{$1}/eg; 3052 3053 ############################################################# 3054 # macro substitution 3055 while (/\@(\w+)/g) 3056 { 3057 if (exists($macros->{$1})) 3058 { 3059 my $before = $`; 3060 my $name = $1; 3061 my $after = $'; 3062 my @args; 3063 my $args; 3064 if ($after =~ /^\s*{(.*?[^\\])}(.*)/) 3065 { 3066 $args = $1; 3067 $after = $2; 3068 } 3069 elsif (@{$macros->{$name}->{Args}} == 1) 3070 { 3071 $args = $after; 3072 $args =~ s/^\s*//; 3073 $args =~ s/\s*$//; 3074 $after = ''; 3075 } 3076 $args =~ s|\\\\|\\|g; 3077 $args =~ s|\\{|{|g; 3078 $args =~ s|\\}|}|g; 3079 if (@{$macros->{$name}->{Args}} > 1) 3080 { 3081 $args =~ s/(^|[^\\]),/$1$;/g ; 3082 $args =~ s|\\,|,|g; 3083 @args = split(/$;\s*/, $args) if (@{$macros->{$name}->{Args}} > 1); 3084 } 3085 else 3086 { 3087 $args =~ s|\\,|,|g; 3088 @args = ($args); 3089 } 3090 my $macrobody = $macros->{$name}->{Body}; 3091 for ($i=0; $i<=$#args; $i++) 3092 { 3093 $macrobody =~ s|\\$macros->{$name}->{Args}->[$i]\\|$args[$i]|g; 3094 } 3095 $macrobody =~ s|\\\\|\\|g; 3096 $_ = $before . $macrobody . $after; 3097 unshift @input_spool, map {$_ = $_."\n"} split(/\n/, $_); 3098 next INPUT_LINE; 3099 } 3100 } # 3101 3102 3103 # 3104 # try to skip the line 3105 # 3106 if ($end_tag) { 3107 $in_titlepage = 0 if $end_tag eq 'titlepage'; 3108 next if $to_skip{"end $end_tag"}; 3109 } elsif ($tag) { 3110 $in_titlepage = 1 if $tag eq 'titlepage'; 3111 next if $to_skip{$tag}; 3112 last if $tag eq 'bye'; 3113 } 3114 if ($in_top) { 3115 # parsing the top node 3116 if ($tag eq 'node' || 3117 ($sec2level{$tag} && $tag !~ /unnumbered/ && $tag !~ /heading/)) 3118 { 3119 # no more in top 3120 $in_top = 0; 3121 push(@lines, $TOPEND); 3122 } 3123 } 3124 unless ($in_pre) { 3125 s/``/\"/g; 3126 s/''/\"/g; 3127 s/([\w ])---([\w ])/$1--$2/g; 3128 } 3129 # 3130 # analyze the tag 3131 # 3132 if ($tag) { 3133 # skip lines 3134 &skip_until($tag), next if $tag eq 'ignore'; 3135 &skip_until($tag), next if $tag eq 'ifnothtml'; 3136 if ($tag eq 'ifinfo') 3137 { 3138 &skip_until($tag), next unless $T2H_EXPAND eq 'info'; 3139 } 3140 if ($tag eq 'iftex') 3141 { 3142 &skip_until($tag), next unless $T2H_EXPAND eq 'tex'; 3143 } 3144 if ($tag eq 'tex') 3145 { 3146 # add to latex2html file 3147 if ($T2H_EXPAND eq 'tex' && $T2H_L2H && ! $in_pre) 3148 { 3149 # add space to the end -- tex(i2dvi) does this, as well 3150 push(@lines, &l2h_ToLatex(&string_until($tag) . " ")); 3151 } 3152 else 3153 { 3154 &skip_until($tag); 3155 } 3156 next; 3157 } 3158 if ($tag eq 'titlepage') 3159 { 3160 next; 3161 } 3162 # handle special tables 3163 if ($tag =~ /^(|f|v|multi)table$/) { 3164 $table_type = $1; 3165 $tag = 'table'; 3166 } 3167 # special cases 3168 if ($tag eq 'top' || ($tag eq 'node' && /^\@node\s+top\s*,/i)) { 3169 $in_top = 1; 3170 $has_top = 1; 3171 $has_top_command = 1 if $tag eq 'top'; 3172 @lines = (); # ignore all lines before top (title page garbage) 3173 next; 3174 } elsif ($tag eq 'node') { 3175 if ($in_top) 3176 { 3177 $in_top = 0; 3178 push(@lines, $TOPEND); 3179 } 3180 warn "$ERROR Bad node line: $_" unless $_ =~ /^\@node\s$NODESRE$/o; 3181 # request of "Richard Y. Kim" <ryk@ap.com> 3182 s/^\@node\s+//; 3183 $_ = &protect_html($_); # if node contains '&' for instance 3184 ($node, $node_next, $node_prev, $node_up) = split(/,/); 3185 &normalise_node($node); 3186 &normalise_node($node_next); 3187 &normalise_node($node_prev); 3188 &normalise_node($node_up); 3189 $node =~ /\"/ ? 3190 push @lines, &html_debug("<A NAME='$node'></A>\n", __LINE__) : 3191 push @lines, &html_debug("<A NAME=\"$node\"></A>\n", __LINE__); 3192 next; 3193 } elsif ($tag eq 'include') { 3194 if (/^\@include\s+($FILERE)\s*$/o) { 3195 $file = LocateIncludeFile($1); 3196 if ($file && -e $file) { 3197 &open($file); 3198 print "# including $file\n" if $T2H_VERBOSE; 3199 } else { 3200 warn "$ERROR Can't find $1, skipping"; 3201 } 3202 } else { 3203 warn "$ERROR Bad include line: $_"; 3204 } 3205 next; 3206 } elsif ($tag eq 'ifclear') { 3207 if (/^\@ifclear\s+($VARRE)\s*$/o) { 3208 next unless defined($value{$1}); 3209 &skip_until($tag); 3210 } else { 3211 warn "$ERROR Bad ifclear line: $_"; 3212 } 3213 next; 3214 } elsif ($tag eq 'ifset') { 3215 if (/^\@ifset\s+($VARRE)\s*$/o) { 3216 next if defined($value{$1}); 3217 &skip_until($tag); 3218 } else { 3219 warn "$ERROR Bad ifset line: $_"; 3220 } 3221 next; 3222 } elsif ($tag eq 'menu') { 3223 unless ($T2H_SHOW_MENU) { 3224 &skip_until($tag); 3225 next; 3226 } 3227 &html_push_if($tag); 3228 push(@lines, &html_debug('', __LINE__)); 3229 } elsif ($format_map{$tag}) { 3230 $in_pre = 1 if $format_map{$tag} eq 'PRE'; 3231 &html_push_if($format_map{$tag}); 3232 push(@lines, &html_debug('', __LINE__)); 3233 $in_list++ if $format_map{$tag} eq 'UL' || $format_map{$tag} eq 'OL' ; 3234# push(@lines, &debug("<BLOCKQUOTE>\n", __LINE__)) 3235# if $tag =~ /example/i; 3236 # sunshine@sunshineco.com: <PRE>bla</PRE> looks better than 3237 # <PRE>\nbla</PRE> (at least on NeXTstep browser 3238 push(@lines, &debug("<$format_map{$tag}>" . 3239 ($in_pre ? '' : "\n"), __LINE__)); 3240 next; 3241 } 3242 elsif (exists $complex_format_map->{$tag}) 3243 { 3244 my $start = eval $complex_format_map->{$tag}->[0]; 3245 if ($@) 3246 { 3247 print "$ERROR: eval of complex_format_map->{$tag}->[0] $complex_format_map->{$tag}->[0]: $@"; 3248 $start = '<pre>' 3249 } 3250 $in_pre = 1 if $start =~ /<pre/; 3251 push(@lines, html_debug($start. ($in_pre ? '' : "\n"), __LINE__)); 3252 next; 3253 } elsif ($tag eq 'table') { 3254 # anorland@hem2.passagen.se 3255 # if (/^\s*\@(|f|v|multi)table\s+\@(\w+)/) { 3256 if (/^\s*\@(|f|v|multi)table\s+\@(\w+)|(\{[^\}]*\})/) { 3257 $in_table = $2; 3258 unshift(@tables, join($;, $table_type, $in_table)); 3259 if ($table_type eq "multi") { 3260 # don't use borders -- gets confused by empty cells 3261 push(@lines, &debug("<TABLE>\n", __LINE__)); 3262 &html_push_if('TABLE'); 3263 } else { 3264 push(@lines, &debug("<DL COMPACT>\n", __LINE__)); 3265 &html_push_if('DL'); 3266 } 3267 push(@lines, &html_debug('', __LINE__)); 3268 } else { 3269 warn "$ERROR Bad table line: $_"; 3270 } 3271 next; 3272 } 3273 elsif ($tag eq 'synindex' || $tag eq 'syncodeindex') 3274 { 3275 if (/^\@$tag\s+(\w+)\s+(\w+)\s*$/) 3276 { 3277 my $from = $1; 3278 my $to = $2; 3279 my $prefix_from = IndexName2Prefix($from); 3280 my $prefix_to = IndexName2Prefix($to); 3281 3282 warn("$ERROR unknown from index name $from ind syn*index line: $_"), next 3283 unless $prefix_from; 3284 warn("$ERROR unknown to index name $to ind syn*index line: $_"), next 3285 unless $prefix_to; 3286 3287 if ($tag eq 'syncodeindex') 3288 { 3289 $index_properties->{$prefix_to}->{'from_code'}->{$prefix_from} = 1; 3290 } 3291 else 3292 { 3293 $index_properties->{$prefix_to}->{'from'}->{$prefix_from} = 1; 3294 } 3295 } 3296 else 3297 { 3298 warn "$ERROR Bad syn*index line: $_"; 3299 } 3300 next; 3301 } 3302 elsif ($tag eq 'defindex' || $tag eq 'defcodeindex') 3303 { 3304 if (/^\@$tag\s+(\w+)\s*$/) 3305 { 3306 my $name = $1; 3307 $index_properties->{$name}->{name} = $name; 3308 $index_properties->{$name}->{code} = 1 if $tag eq 'defcodeindex'; 3309 } 3310 else 3311 { 3312 warn "$ERROR Bad defindex line: $_"; 3313 } 3314 next; 3315 } 3316 elsif (/^\@printindex/) 3317 { 3318 push (@lines, "<!--::${section}::-->$_"); 3319 next; 3320 } 3321 elsif ($tag eq 'sp') { 3322 push(@lines, &debug("<P>\n", __LINE__)); 3323 next; 3324 } elsif ($tag eq 'center') { 3325 push(@lines, &debug("<center>\n", __LINE__)); 3326 s/\@center//; 3327 } elsif ($tag eq 'setref') { 3328 &protect_html; # if setref contains '&' for instance 3329 if (/^\@$tag\s*{($NODERE)}\s*$/) { 3330 $setref = $1; 3331 $setref =~ s/\s+/ /g; # normalize 3332 $setref =~ s/ $//; 3333 $node2sec{$setref} = $name; 3334 $sec2node{$name} = $setref; 3335 $node2href{$setref} = "$docu_doc#$docid"; 3336 } else { 3337 warn "$ERROR Bad setref line: $_"; 3338 } 3339 next; 3340 } elsif ($tag eq 'lowersections') { 3341 local ($sec, $level); 3342 while (($sec, $level) = each %sec2level) { 3343 $sec2level{$sec} = $level + 1; 3344 } 3345 next; 3346 } elsif ($tag eq 'raisesections') { 3347 local ($sec, $level); 3348 while (($sec, $level) = each %sec2level) { 3349 $sec2level{$sec} = $level - 1; 3350 } 3351 next; 3352 } 3353 elsif ($tag eq 'macro' || $tag eq 'rmacro') 3354 { 3355 if (/^\@$tag\s*(\w+)\s*(.*)/) 3356 { 3357 my $name = $1; 3358 my @args; 3359 @args = split(/\s*,\s*/ , $1) 3360 if ($2 =~ /^\s*{(.*)}\s*/); 3361 3362 $macros->{$name}->{Args} = \@args; 3363 $macros->{$name}->{Body} = ''; 3364 while (($_ = &next_line) && $_ !~ /\@end $tag/) 3365 { 3366 $macros->{$name}->{Body} .= $_; 3367 } 3368 die "ERROR: No closing '\@end $tag' found for macro definition of '$name'\n" 3369 unless (/\@end $tag/); 3370 chomp $macros->{$name}->{Body}; 3371 } 3372 else 3373 { 3374 warn "$ERROR: Bad macro defintion $_" 3375 } 3376 next; 3377 } 3378 elsif ($tag eq 'unmacro') 3379 { 3380 delete $macros->{$1} if (/^\@unmacro\s*(\w+)/); 3381 next; 3382 } 3383 elsif ($tag eq 'documentlanguage') 3384 { 3385 SetDocumentLanguage($1) if (!$T2H_LANG && /documentlanguage\s*(\w+)/); 3386 } 3387 elsif (defined($def_map{$tag})) { 3388 if ($def_map{$tag}) { 3389 s/^\@$tag\s+//; 3390 $tag = $def_map{$tag}; 3391 $_ = "\@$tag $_"; 3392 $tag =~ s/\s.*//; 3393 } 3394 } elsif (defined($user_sub{$tag})) { 3395 s/^\@$tag\s+//; 3396 $sub = $user_sub{$tag}; 3397 print "# user $tag = $sub, arg: $_" if $T2H_DEBUG & $DEBUG_USER; 3398 if (defined(&$sub)) { 3399 chop($_); 3400 &$sub($_); 3401 } else { 3402 warn "$ERROR Bad user sub for $tag: $sub\n"; 3403 } 3404 next; 3405 } 3406 if (defined($def_map{$tag})) { 3407 s/^\@$tag\s+//; 3408 if ($tag =~ /x$/) { 3409 # extra definition line 3410 $tag = $`; 3411 $is_extra = 1; 3412 } else { 3413 $is_extra = 0; 3414 } 3415 while (/\{([^\{\}]*)\}/) { 3416 # this is a {} construct 3417 ($before, $contents, $after) = ($`, $1, $'); 3418 # protect spaces 3419 $contents =~ s/\s+/$;9/g; 3420 # restore $_ protecting {} 3421 $_ = "$before$;7$contents$;8$after"; 3422 } 3423 @args = split(/\s+/, &protect_html($_)); 3424 foreach (@args) { 3425 s/$;9/ /g; # unprotect spaces 3426 s/$;7/\{/g; # ... { 3427 s/$;8/\}/g; # ... } 3428 } 3429 $type = shift(@args); 3430 $type =~ s/^\{(.*)\}$/$1/; 3431 print "# def ($tag): {$type} ", join(', ', @args), "\n" 3432 if $T2H_DEBUG & $DEBUG_DEF; 3433 $type .= ':'; # it's nicer like this 3434 my $name = shift(@args); 3435 $name =~ s/^\{(.*)\}$/$1/; 3436 if ($is_extra) { 3437 $_ = &debug("<DT>", __LINE__); 3438 } else { 3439 $_ = &debug("<DL>\n<DT>", __LINE__); 3440 } 3441 if ($tag eq 'deffn' || $tag eq 'defvr' || $tag eq 'deftp') { 3442 $_ .= "<U>$type</U> <B>$name</B>"; 3443 $_ .= " <I>@args</I>" if @args; 3444 } elsif ($tag eq 'deftypefn' || $tag eq 'deftypevr' 3445 || $tag eq 'defcv' || $tag eq 'defop') { 3446 $ftype = $name; 3447 $name = shift(@args); 3448 $name =~ s/^\{(.*)\}$/$1/; 3449 $_ .= "<U>$type</U> $ftype <B>$name</B>"; 3450 $_ .= " <I>@args</I>" if @args; 3451 } else { 3452 warn "$ERROR Unknown definition type: $tag\n"; 3453 $_ .= "<U>$type</U> <B>$name</B>"; 3454 $_ .= " <I>@args</I>" if @args; 3455 } 3456 $_ .= &debug("\n<DD>", __LINE__); 3457 $name = &unprotect_html($name); 3458 if ($tag eq 'deffn' || $tag eq 'deftypefn') { 3459 EnterIndexEntry('f', $name, $docu_doc, $section, \@lines); 3460# unshift(@input_spool, "\@findex $name\n"); 3461 } elsif ($tag eq 'defop') { 3462 EnterIndexEntry('f', "$name on $ftype", $docu_doc, $section, \@lines); 3463# unshift(@input_spool, "\@findex $name on $ftype\n"); 3464 } elsif ($tag eq 'defvr' || $tag eq 'deftypevr' || $tag eq 'defcv') { 3465 EnterIndexEntry('v', $name, $docu_doc, $section, \@lines); 3466# unshift(@input_spool, "\@vindex $name\n"); 3467 } else { 3468 EnterIndexEntry('t', $name, $docu_doc, $section, \@lines); 3469# unshift(@input_spool, "\@tindex $name\n"); 3470 } 3471 $dont_html = 1; 3472 } 3473 } elsif ($end_tag) { 3474 if ($format_map{$end_tag}) { 3475 $in_pre = 0 if $format_map{$end_tag} eq 'PRE'; 3476 $in_list-- if $format_map{$end_tag} eq 'UL' || $format_map{$end_tag} eq 'OL' ; 3477 &html_pop_if('P'); 3478 &html_pop_if('LI'); 3479 &html_pop_if(); 3480 push(@lines, &debug("</$format_map{$end_tag}>\n", __LINE__)); 3481 push(@lines, &html_debug('', __LINE__)); 3482 } 3483 elsif (exists $complex_format_map->{$end_tag}) 3484 { 3485 my $end = eval $complex_format_map->{$end_tag}->[1]; 3486 if ($@) 3487 { 3488 print "$ERROR: eval of complex_format_map->{$end_tag}->[1] $complex_format_map->{$end_tag}->[0]: $@"; 3489 $end = '</pre>' 3490 } 3491 $in_pre = 0 if $end =~ m|</pre>|; 3492 push(@lines, html_debug($end, __LINE__)); 3493 } elsif ($end_tag =~ /^(|f|v|multi)table$/) { 3494 unless (@tables) { 3495 warn "$ERROR \@end $end_tag without \@*table\n"; 3496 next; 3497 } 3498 &html_pop_if('P'); 3499 ($table_type, $in_table) = split($;, shift(@tables)); 3500 unless ($1 eq $table_type) { 3501 warn "$ERROR \@end $end_tag without matching \@$end_tag\n"; 3502 next; 3503 } 3504 if ($table_type eq "multi") { 3505 push(@lines, "</TR></TABLE>\n"); 3506 &html_pop_if('TR'); 3507 } else { 3508 push(@lines, "</DL>\n"); 3509 &html_pop_if('DD'); 3510 } 3511 &html_pop_if(); 3512 if (@tables) { 3513 ($table_type, $in_table) = split($;, $tables[0]); 3514 } else { 3515 $in_table = 0; 3516 } 3517 } elsif (defined($def_map{$end_tag})) { 3518 push(@lines, &debug("</DL>\n", __LINE__)); 3519 } elsif ($end_tag eq 'menu') { 3520 &html_pop_if(); 3521 push(@lines, $_); # must keep it for pass 2 3522 } 3523 next; 3524 } 3525 ############################################################# 3526 # anchor insertion 3527 while (/\@anchor\s*\{(.*?)\}/) 3528 { 3529 $_ = $`.$'; 3530 my $anchor = $1; 3531 $anchor = &normalise_node($anchor); 3532 push @lines, &html_debug("<A NAME=\"$anchor\"></A>\n"); 3533 $node2href{$anchor} = "$docu_doc#$anchor"; 3534 next INPUT_LINE if $_ =~ /^\s*$/; 3535 } 3536 3537 ############################################################# 3538 # index entry generation, after value substitutions 3539 if (/^\@(\w+?)index\s+/) 3540 { 3541 EnterIndexEntry($1, $', $docu_doc, $section, \@lines); 3542 next; 3543 } 3544 # 3545 # protect texi and HTML things 3546 &protect_texi; 3547 $_ = &protect_html($_) unless $dont_html; 3548 $dont_html = 0; 3549 # substitution (unsupported things) 3550 s/^\@exdent\s+//g; 3551 s/\@noindent\s+//g; 3552 s/\@refill\s+//g; 3553 # other substitutions 3554 &simple_substitutions; 3555 s/\@footnote\{/\@footnote$docu_doc\{/g; # mark footnotes, cf. pass 4 3556 # 3557 # analyze the tag again 3558 # 3559 if ($tag) { 3560 if (defined($sec2level{$tag}) && $sec2level{$tag} > 0) { 3561 if (/^\@$tag\s+(.+)$/) { 3562 $name = $1; 3563 $name = &normalise_node($name); 3564 $level = $sec2level{$tag}; 3565 # check for index 3566 $first_index_chapter = $node 3567 if ($level == 1 && !$first_index_chapter && 3568 $name =~ /index/i); 3569 if ($in_top && /heading/){ 3570 $T2H_HAS_TOP_HEADING = 1; 3571 $_ = &debug("<H$level>$name</H$level>\n", __LINE__); 3572 &html_push_if('body'); 3573 print "# top heading, section $name, level $level\n" 3574 if $T2H_DEBUG & $DEBUG_TOC; 3575 } 3576 else 3577 { 3578 unless (/^\@\w*heading/) 3579 { 3580 unless (/^\@unnumbered/) 3581 { 3582 my $number = &update_sec_num($tag, $level); 3583 $name = $number. ' ' . $name if $T2H_NUMBER_SECTIONS; 3584 $sec2number{$name} = $number; 3585 $number2sec{$number} = $name; 3586 } 3587 if (defined($toplevel)) 3588 { 3589 push @lines, ($level==$toplevel ? $CHAPTEREND : $SECTIONEND); 3590 } 3591 else 3592 { 3593 # first time we see a "section" 3594 unless ($level == 1) 3595 { 3596 warn "$WARN The first section found is not of level 1: $_"; 3597 } 3598 $toplevel = $level; 3599 } 3600 push(@sections, $name); 3601 next_doc() if ($T2H_SPLIT eq 'section' || 3602 $T2H_SPLIT && $level == $toplevel); 3603 } 3604 $sec_num++; 3605 $docid = "SEC$sec_num"; 3606 $tocid = (/^\@\w*heading/ ? undef : "TOC$sec_num"); 3607 # check biblio and glossary 3608 $in_bibliography = ($name =~ /^([A-Z]|\d+)?(\.\d+)*\s*bibliography$/i); 3609 $in_glossary = ($name =~ /^([A-Z]|\d+)?(\.\d+)*\s*glossary$/i); 3610 # check node 3611 if ($node) 3612 { 3613 warn "$ERROR Duplicate node found: $node\n" 3614 if ($node2sec{$node}); 3615 } 3616 else 3617 { 3618 $name .= ' ' while ($node2sec{$name}); 3619 $node = $name; 3620 } 3621 $name .= ' ' while ($sec2node{$name}); 3622 $section = $name; 3623 $node2sec{$node} = $name; 3624 $sec2node{$name} = $node; 3625 $node2href{$node} = "$docu_doc#$docid"; 3626 $node2next{$node} = $node_next; 3627 $node2prev{$node} = $node_prev; 3628 $node2up{$node} = $node_up; 3629 print "# node $node, section $name, level $level\n" 3630 if $T2H_DEBUG & $DEBUG_TOC; 3631 3632 $node = ''; 3633 $node_next = ''; 3634 $node_prev = ''; 3635 $node_next = ''; 3636 if ($tocid) 3637 { 3638 # update TOC 3639 while ($level > $curlevel) { 3640 $curlevel++; 3641 push(@toc_lines, "<UL>\n"); 3642 } 3643 while ($level < $curlevel) { 3644 $curlevel--; 3645 push(@toc_lines, "</UL>\n"); 3646 } 3647 $_ = &t2h_anchor($tocid, "$docu_doc#$docid", $name, 1); 3648 $_ = &substitute_style($_); 3649 push(@stoc_lines, "$_<BR>\n") if ($level == 1); 3650 if ($T2H_NUMBER_SECTIONS) 3651 { 3652 push(@toc_lines, $_ . "<BR>\n") 3653 } 3654 else 3655 { 3656 push(@toc_lines, "<LI>" . $_ ."</LI>"); 3657 } 3658 } 3659 else 3660 { 3661 push(@lines, &html_debug("<A NAME=\"$docid\"></A>\n", 3662 __LINE__)); 3663 } 3664 # update DOC 3665 push(@lines, &html_debug('', __LINE__)); 3666 &html_reset; 3667 $_ = "<H$level> $name </H$level>\n<!--docid::${docid}::-->\n"; 3668 $_ = &debug($_, __LINE__); 3669 push(@lines, &html_debug('', __LINE__)); 3670 } 3671 # update DOC 3672 foreach $line (split(/\n+/, $_)) { 3673 push(@lines, "$line\n"); 3674 } 3675 next; 3676 } else { 3677 warn "$ERROR Bad section line: $_"; 3678 } 3679 } else { 3680 # track variables 3681 $value{$1} = Unprotect_texi($2), next if /^\@set\s+($VARRE)\s+(.*)$/o; 3682 delete $value{$1}, next if /^\@clear\s+($VARRE)\s*$/o; 3683 # store things 3684 $value{'_shorttitle'} = Unprotect_texi($1), next if /^\@shorttitle\s+(.*)$/; 3685 $value{'_setfilename'} = Unprotect_texi($1), next if /^\@setfilename\s+(.*)$/; 3686 $value{'_settitle'} = Unprotect_texi($1), next if /^\@settitle\s+(.*)$/; 3687 $value{'_author'} .= Unprotect_texi($1)."\n", next if /^\@author\s+(.*)$/; 3688 $value{'_subtitle'} .= Unprotect_texi($1)."\n", next if /^\@subtitle\s+(.*)$/; 3689 $value{'_title'} .= Unprotect_texi($1)."\n", next if /^\@title\s+(.*)$/; 3690 3691 # list item 3692 if (/^\s*\@itemx?\s+/) { 3693 $what = $'; 3694 $what =~ s/\s+$//; 3695 if ($in_bibliography && $use_bibliography) { 3696 if ($what =~ /^$BIBRE$/o) { 3697 $id = 'BIB' . ++$bib_num; 3698 $bib2href{$what} = "$docu_doc#$id"; 3699 print "# found bibliography for '$what' id $id\n" 3700 if $T2H_DEBUG & $DEBUG_BIB; 3701 $what = &t2h_anchor($id, '', $what); 3702 } 3703 } elsif ($in_glossary && $T2H_USE_GLOSSARY) { 3704 $id = 'GLOSS' . ++$gloss_num; 3705 $entry = $what; 3706 $entry =~ tr/A-Z/a-z/ unless $entry =~ /^[A-Z\s]+$/; 3707 $gloss2href{$entry} = "$docu_doc#$id"; 3708 print "# found glossary for '$entry' id $id\n" 3709 if $T2H_DEBUG & $DEBUG_GLOSS; 3710 $what = &t2h_anchor($id, '', $what); 3711 } 3712 elsif ($in_table && ($table_type eq 'f' || $table_type eq 'v')) 3713 { 3714 EnterIndexEntry($table_type, $what, $docu_doc, $section, \@lines); 3715 } 3716 &html_pop_if('P'); 3717 if ($html_element eq 'DL' || $html_element eq 'DD') { 3718 if ($things_map{$in_table} && !$what) { 3719 # special case to allow @table @bullet for instance 3720 push(@lines, &debug("<DT>$things_map{$in_table}\n", __LINE__)); 3721 } else { 3722 push(@lines, &debug("<DT>\@$in_table\{$what\}\n", __LINE__)); 3723 } 3724 push(@lines, "<DD>"); 3725 &html_push('DD') unless $html_element eq 'DD'; 3726 if ($table_type) { # add also an index 3727 unshift(@input_spool, "\@${table_type}index $what\n"); 3728 } 3729 } elsif ($html_element eq 'TABLE') { 3730 push(@lines, &debug("<TR><TD>$what</TD>\n", __LINE__)); 3731 &html_push('TR'); 3732 } elsif ($html_element eq 'TR') { 3733 push(@lines, &debug("</TR>\n", __LINE__)); 3734 push(@lines, &debug("<TR><TD>$what</TD>\n", __LINE__)); 3735 } else { 3736 push(@lines, &debug("<LI>$what\n", __LINE__)); 3737 &html_push('LI') unless $html_element eq 'LI'; 3738 } 3739 push(@lines, &html_debug('', __LINE__)); 3740 if ($deferred_ref) { 3741 push(@lines, &debug("$deferred_ref\n", __LINE__)); 3742 $deferred_ref = ''; 3743 } 3744 next; 3745 } elsif (/^\@tab\s+(.*)$/) { 3746 push(@lines, "<TD>$1</TD>\n"); 3747 next; 3748 } 3749 } 3750 } 3751 # paragraph separator 3752 if ($_ eq "\n" && ! $in_pre) { 3753 next if $#lines >= 0 && $lines[$#lines] eq "\n"; 3754 if ($html_element eq 'P') { 3755 push (@lines, &debug("</P><P>\n", __LINE__)); 3756 } 3757# else 3758# { 3759# push(@lines, "<P></P>\n"); 3760# $_ = &debug("<P></P>\n", __LINE__); 3761# } 3762 elsif ($html_element eq 'body' || $html_element eq 'BLOCKQUOTE' || $html_element eq 'DD' || $html_element eq 'LI') 3763 { 3764 &html_push('P'); 3765 push(@lines, &debug("<P>\n", __LINE__)); 3766 } 3767 } 3768 # otherwise 3769 push(@lines, $_) unless $in_titlepage; 3770 push(@lines, &debug("</center>\n", __LINE__)) if ($tag eq 'center'); 3771} 3772 3773# finish TOC 3774$level = 0; 3775while ($level < $curlevel) { 3776 $curlevel--; 3777 push(@toc_lines, "</UL>\n"); 3778} 3779 3780print "# end of pass 1\n" if $T2H_VERBOSE; 3781 3782SetDocumentLanguage('en') unless ($T2H_LANG); 3783#+++############################################################################ 3784# # 3785# Stuff related to Index generation # 3786# # 3787#---############################################################################ 3788 3789sub EnterIndexEntry 3790{ 3791 my $prefix = shift; 3792 my $key = shift; 3793 my $docu_doc = shift; 3794 my $section = shift; 3795 my $lines = shift; 3796 local $_; 3797 3798 warn "$ERROR Undefined index command: $_", next 3799 unless (exists ($index_properties->{$prefix})); 3800 $key =~ s/\s+$//; 3801 $_ = $key; 3802 &protect_texi; 3803 $key = $_; 3804 $_ = &protect_html($_); 3805 my $html_key = substitute_style($_); 3806 my $id; 3807 $key = remove_style($key); 3808 $key = remove_things($key); 3809 $_ = $key; 3810 &unprotect_texi; 3811 $key = $_; 3812 while (exists $index->{$prefix}->{$key}) {$key .= ' '}; 3813 if ($lines->[$#lines] =~ /^<!--docid::(.+)::-->$/) 3814 { 3815 $id = $1; 3816 } 3817 else 3818 { 3819 $id = 'IDX' . ++$idx_num; 3820 push(@$lines, &t2h_anchor($id, '', $T2H_INVISIBLE_MARK, !$in_pre)); 3821 } 3822 $index->{$prefix}->{$key}->{html_key} = $html_key; 3823 $index->{$prefix}->{$key}->{section} = $section; 3824 $index->{$prefix}->{$key}->{href} = "$docu_doc#$id"; 3825 print "# found ${prefix}index for '$key' with id $id\n" 3826 if $T2H_DEBUG & $DEBUG_INDEX; 3827} 3828 3829sub IndexName2Prefix 3830{ 3831 my $name = shift; 3832 my $prefix; 3833 3834 for $prefix (keys %$index_properties) 3835 { 3836 return $prefix if ($index_properties->{$prefix}->{name} eq $name); 3837 } 3838 return undef; 3839} 3840 3841sub GetIndexEntries 3842{ 3843 my $normal = shift; 3844 my $code = shift; 3845 my ($entries, $prefix, $key) = ({}); 3846 3847 for $prefix (keys %$normal) 3848 { 3849 for $key (keys %{$index->{$prefix}}) 3850 { 3851 $entries->{$key} = {%{$index->{$prefix}->{$key}}}; 3852 } 3853 } 3854 3855 if (defined($code)) 3856 { 3857 for $prefix (keys %$code) 3858 { 3859 unless (exists $normal->{$keys}) 3860 { 3861 for $key (keys %{$index->{$prefix}}) 3862 { 3863 $entries->{$key} = {%{$index->{$prefix}->{$key}}}; 3864 $entries->{$key}->{html_key} = "<CODE>$entries->{$key}->{html_key}</CODE>"; 3865 } 3866 } 3867 } 3868 } 3869 return $entries; 3870} 3871 3872sub byAlpha 3873{ 3874 if ($a =~ /^[A-Za-z]/) 3875 { 3876 if ($b =~ /^[A-Za-z]/) 3877 { 3878 return lc($a) cmp lc($b); 3879 } 3880 else 3881 { 3882 return 1; 3883 } 3884 } 3885 elsif ($b =~ /^[A-Za-z]/) 3886 { 3887 return -1; 3888 } 3889 else 3890 { 3891 return lc($a) cmp lc($b); 3892 } 3893} 3894 3895sub GetIndexPages 3896{ 3897 my $entries = shift; 3898 my (@Letters, $key); 3899 my ($EntriesByLetter, $Pages, $page) = ({}, [], {}); 3900 my @keys = sort byAlpha keys %$entries; 3901 3902 for $key (@keys) 3903 { 3904 push @{$EntriesByLetter->{uc(substr($key,0, 1))}} , $entries->{$key}; 3905 } 3906 @Letters = sort byAlpha keys %$EntriesByLetter; 3907 3908 $T2H_SPLIT_INDEX = 0 unless ($T2H_SPLIT); 3909 3910 unless ($T2H_SPLIT_INDEX) 3911 { 3912 $page->{First} = $Letters[0]; 3913 $page->{Last} = $Letters[$#Letters]; 3914 $page->{Letters} = \@Letters; 3915 $page->{EntriesByLetter} = $EntriesByLetter; 3916 push @$Pages, $page; 3917 return $Pages; 3918 } 3919 3920 if ($T2H_SPLIT_INDEX =~ /^\d+$/) 3921 { 3922 my $i = 0; 3923 my ($prev_letter, $letter); 3924 $page->{First} = $Letters[0]; 3925 for $letter (@Letters) 3926 { 3927 if ($i > $T2H_SPLIT_INDEX) 3928 { 3929 $page->{Last} = $prev_letter; 3930 push @$Pages, {%$page}; 3931 $page->{Letters} = []; 3932 $page->{EntriesByLetter} = {}; 3933 $page->{First} = $letter; 3934 $i=0; 3935 } 3936 push @{$page->{Letters}}, $letter; 3937 $page->{EntriesByLetter}->{$letter} = [@{$EntriesByLetter->{$letter}}]; 3938 $i += scalar(@{$EntriesByLetter->{$letter}}); 3939 $prev_letter = $letter; 3940 } 3941 $page->{Last} = $Letters[$#Letters]; 3942 push @$Pages, {%$page}; 3943 } 3944 return $Pages; 3945} 3946 3947sub GetIndexSummary 3948{ 3949 my $first_page = shift; 3950 my $Pages = shift; 3951 my $name = shift; 3952 my ($page, $letter, $summary, $i, $l1, $l2, $l); 3953 3954 $i = 0; 3955 $summary = '<table><tr><th valign=top>Jump to: </th><td>'; 3956 3957 for $page ($first_page, @$Pages) 3958 { 3959 for $letter (@{$page->{Letters}}) 3960 { 3961 $l = t2h_anchor('', "$page->{href}#${name}_$letter", "<b>$letter</b>", 3962 0, 'style="text-decoration:none"') . "\n \n"; 3963 3964 if ($letter =~ /^[A-Za-z]/) 3965 { 3966 $l2 .= $l; 3967 } 3968 else 3969 { 3970 $l1 .= $l; 3971 } 3972 } 3973 } 3974 $summary .= $l1 . "<BR>\n" if ($l1); 3975 $summary .= $l2 . '</td></tr></table><br>'; 3976 return $summary; 3977} 3978 3979sub PrintIndexPage 3980{ 3981 my $lines = shift; 3982 my $summary = shift; 3983 my $page = shift; 3984 my $name = shift; 3985 3986 push @$lines, $summary; 3987 3988 push @$lines , <<EOT; 3989<P></P> 3990<TABLE border=0> 3991<TR><TD></TD><TH ALIGN=LEFT>Index Entry</TH><TH ALIGN=LEFT> Section</TH></TR> 3992<TR><TD COLSPAN=3> <HR></TD></TR> 3993EOT 3994 3995 for $letter (@{$page->{Letters}}) 3996 { 3997 push @$lines, "<TR><TH><A NAME=\"${name}_$letter\"></A>$letter</TH><TD></TD><TD></TD></TR>\n"; 3998 for $entry (@{$page->{EntriesByLetter}->{$letter}}) 3999 { 4000 push @$lines, 4001 "<TR><TD></TD><TD valign=top>" . 4002 t2h_anchor('', $entry->{href}, $entry->{html_key}) . 4003 "</TD><TD valign=top>" . 4004 t2h_anchor('', sec_href($entry->{section}), clean_name($entry->{section})) . 4005 "</TD></TR>\n"; 4006 } 4007 push @$lines, "<TR><TD COLSPAN=3> <HR></TD></TR>\n"; 4008 } 4009 push @$lines, "</TABLE><P></P>"; 4010 push @$lines, $summary; 4011} 4012 4013sub PrintIndex 4014{ 4015 my $lines = shift; 4016 my $name = shift; 4017 my $section = shift; 4018 $section = 'Top' unless $section; 4019 my $prefix = IndexName2Prefix($name); 4020 4021 warn ("$ERROR printindex: bad index name: $name"), return 4022 unless $prefix; 4023 4024 if ($index_properties->{$prefix}->{code}) 4025 { 4026 $index_properties->{$prefix}->{from_code}->{$prefix} = 1; 4027 } 4028 else 4029 { 4030 $index_properties->{$prefix}->{from}->{$prefix}= 1; 4031 } 4032 4033 my $Entries = GetIndexEntries($index_properties->{$prefix}->{from}, 4034 $index_properties->{$prefix}->{from_code}); 4035 return unless %$Entries; 4036 4037 if ($T2H_IDX_SUMMARY) 4038 { 4039 my $key; 4040 open(FHIDX, ">$docu_rdir$docu_name" . "_$name.idx") 4041 || die "Can't open > $docu_rdir$docu_name" . "_$name.idx for writing: $!\n"; 4042 print "# writing $name index summary in $docu_rdir$docu_name" . "_$name.idx...\n" if $T2H_VERBOSE; 4043 4044 for $key (sort keys %$Entries) 4045 { 4046 print FHIDX "$key\t$Entries->{$key}->{href}\n"; 4047 } 4048 } 4049 4050 my $Pages = GetIndexPages($Entries); 4051 my $page; 4052 my $first_page = shift @$Pages; 4053 my $sec_name = $section; 4054 # remove section number 4055 $sec_name =~ s/.*? // if $sec_name =~ /^([A-Z]|\d+)\./; 4056 4057 ($first_page->{href} = sec_href($section)) =~ s/\#.*$//; 4058 # Update tree structure of document 4059 if (@$Pages) 4060 { 4061 my $sec; 4062 my @after; 4063 4064 while (@sections && $sections[$#sections] ne $section) 4065 { 4066 unshift @after, pop @sections; 4067 } 4068 4069 for $page (@$Pages) 4070 { 4071 my $node = ($page->{First} ne $page->{Last} ? 4072 "$sec_name: $page->{First} -- $page->{Last}" : 4073 "$sec_name: $page->{First}"); 4074 push @sections, $node; 4075 $node2sec{$node} = $node; 4076 $sec2node{$node} = $node; 4077 $node2up{$node} = $section; 4078 $page->{href} = next_doc(); 4079 $page->{name} = $node; 4080 $node2href{$node} = $page->{href}; 4081 if ($prev_node) 4082 { 4083 $node2next{$prev_node} = $node; 4084 $node2prev{$node} = $prev_node; 4085 } 4086 $prev_node = $node; 4087 } 4088 push @sections, @after; 4089 } 4090 4091 my $summary = GetIndexSummary($first_page, $Pages, $name); 4092 PrintIndexPage($lines, $summary, $first_page, $name); 4093 for $page (@$Pages) 4094 { 4095 push @$lines, ($T2H_SPLIT eq 'chapter' ? $CHAPTEREND : $SECTIONEND); 4096 push @$lines, "<H2 ALIGN=\"Left\">$page->{name}</H2>\n"; 4097 PrintIndexPage($lines, $summary, $page, $name); 4098 } 4099} 4100 4101 4102#+++############################################################################ 4103# # 4104# Pass 2/3: handle style, menu, index, cross-reference # 4105# # 4106#---############################################################################ 4107 4108@lines2 = (); # whole document (2nd pass) 4109@lines3 = (); # whole document (3rd pass) 4110$in_menu = 0; # am I inside a menu 4111 4112while (@lines) { 4113 $_ = shift(@lines); 4114 # 4115 # special case (protected sections) 4116 # 4117 if (/^$PROTECTTAG/o) { 4118 push(@lines2, $_); 4119 next; 4120 } 4121 # 4122 # menu 4123 # 4124 if (/^\@menu\b/) 4125 { 4126 $in_menu = 1; 4127 $in_menu_listing = 1; 4128 push(@lines2, &debug("<BLOCKQUOTE><TABLE BORDER=0 CELLSPACING=0> \n", __LINE__)); 4129 next; 4130 } 4131 if (/^\@end\s+menu\b/) 4132 { 4133 if ($in_menu_listing) 4134 { 4135 push(@lines2, &debug("</TABLE></BLOCKQUOTE>\n", __LINE__)); 4136 } 4137 else 4138 { 4139 push(@lines2, &debug("</BLOCKQUOTE>\n", __LINE__)); 4140 } 4141 $in_menu = 0; 4142 $in_menu_listing = 0; 4143 next; 4144 } 4145 if ($in_menu) 4146 { 4147 my ($node, $name, $descr); 4148 if (/^\*\s+($NODERE)::/o) 4149 { 4150 $node = $1; 4151 $descr = $'; 4152 } 4153 elsif (/^\*\s+(.+):\s+([^\t,\.\n]+)[\t,\.\n]/) 4154 { 4155 $name = $1; 4156 $node = $2; 4157 $descr = $'; 4158 } 4159 elsif (/^\*/) 4160 { 4161 warn "$ERROR Bad menu line: $_"; 4162 } 4163 else 4164 { 4165 if ($in_menu_listing) 4166 { 4167 $in_menu_listing = 0; 4168 push(@lines2, &debug("</TABLE>\n", __LINE__)); 4169 } 4170 # should be like verbatim -- preseve spaces, etc 4171 s/ /\ /g; 4172 $_ .= "<br>\n"; 4173 push(@lines2, $_); 4174 } 4175 if ($node) 4176 { 4177 if (! $in_menu_listing) 4178 { 4179 $in_menu_listing = 1; 4180 push(@lines2, &debug("<TABLE BORDER=0 CELLSPACING=0>\n", __LINE__)); 4181 } 4182 # look for continuation 4183 while ($lines[0] =~ /^\s+\w+/) 4184 { 4185 $descr .= shift(@lines); 4186 } 4187 &menu_entry($node, $name, $descr); 4188 } 4189 next; 4190 } 4191 # 4192 # printindex 4193 # 4194 PrintIndex(\@lines2, $2, $1), next 4195 if (/^<!--::(.*)::-->\@printindex\s+(\w+)/); 4196 # 4197 # simple style substitutions 4198 # 4199 $_ = &substitute_style($_); 4200 # 4201 # xref 4202 # 4203 while (/\@(x|px|info|)ref{([^{}]+)(}?)/) { 4204 # note: Texinfo may accept other characters 4205 ($type, $nodes, $full) = ($1, $2, $3); 4206 ($before, $after) = ($`, $'); 4207 if (! $full && $after) { 4208 warn "$ERROR Bad xref (no ending } on line): $_"; 4209 $_ = "$before$;0${type}ref\{$nodes$after"; 4210 next; # while xref 4211 } 4212 if ($type eq 'x') { 4213 $type = "$T2H_WORDS->{$T2H_LANG}->{'See'} "; 4214 } elsif ($type eq 'px') { 4215 $type = "$T2H_WORDS->{$T2H_LANG}->{'see'} "; 4216 } elsif ($type eq 'info') { 4217 $type = "$T2H_WORDS->{$T2H_LANG}->{'See'} Info"; 4218 } else { 4219 $type = ''; 4220 } 4221 unless ($full) { 4222 $next = shift(@lines); 4223 $next = &substitute_style($next); 4224 chop($nodes); # remove final newline 4225 if ($next =~ /\}/) { # split on 2 lines 4226 $nodes .= " $`"; 4227 $after = $'; 4228 } else { 4229 $nodes .= " $next"; 4230 $next = shift(@lines); 4231 $next = &substitute_style($next); 4232 chop($nodes); 4233 if ($next =~ /\}/) { # split on 3 lines 4234 $nodes .= " $`"; 4235 $after = $'; 4236 } else { 4237 warn "$ERROR Bad xref (no ending }): $_"; 4238 $_ = "$before$;0xref\{$nodes$after"; 4239 unshift(@lines, $next); 4240 next; # while xref 4241 } 4242 } 4243 } 4244 $nodes =~ s/\s+/ /g; # remove useless spaces 4245 @args = split(/\s*,\s*/, $nodes); 4246 $node = $args[0]; # the node is always the first arg 4247 $node = &normalise_node($node); 4248 $sec = $args[2] || $args[1] || $node2sec{$node}; 4249 $href = $node2href{$node}; 4250 if (@args == 5) { # reference to another manual 4251 $sec = $args[2] || $node; 4252 $man = $args[4] || $args[3]; 4253 $_ = "${before}${type}$T2H_WORDS->{$T2H_LANG}->{'section'} `$sec' in \@cite{$man}$after"; 4254 } elsif ($type =~ /Info/) { # inforef 4255 warn "$ERROR Wrong number of arguments: $_" unless @args == 3; 4256 ($nn, $_, $in) = @args; 4257 $_ = "${before}${type} file `$in', node `$nn'$after"; 4258 } elsif ($sec && $href && ! $T2H_SHORT_REF) { 4259 $_ = "${before}${type}"; 4260 $_ .= "$T2H_WORDS->{$T2H_LANG}->{'section'} " if ${type}; 4261 $_ .= &t2h_anchor('', $href, $sec) . $after; 4262 } 4263 elsif ($href) 4264 { 4265 $_ = "${before}${type} " . 4266 &t2h_anchor('', $href, $args[2] || $args[1] || $node) . 4267 $after; 4268 } 4269 else { 4270 warn "$ERROR Undefined node ($node): $_"; 4271 $_ = "$before$;0xref{$nodes}$after"; 4272 } 4273 } 4274 4275 # replace images 4276 s[\@image\s*{(.+?)}] 4277 { 4278 my @args = split (/\s*,\s*/, $1); 4279 my $base = $args[0]; 4280 my $image = 4281 LocateIncludeFile("$base.png") || 4282 LocateIncludeFile("$base.jpg") || 4283 LocateIncludeFile("$base.gif"); 4284 warn "$ERROR no image file for $base: $_" unless ($image && -e $image); 4285 "<IMG SRC=\"$image\" ALT=\"$base\">"; 4286 ($T2H_CENTER_IMAGE ? 4287 "<CENTER><IMG SRC=\"$image\" ALT=\"$base\"></CENTER>" : 4288 "<IMG SRC=\"$image\" ALT=\"$base\">"); 4289 }eg; 4290 4291 # 4292 # try to guess bibliography references or glossary terms 4293 # 4294 unless (/^<H\d><A NAME=\"SEC\d/) { 4295 if ($use_bibliography) { 4296 $done = ''; 4297 while (/$BIBRE/o) { 4298 ($pre, $what, $post) = ($`, $&, $'); 4299 $href = $bib2href{$what}; 4300 if (defined($href) && $post !~ /^[^<]*<\/A>/) { 4301 $done .= $pre . &t2h_anchor('', $href, $what); 4302 } else { 4303 $done .= "$pre$what"; 4304 } 4305 $_ = $post; 4306 } 4307 $_ = $done . $_; 4308 } 4309 if ($T2H_USE_GLOSSARY) { 4310 $done = ''; 4311 while (/\b\w+\b/) { 4312 ($pre, $what, $post) = ($`, $&, $'); 4313 $entry = $what; 4314 $entry =~ tr/A-Z/a-z/ unless $entry =~ /^[A-Z\s]+$/; 4315 $href = $gloss2href{$entry}; 4316 if (defined($href) && $post !~ /^[^<]*<\/A>/) { 4317 $done .= $pre . &t2h_anchor('', $href, $what); 4318 } else { 4319 $done .= "$pre$what"; 4320 } 4321 $_ = $post; 4322 } 4323 $_ = $done . $_; 4324 } 4325 } 4326 # otherwise 4327 push(@lines2, $_); 4328} 4329print "# end of pass 2\n" if $T2H_VERBOSE; 4330 4331# 4332# split style substitutions 4333# 4334while (@lines2) { 4335 $_ = shift(@lines2); 4336 # 4337 # special case (protected sections) 4338 # 4339 if (/^$PROTECTTAG/o) { 4340 push(@lines3, $_); 4341 next; 4342 } 4343 # 4344 # split style substitutions 4345 # 4346 $old = ''; 4347 while ($old ne $_) { 4348 $old = $_; 4349 if (/\@(\w+)\{/) { 4350 ($before, $style, $after) = ($`, $1, $'); 4351 if (defined($style_map{$style})) { 4352 $_ = $after; 4353 $text = ''; 4354 $after = ''; 4355 $failed = 1; 4356 while (@lines2) { 4357 if (/\}/) { 4358 $text .= $`; 4359 $after = $'; 4360 $failed = 0; 4361 last; 4362 } else { 4363 $text .= $_; 4364 $_ = shift(@lines2); 4365 } 4366 } 4367 if ($failed) { 4368 die "* Bad syntax (\@$style) after: $before\n"; 4369 } else { 4370 $text = &apply_style($style, $text); 4371 $_ = "$before$text$after"; 4372 } 4373 } 4374 } 4375 } 4376 # otherwise 4377 push(@lines3, $_); 4378} 4379print "# end of pass 3\n" if $T2H_VERBOSE; 4380 4381#+++############################################################################ 4382# # 4383# Pass 4: foot notes, final cleanup # 4384# # 4385#---############################################################################ 4386 4387@foot_lines = (); # footnotes 4388@doc_lines = (); # final document 4389$end_of_para = 0; # true if last line is <P> 4390 4391while (@lines3) { 4392 $_ = shift(@lines3); 4393 # 4394 # special case (protected sections) 4395 # 4396 if (/^$PROTECTTAG/o) { 4397 push(@doc_lines, $_); 4398 $end_of_para = 0; 4399 next; 4400 } 4401 # 4402 # footnotes 4403 # 4404 while (/\@footnote([^\{\s]+)\{/) { 4405 ($before, $d, $after) = ($`, $1, $'); 4406 $_ = $after; 4407 $text = ''; 4408 $after = ''; 4409 $failed = 1; 4410 while (@lines3) { 4411 if (/\}/) { 4412 $text .= $`; 4413 $after = $'; 4414 $failed = 0; 4415 last; 4416 } else { 4417 $text .= $_; 4418 $_ = shift(@lines3); 4419 } 4420 } 4421 if ($failed) { 4422 die "* Bad syntax (\@footnote) after: $before\n"; 4423 } else { 4424 $foot_num++; 4425 $docid = "DOCF$foot_num"; 4426 $footid = "FOOT$foot_num"; 4427 $foot = "($foot_num)"; 4428 push(@foot_lines, "<H3>" . &t2h_anchor($footid, "$d#$docid", $foot) . "</H3>\n"); 4429 $text = "<P>$text" unless $text =~ /^\s*<P>/; 4430 push(@foot_lines, "$text\n"); 4431 $_ = $before . &t2h_anchor($docid, "$docu_foot#$footid", $foot) . $after; 4432 } 4433 } 4434 # 4435 # remove unnecessary <P> 4436 # 4437 if (/^\s*<P>\s*$/) { 4438 next if $end_of_para++; 4439 } else { 4440 $end_of_para = 0; 4441 } 4442 # otherwise 4443 push(@doc_lines, $_); 4444} 4445 4446print "# end of pass 4\n" if $T2H_VERBOSE; 4447 4448#+++############################################################################ 4449# # 4450# Pass 5: print things # 4451# # 4452#---############################################################################ 4453 4454$T2H_L2H = &l2h_FinishToLatex if ($T2H_L2H); 4455$T2H_L2H = &l2h_ToHtml if ($T2H_L2H); 4456$T2H_L2H = &l2h_InitFromHtml if ($T2H_L2H); 4457 4458# fix node2up, node2prev, node2next, if desired 4459if ($has_top_command) 4460{ 4461 for $section (keys %sec2number) 4462 { 4463 $node = $sec2node{$section}; 4464 $node2up{$node} = Sec2UpNode($section) unless $node2up{$node}; 4465 $node2prev{$node} = Sec2PrevNode($section) unless $node2prev{$node}; 4466 $node2next{$node} = Sec2NextNode($section) unless $node2next{$node}; 4467 } 4468} 4469 4470# prepare %T2H_THISDOC 4471$T2H_THISDOC{fulltitle} = $value{'_title'} || $value{'_settitle'} || "Untitled Document"; 4472$T2H_THISDOC{title} = $value{'_settitle'} || $T2H_THISDOC{fulltitle}; 4473$T2H_THISDOC{author} = $value{'_author'}; 4474$T2H_THISDOC{subtitle} = $value{'_subtitle'}; 4475$T2H_THISDOC{shorttitle} = $value{'_shorttitle'}; 4476for $key (keys %T2H_THISDOC) 4477{ 4478 $_ = &substitute_style($T2H_THISDOC{$key}); 4479 &unprotect_texi; 4480 s/\s*$//; 4481 $T2H_THISDOC{$key} = $_; 4482} 4483 4484# if no sections, then simply print document as is 4485unless (@sections) 4486{ 4487 print "# Writing content into $docu_top_file \n" if $T2H_VERBOSE; 4488 open(FILE, "> $docu_top_file") 4489 || die "$ERROR: Can't open $docu_top_file for writing: $!\n"; 4490 4491 &$T2H_print_page_head(\*FILE); 4492 $T2H_THIS_SECTION = \@doc_lines; 4493 t2h_print_lines(\*FILE); 4494 &$T2H_print_foot_navigation(\*FILE); 4495 &$T2H_print_page_foot(\*FILE); 4496 close(FILE); 4497 goto Finish; 4498} 4499 4500# initialize $T2H_HREF, $T2H_NAME 4501%T2H_HREF = 4502 ( 4503 'First' , sec_href($sections[0]), 4504 'Last', sec_href($sections[$#sections]), 4505 'About', $docu_about. '#SEC_About', 4506 ); 4507 4508# prepare TOC, OVERVIEW, TOP 4509$T2H_TOC = \@toc_lines; 4510$T2H_OVERVIEW = \@stoc_lines; 4511if ($has_top) 4512{ 4513 while (1) 4514 { 4515 $_ = shift @doc_lines; 4516 last if /$TOPEND/; 4517 push @$T2H_TOP, $_; 4518 } 4519 $T2H_HREF{'Top'} = $docu_top . '#SEC_Top'; 4520} 4521else 4522{ 4523 $T2H_HREF{'Top'} = $T2H_HREF{First}; 4524} 4525 4526$node2href{Top} = $T2H_HREF{Top}; 4527$T2H_HREF{Contents} = $docu_toc.'#SEC_Contents' if @toc_lines; 4528$T2H_HREF{Overview} = $docu_stoc.'#SEC_OVERVIEW' if @stoc_lines; 4529 4530# settle on index 4531if ($T2H_INDEX_CHAPTER) 4532{ 4533 $T2H_HREF{Index} = $node2href{normalise_node($T2H_INDEX_CHAPTER)}; 4534 warn "$ERROR T2H_INDEX_CHAPTER '$T2H_INDEX_CHAPTER' not found\n" 4535 unless $T2H_HREF{Index}; 4536} 4537if (! $T2H_HREF{Index} && $first_index_chapter) 4538{ 4539 $T2H_INDEX_CHAPTER = $first_index_chapter; 4540 $T2H_HREF{Index} = $node2href{$T2H_INDEX_CHAPTER}; 4541} 4542 4543print "# Using '" . clean_name($T2H_INDEX_CHAPTER) . "' as index page\n" 4544 if ($T2H_VERBOSE && $T2H_HREF{Index}); 4545 4546%T2H_NAME = 4547 ( 4548 'First', clean_name($sec2node{$sections[0]}), 4549 'Last', clean_name($sec2node{$sections[$#sections]}), 4550 'About', $T2H_WORDS->{$T2H_LANG}->{'About_Title'}, 4551 'Contents', $T2H_WORDS->{$T2H_LANG}->{'ToC_Title'}, 4552 'Overview', $T2H_WORDS->{$T2H_LANG}->{'Overview_Title'}, 4553 'Index' , clean_name($T2H_INDEX_CHAPTER), 4554 'Top', clean_name($T2H_TOP_HEADING || $T2H_THISDOC{'title'} || $T2H_THISDOC{'shorttitle'}), 4555 ); 4556 4557############################################################################# 4558# print frame and frame toc file 4559# 4560if ( $T2H_FRAMES ) 4561{ 4562 open(FILE, "> $docu_frame_file") 4563 || die "$ERROR: Can't open $docu_frame_file for writing: $!\n"; 4564 print "# Creating frame in $docu_frame_file ...\n" if $T2H_VERBOSE; 4565 &$T2H_print_frame(\*FILE); 4566 close(FILE); 4567 4568 open(FILE, "> $docu_toc_frame_file") 4569 || die "$ERROR: Can't open $docu_toc_frame_file for writing: $!\n"; 4570 print "# Creating toc frame in $docu_frame_file ...\n" if $T2H_VERBOSE; 4571 &$T2H_print_toc_frame(\*FILE); 4572 close(FILE); 4573} 4574 4575 4576############################################################################# 4577# print Top 4578# 4579open(FILE, "> $docu_top_file") 4580 || die "$ERROR: Can't open $docu_top_file for writing: $!\n"; 4581&$T2H_print_page_head(\*FILE) unless ($T2H_SPLIT); 4582 4583if ($has_top) 4584{ 4585 print "# Creating Top in $docu_top_file ...\n" if $T2H_VERBOSE; 4586 $T2H_THIS_SECTION = $T2H_TOP; 4587 $T2H_HREF{This} = $T2H_HREF{Top}; 4588 $T2H_NAME{This} = $T2H_NAME{Top}; 4589 &$T2H_print_Top(\*FILE); 4590} 4591 4592close(FILE) if $T2H_SPLIT; 4593 4594############################################################################# 4595# Print sections 4596# 4597$T2H_NODE{Forward} = $sec2node{$sections[0]}; 4598$T2H_NAME{Forward} = &clean_name($sec2node{$sections[0]}); 4599$T2H_HREF{Forward} = sec_href($sections[0]); 4600$T2H_NODE{This} = 'Top'; 4601$T2H_NAME{This} = $T2H_NAME{Top}; 4602$T2H_HREF{This} = $T2H_HREF{Top}; 4603if ($T2H_SPLIT) 4604{ 4605 print "# writing " . scalar(@sections) . 4606 " sections in $docu_rdir$docu_name"."_[1..$doc_num]" 4607 if $T2H_VERBOSE; 4608 $previous = ($T2H_SPLIT eq 'chapter' ? $CHAPTEREND : $SECTIONEND); 4609 undef $FH; 4610 $doc_num = 0; 4611} 4612else 4613{ 4614 print "# writing " . scalar(@sections) . " sections in $docu_top_file ..." 4615 if $T2H_VERBOSE; 4616 $FH = \*FILE; 4617 $previous = ''; 4618} 4619 4620$counter = 0; 4621# loop through sections 4622while ($section = shift(@sections)) 4623{ 4624 if ($T2H_SPLIT && ($T2H_SPLIT eq 'section' || $previous eq $CHAPTEREND)) 4625 { 4626 if ($FH) 4627 { 4628 #close previous page 4629 &$T2H_print_chapter_footer($FH) if $T2H_SPLIT eq 'chapter'; 4630 &$T2H_print_page_foot($FH); 4631 close($FH); 4632 undef $FH; 4633 } 4634 } 4635 $T2H_NAME{Back} = $T2H_NAME{This}; 4636 $T2H_HREF{Back} = $T2H_HREF{This}; 4637 $T2H_NODE{Back} = $T2H_NODE{This}; 4638 $T2H_NAME{This} = $T2H_NAME{Forward}; 4639 $T2H_HREF{This} = $T2H_HREF{Forward}; 4640 $T2H_NODE{This} = $T2H_NODE{Forward}; 4641 if ($sections[0]) 4642 { 4643 $T2H_NODE{Forward} = $sec2node{$sections[0]}; 4644 $T2H_NAME{Forward} = &clean_name($T2H_NODE{Forward}); 4645 $T2H_HREF{Forward} = sec_href($sections[0]); 4646 } 4647 else 4648 { 4649 undef $T2H_HREF{Forward}, $T2H_NODE{Forward}, $T2H_NAME{Forward}; 4650 } 4651 4652 $node = $node2up{$T2H_NODE{This}}; 4653 $T2H_HREF{Up} = $node2href{$node}; 4654 if ($T2H_HREF{Up} eq $T2H_HREF{This} || ! $T2H_HREF{Up}) 4655 { 4656 $T2H_NAME{Up} = $T2H_NAME{Top}; 4657 $T2H_HREF{Up} = $T2H_HREF{Top}; 4658 $T2H_NODE{Up} = 'Up'; 4659 } 4660 else 4661 { 4662 $T2H_NAME{Up} = &clean_name($node); 4663 $T2H_NODE{Up} = $node; 4664 } 4665 4666 $node = $T2H_NODE{This}; 4667 $node = $node2prev{$node}; 4668 $T2H_NAME{Prev} = &clean_name($node); 4669 $T2H_HREF{Prev} = $node2href{$node}; 4670 $T2H_NODE{Prev} = $node; 4671 4672 $node = $T2H_NODE{This}; 4673 if ($node2up{$node} && $node2up{$node} ne 'Top'&& 4674 ($node2prev{$node} eq $T2H_NODE{Back} || ! $node2prev{$node})) 4675 { 4676 $node = $node2up{$node}; 4677 while ($node && $node ne $node2up{$node} && ! $node2prev{$node}) 4678 { 4679 $node = $node2up{$node}; 4680 } 4681 $node = $node2prev{$node} 4682 unless $node2up{$node} eq 'Top' || ! $node2up{$node}; 4683 } 4684 else 4685 { 4686 $node = $node2prev{$node}; 4687 } 4688 $T2H_NAME{FastBack} = &clean_name($node); 4689 $T2H_HREF{FastBack} = $node2href{$node}; 4690 $T2H_NODE{FastBack} = $node; 4691 4692 $node = $T2H_NODE{This}; 4693 $node = $node2next{$node}; 4694 $T2H_NAME{Next} = &clean_name($node); 4695 $T2H_HREF{Next} = $node2href{$node}; 4696 $T2H_NODE{Next} = $node; 4697 4698 $node = $T2H_NODE{This}; 4699 if ($node2up{$node} && $node2up{$node} ne 'Top'&& 4700 ($node2next{$node} eq $T2H_NODE{Forward} || ! $node2next{$node})) 4701 { 4702 $node = $node2up{$node}; 4703 while ($node && $node ne $node2up{$node} && ! $node2next{$node}) 4704 { 4705 $node = $node2up{$node}; 4706 } 4707 } 4708 $node = $node2next{$node}; 4709 $T2H_NAME{FastForward} = &clean_name($node); 4710 $T2H_HREF{FastForward} = $node2href{$node}; 4711 $T2H_NODE{FastForward} = $node; 4712 4713 if (! defined($FH)) 4714 { 4715 my $file = $T2H_HREF{This}; 4716 $file =~ s/\#.*$//; 4717 open(FILE, "> $docu_rdir$file") || 4718 die "$ERROR: Can't open $docu_rdir$file for writing: $!\n"; 4719 $FH = \*FILE; 4720 &$T2H_print_page_head($FH); 4721 t2h_print_label($FH); 4722 &$T2H_print_chapter_header($FH) if $T2H_SPLIT eq 'chapter'; 4723 } 4724 else 4725 { 4726 t2h_print_label($FH); 4727 } 4728 4729 $T2H_THIS_SECTION = []; 4730 while (@doc_lines) { 4731 $_ = shift(@doc_lines); 4732 last if ($_ eq $SECTIONEND || $_ eq $CHAPTEREND); 4733 push(@$T2H_THIS_SECTION, $_); 4734 } 4735 $previous = $_; 4736 &$T2H_print_section($FH); 4737 4738 if ($T2H_VERBOSE) 4739 { 4740 $counter++; 4741 print "." if $counter =~ /00$/; 4742 } 4743} 4744if ($T2H_SPLIT) 4745{ 4746 &$T2H_print_chapter_footer($FH) if $T2H_SPLIT eq 'chapter'; 4747 &$T2H_print_page_foot($FH); 4748 close($FH); 4749} 4750print "\n" if $T2H_VERBOSE; 4751 4752############################################################################# 4753# Print ToC, Overview, Footnotes 4754# 4755undef $T2H_HREF{Prev}; 4756undef $T2H_HREF{Next}; 4757undef $T2H_HREF{Back}; 4758undef $T2H_HREF{Forward}; 4759undef $T2H_HREF{Up}; 4760 4761if (@foot_lines) 4762{ 4763 print "# writing Footnotes in $docu_foot_file...\n" if $T2H_VERBOSE; 4764 open (FILE, "> $docu_foot_file") || die "$ERROR: Can't open $docu_foot_file for writing: $!\n" 4765 if $T2H_SPLIT; 4766 $T2H_HREF{This} = $docu_foot; 4767 $T2H_NAME{This} = $T2H_WORDS->{$T2H_LANG}->{'Footnotes_Title'}; 4768 $T2H_THIS_SECTION = \@foot_lines; 4769 &$T2H_print_Footnotes(\*FILE); 4770 close(FILE) if $T2H_SPLIT; 4771} 4772 4773if (@toc_lines) 4774{ 4775 print "# writing Toc in $docu_toc_file...\n" if $T2H_VERBOSE; 4776 open (FILE, "> $docu_toc_file") || die "$ERROR: Can't open $docu_toc_file for writing: $!\n" 4777 if $T2H_SPLIT; 4778 $T2H_HREF{This} = $T2H_HREF{Contents}; 4779 $T2H_NAME{This} = $T2H_NAME{Contents}; 4780 $T2H_THIS_SECTION = \@toc_lines; 4781 &$T2H_print_Toc(\*FILE); 4782 close(FILE) if $T2H_SPLIT; 4783} 4784 4785if (@stoc_lines) 4786{ 4787 print "# writing Overview in $docu_stoc_file...\n" if $T2H_VERBOSE; 4788 open (FILE, "> $docu_stoc_file") || die "$ERROR: Can't open $docu_stoc_file for writing: $!\n" 4789 if $T2H_SPLIT; 4790 4791 $T2H_HREF{This} = $T2H_HREF{Overview}; 4792 $T2H_NAME{This} = $T2H_NAME{Overview}; 4793 $T2H_THIS_SECTION = \@stoc_lines; 4794 unshift @$T2H_THIS_SECTION, "<BLOCKQUOTE>\n"; 4795 push @$T2H_THIS_SECTION, "\n</BLOCKQUOTE>\n"; 4796 &$T2H_print_Overview(\*FILE); 4797 close(FILE) if $T2H_SPLIT; 4798} 4799 4800if ($about_body = &$T2H_about_body()) 4801{ 4802 print "# writing About in $docu_about_file...\n" if $T2H_VERBOSE; 4803 open (FILE, "> $docu_about_file") || die "$ERROR: Can't open $docu_about_file for writing: $!\n" 4804 if $T2H_SPLIT; 4805 4806 $T2H_HREF{This} = $T2H_HREF{About}; 4807 $T2H_NAME{This} = $T2H_NAME{About}; 4808 $T2H_THIS_SECTION = [$about_body]; 4809 &$T2H_print_About(\*FILE); 4810 close(FILE) if $T2H_SPLIT; 4811} 4812 4813unless ($T2H_SPLIT) 4814{ 4815 &$T2H_print_page_foot(\*FILE); 4816 close (FILE); 4817} 4818 4819Finish: 4820&l2h_FinishFromHtml if ($T2H_L2H); 4821&l2h_Finish if($T2H_L2H); 4822print "# that's all folks\n" if $T2H_VERBOSE; 4823 4824exit(0); 4825 4826#+++############################################################################ 4827# # 4828# Low level functions # 4829# # 4830#---############################################################################ 4831 4832sub LocateIncludeFile 4833{ 4834 my $file = shift; 4835 my $dir; 4836 4837 return $file if (-e $file && -r $file); 4838 foreach $dir (@T2H_INCLUDE_DIRS) 4839 { 4840 return "$dir/$file" if (-e "$dir/$file" && -r "$dir/$file"); 4841 } 4842 return undef; 4843} 4844 4845sub clean_name 4846{ 4847 local ($_); 4848 $_ = &remove_style($_[0]); 4849 &unprotect_texi; 4850 return $_; 4851} 4852 4853sub update_sec_num { 4854 local($name, $level) = @_; 4855 my $ret; 4856 4857 $level--; # here we start at 0 4858 if ($name =~ /^appendix/ || defined(@appendix_sec_num)) { 4859 # appendix style 4860 if (defined(@appendix_sec_num)) { 4861 &incr_sec_num($level, @appendix_sec_num); 4862 } else { 4863 @appendix_sec_num = ('A', 0, 0, 0); 4864 } 4865 $ret = join('.', @appendix_sec_num[0..$level]); 4866 } else { 4867 # normal style 4868 if (defined(@normal_sec_num)) 4869 { 4870 &incr_sec_num($level, @normal_sec_num); 4871 } 4872 else 4873 { 4874 @normal_sec_num = (1, 0, 0, 0); 4875 } 4876 $ret = join('.', @normal_sec_num[0..$level]); 4877 } 4878 4879 $ret .= "." if $level == 0; 4880 return $ret; 4881} 4882 4883sub incr_sec_num { 4884 local($level, $l); 4885 $level = shift(@_); 4886 $_[$level]++; 4887 foreach $l ($level+1 .. 3) { 4888 $_[$l] = 0; 4889 } 4890} 4891 4892sub Sec2UpNode 4893{ 4894 my $sec = shift; 4895 my $num = $sec2number{$sec}; 4896 4897 return '' unless $num; 4898 return 'Top' unless $num =~ /\.\d+/; 4899 $num =~ s/\.[^\.]*$//; 4900 $num = $num . '.' unless $num =~ /\./; 4901 return $sec2node{$number2sec{$num}}; 4902} 4903 4904sub Sec2PrevNode 4905{ 4906 my $sec = shift; 4907 my $num = $sec2number{$sec}; 4908 my ($i, $post); 4909 4910 if ($num =~ /(\w+)(\.$|$)/) 4911 { 4912 $num = $`; 4913 $i = $1; 4914 $post = $2; 4915 if ($i eq 'A') 4916 { 4917 $i = $normal_sec_num[0]; 4918 } 4919 elsif ($i ne '1') 4920 { 4921 # unfortunately, -- operator is not magical 4922 $i = chr(ord($i) + 1); 4923 } 4924 else 4925 { 4926 return ''; 4927 } 4928 return $sec2node{$number2sec{$num . $i . $post}} 4929 } 4930 return ''; 4931} 4932 4933sub Sec2NextNode 4934{ 4935 my $sec = shift; 4936 my $num = $sec2number{$sec}; 4937 my $i; 4938 4939 if ($num =~ /(\w+)(\.$|$)/) 4940 { 4941 $num = $`; 4942 $i = $1; 4943 $post = $2; 4944 if ($post eq '.' && $i eq $normal_sec_num[0]) 4945 { 4946 $i = 'A'; 4947 } 4948 else 4949 { 4950 $i++; 4951 } 4952 return $sec2node{$number2sec{$num . $i . $post}} 4953 } 4954 return ''; 4955} 4956 4957sub check { 4958 local($_, %seen, %context, $before, $match, $after); 4959 4960 while (<>) { 4961 if (/\@(\*|\.|\:|\@|\{|\})/) { 4962 $seen{$&}++; 4963 $context{$&} .= "> $_" if $T2H_VERBOSE; 4964 $_ = "$`XX$'"; 4965 redo; 4966 } 4967 if (/\@(\w+)/) { 4968 ($before, $match, $after) = ($`, $&, $'); 4969 if ($before =~ /\b[\w-]+$/ && $after =~ /^[\w-.]*\b/) { # e-mail address 4970 $seen{'e-mail address'}++; 4971 $context{'e-mail address'} .= "> $_" if $T2H_VERBOSE; 4972 } else { 4973 $seen{$match}++; 4974 $context{$match} .= "> $_" if $T2H_VERBOSE; 4975 } 4976 $match =~ s/^\@/X/; 4977 $_ = "$before$match$after"; 4978 redo; 4979 } 4980 } 4981 4982 foreach (sort(keys(%seen))) { 4983 if ($T2H_VERBOSE) { 4984 print "$_\n"; 4985 print $context{$_}; 4986 } else { 4987 print "$_ ($seen{$_})\n"; 4988 } 4989 } 4990} 4991 4992sub open { 4993 local($name) = @_; 4994 4995 ++$fh_name; 4996 if (open($fh_name, $name)) { 4997 unshift(@fhs, $fh_name); 4998 } else { 4999 warn "$ERROR Can't read file $name: $!\n"; 5000 } 5001} 5002 5003sub init_input { 5004 @fhs = (); # hold the file handles to read 5005 @input_spool = (); # spooled lines to read 5006 $fh_name = 'FH000'; 5007 &open($docu); 5008} 5009 5010sub next_line { 5011 local($fh, $line); 5012 5013 if (@input_spool) { 5014 $line = shift(@input_spool); 5015 return($line); 5016 } 5017 while (@fhs) { 5018 $fh = $fhs[0]; 5019 $line = <$fh>; 5020 return($line) if $line; 5021 close($fh); 5022 shift(@fhs); 5023 } 5024 return(undef); 5025} 5026 5027# used in pass 1, use &next_line 5028sub skip_until { 5029 local($tag) = @_; 5030 local($_); 5031 5032 while ($_ = &next_line) { 5033 return if /^\@end\s+$tag\s*$/; 5034 } 5035 die "* Failed to find '$tag' after: " . $lines[$#lines]; 5036} 5037 5038# used in pass 1 for l2h use &next_line 5039sub string_until { 5040 local($tag) = @_; 5041 local($_, $string); 5042 5043 while ($_ = &next_line) { 5044 return $string if /^\@end\s+$tag\s*$/; 5045# $_ =~ s/hbox/mbox/g; 5046 $string = $string.$_; 5047 } 5048 die "* Failed to find '$tag' after: " . $lines[$#lines]; 5049} 5050 5051# 5052# HTML stacking to have a better HTML output 5053# 5054 5055sub html_reset { 5056 @html_stack = ('html'); 5057 $html_element = 'body'; 5058} 5059 5060sub html_push { 5061 local($what) = @_; 5062 push(@html_stack, $html_element); 5063 $html_element = $what; 5064} 5065 5066sub html_push_if { 5067 local($what) = @_; 5068 push(@html_stack, $html_element) 5069 if ($html_element && $html_element ne 'P'); 5070 $html_element = $what; 5071} 5072 5073sub html_pop { 5074 $html_element = pop(@html_stack); 5075} 5076 5077sub html_pop_if { 5078 local($elt); 5079 5080 if (@_) { 5081 foreach $elt (@_) { 5082 if ($elt eq $html_element) { 5083 $html_element = pop(@html_stack) if @html_stack; 5084 last; 5085 } 5086 } 5087 } else { 5088 $html_element = pop(@html_stack) if @html_stack; 5089 } 5090} 5091 5092sub html_debug { 5093 local($what, $line) = @_; 5094 if ($T2H_DEBUG & $DEBUG_HTML) 5095 { 5096 $what = "\n" unless $what; 5097 return("<!-- $line @html_stack, $html_element -->$what") 5098 } 5099 return($what); 5100} 5101 5102# to debug the output... 5103sub debug { 5104 local($what, $line) = @_; 5105 return("<!-- $line -->$what") 5106 if $T2H_DEBUG & $DEBUG_HTML; 5107 return($what); 5108} 5109 5110sub SimpleTexi2Html 5111{ 5112 local $_ = $_[0]; 5113 &protect_texi; 5114 &protect_html; 5115 $_ = substitute_style($_); 5116 $_[0] = $_; 5117} 5118 5119sub normalise_node { 5120 local $_ = $_[0]; 5121 s/\s+/ /g; 5122 s/ $//; 5123 s/^ //; 5124 &protect_texi; 5125 &protect_html; 5126 $_ = substitute_style($_); 5127 $_[0] = $_; 5128} 5129 5130sub menu_entry 5131{ 5132 my ($node, $name, $descr) = @_; 5133 my ($href, $entry); 5134 5135 &normalise_node($node); 5136 $href = $node2href{$node}; 5137 if ($href) 5138 { 5139 $descr =~ s/^\s+//; 5140 $descr =~ s/\s*$//; 5141 $descr = SimpleTexi2Html($descr); 5142 if ($T2H_NUMBER_SECTIONS && !$T2H_NODE_NAME_IN_MENU && $node2sec{$node}) 5143 { 5144 $entry = $node2sec{$node}; 5145 $name = ''; 5146 } 5147 else 5148 { 5149 &normalise_node($name); 5150 $entry = ($name && ($name ne $node || ! $T2H_AVOID_MENU_REDUNDANCY) 5151 ? "$name : $node" : $node); 5152 } 5153 5154 if ($T2H_AVOID_MENU_REDUNDANCY && $descr) 5155 { 5156 my $clean_entry = $entry; 5157 $clean_entry =~ s/^.*? // if ($clean_entry =~ /^([A-Z]|\d+)\.[\d\.]* /); 5158 $clean_entry =~ s/[^\w]//g; 5159 my $clean_descr = $descr; 5160 $clean_descr =~ s/[^\w]//g; 5161 $descr = '' if ($clean_entry eq $clean_descr) 5162 } 5163 push(@lines2,&debug('<TR><TD ALIGN="left" VALIGN="TOP">' . 5164 &t2h_anchor('', $href, $entry) . 5165 '</TD><TD> </TD><TD ALIGN="left" VALIGN="TOP">' . 5166 $descr . 5167 "</TD></TR>\n", __LINE__)); 5168 } 5169 elsif ($node =~ /^\(.*\)\w+/) 5170 { 5171 push(@lines2,&debug('<TR><TD ALIGN="left" VALIGN="TOP">' . 5172 $entry . 5173 '</TD><TD ALIGN="left" VALIGN="TOP">' . $descr . 5174 "</TD></TR>\n", __LINE__)) 5175 } 5176 else 5177 { 5178 warn "$ERROR Undefined node of menu_entry ($node): $_"; 5179 } 5180} 5181 5182sub do_ctrl { "^$_[0]" } 5183 5184sub do_email { 5185 local($addr, $text) = split(/,\s*/, $_[0]); 5186 5187 $text = $addr unless $text; 5188 &t2h_anchor('', "mailto:$addr", $text); 5189} 5190 5191sub do_sc 5192{ 5193 # l2h does this much better 5194 return &l2h_ToLatex("{\\sc ".&unprotect_html($_[0])."}") if ($T2H_L2H); 5195 return "\U$_[0]\E"; 5196} 5197 5198sub do_math 5199{ 5200 return &l2h_ToLatex("\$".&unprotect_html($_[0])."\$") if ($T2H_L2H); 5201 return "<EM>".$text."</EM>"; 5202} 5203 5204sub do_uref { 5205 local($url, $text, $only_text) = split(/,\s*/, $_[0]); 5206 5207 $text = $only_text if $only_text; 5208 $text = $url unless $text; 5209 &t2h_anchor('', $url, $text); 5210} 5211 5212sub do_url { &t2h_anchor('', $_[0], $_[0]) } 5213 5214sub do_acronym 5215{ 5216 return '<FONT SIZE="-1">' . $_[0] . '</FONT>'; 5217} 5218 5219sub do_accent 5220{ 5221 return "&$_[0]acute;" if $_[1] eq 'H'; 5222 return "$_[0]." if $_[1] eq 'dotaccent'; 5223 return "$_[0]*" if $_[1] eq 'ringaccent'; 5224 return "$_[0]".'[' if $_[1] eq 'tieaccent'; 5225 return "$_[0]".'(' if $_[1] eq 'u'; 5226 return "$_[0]_" if $_[1] eq 'ubaraccent'; 5227 return ".$_[0]" if $_[1] eq 'udotaccent'; 5228 return "$_[0]<" if $_[1] eq 'v'; 5229 return "&$_[0]cedil;" if $_[1] eq ','; 5230 return "$_[0]" if $_[1] eq 'dotless'; 5231 return undef; 5232} 5233 5234sub apply_style { 5235 local($texi_style, $text) = @_; 5236 local($style); 5237 5238 $style = $style_map{$texi_style}; 5239 if (defined($style)) { # known style 5240 if ($style =~ /^\"/) { # add quotes 5241 $style = $'; 5242 $text = "\`$text\'"; 5243 } 5244 if ($style =~ /^\&/) { # custom 5245 $style = $'; 5246 $text = &$style($text, $texi_style); 5247 } elsif ($style) { # good style 5248 $text = "<$style>$text</$style>"; 5249 } else { # no style 5250 } 5251 } else { # unknown style 5252 $text = undef; 5253 } 5254 return($text); 5255} 5256 5257# remove Texinfo styles 5258sub remove_style { 5259 local($_) = @_; 5260 1 while(s/\@\w+{([^\{\}]+)}/$1/g); 5261 return($_); 5262} 5263 5264sub remove_things 5265{ 5266 local ($_) = @_; 5267 s|\@(\w+)\{\}|$1|g; 5268 return $_; 5269} 5270 5271sub substitute_style { 5272 local($_) = @_; 5273 local($changed, $done, $style, $text); 5274 5275 &simple_substitutions; 5276 $changed = 1; 5277 while ($changed) { 5278 $changed = 0; 5279 $done = ''; 5280 while (/\@(\w+){([^\{\}]+)}/ || /\@(,){([^\{\}]+)}/) { 5281 $text = &apply_style($1, $2); 5282 if ($text) { 5283 $_ = "$`$text$'"; 5284 $changed = 1; 5285 } else { 5286 $done .= "$`\@$1"; 5287 $_ = "{$2}$'"; 5288 } 5289 } 5290 $_ = $done . $_; 5291 } 5292 return($_); 5293} 5294 5295sub t2h_anchor { 5296 local($name, $href, $text, $newline, $extra_attribs) = @_; 5297 local($result); 5298 5299 $result = "<A"; 5300 $result .= " NAME=\"$name\"" if $name; 5301 if ($href) 5302 { 5303 $href =~ s|^$T2H_HREF_DIR_INSTEAD_FILE|./| 5304 if ($T2H_HREF_DIR_INSTEAD_FILE); 5305 $result .= ($href =~ /\"/ ? " HREF='$href'" : " HREF=\"$href\""); 5306 } 5307 $result .= " $extra_attribs" if $extra_attribs; 5308 $result .= ">$text</A>"; 5309 $result .= "\n" if $newline; 5310 return($result); 5311} 5312 5313sub pretty_date { 5314 local(@MoY, $sec, $min, $hour, $mday, $mon, $year, $wday, $yday, $isdst); 5315 5316 @MoY = ('January', 'February', 'March', 'April', 'May', 'June', 5317 'July', 'August', 'September', 'October', 'November', 'December'); 5318 ($sec, $min, $hour, $mday, $mon, $year, $wday, $yday, $isdst) = localtime(time); 5319 $year += ($year < 70) ? 2000 : 1900; 5320 # obachman: Let's do it as the Americans do 5321 return("$MoY[$mon], $mday $year"); 5322} 5323 5324sub doc_href { 5325 local($num) = @_; 5326 5327 return("${docu_name}_$num.$docu_ext"); 5328} 5329 5330sub sec_href 5331{ 5332 return $node2href{$sec2node{$_[0]}}; 5333} 5334 5335sub next_doc { 5336 $docu_doc = &doc_href(++$doc_num); 5337} 5338 5339sub t2h_print_lines { 5340 my ($fh, $lines) = @_; 5341 local($_); 5342 $lines = $T2H_THIS_SECTION unless $lines; 5343 my $cnt = 0; 5344 for (@$lines) 5345 { 5346 $_ = l2h_FromHtml($_) if ($T2H_L2H); 5347 if (/^$PROTECTTAG/o) { 5348 $_ = $tag2pro{$_}; 5349 } else { 5350 &unprotect_texi; 5351 } 5352 print $fh $_; 5353 $cnt += split(/\W*\s+\W*/); 5354 } 5355 return $cnt; 5356} 5357 5358sub protect_texi { 5359 # protect @ { } ` ' 5360 s/\@\@/$;0/go; 5361 s/\@\{/$;1/go; 5362 s/\@\}/$;2/go; 5363 s/\@\`/$;3/go; 5364 s/\@\'/$;4/go; 5365} 5366 5367sub protect_html { 5368 local($what) = @_; 5369 # protect & < > 5370 $what =~ s/\&/\&\#38;/g; 5371 $what =~ s/\</\&\#60;/g; 5372 $what =~ s/\>/\&\#62;/g; 5373 # restore anything in quotes 5374 # this fixes my problem where I had: 5375 # < IMG SRC="leftarrow.gif" ALT="<--" > but what if I wanted < in my ALT text ?? 5376 # maybe byte stuffing or some other technique should be used. 5377 $what =~ s/\"([^\&]+)\&\#60;(.*)\"/"$1<$2"/g; 5378 $what =~ s/\"([^\&]+)\&\#62;(.*)\"/"$1>$2"/g; 5379 $what =~ s/\"([^\&]+)\&\#38;(.*)\"/"$1&$2"/g; 5380 # but recognize some HTML things 5381 $what =~ s/\&\#60;\/A\&\#62;/<\/A>/g; # </A> 5382 $what =~ s/\&\#60;A ([^\&]+)\&\#62;/<A $1>/g; # <A [^&]+> 5383 $what =~ s/\&\#60;IMG ([^\&]+)\&\#62;/<IMG $1>/g; # <IMG [^&]+> 5384 return($what); 5385} 5386 5387sub unprotect_texi { 5388 s/$;0/\@/go; 5389 s/$;1/\{/go; 5390 s/$;2/\}/go; 5391 s/$;3/\`/go; 5392 s/$;4/\'/go; 5393} 5394 5395sub Unprotect_texi 5396{ 5397 local $_ = shift; 5398 &unprotect_texi; 5399 return($_); 5400} 5401 5402sub unprotect_html { 5403 local($what) = @_; 5404 $what =~ s/\&\#38;/\&/g; 5405 $what =~ s/\&\#60;/\</g; 5406 $what =~ s/\&\#62;/\>/g; 5407 return($what); 5408} 5409 5410sub t2h_print_label 5411{ 5412 my $fh = shift; 5413 my $href = shift || $T2H_HREF{This}; 5414 $href =~ s/.*#(.*)$/$1/; 5415 print $fh qq{<A NAME="$href"></A>\n}; 5416} 5417 5418############################################################################## 5419 5420 # These next few lines are legal in both Perl and nroff. 5421 5422.00 ; # finish .ig 5423 5424'di \" finish diversion--previous line must be blank 5425.nr nl 0-1 \" fake up transition to first page again 5426.nr % 0 \" start at page 1 5427'; __END__ ############# From here on it's a standard manual page ############ 5428.so /usr/local/man/man1/texi2html.1 5429