summaryrefslogtreecommitdiff
path: root/biblio/bibtex/utils/bib2ml
diff options
context:
space:
mode:
Diffstat (limited to 'biblio/bibtex/utils/bib2ml')
-rw-r--r--biblio/bibtex/utils/bib2ml/AUTHORS14
-rw-r--r--biblio/bibtex/utils/bib2ml/COPYING341
-rw-r--r--biblio/bibtex/utils/bib2ml/Changelog389
-rw-r--r--biblio/bibtex/utils/bib2ml/INSTALL2
-rw-r--r--biblio/bibtex/utils/bib2ml/NEWS2
-rw-r--r--biblio/bibtex/utils/bib2ml/README13
-rw-r--r--biblio/bibtex/utils/bib2ml/TODO3
-rw-r--r--biblio/bibtex/utils/bib2ml/VERSION1
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/deb-specific/checkinstall.pl81
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2html.docs2
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2html.install28
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2html.manpages2
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/debian/bib2html.postinst16
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/debian/bib2html.prerm16
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2ml-common.docs2
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2ml-common.install28
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2sql.docs2
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2sql.install2
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2sql.manpages2
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/debian/bib2sql.postinst16
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/debian/bib2sql.prerm16
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2xml.docs2
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2xml.install4
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/bib2xml.manpages2
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/debian/bib2xml.postinst16
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/debian/bib2xml.prerm16
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/changelog475
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/compat1
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/control48
-rw-r--r--biblio/bibtex/utils/bib2ml/debian/copyright9
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/debian/rules75
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/bibtexml_dtd.html173
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/capture.pngbin0 -> 203295 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/capture2.pngbin0 -> 219500 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/index.html1320
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/mustwork.gifbin0 -> 1245 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/not-validated.gifbin0 -> 1280 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/optional.gifbin0 -> 1326 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/required.gifbin0 -> 1385 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/requiredor.pngbin0 -> 1954 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/requiredor2.pngbin0 -> 1848 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/sql_schema.pngbin0 -> 24379 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/sql_schema_small.pngbin0 -> 8129 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/validated.gifbin0 -> 1301 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/doc/work.gifbin0 -> 1326 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/man/bib2html_en.pod209
-rw-r--r--biblio/bibtex/utils/bib2ml/man/bib2html_fr.pod206
-rw-r--r--biblio/bibtex/utils/bib2ml/man/bib2sql_en.pod215
-rw-r--r--biblio/bibtex/utils/bib2ml/man/bib2sql_fr.pod212
-rw-r--r--biblio/bibtex/utils/bib2ml/man/bib2xml_en.pod214
-rw-r--r--biblio/bibtex/utils/bib2ml/man/bib2xml_fr.pod211
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Checker/Names.pm251
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Encode.pm138
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Error.pm443
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/HTML.pm1539
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Misc.pm1554
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Title.pm145
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Verbose.pm241
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/AbstractGenerator.pm1226
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/DomainGen.pm564
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/ExtendedGen.pm714
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/FileWriter.pm307
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/HTMLGen.pm2334
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang.pm319
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English86
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.HTMLGen54
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.Theme.Dyna22
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French86
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.HTMLGen55
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.Theme.Dyna22
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian86
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.HTMLGen56
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.Theme.Dyna22
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese86
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.HTMLGen56
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.Theme.Dyna22
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish87
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.HTMLGen55
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.Theme.Dyna23
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/LangManager.pm382
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SQLGen.pm746
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/MySql.pm214
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/PgSql.pm214
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/StdOutWriter.pm163
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme.pm1418
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna.pm1401
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/child.gifbin0 -> 91 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/emptychild.gifbin0 -> 53 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/lastchild.gifbin0 -> 88 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/minus.gifbin0 -> 54 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/plus.gifbin0 -> 56 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/samechild.gifbin0 -> 64 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/stylesheet.css180
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Simple.pm678
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Writer.pm211
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/XMLGen.pm1364
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML-ext.dtd161
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML.dtd816
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/drive.pngbin0 -> 926 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/loupe.gifbin0 -> 1194 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-css.gifbin0 -> 1134 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-html401.gifbin0 -> 2328 bytes
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/JabRef/JabRef.pm209
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Main.pm433
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/BibScanner.pm817
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Parser.pm477
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Scanner.pm490
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/StateMachine.pm643
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Release.pm89
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXEntry.pm498
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXName.pm931
-rw-r--r--biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/TeX.pm2603
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/src/bib2html.php41
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/src/bib2html.pl55
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/src/bib2sql.pl57
-rwxr-xr-xbiblio/bibtex/utils/bib2ml/src/bib2xml.pl57
-rw-r--r--biblio/bibtex/utils/bib2ml/test.bib5
117 files changed, 30332 insertions, 0 deletions
diff --git a/biblio/bibtex/utils/bib2ml/AUTHORS b/biblio/bibtex/utils/bib2ml/AUTHORS
new file mode 100644
index 0000000000..075f3145ac
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/AUTHORS
@@ -0,0 +1,14 @@
+Authors:
+Stéphane GALLAND <galland@arakhne.org>
+
+Contributors:
+Aurel GABRIS <gabrisa@optics.szfki.kfki.hu>
+Gasper JAKLIC <gasper.jaklic@fmf.uni-lj.si>
+Tobias LOEW <loew@mathematik.tu-darmstadt.de>
+Joao LOURENCO <joao.lourenco@di.fct.unl.pt>
+Dimitris MICHAIL <michail@mpi-sb.mpg.de>
+Luca PAOLINI <paolini@di.unito.it>
+Norbert PREINING <preining@logic.at>
+Cristian RIGAMONTI <cri@linux.it>
+Sebastian RODRIGUEZ <sebastian.rodriguez@utbm.fr>
+Martin P.J. ZINSER <zinser@zinser.no-ip.info>
diff --git a/biblio/bibtex/utils/bib2ml/COPYING b/biblio/bibtex/utils/bib2ml/COPYING
new file mode 100644
index 0000000000..1942c4334c
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/COPYING
@@ -0,0 +1,341 @@
+ GNU GENERAL PUBLIC LICENSE
+ Version 2, June 1991
+
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.
+ 59 Temple Place - Suite 330
+ Boston, MA 02111-1307, USA.
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+ Preamble
+
+ The licenses for most software are designed to take away your
+freedom to share and change it. By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users. This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it. (Some other Free Software Foundation software is covered by
+the GNU Library General Public License instead.) You can apply it to
+your programs, too.
+
+ When we speak of free software, we are referring to freedom, not
+price. Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+ To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if you
+distribute copies of the software, or if you modify it.
+
+ For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have. You must make sure that they, too, receive or can get the
+source code. And you must show them these terms so they know their
+rights.
+
+ We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+ Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software. If the software is modified by someone else and passed on, we
+want its recipients to know that what they have is not the original, so
+that any problems introduced by others will not reflect on the original
+authors' reputations.
+
+ Finally, any free program is threatened constantly by software
+patents. We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary. To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at all.
+
+ The precise terms and conditions for copying, distribution and
+modification follow.
+
+ GNU GENERAL PUBLIC LICENSE
+ TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+ 0. This License applies to any program or other work which contains
+a notice placed by the copyright holder saying it may be distributed
+under the terms of this General Public License. The "Program", below,
+refers to any such program or work, and a "work based on the Program"
+means either the Program or any derivative work under copyright law:
+that is to say, a work containing the Program or a portion of it,
+either verbatim or with modifications and/or translated into another
+language. (Hereinafter, translation is included without limitation in
+the term "modification".) Each licensee is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope. The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the
+Program (independent of having been made by running the Program).
+Whether that is true depends on what the Program does.
+
+ 1. You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a fee.
+
+ 2. You may modify your copy or copies of the Program or any portion
+of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+ a) You must cause the modified files to carry prominent notices
+ stating that you changed the files and the date of any change.
+
+ b) You must cause any work that you distribute or publish, that in
+ whole or in part contains or is derived from the Program or any
+ part thereof, to be licensed as a whole at no charge to all third
+ parties under the terms of this License.
+
+ c) If the modified program normally reads commands interactively
+ when run, you must cause it, when started running for such
+ interactive use in the most ordinary way, to print or display an
+ announcement including an appropriate copyright notice and a
+ notice that there is no warranty (or else, saying that you provide
+ a warranty) and that users may redistribute the program under
+ these conditions, and telling the user how to view a copy of this
+ License. (Exception: if the Program itself is interactive but
+ does not normally print such an announcement, your work based on
+ the Program is not required to print an announcement.)
+
+These requirements apply to the modified work as a whole. If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works. But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+ 3. You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+ a) Accompany it with the complete corresponding machine-readable
+ source code, which must be distributed under the terms of Sections
+ 1 and 2 above on a medium customarily used for software interchange; or,
+
+ b) Accompany it with a written offer, valid for at least three
+ years, to give any third party, for a charge no more than your
+ cost of physically performing source distribution, a complete
+ machine-readable copy of the corresponding source code, to be
+ distributed under the terms of Sections 1 and 2 above on a medium
+ customarily used for software interchange; or,
+
+ c) Accompany it with the information you received as to the offer
+ to distribute corresponding source code. (This alternative is
+ allowed only for noncommercial distribution and only if you
+ received the program in object code or executable form with such
+ an offer, in accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it. For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable. However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+
+ 4. You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License. Any attempt
+otherwise to copy, modify, sublicense or distribute the Program is
+void, and will automatically terminate your rights under this License.
+However, parties who have received copies, or rights, from you under
+this License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+ 5. You are not required to accept this License, since you have not
+signed it. However, nothing else grants you permission to modify or
+distribute the Program or its derivative works. These actions are
+prohibited by law if you do not accept this License. Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+ 6. Each time you redistribute the Program (or any work based on the
+Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions. You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+ 7. If, as a consequence of a court judgment or allegation of patent
+infringement or for any other reason (not limited to patent issues),
+conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License. If you cannot
+distribute so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you
+may not distribute the Program at all. For example, if a patent
+license would not permit royalty-free redistribution of the Program by
+all those who receive copies directly or indirectly through you, then
+the only way you could satisfy both it and this License would be to
+refrain entirely from distribution of the Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices. Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+
+ 8. If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded. In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+ 9. The Free Software Foundation may publish revised and/or new versions
+of the General Public License from time to time. Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+Each version is given a distinguishing version number. If the Program
+specifies a version number of this License which applies to it and "any
+later version", you have the option of following the terms and conditions
+either of that version or of any later version published by the Free
+Software Foundation. If the Program does not specify a version number of
+this License, you may choose any version ever published by the Free Software
+Foundation.
+
+ 10. If you wish to incorporate parts of the Program into other free
+programs whose distribution conditions are different, write to the author
+to ask for permission. For software which is copyrighted by the Free
+Software Foundation, write to the Free Software Foundation; we sometimes
+make exceptions for this. Our decision will be guided by the two goals
+of preserving the free status of all derivatives of our free software and
+of promoting the sharing and reuse of software generally.
+
+ NO WARRANTY
+
+ 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
+REPAIR OR CORRECTION.
+
+ 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+ END OF TERMS AND CONDITIONS
+
+ How to Apply These Terms to Your New Programs
+
+ If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+ To do so, attach the following notices to the program. It is safest
+to attach them to the start of each source file to most effectively
+convey the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+ <one line to give the program's name and a brief idea of what it does.>
+ Copyright (C) 19yy <name of author>
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; see the file COPYING. If not, write to
+ the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ Boston, MA 02111-1307, USA.
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program is interactive, make it output a short notice like this
+when it starts in an interactive mode:
+
+ Gnomovision version 69, Copyright (C) 19yy name of author
+ Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+ This is free software, and you are welcome to redistribute it
+ under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License. Of course, the commands you use may
+be called something other than `show w' and `show c'; they could even be
+mouse-clicks or menu items--whatever suits your program.
+
+You should also get your employer (if you work as a programmer) or your
+school, if any, to sign a "copyright disclaimer" for the program, if
+necessary. Here is a sample; alter the names:
+
+ Yoyodyne, Inc., hereby disclaims all copyright interest in the program
+ `Gnomovision' (which makes passes at compilers) written by James Hacker.
+
+ <signature of Ty Coon>, 1 April 1989
+ Ty Coon, President of Vice
+
+This General Public License does not permit incorporating your program into
+proprietary programs. If your program is a subroutine library, you may
+consider it more useful to permit linking proprietary applications with the
+library. If this is what you want to do, use the GNU Library General
+Public License instead of this License.
diff --git a/biblio/bibtex/utils/bib2ml/Changelog b/biblio/bibtex/utils/bib2ml/Changelog
new file mode 100644
index 0000000000..2943616466
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/Changelog
@@ -0,0 +1,389 @@
+2011-07-31 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.7
+ * bib2sql: Bug fix: the bibtex_entrytype table is not filled with the types
+ of the entries due to an error in a boolean condition.
+ * bib2sql: Notify with a warning when the same author seems to appear many times
+ for the same entry.
+ * bib2sql: add command line parameter 'sql-engine' which permits to specify
+ the SQL engine for which the SQL script should be generated.
+ * bib2sql: create the MySQL support.
+ * bib2sql: create the PostgreSQL support.
+
+2011-07-27 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.6
+ * bib2sql: the word "order" could not be used as variable name because it is a
+ reserved word in SQL syntax. Rename it as "order_id".
+ * bib2sql: Ensure that the numerical identifiers of the authors and editors are unique.
+
+2009-03-21 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.5
+ * Extend the syntax supported for the bibtex keys, but output a warning.
+ * Add warning message when a language file was not found (verbose mode 2 or higher).
+
+2009-03-15 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.4
+ * Add function which remove the accents from an HTML string. This function is used to have consistent sorting outputs.
+ * Changes the labels of the trees' root nodes.
+ * The C and c acute characters are now correctly substitued.
+ * Bug fix: the caron TeX characters are not translated into well-formated HTML characters. Fixed
+ * Bug fix: in Simple.pm, some hash references have not a generic syntax which cause invalid invalid hash refs exceptions.
+ * Change the official website address from "www.arakhne.org/bib2html" to "www.arakhne.org/bib2ml".
+
+2008-08-01 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.3
+ * Add the support for the TeX command \url.
+ * Major bug fix: the locale support of the Theme were not loaded. Fixed.
+
+2008-05-28 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.2
+ * Bug fix: several thrid-party tools declare BibTeX fields
+ with a name composed of the special characters "-_0-9:.".
+ The BibTeX parser now supports this kind of field name.
+
+2007-07-25 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.1
+ * Rename the tool Bib2HTML into Bib2ML which is more
+ closer to the different available translations.
+ And it will prepare the submission to CTAN.
+
+2007-04-16 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.1
+ * Feature:
+ - When the 'pdf' field contains a local file reference, it
+ will be replaced by the 'localfile' field.
+
+2007-03-21 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 6.0
+ * Feature:
+ - Add the BibTeX field "doi".
+ - Add the support of JabRef's groups.
+
+2006-10-06 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 5.1
+ * Feature:
+ - Add new LaTeX commands: \mathbb, \{, \}
+ * Bug fixes:
+ - in the XML generator, the quotation, the ampersand
+ and the less-then and greater-than characters are
+ not properly processed.
+ - The sorting functions was re-implemented to
+ tackle problems one accentuated characters.
+ - The 'inbook' entries will be proceeded as the
+ "book" entries.
+
+2006-08-31 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 5.0
+ * Feature:
+ - Add the SQL generator.
+ - Add the generator parameter 'xml-encoding'
+ - Add the command line options '--protect', '--cvs', '--svn'
+ * Bug fixes:
+ - Rewrite some error messages to be more understandable.
+
+2006-05-31 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 4.4
+ * Feature:
+ - Add the support for the TeX commands \string, \edef, \xdef
+ - Add the generator parameter 'html-encoding'
+
+2006-05-29 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 4.3
+ * Feature:
+ - Tobia adds the support for some roman characters.
+
+2006-05-03 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 4.2
+ * Feature:
+ - Add the support of the BibTeX field 'adsurl' which permits
+ to link to the standard Astrophysics Citation Reference Database.
+
+2006-04-12 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 4.1
+ * Bug:
+ - When the BibTeX parser find multi-definition of BibTeX strings,
+ it dies on an undefined subroutine error.
+
+2006-04-10 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 4.0
+ * Feature:
+ - Do not display in verbatim mode the BibTeX fields with
+ a name starting with "opt".
+ - Luca patches the TeX translator for supporting more letters
+ with the caron accent.
+ - From a Luca's request, the generator parameter 'hideindex'
+ is introduced to allow hiding of the indexes.
+ - Aurel introduces the generator parameters 'max-titlelength-overview'
+ and 'show-journalparams-overview'.
+ - Stephane introduces the generator parameter 'doc-repository'.
+ - Stephane introduces the command 'bib2xml' as a specialization
+ of bib2html (with the option -g XML).
+ * Bug:
+ - The translator does not produce the right default value for
+ the TeX command \v.
+ - The HTML function which permits to extract author initials
+ was fixed to support in entry name's initials.
+ - The list of generators was ot properly displayed if
+ the absolute path to bib2html contains a directory name
+ with a space character.
+ - The list of support languages was ot properly displayed if
+ the absolute path to bib2html contains a directory name
+ with a space character.
+ - The editors was not displayed when the author's list was empty.
+ - The BibTeX references [???] now support HTML characters.
+
+2005-02-14 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 3.3
+ * Feature:
+ - Add some norvegian characters.
+ * Bug:
+ - The parameter of @preamble is now entirely
+ parsed as a string. You don't need any more
+ to enclose the TeX command by braces.
+ - the parser for the author's names know support
+ HTML entities inside the firstnames.
+
+2005-01-25 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 3.2
+ * Feature:
+ - Add the field 'pdf' which must contains the name
+ of a PDF file (an URL or a local filename).
+ - Add the parameter 'backslash' for the Extended
+ generator.
+ * Bug:
+ - In the parser, The token 'string' could be preceeded
+ by a set of space from the start of the line.
+ - Remove the required display of the field 'date'. In
+ BibTeX, the fields 'year' and 'month' replace it.
+ - Be sure that some characters will not be used
+ inside the filnames (e.g. ':').
+ - Major bug fix inside the parser. Multiple specification
+ of BibTeX filename on the command line is now truly
+ supported.
+
+2004-12-06 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 3.1
+ * Features:
+ - Portuguese is included into the generators by Joao.
+ * Bug:
+ - The name of the language passed with '--lang' is now
+ case-insensitive.
+
+2004-12-03 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 3.0
+ * Features:
+ - More TeX commands are added by Dimitris:
+ \epsilon, \Epsilon, \mathbf, \mathit, \mathrm,
+ \mathsf, \mathtt, \mathnormal, \sqrt
+ - Create a XML generator which respect the DTD from
+ BibTeXML.
+ - Add an XML output inside the HTML generator.
+ * Bug:
+ - The character '+' is not allowed inside the entry keys.
+
+2004-11-26 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 2.0
+ * Features:
+ - Spanish is included into the generators by Sebastian.
+ - Links to the author's list of publication was
+ added for each other inside the entry's field
+ list.
+ - The option '--checknames' permits to check if
+ some author's names are duplicated or contain
+ mistakes.
+ * Bug:
+ - the year does not appears inside the table of
+ the fields.
+ - the language support for theme only applies
+ the English definitions, not the other
+ languages (French, Spanish).
+
+2004-11-12 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 1.5
+ * Bug:
+ - sometimes the carriage return characters was
+ not supported by the BibTeX parser.
+ - Generation of the BibTeX short labels (eg. [ABC04])
+ produces too long labels in case a lot of
+ names was proposed to the function.
+ - The names of the authors are not well upper-cased
+ for each first letter of the words.
+ - if an error occurs during the copy of a pdf file,
+ bib2html will not failed but only warm the user.
+
+2004-09-22 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 1.4
+ * Bug: do not copy the electronical file with
+ the generator parameter 'target-url' was specified
+ for the Extended generator.
+
+2004-08-23 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 1.3
+ * Features:
+ - the generator parameter 'type-matching' has its
+ value's syntax extended.
+ - Add the new BibTeX entry type 'proceedings' and
+ 'unpublished'.
+ * Bugs:
+ - The values of the fields 'localfile' and 'url'
+ were not properly extracted.
+ - Fix the indentation of the generated BibTeX section.
+ - Updates some language's strings
+ - Assumes that the characters '-' and '_' are aliases
+ for the character '-' inside the generator
+ parameter's names.
+ - Fix the output to be validable by the W3C validators
+ (HTML 4.01 and CSS).
+
+2004-08-17 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 1.2
+ * Bugs:
+ - rhe special section @comment{} was not properly
+ parsed. Fix it with an update of the regular
+ expression which matches "@COMMENT".
+ - Allow the state "line_comment" to finish the
+ BibTeX file's parsing.
+
+2004-03-27 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 1.1
+ * Features:
+ - enhances the generator parameters 'author-regexp',
+ etc: add many new types instead of one.
+ - add the support of the BibTeX field 'crossref':
+ it permits to implement a kind of inheritance
+ between two entries
+ - add the generation of a BibTeX code verbatim
+ (and the command line parameter which permits
+ to set it on/off)
+ * Bugs:
+ - in indexes, regroup the reference with the same label
+ - put a better header title inside the HTML files of
+ the entries
+ - w3c norm fix: generates the <body> tags
+ - add a white background color for the theme Simple
+ - in ExtendedGen.pm, DomainGen.pm: fix a syntactical
+ error and update to be compliant with fixes that
+ occurs inside HTMLGen.pm
+ - in HTMLGen.pm, Norbert fixes some bug due to the
+ bad inclusion of their patchs for the release 1.0
+ - in Parser.pm: Norbert fixes a infinite loop recusion
+ bug. This bug is due to the definition of a constant
+ with same name and value (in a lowercase comparison).
+ For example: @STRING{springer=Springer} generates a
+ infinite loop.
+ - some code cleaning
+
+2004-03-17 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 1.0
+ * Features:
+ - add generator parameters for the HTMLGen generator:
+ author-regexp, max-names-overview, max-names-list,
+ newtype, type-matching (added by Norbert)
+ * Bugs:
+ - an exception was generated when an entry has no
+ author nor editor.
+ - in bibtex parsing: now support syntax as foo #
+ " and " # bla
+ - applies patchs from Norbert in TeX.pm, Misc.pm
+ and HTMLGen.pm
+
+2004-02-02 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 0.11
+ * Features:
+ - add an index of authors and of author's publications
+ inside the two left frames
+ - add the class AbstractGenerator.pm
+ - add ExtendedGen.pm which permits to generate HTML
+ page with:
+ a) isbn, issn, and readers
+ b) abstract and keywords
+ c) the support for downloading an electronic
+ document ('localfile')
+ - add the support of LaTeX environments (\begin,\end)
+ - add the generator Domain which permits to support
+ domain for documents (domain, nddomain, rddomain,
+ domains)
+ * Bugs:
+ - in HTMLGen.pm, fixes not initialized variable uses
+ - changes the behavior of some command line options
+ - in Parser.pm, support recursive merging operator for strings
+
+2003-12-11 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 0.10
+ * Bugs:
+ - in BibScanner.pm, did not recognized correctly the
+ @STRING commands
+ - in BibScanner.pm, the concatened strings was too
+ early merged (before any replacement by the
+ @STRING's values)
+ - in BibScanner.pm, the parsed field labels must
+ be automatically lower cased. Ut permits to support
+ case-independent label for BibTeX fields
+ - in Scanner.pm, ungetpattern() does not its job well.
+
+2003-09-19 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 0.9
+ * Features:
+ - Adds the generator 'Extended' which support the
+ bibtex tags:
+ * 'url' : URL to informational web page
+ * 'isbn'
+ * 'issn'
+ * 'localfile' : relative path to a file to download
+ * 'abstract'
+ * 'keywords'
+ * 'readers' : informational tag that indicates who
+ read this entry (according to the bibtex name syntax)
+ - Adds the support of "et al." inside the bibtex names.
+ - Adds some command line arguments
+ * Bugs:
+ - in the HTML filename translations.
+ - get the editor field when the author one is empty.
+ - ignore TeX parsing for the fields 'localfile' and 'url'
+ - support more formats for the bibtex author's names:
+ [von] Last, jr, First [and ...]
+ First [von] Last, jr [and ...]
+ [von] Last, First [jr] [and ...]
+ First [von] Last [jr] [and ...]
+ name, [name, ...] [and name]
+
+2003-08-01 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 0.8
+ * Feature: adds the support of the LaTeX commands
+ \cite[]{}
+ * Bugs:
+ - recognizes the character '-' inside the bibkeys
+ - some other minor bug fixes
+
+2003-07-09 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 0.7
+ * Features:
+ - add the support of mathematical modes (not the support
+ of all TeX commands inside the mathematical mode)
+ - partial support of Math-ML
+ * Bugs:
+ - add support of some TeX commands( \i, \~, ...)
+ - ignore text between bibtex entries
+ - better recognition for author names.
+ - warm the user when the "year" is not a number.
+ - suppress redondant error messages.
+ - bug in the verbosing level calculation
+ - some syntaxic fixes
+
+2003-06-26 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 0.6
+ * Features:
+ - adds the multi-language support
+ - adds theme for the HTML generators
+ * Bugs:
+ - some uses of the function sort inside
+ a return are improper. Fixed to be
+ sure that the return statement takes
+ only one value.
+ - adds the function notempty() to permit to
+ have strings which contain only "0"
+
+2003-03-04 Stéphane GALLAND <galland@arakhne.org>
+ * Release: 0.5
+ This is the first public release on the version
+ entirely based on perl.
+
diff --git a/biblio/bibtex/utils/bib2ml/INSTALL b/biblio/bibtex/utils/bib2ml/INSTALL
new file mode 100644
index 0000000000..35b08e392b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/INSTALL
@@ -0,0 +1,2 @@
+File not used.
+See ./doc/index.html instead.
diff --git a/biblio/bibtex/utils/bib2ml/NEWS b/biblio/bibtex/utils/bib2ml/NEWS
new file mode 100644
index 0000000000..2d8c65b2b6
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/NEWS
@@ -0,0 +1,2 @@
+File not used.
+See Changelog instead.
diff --git a/biblio/bibtex/utils/bib2ml/README b/biblio/bibtex/utils/bib2ml/README
new file mode 100644
index 0000000000..bfd7c3dee3
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/README
@@ -0,0 +1,13 @@
+bib2ml (ex bib2html) from Arakhne.org is a Perl script which permits to create a set of HTML pages, an XML file or a SQL script from a BibTeX file.
+It proposes a convenient look and a lot of features (PDF downloading, scientifical domain tree...).
+
+Official website: http://www.arakhne.org/bib2html/
+
+DISLAIMER FROM AUTHORS:
+I’ve come across mention of other bib2html programs. This program is in no way related to any of them. Other BibTeX-to-HTML tools (non-exhautive list) :
+ * bib2html from Kiri Wagstaff
+ * bib2html from David Kotz (also on CTAN)
+ * bib2html from Eric Marchand
+ * bib2html from Mark Moll and Patrick Riley
+
+See ./doc/index.html for more details.
diff --git a/biblio/bibtex/utils/bib2ml/TODO b/biblio/bibtex/utils/bib2ml/TODO
new file mode 100644
index 0000000000..78b2aa0a6a
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/TODO
@@ -0,0 +1,3 @@
+- work on the parsing/generation performances
+- implements croossrefs inside the BibTeX file
+- add translations for console messages
diff --git a/biblio/bibtex/utils/bib2ml/VERSION b/biblio/bibtex/utils/bib2ml/VERSION
new file mode 100644
index 0000000000..a640cad24a
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/VERSION
@@ -0,0 +1 @@
+bib2ml 6.7
diff --git a/biblio/bibtex/utils/bib2ml/deb-specific/checkinstall.pl b/biblio/bibtex/utils/bib2ml/deb-specific/checkinstall.pl
new file mode 100755
index 0000000000..a35ce5957b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/deb-specific/checkinstall.pl
@@ -0,0 +1,81 @@
+#!/usr/bin/perl -w
+
+use strict;
+
+use File::Spec;
+
+sub readInstallFile($) {
+ my $installFile = shift;
+ my @files = ();
+ local *FILE;
+ open(*FILE, "<$installFile") or die("$installFile: $!\n");
+ while (my $line = <FILE>) {
+ if ($line =~ /^\s*([^\s]+)/i) {
+ my $filename = "$1";
+ push @files, $filename;
+ }
+ }
+ close(*FILE);
+ return @files
+}
+
+sub readDir($$) {
+ my $dir = shift;
+ my $pattern = shift;
+ my @subfiles = ();
+ local *DIR;
+ opendir(*DIR,"$dir") or die("$dir: $!\n");
+ while (my $file = readdir(*DIR)) {
+ if ($file ne File::Spec->curdir() && $file ne File::Spec->updir()) {
+ if ($file =~ /^$pattern$/i) {
+ push @subfiles, File::Spec->catfile($dir,$file);
+ }
+ }
+ }
+ closedir(*DIR);
+ return @subfiles;
+}
+
+my @installFiles = readDir("debian", ".*\.install");
+my @toInstall = ();
+
+foreach my $installFile (@installFiles) {
+
+ my @files = readInstallFile($installFile);
+ push @toInstall, @files;
+
+}
+
+my @dirs = ( "src" );
+my $erroroccured = 0;
+
+while (@dirs) {
+ my $dir = pop @dirs;
+ local *DIR;
+ opendir(*DIR, "$dir") or die("$dir: $!\n");
+ while (my $file = readdir(*DIR)) {
+ if ($file ne File::Spec->curdir() && $file ne File::Spec->updir()) {
+ my $fName = File::Spec->catfile($dir,$file);
+ if (-d $fName) {
+ push @dirs, $fName;
+ }
+ else {
+ my $found = 0;
+ foreach my $if (@toInstall) {
+ if ($if eq $fName || $fName =~ /^\Q$if\E/) {
+ $found = 1;
+ last;
+ }
+ }
+ if (!$found) {
+ $erroroccured = 1;
+ print STDERR "FILE $fName IS NOT INSTALLABLE\n";
+ }
+ }
+ }
+ }
+ closedir(*DIR);
+}
+
+exit($erroroccured ? 1 : 0);
+
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2html.docs b/biblio/bibtex/utils/bib2ml/debian/bib2html.docs
new file mode 100644
index 0000000000..ad1ca2d2e9
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2html.docs
@@ -0,0 +1,2 @@
+man/bib2html_en.pod
+man/bib2html_fr.pod
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2html.install b/biblio/bibtex/utils/bib2ml/debian/bib2html.install
new file mode 100644
index 0000000000..b0e182c185
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2html.install
@@ -0,0 +1,28 @@
+src/Bib2HTML/Generator/DomainGen.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/drive.png usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/ExtendedGen.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/HTMLGen.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/loupe.gif usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/Theme.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/valid-css.gif usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/valid-html401.gif usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/Lang/English.HTMLGen usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/French.HTMLGen usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Spanish.HTMLGen usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Italian.HTMLGen usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Portuguese.HTMLGen usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Theme/Dyna.pm usr/lib/bib2ml/Bib2HTML/Generator/Theme
+src/Bib2HTML/Generator/Theme/Simple.pm usr/lib/bib2ml/Bib2HTML/Generator/Theme
+src/Bib2HTML/Generator/Theme/Dyna/child.gif usr/lib/bib2ml/Bib2HTML/Generator/Theme/Dyna
+src/Bib2HTML/Generator/Theme/Dyna/emptychild.gif usr/lib/bib2ml/Bib2HTML/Generator/Theme/Dyna
+src/Bib2HTML/Generator/Theme/Dyna/lastchild.gif usr/lib/bib2ml/Bib2HTML/Generator/Theme/Dyna
+src/Bib2HTML/Generator/Theme/Dyna/minus.gif usr/lib/bib2ml/Bib2HTML/Generator/Theme/Dyna
+src/Bib2HTML/Generator/Theme/Dyna/plus.gif usr/lib/bib2ml/Bib2HTML/Generator/Theme/Dyna
+src/Bib2HTML/Generator/Theme/Dyna/samechild.gif usr/lib/bib2ml/Bib2HTML/Generator/Theme/Dyna
+src/Bib2HTML/Generator/Theme/Dyna/stylesheet.css usr/lib/bib2ml/Bib2HTML/Generator/Theme/Dyna
+src/Bib2HTML/Generator/Lang/English.Theme.Dyna usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/French.Theme.Dyna usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Italian.Theme.Dyna usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Portuguese.Theme.Dyna usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Spanish.Theme.Dyna usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/bib2html.pl usr/lib/bib2ml
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2html.manpages b/biblio/bibtex/utils/bib2ml/debian/bib2html.manpages
new file mode 100644
index 0000000000..01324bbede
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2html.manpages
@@ -0,0 +1,2 @@
+man/bib2html.1.gz
+man/bib2html.fr.1.gz
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2html.postinst b/biblio/bibtex/utils/bib2ml/debian/bib2html.postinst
new file mode 100755
index 0000000000..53f5f5ea05
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2html.postinst
@@ -0,0 +1,16 @@
+#!/bin/bash
+
+set -e
+
+if [ "$1" = configure ]; then
+
+ echo -n "Installing bib2html... "
+
+ update-alternatives --install /usr/bin/bib2html bib2html /usr/lib/bib2ml/bib2html.pl 500 --slave /usr/bin/bibtex2html bibtex2html /usr/lib/bib2ml/bib2html.pl
+ update-alternatives --auto bib2html
+
+ echo "done."
+
+fi
+
+exit 0
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2html.prerm b/biblio/bibtex/utils/bib2ml/debian/bib2html.prerm
new file mode 100755
index 0000000000..73da216f13
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2html.prerm
@@ -0,0 +1,16 @@
+#!/bin/bash
+
+set -e
+
+case "$1" in
+ remove | deconfigure)
+
+ echo -n "Unstalling bib2html... "
+
+ update-alternatives --remove bib2html /usr/lib/bib2ml/bib2html.pl
+
+ echo "done."
+ ;;
+esac
+
+exit 0
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2ml-common.docs b/biblio/bibtex/utils/bib2ml/debian/bib2ml-common.docs
new file mode 100644
index 0000000000..1090c5fd5b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2ml-common.docs
@@ -0,0 +1,2 @@
+doc/*
+src/bib2html.php
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2ml-common.install b/biblio/bibtex/utils/bib2ml/debian/bib2ml-common.install
new file mode 100644
index 0000000000..de2152aa2f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2ml-common.install
@@ -0,0 +1,28 @@
+src/Bib2HTML/Checker/Names.pm usr/lib/bib2ml/Bib2HTML/Checker
+src/Bib2HTML/General/Encode.pm usr/lib/bib2ml/Bib2HTML/General
+src/Bib2HTML/General/Error.pm usr/lib/bib2ml/Bib2HTML/General
+src/Bib2HTML/General/HTML.pm usr/lib/bib2ml/Bib2HTML/General
+src/Bib2HTML/General/Misc.pm usr/lib/bib2ml/Bib2HTML/General
+src/Bib2HTML/General/Title.pm usr/lib/bib2ml/Bib2HTML/General
+src/Bib2HTML/General/Verbose.pm usr/lib/bib2ml/Bib2HTML/General
+src/Bib2HTML/Parser/BibScanner.pm usr/lib/bib2ml/Bib2HTML/Parser
+src/Bib2HTML/Parser/Parser.pm usr/lib/bib2ml/Bib2HTML/Parser
+src/Bib2HTML/Parser/Scanner.pm usr/lib/bib2ml/Bib2HTML/Parser
+src/Bib2HTML/Parser/StateMachine.pm usr/lib/bib2ml/Bib2HTML/Parser
+src/Bib2HTML/Translator/BibTeXEntry.pm usr/lib/bib2ml/Bib2HTML/Translator
+src/Bib2HTML/Translator/BibTeXName.pm usr/lib/bib2ml/Bib2HTML/Translator
+src/Bib2HTML/Translator/TeX.pm usr/lib/bib2ml/Bib2HTML/Translator
+src/Bib2HTML/Main.pm usr/lib/bib2ml/Bib2HTML
+src/Bib2HTML/Release.pm usr/lib/bib2ml/Bib2HTML
+src/Bib2HTML/Generator/AbstractGenerator.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/FileWriter.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/Lang.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/LangManager.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/StdOutWriter.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/Writer.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/Lang/English usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/French usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Spanish usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Italian usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/Generator/Lang/Portuguese usr/lib/bib2ml/Bib2HTML/Generator/Lang
+src/Bib2HTML/JabRef/JabRef.pm usr/lib/bib2ml/Bib2HTML/JabRef
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2sql.docs b/biblio/bibtex/utils/bib2ml/debian/bib2sql.docs
new file mode 100644
index 0000000000..73cb6bbd8c
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2sql.docs
@@ -0,0 +1,2 @@
+man/bib2sql_en.pod
+man/bib2sql_fr.pod
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2sql.install b/biblio/bibtex/utils/bib2ml/debian/bib2sql.install
new file mode 100644
index 0000000000..46523093af
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2sql.install
@@ -0,0 +1,2 @@
+src/Bib2HTML/Generator/SQLGen.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/bib2sql.pl usr/lib/bib2ml
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2sql.manpages b/biblio/bibtex/utils/bib2ml/debian/bib2sql.manpages
new file mode 100644
index 0000000000..cc79e41f6f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2sql.manpages
@@ -0,0 +1,2 @@
+man/bib2sql.1.gz
+man/bib2sql.fr.1.gz
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2sql.postinst b/biblio/bibtex/utils/bib2ml/debian/bib2sql.postinst
new file mode 100755
index 0000000000..f4b1b490bf
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2sql.postinst
@@ -0,0 +1,16 @@
+#!/bin/bash
+
+set -e
+
+if [ "$1" = configure ]; then
+
+ echo -n "Installing bib2sql... "
+
+ update-alternatives --install /usr/bin/bib2sql bib2sql /usr/lib/bib2ml/bib2sql.pl 500 --slave /usr/bin/bibtex2sql bibtex2sql /usr/lib/bib2ml/bib2sql.pl
+ update-alternatives --auto bib2sql
+
+ echo "done."
+
+fi
+
+exit 0
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2sql.prerm b/biblio/bibtex/utils/bib2ml/debian/bib2sql.prerm
new file mode 100755
index 0000000000..fd9c8a0682
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2sql.prerm
@@ -0,0 +1,16 @@
+#!/bin/bash
+
+set -e
+
+case "$1" in
+ remove | deconfigure)
+
+ echo -n "Unstalling bib2sql... "
+
+ update-alternatives --remove bib2sql /usr/lib/bib2ml/bib2sql.pl
+
+ echo "done."
+ ;;
+esac
+
+exit 0
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2xml.docs b/biblio/bibtex/utils/bib2ml/debian/bib2xml.docs
new file mode 100644
index 0000000000..c88903004b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2xml.docs
@@ -0,0 +1,2 @@
+man/bib2xml_en.pod
+man/bib2xml_fr.pod
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2xml.install b/biblio/bibtex/utils/bib2ml/debian/bib2xml.install
new file mode 100644
index 0000000000..3f5287483c
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2xml.install
@@ -0,0 +1,4 @@
+src/Bib2HTML/Generator/XMLGen.pm usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/bibteXML.dtd usr/lib/bib2ml/Bib2HTML/Generator
+src/Bib2HTML/Generator/bibteXML-ext.dtd usr/lib/bib2ml/Bib2HTML/Generator
+src/bib2xml.pl usr/lib/bib2ml
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2xml.manpages b/biblio/bibtex/utils/bib2ml/debian/bib2xml.manpages
new file mode 100644
index 0000000000..d4e054cd04
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2xml.manpages
@@ -0,0 +1,2 @@
+man/bib2xml.1.gz
+man/bib2xml.fr.1.gz
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2xml.postinst b/biblio/bibtex/utils/bib2ml/debian/bib2xml.postinst
new file mode 100755
index 0000000000..7d176b1749
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2xml.postinst
@@ -0,0 +1,16 @@
+#!/bin/bash
+
+set -e
+
+if [ "$1" = configure ]; then
+
+ echo -n "Installing bib2xml... "
+
+ update-alternatives --install /usr/bin/bib2xml bib2xml /usr/lib/bib2ml/bib2xml.pl 500 --slave /usr/bin/bibtex2xml bibtex2xml /usr/lib/bib2ml/bib2xml.pl
+ update-alternatives --auto bib2xml
+
+ echo "done."
+
+fi
+
+exit 0
diff --git a/biblio/bibtex/utils/bib2ml/debian/bib2xml.prerm b/biblio/bibtex/utils/bib2ml/debian/bib2xml.prerm
new file mode 100755
index 0000000000..abd2a3306d
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/bib2xml.prerm
@@ -0,0 +1,16 @@
+#!/bin/bash
+
+set -e
+
+case "$1" in
+ remove | deconfigure)
+
+ echo -n "Unstalling bib2xml... "
+
+ update-alternatives --remove bib2xml /usr/lib/bib2ml/bib2xml.pl
+
+ echo "done."
+ ;;
+esac
+
+exit 0
diff --git a/biblio/bibtex/utils/bib2ml/debian/changelog b/biblio/bibtex/utils/bib2ml/debian/changelog
new file mode 100644
index 0000000000..a3a254b42c
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/changelog
@@ -0,0 +1,475 @@
+bib2ml (6.7-0arakhne0) natty; urgency=low
+
+ * bib2sql: Bug fix: the bibtex_entrytype table is not filled with the types
+ of the entries due to an error in a boolean condition.
+ * bib2sql: Notify with a warning when the same author seems to appear many times
+ for the same entry.
+ * bib2sql: add command line parameter 'sql-engine' which permits to specify
+ the SQL engine for which the SQL script should be generated.
+ * bib2sql: create the MySQL support.
+ * bib2sql: create the PostgreSQL support.
+
+ -- Stephane GALLAND <galland@arakhne.org> Sun, 31 Jul 2011 18:16:02 +0200
+
+bib2ml (6.6-0arakhne0) natty; urgency=low
+
+ * intrepid -> natty
+ * bib2sql: the word "order" could not be used as variable name because it is a
+ reserved word in SQL syntax. Rename it as "order_id".
+ * bib2sql: Ensure that the numerical identifiers of the authors and editors are unique.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 27 Jul 2011 08:15:25 +0200
+
+bib2ml (6.5-0arakhne2) intrepid; urgency=low
+
+ * Put missed files in the Debian packages (language files for Dyna theme).
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 25 Mar 2009 10:39:05 +0100
+
+bib2ml (6.5-0arakhne1) intrepid; urgency=low
+
+ * Do not recommend any more the teTeX packages. Recommend TeXLive in place.
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 23 Mar 2009 00:22:46 +0100
+
+bib2ml (6.5-0arakhne0) intrepid; urgency=low
+
+ * Extend the syntax supported for the bibtex keys, but output a warning.
+ * Add warning message when a language file was not found (verbose mode 2 or higher).
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 23 Mar 2009 00:08:56 +0100
+
+bib2ml (6.4-0arakhne0) intrepid; urgency=low
+
+ * Add function which remove the accents from an HTML string. This function is used to have consistent sorting outputs.
+ * Changes the labels of the trees' root nodes.
+ * The C and c acute characters are now correctly substitued.
+ * Bug fixes:
+ - the caron TeX characters are not translated into well-formated HTML characters;
+ - in Simple.pm, some hash references have not a generic syntax which cause invalid invalid hash refs exceptions;
+ * Change the official website address from "www.arakhne.org/bib2html" to "www.arakhne.org/bib2ml".
+
+ -- Stephane GALLAND <galland@arakhne.org> Sun, 15 Mar 2009 15:24:50 +0100
+
+bib2ml (6.3-0arakhne0) unstable; urgency=low
+
+ * Add the support for the TeX command \url.
+ * Major bug fix: the locale support of the Theme were not loaded. Fixed.
+
+ -- Stephane GALLAND <galland@arakhne.org> Fri, 01 Aug 2008 10:30:37 +0200
+
+bib2ml (6.2-0arakhne0) unstable; urgency=low
+
+ * Bug fix: several thrid-party tools declare BibTeX fields
+ with a name composed of the special characters "-_0-9:.".
+ The BibTeX parser now supports this kind of field name.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 28 May 2008 08:55:24 +0200
+
+bib2ml (6.1-4) unstable; urgency=low
+
+ * Use Debian alternatives instead of direct links from /usr/bin to the Perl scripts.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 25 Jul 2007 08:43:22 +0200
+
+bib2ml (6.1-3) unstable; urgency=low
+
+ * Not enough file included into the bib2ml-common package.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 25 Jul 2007 07:01:49 +0200
+
+bib2ml (6.1-2) unstable; urgency=low
+
+ * Rename the tool Bib2HTML into Bib2ML which is more
+ closer to the different available translations.
+ And it will prepare the submission to CTAN.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 25 Jul 2007 06:08:43 +0200
+
+bib2html (6.1-1) unstable; urgency=low
+
+ * Feature:
+ - When the 'pdf' field contains a local file reference, it
+ will be replaced by the 'localfile' field.
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 16 Apr 2007 10:49:53 +0200
+
+bib2html (6.0-1) unstable; urgency=low
+
+ * Feature:
+ - Add the field 'doi' inside the Extended generator.
+ - Add the support of the JabRef's groups.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 21 Mar 2007 13:33:13 +0100
+
+bib2html (5.1-1) unstable; urgency=low
+
+ * Feature:
+ - Add new latex commands: \mathbb, \{, \}
+ * Bug fixes:
+ - in the XML generator, the quotation, the ampersand
+ and the less-then and greater-than characters are
+ not properly processed.
+ - The sorting functions was re-implemented to
+ tackle problems one accentuated characters.
+ - The 'inbook' entries will be proceeded as the
+ "book" entries.
+
+ -- Stephane GALLAND <galland@arakhne.org> Fri, 06 Oct 2006 21:16:14 +0200
+
+bib2html (5.0-1) unstable; urgency=low
+
+ * Feature:
+ - Add the SQL generator.
+ - Add several generator's parameters in the HTML and the XML generators.
+ - Add the command line options '--protect', '--cvs', '--svn'
+ * Bug fixes:
+ - Rewrite some error messages to be more understandable.
+ * Packaging:
+ - Split the original bib2html Debian package into more dedicated packages.
+
+ -- Stephane GALLAND <galland@arakhne.org> Thu, 31 Aug 2006 15:01:24 +0200
+
+bib2html (4.3-1) unstable; urgency=low
+
+ * Feature:
+ - Tobia adds the support for some roman characters.
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 29 May 2006 21:38:18 +0200
+
+bib2html (4.2-1) unstable; urgency=low
+
+ * Feature:
+ - Add the support of the BibTeX field 'adsurl' which permits
+ to link to the standard Astrophysics Citation Reference Database.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 03 May 2006 13:59:37 +0200
+
+bib2html (4.1-1) unstable; urgency=low
+
+ * Bugs:
+ - When the BibTeX parser find multi-definition of BibTeX strings,
+ it dies on an undefined subroutine error.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 12 Apr 2006 15:47:52 +0200
+
+bib2html (4.0-1) unstable; urgency=low
+
+ * Features:
+ - Do not display in verbatim mode the BibTeX fields with
+ a name starting with "opt".
+ - Luca patches the TeX translator for supporting more letters
+ with the caron accent.
+ - From a Luca's request, the generator parameter 'hideindex'
+ is introduced to allow hiding of the indexes.
+ - Aurel introduces the generator parameters 'max-titlelength-overview'
+ and 'show-journalparams-overview'.
+ - Stephane introduces the generator parameter 'doc-repository'.
+ - Stephane introduces the command 'bib2xml' as a specialization
+ of bib2html (with the option -g XML).
+ * Bugs:
+ - The translator does not produce the right default value for
+ the TeX command \v.
+ - The HTML function which permits to extract author initials
+ was fixed to support in entry name's initials.
+ - The list of generators was ot properly displayed if
+ the absolute path to bib2html contains a directory name
+ with a space character.
+ - The list of support languages was ot properly displayed if
+ the absolute path to bib2html contains a directory name
+ with a space character.
+ - The editors was not displayed when the author's list was empty.
+ - The BibTeX references [???] now support HTML characters.
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 10 Apr 2006 18:28:32 +0200
+
+bib2html (3.3-1) unstable; urgency=low
+
+ * Features:
+ - Add some norvegian characters.
+ * Bugs:
+ - The parameter of @preamble is now entirely
+ parsed as a string. You don't need any more
+ to enclose the TeX command by braces.
+ - the parser for the author's names know support
+ HTML entities inside the firstnames.
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 14 Feb 2005 18:28:32 +0200
+
+bib2html (3.2-1) unstable; urgency=low
+
+ * Features:
+ - Add the field 'pdf' which must contains the name
+ of a PDF file (an URL or a local filename).
+ - Add the parameter 'backslash' for the Extended
+ generator.
+ * Bugs:
+ - In the parser, The token 'string' could be preceeded
+ by a set of space from the start of the line.
+ - Remove the required display of the field 'date'. In
+ BibTeX, the fields 'year' and 'month' replace it.
+ - Be sure that some characters will not be used
+ inside the filnames (e.g. ':').
+ - Major bug fix inside the parser. Multiple specification
+ of BibTeX filename on the command line is now truly
+ supported.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 05 Jan 2005 18:28:32 +0200
+
+bib2html (3.1-1) unstable; urgency=low
+
+ * Features:
+ - Portuguese is included into the generators by Joao.
+ * Bugs:
+ - The name of the language passed with '--lang' is now
+ case-insensitive.
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 06 Dec 2004 18:28:32 +0200
+
+bib2html (3.0-1) unstable; urgency=low
+
+ * Features:
+ - More TeX commands are added by Dimitris:
+ \epsilon, \Epsilon, \mathbf, \mathit, \mathrm,
+ \mathsf, \mathtt, \mathnormal, \sqrt
+ - Create a XML generator which respect the DTD from
+ BibTeXML.
+ - Add an XML output inside the HTML generator.
+ * Bugs:
+ - The character '+' is not allowed inside the entry keys.
+
+ -- Stephane GALLAND <galland@arakhne.org> Fri, 03 Dec 2004 18:28:32 +0200
+
+bib2html (2.0-1) unstable; urgency=low
+
+ * Features:
+ - Spanish is included into the generators by Sebastian.
+ - Links to the author's list of publication was
+ added for each other inside the entry's field
+ list.
+ - The option '--checknames' permits to check if
+ some author's names are duplicated or contain
+ mistakes.
+ * Bugs:
+ - the year does not appears inside the table of
+ the fields.
+ - the language support for theme only applies
+ the English definitions, not the other
+ languages (French, Spanish).
+
+ -- Stephane GALLAND <galland@arakhne.org> Fri, 26 Nov 2004 18:28:32 +0200
+
+bib2html (1.5-1) unstable; urgency=low
+
+ * Bugs:
+ - sometimes the carriage return characters was
+ not supported by the BibTeX parser.
+ - Generation of the BibTeX short labels (eg. [ABC04])
+ produces too long labels in case a lot of
+ names was proposed to the function.
+ - The names of the authors are not well upper-cased
+ for each first letter of the words.
+ - if an error occurs during the copy of a pdf file,
+ bib2html will not failed but only warm the user.
+
+ -- Stephane GALLAND <galland@arakhne.org> Thu, 12 Nov 2004 18:28:32 +0200
+
+bib2html (1.4-1) unstable; urgency=low
+
+ * Bugs:
+ - do not copy the electronical file with
+ the generator parameter 'target-url' was specified
+ for the Extended generator.
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 22 Sep 2004 18:28:32 +0200
+
+bib2html (1.3-1) unstable; urgency=low
+
+ * Features:
+ - the generator parameter 'type-matching' has its
+ value's syntax extended.
+ - Add the new BibTeX entry type 'proceedings' and
+ 'unpublished'.
+ * Bugs:
+ - The values of the fields 'localfile' and 'url'
+ were not properly extracted.
+ - Fix the indentation of the generated BibTeX section.
+ - Updates some language's strings
+ - Assumes that the characters '-' and '_' are aliases
+ for the character '-' inside the generator
+ parameter's names.
+ - Fix the output to be validable by the W3C validators
+ (HTML 4.01 and CSS).
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 23 Aug 2004 18:28:32 +0200
+
+bib2html (1.2-1) unstable; urgency=low
+
+ * Bugs:
+ - the special section @comment{} was not properly
+ parsed. Fix it with an update of the regular
+ expression which matches "@COMMENT".
+ - Allow the state "line_comment" to finish the
+ BibTeX file's parsing.
+
+ -- Stephane GALLAND <galland@arakhne.org> Tue, 17 Aug 2004 18:28:32 +0200
+
+bib2html (1.1-1) unstable; urgency=low
+
+ * Features:
+ - enhances the generator parameters 'author-regexp',
+ etc: add many new types instead of one.
+ - add the support of the BibTeX field 'crossref':
+ it permits to implement a kind of inheritance
+ between two entries
+ - add the generation of a BibTeX code verbatim
+ (and the command line parameter which permits
+ to set it on/off)
+ * Bugs:
+ - in indexes, regroup the reference with the same label
+ - put a better header title inside the HTML files of
+ the entries
+ - w3c norm fix: generates the <body> tags
+ - add a white background color for the theme Simple
+ - in ExtendedGen.pm, DomainGen.pm: fix a syntactical
+ error and update to be compliant with fixes that
+ occurs inside HTMLGen.pm
+ - in HTMLGen.pm, Norbert fixes some bug due to the
+ bad inclusion of their patchs for the release 1.0
+ - in Parser.pm: Norbert fixes a infinite loop recusion
+ bug. This bug is due to the definition of a constant
+ with same name and value (in a lowercase comparison).
+ For example: @STRING{springer=Springer} generates a
+ infinite loop.
+ - some code cleaning
+
+ -- Stephane GALLAND <galland@arakhne.org> Sat, 27 Mar 2004 18:28:32 +0200
+
+bib2html (1.0-1) unstable; urgency=low
+
+ * Features:
+ - add generator parameters for the HTMLGen generator:
+ author-regexp, max-names-overview, max-names-list,
+ newtype, type-matching (added by Norbert)
+ * Bugs:
+ - an exception was generated when an entry has no
+ author nor editor.
+ - in bibtex parsing: now support syntax as foo #
+ " and " # bla
+ - applies patchs from Norbert in TeX.pm, Misc.pm
+ and HTMLGen.pm
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 17 Mar 2004 18:28:32 +0200
+
+bib2html (0.11-1) unstable; urgency=low
+
+ * Features:
+ - add an index of authors and of author's publications
+ inside the two left frames
+ - add the class AbstractGenerator.pm
+ - add ExtendedGen.pm which permits to generate HTML
+ page with:
+ a) isbn, issn, and readers
+ b) abstract and keywords
+ c) the support for downloading an electronic
+ document ('localfile')
+ - add the support of LaTeX environments (\begin,\end)
+ - add the generator Domain which permits to support
+ domain for documents (domain, nddomain, rddomain,
+ domains)
+ * Bugs:
+ - in HTMLGen.pm, fixes not initialized variable uses
+ - changes the behavior of some command line options
+ - in Parser.pm, support recursive merging operator for strings
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 02 Feb 2004 18:28:32 +0200
+
+bib2html (0.10-1) unstable; urgency=low
+
+ * Bugs:
+ - in BibScanner.pm, did not recognized correctly the
+ @STRING commands
+ - in BibScanner.pm, the concatened strings was too
+ early merged (before any replacement by the
+ @STRING's values)
+ - in BibScanner.pm, the parsed field labels must
+ be automatically lower cased. Ut permits to support
+ case-independent label for BibTeX fields
+ - in Scanner.pm, ungetpattern() does not its job well.
+
+ -- Stephane GALLAND <galland@arakhne.org> Thu, 11 Dec 2003 18:28:32 +0200
+
+bib2html (0.9-1) unstable; urgency=low
+
+ * Features:
+ - Adds the generator 'Extended' which support the
+ bibtex tags:
+ * 'url' : URL to informational web page
+ * 'isbn'
+ * 'issn'
+ * 'localfile' : relative path to a file to download
+ * 'abstract'
+ * 'keywords'
+ * 'readers' : informational tag that indicates who
+ read this entry (according to the bibtex name syntax)
+ - Adds the support of "et al." inside the bibtex names.
+ - Adds some command line arguments
+ * Bugs:
+ - in the HTML filename translations.
+ - get the editor field when the author one is empty.
+ - ignore TeX parsing for the fields 'localfile' and 'url'
+ - support more formats for the bibtex author's names:
+ [von] Last, jr, First [and ...]
+ First [von] Last, jr [and ...]
+ [von] Last, First [jr] [and ...]
+ First [von] Last [jr] [and ...]
+ name, [name, ...] [and name]
+
+ -- Stephane GALLAND <galland@arakhne.org> Fri, 19 Sep 2003 18:28:32 +0200
+
+bib2html (0.8-1) unstable; urgency=low
+
+ * Features:
+ - adds the support of the LaTeX commands \cite[]{}
+ * Bugs:
+ - recognizes the character '-' inside the bibkeys
+ - some other minor bug fixes
+
+ -- Stephane GALLAND <galland@arakhne.org> Fri, 01 Aug 2003 18:28:32 +0200
+
+bib2html (0.7-1) unstable; urgency=low
+
+ * Features:
+ - add the support of mathematical modes (not the support
+ of all TeX commands inside the mathematical mode)
+ - partial support of Math-ML
+ * Bugs:
+ - add support of some TeX commands( \i, \~, ...)
+ - ignore text between bibtex entries
+ - better recognition for author names.
+ - warm the user when the "year" is not a number.
+ - suppress redondant error messages.
+ - bug in the verbosing level calculation
+ - some syntaxic fixes
+
+ -- Stephane GALLAND <galland@arakhne.org> Wed, 09 Jul 2003 18:28:32 +0200
+
+bib2html (0.6-1) unstable; urgency=low
+
+ * Features:
+ - adds the multi-language support.
+ - adds theme for the HTML generators.
+ * Bugs:
+ - some uses of the function sort inside a
+ return are improper. Fixed to be sure
+ that the return statement takes only one value.
+ - adds the function notempty() to permit to
+ have strings which contain only "0".
+
+ -- Stephane GALLAND <galland@arakhne.org> Thu, 26 Jun 2003 18:28:32 +0200
+
+bib2html (0.5-1) unstable; urgency=low
+
+ * This is the first public release on the version entirely based on perl.
+
+ -- Stephane GALLAND <galland@arakhne.org> Mon, 03 Mar 2003 18:28:32 +0200
diff --git a/biblio/bibtex/utils/bib2ml/debian/compat b/biblio/bibtex/utils/bib2ml/debian/compat
new file mode 100644
index 0000000000..b8626c4cff
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/compat
@@ -0,0 +1 @@
+4
diff --git a/biblio/bibtex/utils/bib2ml/debian/control b/biblio/bibtex/utils/bib2ml/debian/control
new file mode 100644
index 0000000000..e60859688f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/control
@@ -0,0 +1,48 @@
+Source: bib2ml
+Section: universe/tex
+Priority: optional
+Maintainer: Stephane GALLAND <galland@arakhne.org>
+Build-Depends-Indep: debhelper (>= 4.1.0), perl (>= 5.8), perl-modules (>= 5.8)
+Standards-Version: 3.7.3
+Homepage: http://www.arakhne.org/bib2ml/
+
+Package: bib2ml-common
+Architecture: all
+Depends: perl (>= 5.8), perl-modules (>= 5.8)
+Conflicts: bib2html-common (<= 6.1-1)
+Recommends: texlive
+Description: Translator from BibTeX files to HTML
+ bib2ml is a powerfull translator of
+ BibTeX files into HTML, XML or SQL files.
+ .
+ This package provides the common libraries.
+
+Package: bib2html
+Architecture: all
+Depends: perl (>= 5.8), perl-modules (>= 5.8), bib2ml-common (= ${Source-Version})
+Provides: bib2ml
+Description: Translator from BibTeX files to HTML
+ bib2ml is a powerfull translator of
+ BibTeX files into HTML, XML or SQL files.
+ .
+ This package provides bib2html.
+
+Package: bib2xml
+Architecture: all
+Depends: perl (>= 5.8), perl-modules (>= 5.8), bib2ml-common (= ${Source-Version})
+Provides: bib2ml
+Description: Translator from BibTeX files to HTML
+ bib2ml is a powerfull translator of
+ BibTeX files into HTML, XML or SQL files.
+ .
+ This package provides bib2xml.
+
+Package: bib2sql
+Architecture: all
+Depends: perl (>= 5.8), perl-modules (>= 5.8), bib2ml-common (= ${Source-Version})
+Provides: bib2ml
+Description: Translator from BibTeX files to HTML
+ bib2ml is a powerfull translator of
+ BibTeX files into HTML, XML or SQL files.
+ .
+ This package provides bib2sql.
diff --git a/biblio/bibtex/utils/bib2ml/debian/copyright b/biblio/bibtex/utils/bib2ml/debian/copyright
new file mode 100644
index 0000000000..487817878b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/copyright
@@ -0,0 +1,9 @@
+This package was debianized by Stephane GALLAND <galland@arakhne.org>
+on Tue, 11 Mar 2006.
+
+Copyright:
+This package is licensed under the GNU General Public License.
+
+ You can find the full text of the GPL in
+ /usr/share/common-licenses/GPL in your Debian system.
+ Look there for details not shown above.
diff --git a/biblio/bibtex/utils/bib2ml/debian/rules b/biblio/bibtex/utils/bib2ml/debian/rules
new file mode 100755
index 0000000000..2006e7602e
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/debian/rules
@@ -0,0 +1,75 @@
+#!/usr/bin/make -f
+
+build: build-stamp
+
+build-stamp:
+ dh_testdir
+
+ pod2man --section=1 --center=Bib2HTML --name=Bib2HTML man/bib2html_en.pod man/bib2html.1
+ gzip man/bib2html.1
+
+ pod2man --section=1 --center=Bib2HTML --name=Bib2HTML man/bib2html_fr.pod man/bib2html.fr.1
+ gzip man/bib2html.fr.1
+
+ pod2man --section=1 --center=Bib2XML --name=Bib2XML man/bib2xml_en.pod man/bib2xml.1
+ gzip man/bib2xml.1
+
+ pod2man --section=1 --center=Bib2XML --name=Bib2XML man/bib2xml_fr.pod man/bib2xml.fr.1
+ gzip man/bib2xml.fr.1
+
+ pod2man --section=1 --center=Bib2XML --name=Bib2XML man/bib2sql_en.pod man/bib2sql.1
+ gzip man/bib2sql.1
+
+ pod2man --section=1 --center=Bib2XML --name=Bib2XML man/bib2sql_fr.pod man/bib2sql.fr.1
+ gzip man/bib2sql.fr.1
+
+ touch build-stamp
+
+clean:
+ dh_testdir
+ dh_testroot
+ rm -f build-stamp
+
+ rm -f man/bib2html.1*
+ rm -f man/bib2html.*.1*
+
+ rm -f man/bib2xml.1*
+ rm -f man/bib2xml.*.1*
+
+ rm -f man/bib2sql.1*
+ rm -f man/bib2sql.*.1*
+
+ dh_clean
+
+install: build
+ dh_testdir
+ dh_testroot
+ dh_clean -k
+ dh_installdirs
+
+ dh_install
+
+ dh_link
+
+ dh_installman
+
+ dh_installdocs
+
+binary-arch:
+
+binary-indep: build install
+ dh_testdir
+ dh_testroot
+ dh_installchangelogs
+ dh_installdocs README
+ dh_installdefoma
+ dh_compress
+ dh_fixperms
+ dh_installdeb
+ dh_gencontrol
+ dh_md5sums
+ dh_builddeb
+
+binary: binary-indep binary-arch
+
+.PHONY: build clean install binary-arch binary-indep binary
diff --git a/biblio/bibtex/utils/bib2ml/doc/bibtexml_dtd.html b/biblio/bibtex/utils/bib2ml/doc/bibtexml_dtd.html
new file mode 100644
index 0000000000..f4e97dfde0
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/bibtexml_dtd.html
@@ -0,0 +1,173 @@
+<!DOCTYPE HTML PUBLIC "-/W3C/DTD HTML 4.01 Transitional/EN" "http:/www.w3.org/TR/html4/loose.dtd">
+<html>
+ <head>
+ <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+ <title>BibteXML DTD</title>
+ </head>
+ <body bgcolor='#dae6e6'>
+ <pre>
+<font color="gray">&lt;!--
+ - File: $Id: bibteXML-ext.dtd, 2003.06.26 13:52:00 vbg Exp $
+ -
+ - This DTD expresses XML markup similar to the BibTeX language
+ - specified for LaTeX, or actually its content model.
+ - For documentation on BibTeX, see
+ - http://www.ctan.org/tex-archive/biblio/bibtex/distribs/doc/
+ -
+ - Suggested invocation:
+ -
+ - &lt;?xml version="1.0" encoding="UTF-8"?&gt;
+ - &lt;!DOCTYPE bibtex:file PUBLIC
+ - "-//BibTeXML//DTD XML for BibTeX (extended) v1.0//EN"
+ - "bibteXML-ext.dtd" &gt;
+ - &lt;bibtex:file xmlns:bibtex="http://bibtexml.sf.net/"&gt;
+ - ...
+ - &lt;/bibtex:file&gt;
+ -
+ - Available from http://bibtexml.sf.net/
+ -
+ - This code originally developed by
+ - Vidar Bronken Gundersen
+ - Zeger W. Hendrikse
+ -
+ - This program is free software; you can redistribute it and/or
+ - modify it under the terms of the GNU General Public License.
+ - See http://www.gnu.org/copyleft/gpl.html
+ -
+--&gt;</font>
+
+
+<font color="gray">&lt;!-- popular user fields --&gt;</font>
+
+<b>&lt;!ENTITY</b> % user.fields
+ "( bibtex:abstract?, bibtex:affiliation?,
+ bibtex:contents?, bibtex:copyright?,
+ (bibtex:isbn | bibtex:issn)?, bibtex:doi?,
+ bibtex:keywords?, bibtex:language?, bibtex:lccn?,
+ bibtex:location?, bibtex:mrnumber?, bibtex:price?,
+ bibtex:size?, bibtex:url?, bibtex:category? )"<b>&gt;</b>
+
+<b>&lt;!ENTITY</b> % BibTeXML.common.standard.fields
+ ", bibtex:key?, bibtex:crossref?, %user.fields;"<b>&gt;</b>
+
+
+<font color="gray">&lt;!-- ..................................................................... --&gt;</font>
+<font color="gray">&lt;!-- Other popular fields
+ -
+ - BibTeX is extremely popular, and many people have used it to store
+ - information. Here is a list of some of the more common fields:
+ -
+ - [affiliation] The authors affiliation.
+ - [abstract] An abstract of the work.
+ - [contents] A Table of Contents
+ - [copyright] Copyright information.
+ - [ISBN] The International Standard Book Number.
+ - [ISSN] The International Standard Serial Number.
+ - Used to identify a journal.
+ - [keywords] Key words used for searching or possibly for annotation.
+ - [language] The language the document is in.
+ - [location] A location associated with the entry,
+ - such as the city in which a conference took place.
+ - [LCCN] The Library of Congress Call Number.
+ - I've also seen this as lib-congress.
+ - [mrnumber] The Mathematical Reviews number.
+ - [price] The price of the document.
+ - [size] The physical dimensions of a work.
+ - [URL] The WWW Universal Resource Locator that points to the item being
+ - referenced. This often is used for technical reports to point to the
+ - ftp site where the postscript source of the report is located.
+ -
+ - When using BibTeX with LaTeX you need
+ - BibTeX style files to print these data.
+ -
+ - Ref: www.ecst.csuchico.edu/~jacobsd/bib/formats/bibtex.html
+--&gt;</font>
+
+<b>&lt;!ELEMENT</b> bibtex:abstract (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:affiliation (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:contents (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:copyright (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:isbn (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:issn (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:language (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:lccn (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:location (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:mrnumber (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:price (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:size (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:url (#PCDATA) <b>&gt;</b>
+
+
+<font color="gray">&lt;!-- User requested fields
+ - [category] Category of this bibitem
+ - [DOI] The Digital Object Identifier (www.doi.org)
+ - used to redirect to articles, a key like 10.1000/203
+--&gt;</font>
+
+<b>&lt;!ELEMENT</b> bibtex:category (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:doi (#PCDATA) <b>&gt;</b>
+
+
+<font color="gray">&lt;!-- ..................................................................... --&gt;</font>
+<font color="gray">&lt;!-- Alternative syntax for compound fields
+ - for author, editor, keywords and title fields.
+ - Backwards compatible syntax.
+--&gt;</font>
+
+<b>&lt;!ENTITY</b> % BibTeXML.author.element "IGNORE"<b>&gt;</b>
+<b>&lt;!ENTITY</b> % BibTeXML.editor.element "IGNORE"<b>&gt;</b>
+
+<b>&lt;!ENTITY</b> % author.qname "(bibtex:author | bibtex:authorlist)"<b>&gt;</b>
+<b>&lt;!ENTITY</b> % editor.qname "(bibtex:editor | bibtex:editorlist)"<b>&gt;</b>
+
+<b>&lt;!ELEMENT</b> bibtex:authorlist (bibtex:person+) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:editorlist (bibtex:person+) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:author (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:editor (#PCDATA) <b>&gt;</b>
+
+<b>&lt;!ELEMENT</b> bibtex:person ( ( bibtex:initials |
+ (bibtex:first, bibtex:middle?)),
+ bibtex:prelast?, bibtex:last,
+ bibtex:lineage?)<b>&gt;</b>
+
+<font color="gray">&lt;!-- first, middle and last name should be obvious
+ - preLast is for names like Thomas *de* Burghes,
+ - lineage is used for "Jr" in names like "James T. Kirk, Jr."
+ --&gt;</font>
+<b>&lt;!ATTLIST</b> bibtex:person email CDATA #IMPLIED
+ url CDATA #IMPLIED
+<b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:first (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:initials (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:last (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:middle (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:prelast (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:lineage (#PCDATA) <b>&gt;</b>
+
+
+<b>&lt;!ENTITY</b> % BibTeXML.title.element "IGNORE"<b>&gt;</b>
+<b>&lt;!ENTITY</b> % title.qname "(bibtex:title | bibtex:titlelist)"<b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:titlelist (bibtex:title, bibtex:subtitle?)<b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:subtitle (#PCDATA) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:title (#PCDATA) <b>&gt;</b>
+
+<b>&lt;!ENTITY</b> % BibTeXML.keywords.element "IGNORE"<b>&gt;</b>
+<b>&lt;!ENTITY</b> % keywords.qname "bibtex:keywords"<b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:keywords (bibtex:keyword+) <b>&gt;</b>
+<b>&lt;!ELEMENT</b> bibtex:keyword (#PCDATA) <b>&gt;</b>
+
+
+<font color="gray">&lt;!-- ..................................................................... --&gt;</font>
+<font color="gray">&lt;!-- reuse the strict BibTeXML DTD --&gt;</font>
+<b>&lt;!ENTITY</b> % BibTeXML-strict PUBLIC
+ "-//BibTeXML//DTD XML for BibTeX v1.0//EN"
+ "bibteXML.dtd"<b>&gt;</b>
+%BibTeXML-strict;
+
+
+<font color="gray">&lt;!-- ..................................................................... --&gt;</font>
+<font color="gray">&lt;!-- End of bibtex dtd --&gt;</font>
+
+ </pre>
+ </body>
+</html>
diff --git a/biblio/bibtex/utils/bib2ml/doc/capture.png b/biblio/bibtex/utils/bib2ml/doc/capture.png
new file mode 100644
index 0000000000..55d9cc4f20
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/capture.png
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/capture2.png b/biblio/bibtex/utils/bib2ml/doc/capture2.png
new file mode 100644
index 0000000000..06ca4954a9
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/capture2.png
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/index.html b/biblio/bibtex/utils/bib2ml/doc/index.html
new file mode 100644
index 0000000000..1d593ea834
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/index.html
@@ -0,0 +1,1320 @@
+<!DOCTYPE HTML PUBLIC "-/W3C/DTD HTML 4.01 Transitional/EN" "http:/www.w3.org/TR/html4/loose.dtd">
+<html>
+ <head>
+ <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+ <title>Documentation of Bib2ML (aka. Bib2HTML)</title>
+ </head>
+ <body bgcolor='#dae6e6'>
+
+ <h1 align="center">Documentation of Bib2ML (aka. Bib2HTML)</h1>
+
+ <p align="center"><small>Written by <a href="mailto:galland@arakhne.org">Stéphane GALLAND</a><br>
+ Version: 2011-07-31<br>
+ Documentation for bib2ml 6.7 and later</small></p>
+
+ <hr width="100%">
+
+ <p><a href="#introduction">1. Introduction/Overview</a></p>
+ <p><a href="#install">2. How to install Bib2ML?</a><ul>
+ <li><a href="#install_require">2.1 Prerequires</a></li>
+ <li><a href="#install_reports">2.2 Installation Reports on Several Operating Systems</a></li>
+ <li><a href="#install_download">2.3 Download</a></li>
+ <li><a href="#install_unix">2.4 Install on Unix Systems</a><ul>
+ <li><a href="#install_unix_uncompress">2.4.1 Uncompress</a></li>
+ <li><a href="#install_unix_copy">2.4.2 Copy the files</a></li>
+ <li><a href="#install_unix_finalize">2.4.3 Finalize the installation</a></li>
+ <li><a href="#install_unix_packages">2.4.4 Simplify your life: use a Linux packages</a></li>
+ </ul></li>
+ <li><a href="#install_win">2.5 Install on Windows&reg; Systems without CygWin</a></li>
+ <li><a href="#install_cygwin">2.6 Install on Windows&reg; Systems with CygWin</a></li>
+ </ul></p>
+ <p><a href="#run">3. How to run Bib2ML?</a></p>
+ <p><a href="#format">4. Some words about the BibTeX format supported by Bib2ML</a><ul>
+ <li><a href="#format_recall">4.1 Short Recall on Bib2TeX's File Format</a></li>
+ <li><a href="#format_types">4.2 Recognized Entry Types</a></li>
+ <li><a href="#format_fields">4.2 Recognized Fields</a></li>
+ <li><a href="#format_string">4.4 Definition of Strings and Preambles</a></li>
+ <li><a href="#format_names">4.5 Definition of the Lists of Names</a></li>
+ </ul></p>
+ <p><a href="#generators">5. Supported Generators</a><ul>
+ <li><a href="#generator_HTML">5.1. Generator HTML</a></li>
+ <li><a href="#generator_Extended">5.2. Generator Extended</a></li>
+ <li><a href="#generator_Domain">5.3. Generator Domain</a></li>
+ <li><a href="#generator_XML">5.4. Generator XML</a></li>
+ <li><a href="#generator_SQL">5.5. Generator SQL</a></li>
+ </ul></p>
+ <p><a href="#themes">6. Supported Themes</a><ul>
+ <li><a href="#theme_Simple">6.1 Theme Simple</a></li>
+ <li><a href="#theme_Dyna">6.2 Theme Dyna</a></li>
+ <li><a href="#theme_contrib">6.3 Contribute</a></li>
+ </ul></p>
+ <p><a href="#languages">7. Supported Languages</a><ul>
+ <li><a href="#languages_contrib">7.1 Contribute</a></li>
+ </ul></p>
+ <p><a href="#license">8. License</a></p>
+ <p><a href="#contributor">9. Contributors</a></p>
+ <p><a href="#bugreport">10. Bug Reporting</a></p>
+
+ <hr width="100%">
+
+ <a name="introduction"></a><h2>1. Introduction/Overview</h2>
+
+ <p>Many researchers make use of <a href="http://www.cc.gatech.edu/classes/RWL/Projects/citation/Docs/UserManuals/Reference_Pages/bibtex_doc.html">BibTeX</a> for maintaining a comprehensive bibliography which they can then draw on at will when writing papers.</p>
+
+ <p>Bib2ML is a handy utility that converts BibTeX files into HTML pages. You can use it to easily maintain an updated online bibliography. In addition, it is possible to specify, for each bibfile entry, a set of additional information that will appears inside the generated pages.</p>
+
+ <p>The output depends of the used theme. But the pages' hierarchy has a similar structure that the <a href="http://java.sun.com/j2se/javadoc/">JavaDoc</a>'s ones (see the two screenshots generated with the theme <a href="#theme_Simple">Simple</a> and the theme <a href="#theme_Dyna">Dyna</a>). It includes a overview page, an index, an list of scientifical domains in which the BibTeX's entries are...</p>
+
+ <p><strong>Disclaimer:</strong> I've come across mention of other Bib2ML programs. This program is in no way related to any of them. For the curious, it was implemented using Perl.</p>
+
+ <hr width="100%">
+
+ <a name="install"></a><h2>2. How to install Bib2ML?</h2>
+
+ <a name="install_require"></a><h3>2.1. Prerequires</h3>
+
+ <p>To run BibHTML you must install a Perl interpreter. Bib2ML was tested with Perl v5.8.3 under Linux.</p>
+
+ <p>You must also install the following Perl packages (mostly included inside the default Perl distributions):<ul>
+ <li><code>File::Basename</code></li>
+ <li><code>File::Path</code></li>
+ <li><code>File::Spec</code></li>
+ <li><code>Getopt::Long</code></li>
+ <li><code>Pod::Usage</code></li>
+ </ul></p>
+
+ <a name="install_reports"></a><h3>2.2 Installation Reports on Several Operating Systems</h3>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%" cols="4">
+ <tr><td bgcolor="#cccccc" colspan="4" align="center"><i>Bib2ML and the Operating System's Supports</i></td></tr>
+ <tr><td valign="middle" align="center">GNU/Linux Mandrake</td>
+ <td valign="middle" align="center"><img src="./validated.gif" alt="ok"></td>
+ <td valign="middle" align="center">GNU/Linux Debian</td>
+ <td valign="middle" align="center"><img src="./validated.gif" alt="ok"></td></tr>
+ <tr><td valign="middle" align="center">GNU/Linux Ubuntu<sup>[<a href="#note1">1</a>]</sup></td>
+ <td valign="middle" align="center"><img src="./validated.gif" alt="ok"></td>
+ <td valign="middle" align="center">GNU/Linux Slackware</td>
+ <td valign="middle" align="center"><img src="./work.gif" alt="work"></td></tr>
+ <tr><td valign="middle" align="center">GNU/Linux RedHat</td>
+ <td valign="middle" align="center"><img src="./work.gif"alt="must work"></td>
+ <td valign="middle" align="center">Mac OS X</td>
+ <td valign="middle" align="center"><img src="./work.gif" alt="work"></td></tr>
+ <tr><td valign="middle" align="center">Windows&reg; without Cygwin</td>
+ <td valign="middle" align="center"><img src="./work.gif" alt="work"></td>
+ <td valign="middle" align="center">Windows&reg; with Cygwin</td>
+ <td valign="middle" align="center"><img src="./validated.gif" alt="ok"></td></tr>
+ <tr><td valign="middle" align="center">GNU/Linux Suze</td>
+ <td valign="middle" align="center"><img src="./not-validated.gif" alt="not validated"></td>
+ <td valign="middle" align="center">GNU/Linux Mandrivia</td>
+ <td valign="middle" align="center"><img src="./not-validated.gif" alt="ok"></td></tr>
+ <tr><td valign="middle" align="center">Other UNIX</td>
+ <td valign="middle" align="center"><img src="./not-validated.gif" alt="not validated"></td>
+ <td valign="middle" align="center"></td>
+ <td valign="middle" align="center"></td></tr>
+ <tr><td colspan="4"><img src="./validated.gif" align="center" alt="not validated">:<small> I'd tested Bib2ML and validated it</small><br>
+ <img src="./work.gif" align="center" alt="work">:<small> one user has reported a success for Bib2ML</small><br>
+ <img src="./not-validated.gif" align="center" alt="not validated">:<small> No test nor report for a successfull installation and a successfull use of Bib2ML</small><br>
+ <img src="./mustwork.gif" align="center" alt="must work">:<small> Bib2ML must work as for another operating system</small><br><br>
+ <small><a name="note1"></a>[1] GNU/Linux Ubuntu is the reference operating system for Bib2ML</td></tr>
+ </table></p>
+
+ <a name="install_download"></a><h3>2.3. Download</h3>
+
+ <p>You could download the lastest sources from the Bib2ML web page: <a href="http://www.arakhne.org/bib2ml/">http://www.arakhne.org/bib2ml/</a> or <a href="http://download.tuxfamily.org/arakhne/pool/b/bib2ml/">http://download.tuxfamily.org/arakhne/pool/b/bib2ml/</a>.</p>
+
+ <p>The sources are commonly stored inside an archive called <code>bib2ml-x.x.tar.gz</code> where <code>x.x</code> is the number of the Bib2ML's version.</p>
+
+ <a name="install_unix"></a><h3>2.4 Install on Unix Systems</h3>
+
+ <a name="install_unix_uncompress"></a><h4>2.4.1. Uncompress</h4>
+
+ <p>After downloading the sources' archive, you could uncompress it:
+ <pre><code>
+ $ gzip -d -c bib2ml-x.x.tar.gz | tar -x
+ </code></pre></p>
+
+ <p>This command will create the directory <code>./bib2ml-x.x</code> in which all the sources are.</p>
+
+ <a name="install_unix_copy"></a><h4>2.4.2 Copy the files</h4>
+
+ <p>The main step of the installation is the copy of all the files required by Bib2ML. In fact, only a copy was necessary to install Bib2ML, <i>no compilation</i>.</p>
+
+ <p>I assume that you want to install Bib2ML into the directory <code>/usr/local/lib/bib2ml</code>. Type the following commands to install Bib2ML:<ul>
+ <li>installation of the Perl's packages, copy all the content of the subdirectory <code>./src</code>:
+ <pre><code>
+ $ cd bib2ml-x.x
+ $ mkdir /usr/local/lib/bib2ml
+ $ cp -R -f ./src/* /usr/local/lib/bib2ml/
+ </code></pre></li>
+ <li>Be sure that the Perl's script was runable:
+ <pre><code>
+ $ chmod ugo+x /usr/local/lib/bib2ml/bib2html.pl
+ </code></pre></li>
+ <li>Copy some additional documentation's files, if you want:
+ <pre><code>
+ $ cp -f ./COPYING /usr/local/lib/bib2ml/
+ $ cp -f ./Changelog /usr/local/lib/bib2ml/
+ $ cp -f ./AUTHORS /usr/local/lib/bib2ml/
+ $ cp -f ./AUTHORS /usr/local/lib/bib2ml/
+ $ cp -f ./VERSION /usr/local/lib/bib2ml/
+ </code></pre></li>
+ </ul></p>
+
+ <p>From now you could launch Bib2ML by typing one of the following commands:<ul>
+ <li>if the Perl interpreter is <code>/usr/bin/perl</code>:
+ <pre><code>
+ $ /usr/local/lib/bib2ml/bib2html.pl
+ </code></pre></li>
+ <li>if the Perl interpreter is not <code>/usr/bin/perl</code>:
+ <pre><code>
+ $ path_to_perl/perl /usr/local/lib/bib2ml/bib2html.pl
+ </code></pre></li>
+ </ul></p>
+
+ <p>Inside the section where I explain <a href="#run">how to run Bib2ML</a>, I assume that the launching command was <code>bib2html</code>. If you don't apply the commands from the section <a href="#install_unix_finalize">2.4.3</a>, you must replace <code>bib2html</code> by one of the above commands.
+
+ <a name="install_unix_finalize"></a><h4>2.4.3. Finalize the installation</h4>
+
+ <p>To finalize the installation, you could create a symbolic link to the Bib2ML's script from one of the directories inside your <code>PATH</code> (I assume that <code>/usr/local/bin</code> was in your <code>PATH</code>):
+ <pre><code>
+ $ cd /usr/local/bin
+ $ ln -s -f /usr/local/lib/bib2ml/bib2html.pl bib2html
+ </code></pre></p>
+
+ <p>This recommendation will permits to all the users to run Bib2ML very simply.</p>
+
+ <p><u><i>Warning:</i></u> this recommendation works only if the Perl's interpreter was <code>/usr/bin/perl</code>.</p>
+
+ <a name="install_unix_packages"></a><h4>2.4.4. Simplify your life: use a Linux packages</h4>
+
+ <p>You could simplify your life by installing Bib2ML with one of the proposed packages (see the <a href="http://www.arakhne.org/bib2ml/">download page</a> or the <a href="http://download.tuxfamily.org/arakhne.org/pool/b/bib2ml/">download repository</a>) for a Linux distributions.</p>
+
+ <a name="install_win"></a><h3>2.5 Install on Windows&reg; Systems without CygWin</h3>
+
+<p>This section explains how to install Bib2ML on a Windows&reg; operating system <strong>without CygWin</strong> installed. Bib2ML was successfully installed on WinXP with TeXLive2007 and ActivePerl 5.8.8.</p>
+
+<p>The installation steps are the steps (thanks to Dan Luecking for his report):
+<ul>
+<li>Create a directory named <code>scripts\</code> in one of the <code>texmf</code> trees (if one doesn't exist). Make a subdirectory named <code>bib2ml\</code> in <code>scripts\</code> and a subdirectory named <code>man\</code> in <code>scripts\bib2ml\</code>. The obtained directory tree should be:<pre><code>C:\path_to_texmf\texmf\
+ |
+ \- scripts\
+ |
+ \-- man\
+</code></pre></li>
+<li>Copy the contents of <code>src\</code> from the Bib2ML archive and all subdirectories to <code>scripts\bib2ml\</code> preserving the subdirectory structure.</li>
+<li>Copy the contents of <code>man\</code> from the Bib2ML archive to <code>scripts\bib2ml\man\</code>.</li>
+<li>Copy the contents of <code>doc\</code> to the documentation area of the texmf tree.</li>
+<li>create links:<pre><code>C:\path_to_texmf\texmf\scripts\bib2ml\> irun bib2html.pl bib2html.exe
+C:\path_to_texmf\texmf\scripts\bib2ml\> irun bib2sql.pl bib2sql.exe
+C:\path_to_texmf\texmf\scripts\bib2ml\> irun bib2xml.pl bib2xml.exe
+</code></pre></li>
+<li>Copy <code>*.exe</code> to <code>C:\TeXLive\bin\win32\</code></li>
+<li>run <code>texhash</code></li>
+</ul></p>
+
+<p>The links created by <code>irun</code> (part of TeXLive) use the <code>kpsewhich</code> libraries
+and <code>texmf.cnf</code> to find the perl scripts. The default setup should work
+since the search path for scripts is <code>%TEXMF%/scripts/</code>.</p>
+
+ <a name="install_cygwin"></a><h3>2.6 Install on Windows&reg; Systems with CygWin</h3>
+
+<p>This section explains how to install Bib2ML on a Windows&reg; operating system <strong>with CygWin</strong> installed. Bib2ML was successfully installed on WinXP with CygWin 1.5.24.</p>
+
+<p>Bib2ML should be installed on Windows&reg; Systems with CygWin in the same way as for Unix operating systems. Please see the section <a href="#install_unix">2.4 Install on Unix Systems</a> for the details.</p>
+
+ <hr width="100%">
+
+ <a name="run"></a><h2>3. How to run Bib2ML?</h2>
+
+ <p>Bib2ML takes a list of arguments: the names of the bibfiles you wish to process, e.g.
+ <pre><code>
+ $ bib2html firstfile.bib secondfile.bib
+ </code></pre></p>
+
+ <p>The output is written by default is the directory <code>./bib2html</code>.</p>
+
+ <p><strong>SYNOPSYS</strong>
+ <pre><code>
+ bib2html [options] file [file ...]
+ </code></pre></p>
+
+ <p><strong>OPTIONS</strong>
+ <table border="1" cellspacing="0" cellpadding="5" width="100%">
+
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>General options</i></td></tr>
+
+ <tr><td valign="top">
+ <code>-[no]b</code><br>
+ <code> --[no]bibtex</code></td><td valign="top">
+ These options permit to generate (or not) a verbatim of the BibTeX entry.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--cvs</code></td><td valign="top">
+ If specified, this option disables the deletion of the subfiles
+ <code>.cvs</code>, <code>CVS</code> and <code>CVSROOT</code> in
+ the output directory.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--doctitle text</code></td><td valign="top">
+ Sets the title that appears in the main page.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>-f</code><br>
+ <code>--force</code></td><td valign="top">
+ Forces to overwrite into the output directory.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>-?</code><br>
+ <code>-h</code></td><td valign="top">
+ Show the list of supported options.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--help</code><br>
+ <code>--man</code><br>
+ <code>--manual</code></td><td valign="top">
+ Show the manual page.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>-o directory</code><br>
+ <code>--output&bnsp;directory</code></td><td valign="top">
+ Sets the <code>directory</code> in which the pages will be generated.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--protect shell_wildcard</code></td><td valign="top">
+ If specified, this option disables the deletion of the subfiles
+ that match the specified shell's wildcard in the output directory.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--svn</code></td><td valign="top">
+ If specified, this option disables the deletion of the subfiles
+ <code>.svn</code> and <code>svn</code> in the output directory.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--version</code></td><td valign="top">
+ Show the version of Bib2ML.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--windowtitle text</code></td><td valign="top">
+ Sets the text that appears as the window's title.
+ </td></tr>
+
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>Generator options</i></td></tr>
+
+ <tr><td valign="top">
+ <code>--d name[=value]</code><br>
+ <code>--generatorparam name[=value]</code></td><td valign="top">
+ Sets a generator param. It must be a <code>key=value</code> pair or simply a name. Example: "<code>target=thisdirectory</code>" defines the parameter <code>target</code> with corresponding value "<code>thisdirectory</code>". The specified parameters which are not supported by the generator are ignored.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--g class</code><br>
+ <code>--generator class</code></td><td valign="top">
+ Specify the generator to use. <code>class</code> must be a predefined generator's identifier of a valid Perl classname. See <code>--genlist</code> to obtain the list of the predefined generators. The default generator is <code>HTML</code>. See the <a href="#generators">list of supported generators</a> for more details.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--generatorparams</code></td><td valign="top">
+ Shows the list of supported parameters, and their semantics for the selected generator.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--genlist</code></td><td valign="top">
+ Shows the list of the supported generators.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--jabref</code></td><td valign="top">
+ The generator will translate JabRef's groups into Bib2ML domains.
+ </td></tr>
+
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>Checker options</i></td></tr>
+
+ <tr><td valign="top">
+ <code>--[no]checknames</code></td><td valign="top">
+ Force Bib2ML to check the author's names. This checking includes:<ul>
+ <li>only the second first names of two authors differ</li>
+ <li>two last names are a similar syntax (90% or more similar)</li>
+ </ul></td></tr>
+
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>Theme options</i></td></tr>
+
+ <tr><td valign="top">
+ <code>--theme name</code></td><td valign="top">
+ Specify the theme used by the generator. See the option <code>--themelist</code> to obtain the complete list of supported themes. See the <a href="#themes">list of the supported themes</a> for more details about them.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--themelist</code></td><td valign="top">
+ Shows the list of supported themes. See the <a href="#themes">list of the supported themes</a> for more details about them.
+ </td></tr>
+
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>Localization options</i></td></tr>
+
+ <tr><td valign="top">
+ <code>--lang name</code></td><td valign="top">
+ Sets the language used by the generator. See <code>--langlist</code> to obtain the list of the supported languages.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--langlist</code></td><td valign="top">
+ Shows the list of supported language.
+ </td></tr>
+
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>TeX options</i></td></tr>
+
+ <tr><td valign="top">
+ <code>-p file</code><br>
+ <code>--preamble file</code></td><td valign="top">
+ Sets the name of the file to read to include some TeX preambles. You could use this option to dynamicaly defined some unsupported LaTeX commands (see <a href="#format_string">how to define and use a preamble</a>).
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--texcmd</code></td><td valign="top">
+ Shows the list of supported LaTeX commands. The supported TeX commands permits to create a specific HTML output accordingly to the TeX semantic.
+ </td></tr>
+
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>Logging options</i></td></tr>
+
+ <tr><td valign="top">
+ <code>-q</code></td><td valign="top">
+ Don't be verbose: only error messages are displayed.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--[no]sortw</code></td><td valign="top">
+ Shows (or not) a sorted list of warnings by appearence line. For example, this could be use to obtain a better output for a parsing program.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>-v</code></td><td valign="top">
+ Be more verbose. Each time this option was specified, the verbosing level was increazed.
+ </td></tr>
+
+ <tr><td valign="top">
+ <code>--[no]warning</code></td><td valign="top">
+ If false, the warning are converted to errors. An error stops the program when it occurs. A warning does not stops the program.
+ </td></tr>
+
+ </table></p>
+
+ <hr width="100%">
+
+ <a name="format"></a><h2>4. Some words about the BibTeX format supported by Bib2ML</h2>
+
+ Bib2ML use as input files which respest as much as possible the <a href="http://www.cc.gatech.edu/classes/RWL/Projects/citation/Docs/UserManuals/Reference_Pages/bibtex_doc.html">BibTeX file format</a>. It add more restrictive constraints than this <i>official</i> format, and includes some additional fields.
+
+ <a name="format_recall"></a><h3>4.1 Short Recall on Bib2TeX's File Format</h3>
+
+ <p>To be recognized by Bib2ML, each entry must begin with an '<code>@</code>', immediately followed by the type of entry it is (see the <a href="#format_types">list of recognized entry types</a>), immediately followed by a '<code>{</code>'. It will then process the fields you've specified for that entry until it hits the closing '<code>}</code>' (see the <a href="#format_fields">list of recognized fields</a>). The format then looks something like this:
+ <pre><code>
+ @entrytype{entry_key,
+ fieldname1 = "Contents",
+ fieldname2 = {Contents},
+ fieldname3 = contents,
+ ...
+ }
+ </code></pre></p>
+
+ <p>The first information required by the BibTeX's file format is the identifier of the entry. This <code>entry_key</code> must be unique and, in most of the cases, it is composed by the author's name, the publication year... In <a href="http://www.latex-project.org/">LaTeX</a>, this key was used to reference this bibliographical entry.</p>
+
+ <p>Three types of field contents are valid, as shown here. In <code>fieldname1</code>, the contents are enclosed in quotes; in <code>fieldname2</code> they are enclosed in curly braces, and in <code>fieldname3</code> there are no surrounding characters. The third type is often used to specify pre-defined <a href="#format_string">string values</a>, and any value specified in this way will be compared to the list of <code>@strings</code> you've defined for a possible match (if there is a match, it will be expanded out to the full value of the <code>@string</code>).</p>
+
+ <p>Any amount of whitespace can come between the <code>fieldname</code> and the '<code>=</code>', or between the '<code>=</code>' and the contents. In addition, Bib2ML can handle nested <code>{}</code>'s in the contents of a field.</p>
+
+ <hr width="100%">
+
+ <a name="format_recall"></a><h3>4.2 Recognized Entry Types</h3>
+
+ <p>Bib2ML recognizes the following bibliography entry types (by the generator <a href="#generator_HTML">HTML</a>):<ul>
+ <li><code>@article</code>: an article inside a national or international <i>journal</i>, e.g. <i>International Journal of Production Economics</i>.</li>
+ <li><code>@book</code>: a <i>book</i>, e.g. <i>Les Systèmes Multi-Agents</i> by Professor Jacques Ferber.</li>
+ <li><code>@booklet</code>: a <i>standalone part</i> of a book, i.e. a part with its own author, title...</li>
+ <li><code>@inbook</code>: a <i>chapter</i> or a <i>part</i> of a book.</li>
+ <li><code>@incollection</code>: an article inside a <i>collection</i> of national or international journals, e.g. <i>Lecture Notes on Artificial Intelligence</i>.</li>
+ <li><code>@inproceedings</code>: a <i>paper</i> inside the proceedings of an national ou international conference, e.g. <i>European Simulaton Multiconferences</i>.</li>
+ <li><code>@manual</code>: a <i>technical manual</i> published (or not) by an university. <i>Don't be confused</i> with the technical report which is a report, not a manual.</li>
+ <li><code>@mastersthesis</code>: a <i>student thesis</i> made under the authority of an university of a school, e.g. engineering's report.</li>
+ <li><code>@misc: see the note below</code></li>
+ <li><code>@phdthesis</code>: a <i>research thesis</i> made under the authority of a laboratory, an institution, an university, e.g. PhD thesis, Doctorat thesis...</li>
+ <li><code>@proceedings</code>: a book that contains <i>all the papers</i> of a conference. <i>Don't choose</i> if you want a paper inside a conference (see the <code>@inproceedings</code> instead), e.g. <i>Proceedings of the International Conference on Multi-Agent Systems</i>.</li>
+ <li><code>@techreport</code>: a <i>technical report</i> published by an university. In general a technical report has a internal number which is specific to the institution. <i>Don't be confused</i> with the technical manual which is a manual, not a report.</li>
+ <li><code>@unpublished: a document which are never published.</code></li>
+ </ul></p>
+
+ <p>Any other entry type will be proceeded as <code>@misc</code>.</p>
+
+ <p><u>Note about the type <code>@misc</code>:</u><br>
+ this entry type is considered as the default. It requires the following fields: <code>author</code> and <code>year</code>. This constraint is not from the definition of the standard BibTeX file format. But it was introduced for the page's generation of Bib2ML.</p>
+
+ <p>I welcome requests to support other entry types. The generators could support their own entry types. See the section about <a href="#generators">supported generator</a> for more details</p>
+
+ <hr width="100%">
+
+ <a name="format_fields"></a><h3>4.3 Recognized Fields</h3>
+
+ <p>Bib2ML recognizes the following bibliography field types (by the generator <a href="#generator_HTML">HTML</a>):<ul>
+ <li><code>address</code></li>
+ <li><code>annote</code></li>
+ <li><code>author</code> (see the <a href="#format_names">definitions of the names</a>)</li>
+ <li><code>booktitle</code></li>
+ <li><code>chapter</code></li>
+ <li><code>comments</code> (alias <code>annote</code>)</li>
+ <li><code>edition</code></li>
+ <li><code>editor</code> (see the <a href="#format_names">definitions of the names</a>)</li>
+ <li><code>howpublished</code></li>
+ <li><code>institution</code></li>
+ <li><code>month</code></li>
+ <li><code>note</code></li>
+ <li><code>number</code></li>
+ <li><code>organization</code></li>
+ <li><code>pages</code></li>
+ <li><code>publisher</code></li>
+ <li><code>school</code></li>
+ <li><code>series</code></li>
+ <li><code>title</code></li>
+ <li><code>type</code></li>
+ <li><code>volume</code></li>
+ <li><code>year</code></li>
+ </ul></p>
+
+ <p>The real support of a field depends on the entry type in which it appears. The following table explains where the fields are needed and where they are optional.</p>
+
+ <p><a name="table_HTMLfields"></a><table border="1" cellspacing="0" cellpadding="2" width="100%">
+ <tr bgcolor="#cccccc"><td colspan="13" align="center"><small><i>Supported Fields by the Generator HTML</i></small></td></tr>
+ <tr bgcolor="#cccccc"><td><!-- --></td>
+ <td align="center"><small>article</small></td>
+ <td align="center"><small>book</small></td>
+ <td align="center"><small>booklet</small></td>
+ <td align="center"><small>inbook</small></td>
+ <td align="center"><small>inproceeding<br>incollection</small></td>
+ <td align="center"><small>manual</small></td>
+ <td align="center"><small>masterthesis</small></td>
+ <td align="center"><small>misc</small></td>
+ <td align="center"><small>phdthesis</small></td>
+ <td align="center"><small>proceedings</small></td>
+ <td align="center"><small>techreport</small></td>
+ <td align="center"><small>unpublished</small></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>address</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>annote</small></td>
+ <td align="center"><!-- article --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- misc --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- phdthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- unpublished --><img src="./optional.gif" alt="O"></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>author</small></td>
+ <td align="center"><!-- article --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- book --><img src="./requiredor.png" alt="RO"></td>
+ <td align="center"><!-- booklet --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- inbook --><img src="./requiredor.png" alt="RO"></td>
+ <td align="center"><!-- inproceedings --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- manual --><img src="./required.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- misc --><img src="./requiredor.png" alt="RO"></td>
+ <td align="center"><!-- phdthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- proceedings --><img src="./requiredor.png" alt="RO"></td>
+ <td align="center"><!-- techreport --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- unpublished --><img src="./required.gif" alt="R"></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>booktitle</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --></td>
+ <td align="center"><!-- inproceedings --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>chapter</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- inproceedings --></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>edition</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --></td>
+ <td align="center"><!-- manual --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>editor</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --><img src="./requiredor2.png" alt="RO"></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./requiredor2.png" alt="RO"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --><img src="./requiredor2.png" alt="RO"></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --><img src="./requiredor2.png" alt="RO"></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>howpublished</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inbook --></td>
+ <td align="center"><!-- inproceedings --></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>institution</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --></td>
+ <td align="center"><!-- inproceedings --></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>journal</small></td>
+ <td align="center"><!-- article --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --></td>
+ <td align="center"><!-- inproceedings --></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>month</small></td>
+ <td align="center"><!-- article --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- misc --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- phdthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>note</small></td>
+ <td align="center"><!-- article --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- misc --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- phdthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- unpublished --><img src="./required.gif" alt="R"></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>number</small></td>
+ <td align="center"><!-- article --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>organization</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>pages</small></td>
+ <td align="center"><!-- article --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>publisher</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>school</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --></td>
+ <td align="center"><!-- inproceedings --></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>series</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>title</small></td>
+ <td align="center"><!-- article --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- book --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- booklet --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- inbook --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- inproceedings --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- manual --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- masterthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- misc --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- phdthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- proceedings --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- techreport --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- unpublished --><img src="./required.gif" alt="R"></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>type</small></td>
+ <td align="center"><!-- article --></td>
+ <td align="center"><!-- book --></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- proceedings --></td>
+ <td align="center"><!-- techreport --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>volume</small></td>
+ <td align="center"><!-- article --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- book --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- booklet --></td>
+ <td align="center"><!-- inbook --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- inproceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- manual --></td>
+ <td align="center"><!-- masterthesis --></td>
+ <td align="center"><!-- misc --></td>
+ <td align="center"><!-- phdthesis --></td>
+ <td align="center"><!-- proceedings --><img src="./optional.gif" alt="O"></td>
+ <td align="center"><!-- techreport --></td>
+ <td align="center"><!-- unpublished --></td>
+ </tr>
+ <tr><td bgcolor="#cccccc"><small>year</small></td>
+ <td align="center"><!-- article --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- book --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- booklet --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- inbook --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- inproceedings --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- manual --><img src="./required.gif" alt="O"></td>
+ <td align="center"><!-- masterthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- misc --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- phdthesis --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- proceedings --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- techreport --><img src="./required.gif" alt="R"></td>
+ <td align="center"><!-- unpublished --><img src="./required.gif" alt="R"></td>
+ </tr>
+
+ <tr><td colspan="13"><img src="./required.gif" alt="R" align="center">: this field was required by Bib2ML<br>
+ <img src="./requiredor.png" alt="RO" align="center">: this field was required by Bib2ML if the other required field was not given<br>
+ <img src="./requiredor2.png" alt="RO" align="center">: this field was required by Bib2ML if the other required field was not given<br>
+ <img src="./optional.gif" alt="O" align="center">: this field was not required by Bib2ML<br>
+ When a cell was empty, this field is ignored by Bib2ML</td></tr></table></p>
+
+ <p>I welcome requests to support other fields. The generators could support their own. See the section about <a href="#generators">supported generator</a> for more details</p>
+
+ <a name="format_string"></a><h3>4.4 Definition of Strings and Preambles</h3>
+
+ <p>Like BibTeX, Bib2ML also handles arbitrary <code>@string</code> definitions, which can be used in any entry field, e.g.
+ <pre><code>
+ @string{acl = "Association for Computational Linguistics"}
+ ...
+ @proceedings{PROC,
+ publisher = acl,
+ ...
+ }
+ </code></pre></p>
+
+ <p>Bib2ML also supports the definition of TeX preambles. The TeX preambles are TeX commands which are evaluated and ran before any treatement on the BibTeX entries. The definition of a preamble is done with <code>@preamble</code>, e.g.
+ <pre><code>
+ @preamble{\def\th{\ensuremath{^{th}}}}
+ ...
+ </code></pre></p>
+
+ <p>The TeX commands which can be put inside a <code>@preamble</code> are limited to the commands supported by Bib2ML (see the command-line option <code>--texcmd</code> to obtain a list).</p>
+
+ <a name="format_names"></a><h3>4.5 Definition of the Lists of Names</h3>
+
+ <p>In some fields (e.g. <code>author</code> and <code>editor</code>) you must specify a list of names. This list is composed of names separated by the keyword <code>AND</code>. Each name must respect one of the following syntaxes:<ul>
+ <li><code>[von] Last, jr, First</code></li>
+ <li><code>First [von] Last, jr</code></li>
+ <li><code>[von] Last, First [jr]</code></li>
+ <li><code>First [von] Last [jr]</code></li>
+ </ul></p>
+
+ <p>If present the <code>jr</code> part must be one of '<code>junior</code>', '<code>jr.</code>', '<code>jr</code>', '<code>senior</code>', '<code>sen.</code>', '<code>sen</code>', '<code>esq.</code>', '<code>esq</code>', '<code>phd.</code>' and '<code>phd</code>'.
+
+ <p><u>Good Example:</u> <code>DUPONT, Henri and Pierre, Alain Michel and Jim WASHINGTON jr.
+ <table border="1" cellspacing="0" cellpadding="0">
+ <tr><td><code>DUPONT, </code></td><td><code>Henri</code></td><td><code> and </code></td><td><code>Pierre, </code></td><td><code>Alain Michel</code></td><td><code> and </code></td><td><code>Jim </code></td><td><code>WASHINGTON </code></td><td><code>jr.</code></td></tr>
+ <tr><td><code>last</code></td><td><code>first</code></td><td><code></code></td><td><code>last</code></td><td><code>first</code></td><td><code></code></td><td><code>first</code></td><td><code>fast</code></td><td><code>jr</code></td></tr>
+ </table></p>
+
+ <p><u>Bad Example:</u> <code>Henri DUPONT, Alain Michel Pierre and Jim WASHINGTON jr.
+ <table border="1" cellspacing="0" cellpadding="0">
+ <tr><td><code>Henri DUPONT, </code></td><td><code>Alain Michel Pierre</code></td><td><code> and </code></td><td><code>Jim </code></td><td><code>WASHINGTON </code></td><td><code>jr.</code></td></tr>
+ <tr><td><code>last</code></td><td><code>first</code></td><td><code></code></td><td><code>first</code></td><td><code>fast</code></td><td><code>jr</code></td></tr>
+ </table></p>
+
+ <hr width="100%">
+
+ <a name="generators"></a><h2>5. Supported Generators</h2>
+
+ <p>The generator is one of the major module of Bib2ML (with the BibTeX parser). It aims to create the HTML files from the internal data structure given by the parser. It is the generator which apply the canvas of the generated pages (use of 3 frames, links to the overview the index from the header of each entry's page...).</p>
+
+ <p>In addition to the usable generator listed below, Bib2ML includes an abstract generator which is the basis of all the others.</p>
+
+ <a name="generator_HTML"></a><h3>5.1. Generator HTML</h3>
+
+ <p>The generator called <code>HTML</code> is the default HTML generator of Bib2ML. Its purpose is to generate a basic content which is quiet similar to a lot of BibTeX to HTML tools (such as the LaTeX distribution's <code>bib2html</code>).</p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" align="center"><i>SUPPORTED FIELDS</i></td></tr>
+ <tr><td valign="top">
+ See this <a href="#table_HTMLfields">table</a>.
+ </td></tr>
+ </table></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" align="center"><i>FEATURES</i></td></tr>
+ <tr><td valign="top">
+ The generated result in based on <i>three frames</i>:<ul>
+ <li>upper-left frame: a brief overview which permits to do some high-level selection,</li>
+ <li>lower-left frame: a overview of all the entries which are selected accordingly to the selection made inside the upper-left frame,</li>
+ <li>right frame: the main frame which aims to display all the informations (overview, entry's pages...).</li>
+ </ul>
+ </td></tr>
+ <tr><td valign="top">
+ One page per <i>entry</i>:<ul>
+ <li>All the required and optional fields listed in <a href="#table_HTMLfields">this table</a> are displayed inside a table (except the field <code>annote</code>).</li>
+ <li>Display the content of the field <code>annote</code> (or <code>comments</code>) inside a section just below the field's table.</li>
+ <li>If the command-line option <code>--bitex</code> was specified (default), a verbatim output of the BibTeX entry was generated in its own section.</li>
+ </ul>
+ </td></tr>
+ <tr><td valign="top">
+ One short-overview page (inside the upper-left frame) which contains all the entry's types.
+ </td></tr>
+ <tr><td valign="top">
+ One short-overview page (inside the lower-left frame) which contains all the entries grouped by year and sorted by authors and publication date.
+ </td></tr>
+ <tr><td valign="top">
+ One <i>overview</i> page (inside the right frame) which contains a list of all the entries grouped by year and sorted by authors and publication date.
+ </td></tr>
+ <tr><td valign="top">
+ One <i>tree-view</i> page which contains all the entries grouped by publication's type and sorted by authors and publication date. This page could be overwriting by subclasses of this generator to provide antoher kind of tree-view.
+ </td></tr>
+ <tr><td valign="top">
+ A set of <i>index</i> pages. The index lists the significant words found inside the BibTeX file and propose a link to the entry's page where this word is. The generator produces one HTML page for each letter of the alphabet.<br>
+ A significant word is a word which has more than 2 letters and which are not known are not-significant by the Bib2ML's internal database.
+ </td></tr>
+ </table></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>GENERATOR'S PARAMETERS</i></td></tr>
+ <tr><td valign="top"><code>author-regexp=<u>expr</u></code></td>
+ <td valign="top">
+ A <a href="http://www.perldoc.com/perl5.8.4/pod/perlre.html">Perl's regular expression</a> (which is case-insensitive) against which the
+ lastname of an author is matched. If the author matches, (s)he is included in the overview window author list.
+ </td></tr>
+ <tr><td valign="top"><code>hideindex</code></td>
+ <td valign="top">
+ If presents, hide the index link and do not generate the index files.
+ </td></tr>
+ <tr><td valign="top"><code>html-generator=<u>encoding</u></code></td>
+ <td valign="top">
+ This parameter is a string that correspond to the character encoding of the generated HTML pages.
+ The default encoding is <code>ISO-8859-1</code>.
+ </td></tr>
+ <tr><td valign="top"><code>max-names-overview=<u>integer</u></code></td>
+ <td valign="top">
+ An integer which is the maximal count of authors in the overview page.
+ </td></tr>
+ <tr><td valign="top"><code>max-names-list=<u>integer</u></code></td>
+ <td valign="top">
+ An integer which is the maximal count of authors on the listing in the lower-left frame.
+ </td></tr>
+ <tr><td valign="top"><code>newtype=<u>expr</u></code></td>
+ <td valign="top">
+ A comma separated list of new publication's types, with singular and plural label.<br>
+ <p>The value must respect the format: <code>type:Singular:Plural[,type:Singular:Plural...]</code><br>
+ where <code>type</code> is the identifier of the new type, <code>Singular</code> is the label used
+ when this type has zero or one entry, <code>Plurial</code> is the label used when this type
+ has two or more entries.</p>
+ Each new type will appears inside the overview's pages. But this feature does not explain
+ how to generate the content of the corresponding entry's pages. So, the entry's pages will
+ be generated as for <code>@misc</code> entries (except if you define your own generator).
+ </td></tr>
+ <tr><td valign="top"><code>stdout</code></td>
+ <td valign="top">
+ If presents, this option force Bib2ML to output the files onto the standard output instead of files.
+ </td></tr>
+ <tr><td valign="top"><code>type-matching=<u>expr</u></code></td>
+ <td valign="top">
+ A coma separated list of items which inititalizes an associative array of type entry mappings.<br>
+ Each item must respect one of the following syntaxes:<ul>
+ <li><code>type =&gt; type</code> (since the version 1.3)</li>
+ <li><code>type -&gt; type</code> (since the version 1.3)</li>
+ <li><code>type &gt; type</code> (since the version 1.3)</li>
+ <li><code>type , type</code> (original syntax)</li>
+ </ul>
+ For example <code>incollection,article,inproceedings,article</code> means that all the
+ BibTeX's <code>@incollection</code> entries will be displayed as <code>@article</code> entries.
+ The same thing for the <code>@inproceedings</code>.<br>
+ So, the specified value for this parameters <strong>must</strong> be a list of pairs.<br>
+ An alternative syntax is: <code>type=&gt;type[,type=&gt;type...]</code>. With the same example a above,
+ the value should be <code>incollection=&gt;article,inproceedings=&gt;article</code>.
+ </td></tr>
+ <tr><td valign="top"><code>xml-verbatim</code></td>
+ <td valign="top">
+ If this parameter was given, Bib2ML will generate a verbatim text that corresponds to the XML specification of the entries. This text is put just below the BibTeX verbatim text.
+ </td></tr>
+ </table></p>
+
+ <a name="generator_Extended"></a><h3>5.2. Generator Extended</h3>
+
+ <p>The generator <code>Extended</code> is an extension of <code>HTML</code>. Its purpose is to provide some additional features.</p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>NEW SUPPORTED FIELDS</i></td></tr>
+ <tr><td valign="top"><code>abstract</code></td>
+ <td valign="top">is the abstract associated to the entry (in most of the case, it is written
+ at the begining of the paper's article).
+ </td></tr>
+ <tr><td valign="top"><code>adsurl</code></td>
+ <td valign="top">is an URL from the Astrophysics Citation Reference System which is corresponds
+ to the entry. This field supports the URL's protocols
+ <code>ftp:</code>, <code>file:</code>, <code>https:</code>,
+ <code>gopher:</code>, <code>mailto:</code> and <code>http:</code> (this last is the default).
+ </td></tr>
+ <tr><td valign="top"><code>doi</code></td>
+ <td valign="top">is the Document Object Identifier (DOI) which is assumed to be an URL
+ linked to a document on Internet. This field supports the URL's protocols
+ <code>ftp:</code>, <code>file:</code>, <code>https:</code>,
+ <code>gopher:</code>, <code>mailto:</code> and <code>http:</code> (this last is the default).
+ </td></tr>
+ <tr><td valign="top"><code>isbn</code></td>
+ <td valign="top">is the <a href="http://www.isbn.org/">ISBN number</a> of the entry.
+ </td></tr>
+ <tr><td valign="top"><code>issn</code></td>
+ <td valign="top">is the <a href="http://www.issn.org/">ISSN number</a> of the entry.
+ </td></tr>
+ <tr><td valign="top"><code>keywords</code></td>
+ <td valign="top">is list of the keywords associated to the entry (in most of the case, they
+ are mentionned at the begining of the paper's article).
+ </td></tr>
+ <tr><td valign="top"><code>localfile</code></td>
+ <td valign="top">is the path (on your local host) to a electronical version of
+ the document that is described by the entry (I recommended to put only
+ a PDF or a Postscript file here).<br>
+ If this field was present and the corresponding file was found, Bib2ML
+ generates a link to this into the entry's page.<br>
+ See the parameters of this generator to influence the default location of the
+ electronical files.
+ </td></tr>
+ <tr><td valign="top"><code>readers</code></td>
+ <td valign="top">is a list of people who read this entry. The value of this field <strong>must</strong>
+ support the <a href="#format_names">BibTeX's syntax for names</a>.
+ </td></tr>
+ <tr><td valign="top"><code>url</code></td>
+ <td valign="top">is an URL associated to the entry. This field supports the URL's protocols
+ <code>ftp:</code>, <code>file:</code>, <code>https:</code>,
+ <code>gopher:</code>, <code>mailto:</code> and <code>http:</code> (this last is the default).
+ </td></tr>
+ <tr><td valign="top"><code>pdf</code></td>
+ <td valign="top">is an URL associted to the entry with
+ corresponds to a PDF file. This field supports the URL's protocols
+ <code>ftp:</code>, <code>file:</code>, <code>https:</code>,
+ <code>gopher:</code>, <code>mailto:</code> and <code>http:</code>.
+ </td></tr>
+ </table></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" align="center"><i>NEW FEATURES</i></td></tr>
+ <tr><td valign="top">
+ In the entry's pages:<ul>
+ <li>The new fields are added into the generated table (except for <code>abstract</code> and <code>keywords</code>).</li>
+ <li>The values of the fields <code>abstract</code> and <code>keywords</code> are put inside a specific section.</li>
+ </ul>
+ </td></tr>
+ <tr><td valign="top">
+ The overview page is extended with the list of all the authors.
+ </td></tr>
+ </table></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>NEW GENERATOR'S PARAMETERS</i></td></tr>
+ <tr><td valign="top"><code>absolute-source=<u>path</u></code></td>
+ <td valign="top">
+ is the absolute path of the directory where the downloadable documents could be found
+ (see the field <code>localfile</code> for details about the downloadable documents).<br>
+ The parameters <code>absolute-source</code>, <code>relative-source</code> and
+ <code>target-url</code> are mutually exclusive.
+ </td></tr>
+ <tr><td valign="top"><code>backslash</code></td>
+ <td valign="top">
+ if presents, indicates that backslashes will be removed from the link fields (url,ftp...).
+ </td></tr>
+ <tr><td valign="top"><code>doc-repository=<u>path</u></code></td>
+ <td valign="top">
+ if presents, indicates the directory where are stored the electronical documents. This option assumes hat electronical documents have a name similar to the BibTeX key. For example the entry with the key <code>Galland.esm00</code> could have an associated electronical document with its name equals to one of <code>Galland.esm00.pdf</code>, <code>Galland.esm00.PDF</code>, <code>Galland.esm00.ps</code> or <code>Galland.esm00.PS</code>.
+ </td></tr>
+ <tr><td valign="top"><code>nodownload</code></td>
+ <td valign="top">
+ if presents, indicates that no link to the electronic
+ documents will be generated. By extension, if
+ presents no copy of there files will be made.
+ </td></tr>
+ <tr><td valign="top"><code>relative-source=<u>path</u></code></td>
+ <td valign="top">
+ is the relative path of the directory where the downloadable documents could be found
+ (see the field <code>localfile</code> for details about the downloadable documents).
+ This path is relative to the directory where the BibTeX file is located.<br>
+ The parameters <code>absolute-source</code>, <code>relative-source</code> and
+ <code>target-url</code> are mutually exclusive.
+ </td></tr>
+ <tr><td valign="top"><code>target-url=<u>url</u></code></td>
+ <td valign="top">
+ is an URL where the downloadable documents could be find. It means that
+ if this URL was specified, Bib2ML assumes that all the files
+ could be download from the specified URL. It means also that
+ no copy will be made by Bib2ML.<br>
+ The parameters <code>absolute-source</code>, <code>relative-source</code> and
+ <code>target-url</code> are mutually exclusive.
+ </td></tr>
+ </table></p>
+
+ <a name="generator_Domain"></a><h3>5.3. Generator Domain</h3>
+
+ <p>The generator <code>Domain</code> is an extension of <code>Extended</code>. Its purpose is to provide some additional features about the scientifical domains of the entries.</p>
+
+ <p>This generator introduces the concept of &laquo;domain&raquo; which corresponds to the name of a scientifical context/domain. An entry could be inside one or more domains.</p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>NEW SUPPORTED FIELDS</i></td></tr>
+ <tr><td valign="top"><code>domain</code></td>
+ <td valign="top">is the first domain in which this entry was.<br>
+ This field does not overset the previous domain's setting (except for
+ <code>domain</code>).
+ </td></tr>
+ <tr><td valign="top"><code>domains</code></td>
+ <td valign="top">is a list of domains in which this entry was. The domain's separator is the character '<code>:</code>'.<br>
+ This field does not overset the previous domain's setting (except for
+ <code>domains</code>).
+ </td></tr>
+ <tr><td valign="top"><code>nddomain</code></td>
+ <td valign="top">is the second domain in which this entry was.<br>
+ This field does not overset the previous domain's setting (except for
+ <code>nddomain</code>).
+ </td></tr>
+ <tr><td valign="top"><code>rddomain</code></td>
+ <td valign="top">is the third domain in which this entry was.<br>
+ This field does not overset the previous domain's setting (except for
+ <code>rddomain</code>).
+ </td></tr>
+ </table></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" align="center"><i>NEW FEATURES</i></td></tr>
+ <tr><td valign="top">
+ Inside the entry's page, a section with the other entries inside the same domains was added. The entries of this list are grouped by domains and sorted by authors.
+ </td></tr>
+ <tr><td valign="top">
+ One <i>domain-view</i> page which contains all the entries grouped by domain and sorted by authors and publication date. This page could be overwriting by subclasses of this generator to provide antoher kind of domain-view.
+ </td></tr>
+ </table></p>
+
+ <a name="generator_XML"></a><h3>5.4. Generator XML</h3>
+
+ <p>The generator called <code>XML</code> is the default XML generator of Bib2ML. Its purpose is to generate a basic content which respects the XML <a href="./bibtexml_dtd.html">DTD</a> defined by <a href="http://bibtexml.sf.net/">BibteXML</a>.</p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" align="center"><i>SUPPORTED FIELDS</i></td></tr>
+ <tr><td valign="top">
+ See this <a href="#table_HTMLfields">table</a> and the definition of the BibteXML's <a href="./bibtexml_dtd.html">DTD</a>.
+ </td></tr>
+ </table></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>GENERATOR'S PARAMETERS</i></td></tr>
+ <tr><td valign="top"><code>stdout</code></td>
+ <td valign="top">
+ If presents, this option force Bib2ML to output the files onto the standard output instead of files.
+ </td></tr>
+ <tr><td valign="top"><code>xml-encoding=<u>encoding</u></code></td>
+ <td valign="top">
+ is character encoding which will be put into the header of the generated XML file.
+ All values for the character encoding supported by the XML specifications are allowed (<code>ISO-8859-1</code>, <code>UTF8</code>...). The default value is <code>ISO-8859-1</code>.
+ </td></tr>
+ </table></p>
+
+ <a name="generator_SQL"></a><h3>5.5. Generator SQL</h3>
+
+ <p>The generator called <code>SQL</code> is the default SQL generator of Bib2ML. Its purpose is to generate a basic content which respects the SQL schema illustrated by the following figure.</p>
+
+ <p style="text-align: center;"><a href="./sql_schema.png"><img src="./sql_schema_small.png"></a></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" align="center"><i>SUPPORTED FIELDS</i></td></tr>
+ <tr><td valign="top">
+ See this <a href="#table_HTMLfields">table</a>.
+ </td></tr>
+ </table></p>
+
+ <p><table border="1" cellspacing="0" cellpadding="5" width="100%">
+ <tr><td bgcolor="#cccccc" colspan="2" align="center"><i>GENERATOR'S PARAMETERS</i></td></tr>
+ <tr><td valign="top"><code>sql-encoding=<u>name</u></code></td>
+ <td valign="top">
+ Defines the character encoding used to generate the SQL script.
+ </td></tr>
+ <tr><td valign="top"><code>sql-engine=<u>name</u></code></td>
+ <td valign="top">
+ Defines the SQL engine for which the SQL script should be generated.
+ The supported engines are: "mysql" and "pgsql".
+ </td></tr>
+ <tr><td valign="top"><code>stdout</code></td>
+ <td valign="top">
+ If presents, this option force Bib2ML to output the files onto the standard output instead of files.
+ </td></tr>
+ </table></p>
+
+ <hr width="100%">
+
+ <a name="themes"></a><h2>6. Supported Themes</h2>
+
+ Bib2ML permits to select a theme which influence the look of the generated pages. You could select a theme which the command-line option <code>--theme</code> and list all the supported themes which <code>--themelist</code>.</p>
+
+ <a name="theme_Simple"></a><h2>6.1. Theme Simple</h2>
+
+ <p>The theme <code>Simple</code> is the default theme. It is quiet similar to the default output of <a href="http://java.sun.com/j2se/javadoc/">JavaDoc</a>.</p>
+ <center><a href="./capture2.png"><img src="./capture2.png" width="50%"></a></center>
+
+ <a name="theme_Dyna"></a><h2>6.2. Theme Dyna</h2>
+
+ <p>The theme <code>Dyna</code> is an experimental theme. It uses its own look policy and includes some dynamical features such a collapsing lists...</p>
+
+ <center><a href="./capture.png"><img src="./capture.png" width="50%"></a></center>
+
+ <a name="theme_contrib"></a><h2>6.3. Contribute</h2>
+
+ <p>Do you want to have your own theme for the HMTL generators? If yes, you should write your own theme in Perl.</p>
+
+ <p>Create a Perl class which extends the class <code>Bib2HTML::Generator::Theme</code> and implements the required functions. To have any example of implementation, see the two default themes: <code>Bib2HTML::Generator::Theme::Simple</code> and <code>Bib2HTML::Generator::Theme::Dyna</code>. Caution: you must put your theme class inside the same directory as <code>Simple</code> and <code>Dyna</code>.</p>
+
+ <hr width="100%">
+
+ <a name="languages"></a><h2>7. Supported Languages</h2>
+
+ <p>Bib2ML supports the French, the English, Spanish (thanks to Sebastian), Portuguese (thanks to João) and Italian (thanks to Cristian).</p>
+
+ <a name="languages_contrib"></a><h2>7.1. Contribute</h2>
+
+ <p>If you want to add the support for a specifical language, you need to create the following files inside the language directory (<code>/path/to/bib2ml/Bib2HTML/Generator/Lang</code>):<ul>
+ <li>copy the file <code>ENGLISH</code> as <code>LANGUAGE</code> (where <code>LANGUAGE</code> is the name of your language);</li>
+ <li>edit the file <code>LANGUAGE</code>; each line must start with the string identifier, which must be unchanged, followed by the string to display (see below for the syntax);</li>
+ <li>Repeat the two previous steps for each file for which the name starts by <code>ENGLISH</code>.</li>
+ <li>The file associated to an HTML generation has the name <code>&lt;LANGUAGE&gt;.&lt;GENERATION_NAME&gt;</code>.</li>
+ <li>The file associated to an HTML theme has the name <code>&lt;LANGUAGE&gt;.Theme.&lt;THEME_NAME&gt;</code>.</li>
+ </ul></p>
+
+ <p>The syntax of the language files is:<ul>
+ <li>Each line starting with '<code>#</code>' is a comment</li>
+ <li>Each language line must respect the syntax: <code>IDENTIFIER = STRING</code> where <code>IDENTIFIER</code> is the name of the string specified inside the Perl source code of Bib2ML, and <code>STRING</code> is the value of the string</li>
+ <li>Empty lines are ignored</li>
+ <li>If the string value finished by the character backslash (<code>\</code>), the value is assumed to continue on the next line (the spaces characters starting the next line will be ignored)</li>
+ <li>If the string value contains a substring of the form <code>{{NAME}}</code>, the substring will be replaced by the result of a call to the Perl function called <code>NAME</code></li>
+ <li>If the string value contains a substring of the form <code>#NUMBER</code>, the substring will be dynamically replaced by the value of the <code>NUMBER</code>-th parameter passed to the Perl function which permits to get the value.</li>
+ </ul></p>
+
+ <hr width="100%">
+
+ <a name="license"></a><h2>8. License</h2>
+
+ <p>Bib2ML is under the GNU GPL</a> license.</p>
+
+ <p>Bib2ML is a converter of BibTeX data files into HTML pages.<br>
+ Copyright &copy; 1998-2006 Stéphane GALLAND &lt;galland@arakhne.org&gt;</p>
+
+ <p>This program is free software; you can redistribute it and/or modify it under the terms of the <a href="http://www.gnu.org/copyleft/gpl.html">GNU General Public License</a> as published by the <a href="http://www.fsf.org/">Free Software Foundation</a>; either version 2 of the License, or (at your option) any later version.</p>
+
+ <p> This program is distributed in the hope that it will be useful, but <strong>WITHOUT ANY WARRANTY</strong>; without even the implied warranty of <strong>MERCHANTABILITY</strong> or <strong>FITNESS FOR A PARTICULAR PURPOSE</strong>. See the GNU General Public License for more details.</p>
+
+ <p>You should have received a copy of the GNU General Public License along with this program; see the file <code>COPYING</code>. If not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.</p>
+
+ <hr width="100%">
+
+ <a name="contributor"></a><h2>9. Contributors</h2>
+
+ <p>I would like to thank the following people for generously taking the
+ time to point out bugs, suggest improvements, or send me Bib2ML
+ patches. Many thanks to:<ul>
+ <li><a href="mailto:joao.lourenco@di.fct.unl.pt">João LOURENCO</a> has:<ul>
+ <li>submited the Portuguese translations.</li>
+ </ul></li>
+ <li><a href="mailto:michail@mpi-sb.mpg.de">Dimitris MICHAIL</a> has:<ul>
+ <li>added TeX commands.</li>
+ </ul></li>
+ <li><a href="mailto:preining@logic.at">Norbert PREINING</a> has:<ul>
+ <li>added the function <code>uniq</code> to eliminate redundant
+ values from a sorted list.</li>
+ <li>added the TeX's commands '<code>\#</code>' and '<code>\L</code>'.</li>
+ <li>added a warning message inside <code>__texcommand_map_to</code> when
+ a accentuated TeX command was encoutered but
+ Bib2ML does not known any corresponding HTML character
+ (e.g. <code>\'b</code>).</li>
+ <li>fixed a bug inside <code>__texcommand_map_to</code> which does not
+ return the right variable's value.</li>
+ <li>fixed two bugs inside <code>save_generator_parameter</code> which prevent
+ to properly set the parameters' values.</li>
+ </ul></li>
+ <li><a href="mailto:sebastian.rodriguez@utbm.fr">Sebastian RODRIGUEZ</a> has:<ul>
+ <li>reported bugs and submited the Spanish translations.</li>
+ </ul></li>
+ <li><a href="mailto:zinser@zinser.no-ip.info">Martin P.J. ZINSER</a> has:<ul>
+ <li>fixed a bug inside the function <code>addentry</code>
+ which permits to add an BibTeX's field.
+ All the fields' names are lower-cased to avoid
+ setting problems.</li>
+ </ul></li>
+ <li><a href="mailto:cri@linux.it">Cristian RIGAMONTI</a> has:<ul>
+ <li>submited the Italian translations.</li>
+ </ul></li>
+ <li><a href="mailto:paolini@di.unito.it">Luca PAOLINI</a> has:<ul>
+ <li>submited a patch that permits to support more letters with the caron accent.</li>
+ </ul></li>
+ <li><a href="mailto:gabrisa@optics.szfki.kfki.hu">Aurel GABRIS</a> has:<ul>
+ <li>submited a patch that add the generator parameters <code>max-titlelength-overview</code> and <code>show-journalparams-overview</code>.</li>
+ </ul></li>
+ <li><a href="mailto:loew@mathematik.tu-darmstadt.de">Tobias LOEW</a> has:<ul>
+ <li>patched the TeX parser to support some roman characters.</li>
+ </ul></li>
+ <li><a href="mailto:gasper.jaklic@fmf.uni-lj.si">Gasper JAKLIC</a> has:<ul>
+ <li>patched the TeX parser to support some locale characters;</li>
+ <li>reproduced high priority bugs and mismatches.</li>
+ </ul></li>
+ <li><a href="mailto:olivier.hugues@gmail.com">Olivier HUGUES</a> has:<ul>
+ <li>reported bugs in bib2sql tool.</li>
+ </ul></li>
+
+ </ul></p>
+
+ <hr width="100%">
+
+ <a name="bugreport"></a><h2>10. Bug Reporting</h2>
+
+ <p>You could submit bugs, suggest improvements, or send Bib2ML patches by using one of the following methods:<ul>
+ <li>send an email to <a href="mailto:galland@arakhne.org"><code>galland@arakhne.org</code></a>;</li>
+ </ul></p>
+
+ <p align="right"><small>Copyright 2004-11 &copy; Stéphane GALLAND<br><code>&lt;galland@arakhne.org&gt;</code></small></p>
+
+ </body>
+</html>
diff --git a/biblio/bibtex/utils/bib2ml/doc/mustwork.gif b/biblio/bibtex/utils/bib2ml/doc/mustwork.gif
new file mode 100644
index 0000000000..8f643bcc02
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/mustwork.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/not-validated.gif b/biblio/bibtex/utils/bib2ml/doc/not-validated.gif
new file mode 100644
index 0000000000..7a07946fc6
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/not-validated.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/optional.gif b/biblio/bibtex/utils/bib2ml/doc/optional.gif
new file mode 100644
index 0000000000..5fb591bef3
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/optional.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/required.gif b/biblio/bibtex/utils/bib2ml/doc/required.gif
new file mode 100644
index 0000000000..447dd84312
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/required.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/requiredor.png b/biblio/bibtex/utils/bib2ml/doc/requiredor.png
new file mode 100644
index 0000000000..6bc13934eb
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/requiredor.png
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/requiredor2.png b/biblio/bibtex/utils/bib2ml/doc/requiredor2.png
new file mode 100644
index 0000000000..b7d98879c8
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/requiredor2.png
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/sql_schema.png b/biblio/bibtex/utils/bib2ml/doc/sql_schema.png
new file mode 100644
index 0000000000..e2bda8d8e6
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/sql_schema.png
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/sql_schema_small.png b/biblio/bibtex/utils/bib2ml/doc/sql_schema_small.png
new file mode 100644
index 0000000000..85080ac85f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/sql_schema_small.png
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/validated.gif b/biblio/bibtex/utils/bib2ml/doc/validated.gif
new file mode 100644
index 0000000000..12b60befe7
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/validated.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/doc/work.gif b/biblio/bibtex/utils/bib2ml/doc/work.gif
new file mode 100644
index 0000000000..5fb591bef3
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/doc/work.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/man/bib2html_en.pod b/biblio/bibtex/utils/bib2ml/man/bib2html_en.pod
new file mode 100644
index 0000000000..a84355fb61
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/man/bib2html_en.pod
@@ -0,0 +1,209 @@
+=head1 NAME
+
+bib2html - A perl script that generates an HTML documentation for a BibTeX database
+
+
+=head1 SYNOPSYS
+
+bib2html [options] F<file> [F<file> ...]
+
+=head1 DESCRIPTION
+
+bib2html is a script which permits to generate a set of HTML pages for
+the entries of BibTeX files.
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-[no]b>
+
+=item B<--[no]bibtex>
+
+This option permits to generate, or not, a verbatim of the
+BibTeX entry code.
+
+=item B<--[no]checknames>
+
+This option permits to check if the some author's names are
+similar and generates a set of warnings about each of them.
+
+=item B<--cvs>
+
+If specified, this option disables the deletion of the subfiles
+'.cvs', 'CVS' and 'CVSROOT' in the output directory.
+
+=item B<-d> I<name>[=I<value>]
+
+See B<--generatorparam>.
+
+=item B<--doctitle> I<text>
+
+Sets the title that appears in the main page.
+
+=item B<-f>
+
+=item B<--force>
+
+Forces to overwrite into the output directory.
+
+=item B<-g> I<class>
+
+=item B<--generator> I<class>
+
+Sets the generator to use. I<class> must be a valid Perl class.
+
+=item B<--generatorparam> I<name>[=I<value>]
+
+Sets a generator param. It must be a I<key>=I<value> pair or
+simply a I<name>.
+Example: "target=thisdirectory" defines the parameter target
+with corresponding value "thisdirectory". The specified
+parameters which are not supported by the generator are
+ignored.
+
+=item B<--generatorparams>
+
+Shows the list of supported parameters, and their
+semantics for the current generator.
+
+=item B<--genlist>
+
+Shows the list of supported generators.
+
+=item B<-?>
+
+=item B<-h>
+
+Show the list of available options.
+
+=item B<--help>
+
+See B<--man>.
+
+=item B<--jabref>
+
+The generator will translate JabRef's groups
+into Bib2HTML's domains.
+
+=item B<--lang> I<name>
+
+Sets the language used by the generator.
+
+=item B<--langlist>
+
+Shows the list of supported language.
+
+=item B<--man>
+
+=item B<--manual>
+
+Show the manual page.
+
+=item B<-o> F<file>
+
+=item B<--output> F<file>
+
+Sets the directory or the F<file> in which the documentation will be put.
+
+=item B<-p> F<file>
+
+=item B<--preamble> F<file>
+
+Sets the name of the F<file> to read to include some TeX preambles.
+You could use this option to dynamicaly defined some unsupported
+LaTeX commands.
+
+=item B<--protect> F<shell_wildcard>
+
+If specified, this option disables the deletion in the target
+directory of the subfiles that match the specified shell
+expression.
+
+=item B<-q>
+
+Don't be verbose: only error messages are displayed.
+
+=item B<--[no]sortw>
+
+Shows (or not) a sorted list of warnings.
+
+=item B<--stdout>
+
+Force the output of the generated files onto the standard output.
+This option is equivalent to C<-d stdout>.
+
+=item B<--svn>
+
+If specified, this option disables the deletion of the subfiles
+'.svn' and 'svn' in the output directory.
+
+=item B<--texcmd>
+
+Shows the list of supported LaTeX commands.
+
+=item B<--theme> I<name>
+
+Sets the theme used by the generator.
+
+=item B<--themelist>
+
+Shows the list of supported themes.
+
+=item B<-v>
+
+Be more verbose.
+
+=item B<--version>
+
+Show the version of this script.
+
+=item B<--[no]warning>
+
+If false, the warning are converted to errors.
+
+=item B<--windowtitle> I<text>
+
+Sets the title that appears as the window's title.
+
+=back
+
+=head1 LICENSE
+
+S<GNU Public License (GPL)>
+
+=head1 COPYRIGHT
+
+S<Copyright (c) 1998-06 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+
+=head1 CONTRIBUTORS
+
+=over
+
+=item S<Aurel GABRIS E<lt>L<gabrisa@optics.szfki.kfki.hu>E<gt>>
+
+=item S<Gasper JAKLIC E<lt>L<gasper.jaklic@fmf.uni-lj.si>E<gt>>
+
+=item S<Tobias LOEW E<lt>L<loew@mathematik.tu-darmstadt.de>E<gt>>
+
+=item S<Joao LOURENCO E<lt>L<joao.lourenco@di.fct.unl.pt>E<gt>>
+
+=item S<Dimitris MICHAIL E<lt>L<michail@mpi-sb.mpg.de>E<gt>>
+
+=item S<Luca PAOLINI E<lt>L<paolini@di.unito.it>E<gt>>
+
+=item S<Norbert PREINING E<lt>L<preining@logic.at>E<gt>>
+
+=item S<Cristian RIGAMONTI E<lt>L<cri@linux.it>E<gt>>
+
+=item S<Sebastian RODRIGUEZ E<lt>L<sebastian.rodriguez@utbm.fr>E<gt>>
+
+=item S<Martin P.J. ZINSER E<lt>L<zinser@zinser.no-ip.info>E<gt>>
+
+=item S<Olivier HUGHES E<lt>L<olivier.hugues@gmail.com>E<gt>>
+
+=back
+
+=head1 SEE ALSO
+
+L<latex>, L<bibtex>
diff --git a/biblio/bibtex/utils/bib2ml/man/bib2html_fr.pod b/biblio/bibtex/utils/bib2ml/man/bib2html_fr.pod
new file mode 100644
index 0000000000..2df2a437cd
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/man/bib2html_fr.pod
@@ -0,0 +1,206 @@
+=head1 NOM
+
+bib2html - Script Perl générant des pages HTML à partir de fichiers BibTeX
+
+=head1 SYNOPSIS
+
+bib2html [options] F<fichier> [F<fichier> ...]
+
+=head1 DESCRIPTION
+
+bib2html est un script permettant de generer des pages HTML structurant et décrivant le contenu d'une base bibliographique écrite dans le format BibTeX.
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-[no]b>
+
+=item B<--[no]bibtex>
+
+Génération (ou non) du code BibTeX dans les pages HTML.
+
+=item B<--[no]checknames>
+
+Vérification de la cohérence des noms des auteurs. Un avertissement sera
+exprimée chaque fois que bib2html détectera des noms dupliqués ou des
+fautes de frappe.
+
+=item B<--cvs>
+
+Si spécifiée, cette option interdit la suppression des sous-fichiers
+'.cvs', 'CVS' et 'CVSROOT' dans le répertoire destination.
+
+=item B<-d> I<nom>[=I<valeur>]
+
+Voir B<--generatorparam>.
+
+=item B<--doctitle> I<texte>
+
+Initialisation du titre de la page principale.
+
+=item B<-f>
+
+=item B<--force>
+
+Force l'écriture des pages HTML dans le répertoire destination.
+
+=item B<-g> I<classe>
+
+=item B<--generator> I<classe>
+
+Spécification du générateur à utiliser. I<class> doit être une classe Perl
+valide.
+
+=item B<--generatorparam> I<nom>[=I<valeur>]
+
+Initialisation de la valeur d'un paramètre du générateur. Ce paramètre doit être une paire I<nom>=I<valeur> ou simplement un I<nom>.
+Exemple: "target=thisdirectory" défini le paramètre 'target'
+avec la valeur "thisdirectory".
+
+=item B<--generatorparams>
+
+Affiche la liste des paramètres supportés par le générateur.
+
+=item B<--genlist>
+
+Affiche la liste des générateurs supportés.
+
+=item B<-?>
+
+=item B<-h>
+
+Affiche la liste des options de bib2html.
+
+=item B<--help>
+
+Voir B<--man>.
+
+=item B<--jabref>
+
+Le générateur traduira les groupes de JabRef
+en domaines Bib2HTML.
+
+=item B<--lang> I<nom>
+
+Initialisation de la langue à utiliser.
+
+=item B<--langlist>
+
+Affiche la liste des langues supportées.
+
+=item B<--man>
+
+=item B<--manual>
+
+Affiche la page de manual.
+
+=item B<-o> F<fichier>
+
+=item B<--output> F<fichier>
+
+Initialise le répertoire où la documentation générée sera déposées.
+
+=item B<-p> F<fichier>
+
+=item B<--preamble> F<fichier>
+
+Initialise le nom du F<fichier> à lire et contenant des préambules TeX.
+Vous pouvez utiliser cette option pour définir des commandes LaTeX
+que ne supporte pas encore bib2html.
+
+=item B<--protect> F<shell_wildcard>
+
+Si spécifiée, cette option interdit la suppression dans le répertoire
+destination des sous-fichiers correspondant à l'expression shell
+spécifiée.
+
+=item B<-q>
+
+Mode non verbeux: seuls les messages d'erreurs sont affichés.
+
+=item B<--[no]sortw>
+
+Tri (ou non) les avertissement par ordre croissant des lignes où
+ils apparaissent.
+
+=item B<--stdout>
+
+Force la sortie des fichiers générés sur la sortie standard.
+Cette option est équivalente à C<-d stdout>.
+
+=item B<--svn>
+
+Si spécifiée, cette option interdit la suppression des sous-fichiers
+'.svn' et 'svn' dans le répertoire destination.
+
+=item B<--texcmd>
+
+Affiche la liste des commandes TeX supportées.
+
+=item B<--theme> I<name>
+
+Initialise le thème devant être utilisé par le générateur.
+
+=item B<--themelist>
+
+Affiche la liste des thèmes disponibles.
+
+=item B<-v>
+
+Augmente la verbosité de bib2html.
+
+=item B<--version>
+
+Affiche la version de ce script.
+
+=item B<--[no]warning>
+
+Si faux, les avertissements sont convertis en erreurs.
+
+=item B<--windowtitle> I<text>
+
+Initialise le titre des pages HTML devant apparaître dans
+la barre de titre des fenêtres du navigateur.
+
+=back
+
+=head1 LICENCE
+
+S<GNU Public License (GPL)>
+
+=head1 COPYRIGHT
+
+S<Copyright (c) 1998-06 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+
+=head1 CONTRIBUTEURS
+
+=over
+
+=item S<Aurel GABRIS E<lt>L<gabrisa@optics.szfki.kfki.hu>E<gt>>
+
+=item S<Gasper JAKLIC E<lt>L<gasper.jaklic@fmf.uni-lj.si>E<gt>>
+
+=item S<Tobias LOEW E<lt>L<loew@mathematik.tu-darmstadt.de>E<gt>>
+
+=item S<Joao LOURENCO E<lt>L<joao.lourenco@di.fct.unl.pt>E<gt>>
+
+=item S<Dimitris MICHAIL E<lt>L<michail@mpi-sb.mpg.de>E<gt>>
+
+=item S<Luca PAOLINI E<lt>L<paolini@di.unito.it>E<gt>>
+
+=item S<Norbert PREINING E<lt>L<preining@logic.at>E<gt>>
+
+=item S<Cristian RIGAMONTI E<lt>L<cri@linux.it>E<gt>>
+
+=item S<Sebastian RODRIGUEZ E<lt>L<sebastian.rodriguez@utbm.fr>E<gt>>
+
+=item S<Martin P.J. ZINSER E<lt>L<zinser@zinser.no-ip.info>E<gt>>
+
+=item S<Olivier HUGHES E<lt>L<olivier.hugues@gmail.com>E<gt>>
+
+=back
+
+=head1 SEE ALSO
+
+L<latex>, L<bibtex>
diff --git a/biblio/bibtex/utils/bib2ml/man/bib2sql_en.pod b/biblio/bibtex/utils/bib2ml/man/bib2sql_en.pod
new file mode 100644
index 0000000000..af9477cbe6
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/man/bib2sql_en.pod
@@ -0,0 +1,215 @@
+=head1 NAME
+
+bib2sql - A perl script that generates an SQL file for a BibTeX database
+
+
+=head1 SYNOPSYS
+
+bib2sql [options] F<file> [F<file> ...]
+
+=head1 DESCRIPTION
+
+bib2sql is a script which permits to generate a SQL file for
+the entries of BibTeX files.
+
+The generated SQL file is compliant with the following data structure:
+
+The bib2sql command is equivalent to:
+bib2html [options] F<file> [F<file> ...] -g XML
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-[no]b>
+
+=item B<--[no]bibtex>
+
+This option permits to generate, or not, a verbatim of the
+BibTeX entry code.
+
+=item B<--[no]checknames>
+
+This option permits to check if the some author's names are
+similar and generates a set of warnings about each of them.
+
+=item B<--cvs>
+
+If specified, this option disables the deletion of the subfiles
+'.cvs', 'CVS' and 'CVSROOT' in the output directory.
+
+=item B<-d> I<name>[=I<value>]
+
+See B<--generatorparam>.
+
+=item B<--doctitle> I<text>
+
+Sets the title that appears in the main page.
+
+=item B<-f>
+
+=item B<--force>
+
+Forces to overwrite into the output directory.
+
+=item B<-g> I<class>
+
+=item B<--generator> I<class>
+
+Sets the generator to use. I<class> must be a valid Perl class.
+
+=item B<--generatorparam> I<name>[=I<value>]
+
+Sets a generator param. It must be a I<key>=I<value> pair or
+simply a I<name>.
+Example: "target=thisdirectory" defines the parameter target
+with corresponding value "thisdirectory". The specified
+parameters which are not supported by the generator are
+ignored.
+
+=item B<--generatorparams>
+
+Shows the list of supported parameters, and their
+semantics for the current generator.
+
+=item B<--genlist>
+
+Shows the list of supported generators.
+
+=item B<-?>
+
+=item B<-h>
+
+Show the list of available options.
+
+=item B<--help>
+
+See B<--man>.
+
+=item B<--jabref>
+
+The generator will translate JabRef's groups
+into Bib2HTML's domains.
+
+=item B<--lang> I<name>
+
+Sets the language used by the generator.
+
+=item B<--langlist>
+
+Shows the list of supported language.
+
+=item B<--man>
+
+=item B<--manual>
+
+Show the manual page.
+
+=item B<-o> F<file>
+
+=item B<--output> F<file>
+
+Sets the directory or the F<file> in which the documentation will be put.
+
+=item B<-p> F<file>
+
+=item B<--preamble> F<file>
+
+Sets the name of the F<file> to read to include some TeX preambles.
+You could use this option to dynamicaly defined some unsupported
+LaTeX commands.
+
+=item B<--protect> F<shell_wildcard>
+
+If specified, this option disables the deletion in the target
+directory of the subfiles that match the specified shell
+expression.
+
+=item B<-q>
+
+Don't be verbose: only error messages are displayed.
+
+=item B<--[no]sortw>
+
+Shows (or not) a sorted list of warnings.
+
+=item B<--stdout>
+
+Force the output of the generated files onto the standard output.
+This option is equivalent to C<-d stdout>.
+
+=item B<--svn>
+
+If specified, this option disables the deletion of the subfiles
+'.svn' and 'svn' in the output directory.
+
+=item B<--texcmd>
+
+Shows the list of supported LaTeX commands.
+
+=item B<--theme> I<name>
+
+Sets the theme used by the generator.
+
+=item B<--themelist>
+
+Shows the list of supported themes.
+
+=item B<-v>
+
+Be more verbose.
+
+=item B<--version>
+
+Show the version of this script.
+
+=item B<--[no]warning>
+
+If false, the warning are converted to errors.
+
+=item B<--windowtitle> I<text>
+
+Sets the title that appears as the window's title.
+
+=back
+
+=head1 LICENSE
+
+S<GNU Public License (GPL)>
+
+=head1 COPYRIGHT
+
+S<Copyright (c) 1998-06 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+S<Copyright (c) 2011 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+
+=head1 CONTRIBUTORS
+
+=over
+
+=item S<Aurel GABRIS E<lt>L<gabrisa@optics.szfki.kfki.hu>E<gt>>
+
+=item S<Gasper JAKLIC E<lt>L<gasper.jaklic@fmf.uni-lj.si>E<gt>>
+
+=item S<Tobias LOEW E<lt>L<loew@mathematik.tu-darmstadt.de>E<gt>>
+
+=item S<Joao LOURENCO E<lt>L<joao.lourenco@di.fct.unl.pt>E<gt>>
+
+=item S<Dimitris MICHAIL E<lt>L<michail@mpi-sb.mpg.de>E<gt>>
+
+=item S<Luca PAOLINI E<lt>L<paolini@di.unito.it>E<gt>>
+
+=item S<Norbert PREINING E<lt>L<preining@logic.at>E<gt>>
+
+=item S<Cristian RIGAMONTI E<lt>L<cri@linux.it>E<gt>>
+
+=item S<Sebastian RODRIGUEZ E<lt>L<sebastian.rodriguez@utbm.fr>E<gt>>
+
+=item S<Martin P.J. ZINSER E<lt>L<zinser@zinser.no-ip.info>E<gt>>
+
+=item S<Olivier HUGHES E<lt>L<olivier.hugues@gmail.com>E<gt>>
+
+=back
+
+=head1 SEE ALSO
+
+L<bib2html>, L<latex>, L<bibtex>
diff --git a/biblio/bibtex/utils/bib2ml/man/bib2sql_fr.pod b/biblio/bibtex/utils/bib2ml/man/bib2sql_fr.pod
new file mode 100644
index 0000000000..536a047011
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/man/bib2sql_fr.pod
@@ -0,0 +1,212 @@
+=head1 NOM
+
+bib2sql - Script Perl générant des fichiers SQL à partir de fichiers BibTeX
+
+=head1 SYNOPSIS
+
+bib2sql [options] F<fichier> [F<fichier> ...]
+
+=head1 DESCRIPTION
+
+bib2sql est un script permettant de generer des fichiers SQL structurant et décrivant le contenu d'une base bibliographique écrite dans le format BibTeX.
+
+Le fichier SQL généré est conforme aux spécifications suivantes :
+
+Cette commande est équivalente à:
+bib2html [options] F<fichier> [F<fichier> ...] -g XML
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-[no]b>
+
+=item B<--[no]bibtex>
+
+Génération (ou non) du code BibTeX dans les pages HTML.
+
+=item B<--[no]checknames>
+
+Vérification de la cohérence des noms des auteurs. Un avertissement sera
+exprimée chaque fois que bib2html détectera des noms dupliqués ou des
+fautes de frappe.
+
+=item B<--cvs>
+
+Si spécifiée, cette option interdit la suppression des sous-fichiers
+'.cvs', 'CVS' et 'CVSROOT' dans le répertoire destination.
+
+=item B<-d> I<nom>[=I<valeur>]
+
+Voir B<--generatorparam>.
+
+=item B<--doctitle> I<texte>
+
+Initialisation du titre de la page principale.
+
+=item B<-f>
+
+=item B<--force>
+
+Force l'écriture des pages HTML dans le répertoire destination.
+
+=item B<-g> I<classe>
+
+=item B<--generator> I<classe>
+
+Spécification du générateur à utiliser. I<class> doit être une classe Perl
+valide.
+
+=item B<--generatorparam> I<nom>[=I<valeur>]
+
+Initialisation de la valeur d'un paramètre du générateur. Ce paramètre doit être une paire I<nom>=I<valeur> ou simplement un I<nom>.
+Exemple: "target=thisdirectory" défini le paramètre 'target'
+avec la valeur "thisdirectory".
+
+=item B<--generatorparams>
+
+Affiche la liste des paramètres supportés par le générateur.
+
+=item B<--genlist>
+
+Affiche la liste des générateurs supportés.
+
+=item B<-?>
+
+=item B<-h>
+
+Affiche la liste des options de bib2html.
+
+=item B<--help>
+
+Voir B<--man>.
+
+=item B<--jabref>
+
+Le générateur traduira les groupes de JabRef
+en domaines Bib2HTML.
+
+=item B<--lang> I<nom>
+
+Initialisation de la langue à utiliser.
+
+=item B<--langlist>
+
+Affiche la liste des langues supportées.
+
+=item B<--man>
+
+=item B<--manual>
+
+Affiche la page de manual.
+
+=item B<-o> F<fichier>
+
+=item B<--output> F<fichier>
+
+Initialise le répertoire où la documentation générée sera déposées.
+
+=item B<-p> F<fichier>
+
+=item B<--preamble> F<fichier>
+
+Initialise le nom du F<fichier> à lire et contenant des préambules TeX.
+Vous pouvez utiliser cette option pour définir des commandes LaTeX
+que ne supporte pas encore bib2html.
+
+=item B<--protect> F<shell_wildcard>
+
+Si spécifiée, cette option interdit la suppression dans le répertoire
+destination des sous-fichiers correspondant à l'expression shell
+spécifiée.
+
+=item B<-q>
+
+Mode non verbeux: seuls les messages d'erreurs sont affichés.
+
+=item B<--[no]sortw>
+
+Tri (ou non) les avertissement par ordre croissant des lignes où
+ils apparaissent.
+
+=item B<--stdout>
+
+Force la sortie des fichiers générés sur la sortie standard.
+Cette option est équivalente à C<-d stdout>.
+
+=item B<--svn>
+
+Si spécifiée, cette option interdit la suppression des sous-fichiers
+'.svn' et 'svn' dans le répertoire destination.
+
+=item B<--texcmd>
+
+Affiche la liste des commandes TeX supportées.
+
+=item B<--theme> I<name>
+
+Initialise le thème devant être utilisé par le générateur.
+
+=item B<--themelist>
+
+Affiche la liste des thèmes disponibles.
+
+=item B<-v>
+
+Augmente la verbosité de bib2html.
+
+=item B<--version>
+
+Affiche la version de ce script.
+
+=item B<--[no]warning>
+
+Si faux, les avertissements sont convertis en erreurs.
+
+=item B<--windowtitle> I<text>
+
+Initialise le titre des pages HTML devant apparaître dans
+la barre de titre des fenêtres du navigateur.
+
+=back
+
+=head1 LICENCE
+
+S<GNU Public License (GPL)>
+
+=head1 COPYRIGHT
+
+S<Copyright (c) 1998-06 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+S<Copyright (c) 2011 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+
+=head1 CONTRIBUTEURS
+
+=over
+
+=item S<Aurel GABRIS E<lt>L<gabrisa@optics.szfki.kfki.hu>E<gt>>
+
+=item S<Gasper JAKLIC E<lt>L<gasper.jaklic@fmf.uni-lj.si>E<gt>>
+
+=item S<Tobias LOEW E<lt>L<loew@mathematik.tu-darmstadt.de>E<gt>>
+
+=item S<Joao LOURENCO E<lt>L<joao.lourenco@di.fct.unl.pt>E<gt>>
+
+=item S<Dimitris MICHAIL E<lt>L<michail@mpi-sb.mpg.de>E<gt>>
+
+=item S<Luca PAOLINI E<lt>L<paolini@di.unito.it>E<gt>>
+
+=item S<Norbert PREINING E<lt>L<preining@logic.at>E<gt>>
+
+=item S<Cristian RIGAMONTI E<lt>L<cri@linux.it>E<gt>>
+
+=item S<Sebastian RODRIGUEZ E<lt>L<sebastian.rodriguez@utbm.fr>E<gt>>
+
+=item S<Martin P.J. ZINSER E<lt>L<zinser@zinser.no-ip.info>E<gt>>
+
+=item S<Olivier HUGHES E<lt>L<olivier.hugues@gmail.com>E<gt>>
+
+=back
+
+=head1 SEE ALSO
+
+L<bib2html>, L<latex>, L<bibtex>
diff --git a/biblio/bibtex/utils/bib2ml/man/bib2xml_en.pod b/biblio/bibtex/utils/bib2ml/man/bib2xml_en.pod
new file mode 100644
index 0000000000..a7b82bf6aa
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/man/bib2xml_en.pod
@@ -0,0 +1,214 @@
+=head1 NAME
+
+bib2xml - A perl script that generates an XML file for a BibTeX database
+
+
+=head1 SYNOPSYS
+
+bib2xml [options] F<file> [F<file> ...]
+
+=head1 DESCRIPTION
+
+bib2xml is a script which permits to generate a XML file for
+the entries of BibTeX files.
+
+The generated XML file is compliant with the DTD from http://bibtexml.sf.net
+
+The bib2xml command is equivalent to:
+bib2html [options] F<file> [F<file> ...] -g XML
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-[no]b>
+
+=item B<--[no]bibtex>
+
+This option permits to generate, or not, a verbatim of the
+BibTeX entry code.
+
+=item B<--[no]checknames>
+
+This option permits to check if the some author's names are
+similar and generates a set of warnings about each of them.
+
+=item B<--cvs>
+
+If specified, this option disables the deletion of the subfiles
+'.cvs', 'CVS' and 'CVSROOT' in the output directory.
+
+=item B<-d> I<name>[=I<value>]
+
+See B<--generatorparam>.
+
+=item B<--doctitle> I<text>
+
+Sets the title that appears in the main page.
+
+=item B<-f>
+
+=item B<--force>
+
+Forces to overwrite into the output directory.
+
+=item B<-g> I<class>
+
+=item B<--generator> I<class>
+
+Sets the generator to use. I<class> must be a valid Perl class.
+
+=item B<--generatorparam> I<name>[=I<value>]
+
+Sets a generator param. It must be a I<key>=I<value> pair or
+simply a I<name>.
+Example: "target=thisdirectory" defines the parameter target
+with corresponding value "thisdirectory". The specified
+parameters which are not supported by the generator are
+ignored.
+
+=item B<--generatorparams>
+
+Shows the list of supported parameters, and their
+semantics for the current generator.
+
+=item B<--genlist>
+
+Shows the list of supported generators.
+
+=item B<-?>
+
+=item B<-h>
+
+Show the list of available options.
+
+=item B<--help>
+
+See B<--man>.
+
+=item B<--jabref>
+
+The generator will translate JabRef's groups
+into Bib2HTML's domains.
+
+=item B<--lang> I<name>
+
+Sets the language used by the generator.
+
+=item B<--langlist>
+
+Shows the list of supported language.
+
+=item B<--man>
+
+=item B<--manual>
+
+Show the manual page.
+
+=item B<-o> F<file>
+
+=item B<--output> F<file>
+
+Sets the directory or the F<file> in which the documentation will be put.
+
+=item B<-p> F<file>
+
+=item B<--preamble> F<file>
+
+Sets the name of the F<file> to read to include some TeX preambles.
+You could use this option to dynamicaly defined some unsupported
+LaTeX commands.
+
+=item B<--protect> F<shell_wildcard>
+
+If specified, this option disables the deletion in the target
+directory of the subfiles that match the specified shell
+expression.
+
+=item B<-q>
+
+Don't be verbose: only error messages are displayed.
+
+=item B<--[no]sortw>
+
+Shows (or not) a sorted list of warnings.
+
+=item B<--stdout>
+
+Force the output of the generated files onto the standard output.
+This option is equivalent to C<-d stdout>.
+
+=item B<--svn>
+
+If specified, this option disables the deletion of the subfiles
+'.svn' and 'svn' in the output directory.
+
+=item B<--texcmd>
+
+Shows the list of supported LaTeX commands.
+
+=item B<--theme> I<name>
+
+Sets the theme used by the generator.
+
+=item B<--themelist>
+
+Shows the list of supported themes.
+
+=item B<-v>
+
+Be more verbose.
+
+=item B<--version>
+
+Show the version of this script.
+
+=item B<--[no]warning>
+
+If false, the warning are converted to errors.
+
+=item B<--windowtitle> I<text>
+
+Sets the title that appears as the window's title.
+
+=back
+
+=head1 LICENSE
+
+S<GNU Public License (GPL)>
+
+=head1 COPYRIGHT
+
+S<Copyright (c) 1998-06 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+
+=head1 CONTRIBUTORS
+
+=over
+
+=item S<Aurel GABRIS E<lt>L<gabrisa@optics.szfki.kfki.hu>E<gt>>
+
+=item S<Gasper JAKLIC E<lt>L<gasper.jaklic@fmf.uni-lj.si>E<gt>>
+
+=item S<Tobias LOEW E<lt>L<loew@mathematik.tu-darmstadt.de>E<gt>>
+
+=item S<Joao LOURENCO E<lt>L<joao.lourenco@di.fct.unl.pt>E<gt>>
+
+=item S<Dimitris MICHAIL E<lt>L<michail@mpi-sb.mpg.de>E<gt>>
+
+=item S<Luca PAOLINI E<lt>L<paolini@di.unito.it>E<gt>>
+
+=item S<Norbert PREINING E<lt>L<preining@logic.at>E<gt>>
+
+=item S<Cristian RIGAMONTI E<lt>L<cri@linux.it>E<gt>>
+
+=item S<Sebastian RODRIGUEZ E<lt>L<sebastian.rodriguez@utbm.fr>E<gt>>
+
+=item S<Martin P.J. ZINSER E<lt>L<zinser@zinser.no-ip.info>E<gt>>
+
+=item S<Olivier HUGHES E<lt>L<olivier.hugues@gmail.com>E<gt>>
+
+=back
+
+=head1 SEE ALSO
+
+L<bib2html>, L<latex>, L<bibtex>
diff --git a/biblio/bibtex/utils/bib2ml/man/bib2xml_fr.pod b/biblio/bibtex/utils/bib2ml/man/bib2xml_fr.pod
new file mode 100644
index 0000000000..afbfa31fbd
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/man/bib2xml_fr.pod
@@ -0,0 +1,211 @@
+=head1 NOM
+
+bib2xml - Script Perl générant des fichiers XML à partir de fichiers BibTeX
+
+=head1 SYNOPSIS
+
+bib2xml [options] F<fichier> [F<fichier> ...]
+
+=head1 DESCRIPTION
+
+bib2xml est un script permettant de generer des fichiers XML structurant et décrivant le contenu d'une base bibliographique écrite dans le format BibTeX.
+
+Le fichier XML généré est conforme à la DTD de http://bibtexml.sf.net
+
+Cette commande est équivalente à:
+bib2html [options] F<fichier> [F<fichier> ...] -g XML
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-[no]b>
+
+=item B<--[no]bibtex>
+
+Génération (ou non) du code BibTeX dans les pages HTML.
+
+=item B<--[no]checknames>
+
+Vérification de la cohérence des noms des auteurs. Un avertissement sera
+exprimée chaque fois que bib2html détectera des noms dupliqués ou des
+fautes de frappe.
+
+=item B<--cvs>
+
+Si spécifiée, cette option interdit la suppression des sous-fichiers
+'.cvs', 'CVS' et 'CVSROOT' dans le répertoire destination.
+
+=item B<-d> I<nom>[=I<valeur>]
+
+Voir B<--generatorparam>.
+
+=item B<--doctitle> I<texte>
+
+Initialisation du titre de la page principale.
+
+=item B<-f>
+
+=item B<--force>
+
+Force l'écriture des pages HTML dans le répertoire destination.
+
+=item B<-g> I<classe>
+
+=item B<--generator> I<classe>
+
+Spécification du générateur à utiliser. I<class> doit être une classe Perl
+valide.
+
+=item B<--generatorparam> I<nom>[=I<valeur>]
+
+Initialisation de la valeur d'un paramètre du générateur. Ce paramètre doit être une paire I<nom>=I<valeur> ou simplement un I<nom>.
+Exemple: "target=thisdirectory" défini le paramètre 'target'
+avec la valeur "thisdirectory".
+
+=item B<--generatorparams>
+
+Affiche la liste des paramètres supportés par le générateur.
+
+=item B<--genlist>
+
+Affiche la liste des générateurs supportés.
+
+=item B<-?>
+
+=item B<-h>
+
+Affiche la liste des options de bib2html.
+
+=item B<--help>
+
+Voir B<--man>.
+
+=item B<--jabref>
+
+Le générateur traduira les groupes de JabRef
+en domaines Bib2HTML.
+
+=item B<--lang> I<nom>
+
+Initialisation de la langue à utiliser.
+
+=item B<--langlist>
+
+Affiche la liste des langues supportées.
+
+=item B<--man>
+
+=item B<--manual>
+
+Affiche la page de manual.
+
+=item B<-o> F<fichier>
+
+=item B<--output> F<fichier>
+
+Initialise le répertoire où la documentation générée sera déposées.
+
+=item B<-p> F<fichier>
+
+=item B<--preamble> F<fichier>
+
+Initialise le nom du F<fichier> à lire et contenant des préambules TeX.
+Vous pouvez utiliser cette option pour définir des commandes LaTeX
+que ne supporte pas encore bib2html.
+
+=item B<--protect> F<shell_wildcard>
+
+Si spécifiée, cette option interdit la suppression dans le répertoire
+destination des sous-fichiers correspondant à l'expression shell
+spécifiée.
+
+=item B<-q>
+
+Mode non verbeux: seuls les messages d'erreurs sont affichés.
+
+=item B<--[no]sortw>
+
+Tri (ou non) les avertissement par ordre croissant des lignes où
+ils apparaissent.
+
+=item B<--stdout>
+
+Force la sortie des fichiers générés sur la sortie standard.
+Cette option est équivalente à C<-d stdout>.
+
+=item B<--svn>
+
+Si spécifiée, cette option interdit la suppression des sous-fichiers
+'.svn' et 'svn' dans le répertoire destination.
+
+=item B<--texcmd>
+
+Affiche la liste des commandes TeX supportées.
+
+=item B<--theme> I<name>
+
+Initialise le thème devant être utilisé par le générateur.
+
+=item B<--themelist>
+
+Affiche la liste des thèmes disponibles.
+
+=item B<-v>
+
+Augmente la verbosité de bib2html.
+
+=item B<--version>
+
+Affiche la version de ce script.
+
+=item B<--[no]warning>
+
+Si faux, les avertissements sont convertis en erreurs.
+
+=item B<--windowtitle> I<text>
+
+Initialise le titre des pages HTML devant apparaître dans
+la barre de titre des fenêtres du navigateur.
+
+=back
+
+=head1 LICENCE
+
+S<GNU Public License (GPL)>
+
+=head1 COPYRIGHT
+
+S<Copyright (c) 1998-06 Stéphane Galland E<lt>galland@arakhne.orgE<gt>>
+
+=head1 CONTRIBUTEURS
+
+=over
+
+=item S<Aurel GABRIS E<lt>L<gabrisa@optics.szfki.kfki.hu>E<gt>>
+
+=item S<Gasper JAKLIC E<lt>L<gasper.jaklic@fmf.uni-lj.si>E<gt>>
+
+=item S<Tobias LOEW E<lt>L<loew@mathematik.tu-darmstadt.de>E<gt>>
+
+=item S<Joao LOURENCO E<lt>L<joao.lourenco@di.fct.unl.pt>E<gt>>
+
+=item S<Dimitris MICHAIL E<lt>L<michail@mpi-sb.mpg.de>E<gt>>
+
+=item S<Luca PAOLINI E<lt>L<paolini@di.unito.it>E<gt>>
+
+=item S<Norbert PREINING E<lt>L<preining@logic.at>E<gt>>
+
+=item S<Cristian RIGAMONTI E<lt>L<cri@linux.it>E<gt>>
+
+=item S<Sebastian RODRIGUEZ E<lt>L<sebastian.rodriguez@utbm.fr>E<gt>>
+
+=item S<Martin P.J. ZINSER E<lt>L<zinser@zinser.no-ip.info>E<gt>>
+
+=item S<Olivier HUGHES E<lt>L<olivier.hugues@gmail.com>E<gt>>
+
+=back
+
+=head1 SEE ALSO
+
+L<bib2html>, L<latex>, L<bibtex>
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Checker/Names.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Checker/Names.pm
new file mode 100644
index 0000000000..2c006cc65f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Checker/Names.pm
@@ -0,0 +1,251 @@
+# Copyright (C) 2004-07 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Checker::Names - A checker for BibTeX names.
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Checker::Names ;
+
+my $gen = Bib2HTML::Checker::Names->new() ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Checker::Names is a Perl module, which checks
+if author's names are similar or not.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To create a parser, say something like this:
+
+ use Bib2HTML::Checker::Names;
+
+ my $parser = Bib2HTML::Checker::Names->new() ;
+
+...or something similar.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Names.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Checker::Names;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use Bib2HTML::Translator::BibTeXName ;
+use Bib2HTML::General::Error ;
+use Bib2HTML::General::Misc ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the checker
+my $VERSION = "0.1" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ }
+ else {
+ $self = {} ;
+ }
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Checking
+#
+#------------------------------------------------------
+
+=pod
+
+=item * check()
+
+Check the names.
+Takes 1 arg:
+
+=over
+
+=item * database (hash ref)
+
+is the entire data structure toi check.
+
+=back
+
+=cut
+sub check(\%) : method {
+ my $self = shift ;
+ if ($_[0]) {
+ my %authors = $self->get_all_authors($_[0]->{'entries'}) ;
+ my @ids = sortbyletters(keys %authors) ;
+
+ for(my $i=0; $i<$#ids; $i++) {
+ my $name1 = lc($authors{$ids[$i]}{'last'}) ;
+ for(my $j=$i+1; $j<=$#ids; $j++) {
+ my $name2 = lc($authors{$ids[$j]}{'last'}) ;
+
+ my $error_msg = join('',
+ " name1=".$authors{$ids[$i]}{'last'},
+ ",",
+ $authors{$ids[$i]}{'first'},
+ " (",
+ $authors{$ids[$i]}{'location'},
+ ")\n name2=",
+ $authors{$ids[$j]}{'last'},
+ ",",
+ $authors{$ids[$j]}{'first'},
+ " (",
+ $authors{$ids[$j]}{'location'},
+ ")") ;
+
+ # Check for the same name defined many times
+ if ($name1 eq $name2) {
+ Bib2HTML::General::Error::syswarm("multiple author's name syntax for '$name1':\n".
+ $error_msg) ;
+ }
+
+ # Check for the same name defined many times but with keyboard's mistaskes
+ elsif ($self->is_similar($name1, $name2)) {
+ Bib2HTML::General::Error::syswarm("possible author's name mistake?\n".
+ $error_msg) ;
+ }
+
+ }
+ }
+ }
+}
+
+=item * is_similar()
+
+Replies if the 2 names have similar syntax
+Takes 2 args:
+
+=over
+
+=item * name1 (string)
+
+=item * name2 (string)
+
+=back
+
+=cut
+sub is_similar($$) : method {
+ my $self = shift ;
+ my $percent = levenshtein($_[0],$_[1]) ;
+ return ($percent>=90) ;
+}
+
+=item * get_all_authors()
+
+Replies an array of entry authors.
+Takes 1 arg:
+
+=over
+
+=item * data (hash ref)
+
+=back
+
+=cut
+sub get_all_authors($) : method {
+ my $self = shift ;
+ my %authors = () ;
+ my $parser = Bib2HTML::Translator::BibTeXName->new() ;
+ foreach my $entry (sortbyletters(keys %{$_[0]})) {
+ if ( $_[0]->{$entry}{'fields'}{'author'} ) {
+ my @auts = $parser->splitnames($_[0]->{$entry}{'fields'}{'author'}) ;
+ foreach my $aut (@auts) {
+ if ( ! $aut->{'et al'} ) {
+ $aut->{'location'} = $_[0]->{$entry}{'location'} ;
+ my $key = lc($parser->formatname( $aut, 'l f.' )) ;
+ $key =~ s/[^a-zA-Z0-1]+//g ;
+ my $count = 0 ;
+ my $thekey = $key ;
+ while ( ( $count >= 0 ) && ( exists $authors{$thekey} ) ) {
+ if ( $parser->samenames($aut,$authors{$thekey}) ) {
+ $count = -1 ;
+ }
+ else {
+ $count ++ ;
+ $thekey = "${key}_${count}" ;
+ }
+ }
+ if ( $count >= 0 ) {
+ $authors{$thekey} = $aut ;
+ }
+ }
+ }
+ }
+ }
+ return %authors ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 2004-07 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Encode.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Encode.pm
new file mode 100644
index 0000000000..5f7065b6bf
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Encode.pm
@@ -0,0 +1,138 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::General::Encode - String encoding functions
+
+=head1 DESCRIPTION
+
+Bib2HTML::General::Encode is a Perl module, which proposes
+a set of functions for string encoding.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Encode.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::General::Encode;
+
+@ISA = ('Exporter');
+@EXPORT = qw( &set_default_encoding &get_default_encoding &get_encoded_str );
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+
+use Encode;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the encode functions
+my $VERSION = "1.0" ;
+
+# Default encoding
+my $DEFAULT_ENCODING = "utf-8";
+
+#------------------------------------------------------
+#
+# Functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * set_default_encoding($)
+
+Set the default encoding
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+is a I<string> which correspond to the name of the encoding.
+
+=back
+
+=cut
+sub set_default_encoding($) {
+ $DEFAULT_ENCODING = $_[0];
+}
+
+=pod
+
+=item * get_default_encoding()
+
+Replies the default encoding.
+
+=cut
+sub get_default_encoding() {
+ return $DEFAULT_ENCODING;
+}
+
+=pod
+
+=item * get_encode_str($)
+
+Replies the specified string in the current string encoding.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub get_encoded_str($) {
+ return encode($DEFAULT_ENCODING, $_[0]);
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Error.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Error.pm
new file mode 100644
index 0000000000..2bd8aaced3
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Error.pm
@@ -0,0 +1,443 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::General::Error - Error functions
+
+=head1 DESCRIPTION
+
+Bib2HTML::General::Error is a Perl module, which proposes
+a set of functions to manage the errors.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Error.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::General::Error;
+
+@ISA = ('Exporter');
+@EXPORT = qw( &warm &err &warningcount
+ &syserr &syswarm &printwarningcount
+ &unsetwarningaserror
+ &setwarningaserror
+ &unsetsortwarnings
+ &setsortwarnings
+ &notempty );
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+
+use Carp ;
+
+use Bib2HTML::General::Verbose ;
+use Bib2HTML::General::Misc ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the error functions
+my $VERSION = "1.0" ;
+
+# The quantity of warning encounted during the generation
+my $WARNING_COUNT = 0 ;
+
+# Indicates that the warnings are considered as errors
+my $WARNING_HAS_ERROR = 0 ;
+
+# Indicates if the warnings must be sorted
+my $SORT_WARNINGS = 0 ;
+
+# List of generated warning messages
+my %__GENERATED_WARNINGS = () ;
+
+#------------------------------------------------------
+#
+# Warning getters/setters
+#
+#------------------------------------------------------
+
+=pod
+
+=item * warningcount()
+
+Replies the quantity of warnings.
+
+=cut
+sub warningcount() {
+ return $WARNING_COUNT ;
+}
+
+=pod
+
+=item * setwarningaserror()
+
+Sets that the warnings will be considered as errors.
+
+=cut
+sub setwarningaserror() {
+ $WARNING_HAS_ERROR = 1 ;
+}
+
+=pod
+
+=item * unsetwarningaserror()
+
+Sets that the warnings will not be considered as errors.
+
+=cut
+sub unsetwarningaserror() {
+ $WARNING_HAS_ERROR = 0 ;
+}
+
+=pod
+
+=item * setsortwarnings()
+
+Sets the sorting flag of warnings
+
+=cut
+sub setsortwarnings() {
+ $SORT_WARNINGS = 1 ;
+}
+
+=pod
+
+=item * unsetsortwarnings()
+
+Unsets the sorting flag of warnings
+
+=cut
+sub unsetsortwarnings() {
+ $SORT_WARNINGS = 0 ;
+}
+
+#------------------------------------------------------
+#
+# Error reporting
+#
+#------------------------------------------------------
+
+=pod
+
+=item * syserr()
+
+Displays an error and stop.
+Takes 1 arg:
+
+=over
+
+=item * message (string)
+
+is the error message to display.
+
+=back
+
+=cut
+sub syserr($) {
+ my $msg = $_[0] || '' ;
+ $msg =~ s/\n+$// ;
+ printwarningcount() ;
+ die( "Error: $msg\n" ) ;
+}
+
+=pod
+
+=item * syswarm()
+
+Displays a warning and stop.
+Takes 1 arg:
+
+=over
+
+=item * message (string)
+
+is the warning message to display.
+
+=back
+
+=cut
+sub syswarm($) {
+ my $msg = $_[0] || '' ;
+ $msg =~ s/^[ \t\r\n]+// ;
+ $msg =~ s/[ \t\r\n]+$// ;
+ if ( ! $WARNING_HAS_ERROR ) {
+
+ if ( __is_not_logged_warning( $msg, '', 0 ) ) {
+
+ __log_warning( $msg, '', 0 ) ;
+
+ $WARNING_COUNT ++ ;
+ if ( ( ! $SORT_WARNINGS ) &&
+ ( Bib2HTML::General::Verbose::currentlevel() >= 0 ) ) {
+ print STDERR "Warning: $msg\n" ;
+ }
+
+ }
+ }
+ else {
+ syserr( $msg ) ;
+ }
+}
+
+# Replies if the specified message was already generated
+# __is_not_logged_warning( text, file, lineno )
+sub __is_not_logged_warning($$$) {
+ return 0 unless $_[0] ;
+ if ( ! exists $__GENERATED_WARNINGS{$_[0]} ) {
+ return 1 ;
+ }
+ my $location = ( $_[1] || '' ).':'.( ( $_[1] && $_[2] ) || '' ) ;
+ if ( $location eq ':' ) {
+ return ( int(@{$__GENERATED_WARNINGS{$_[0]}}) > 0 ) ;
+ }
+ else {
+ return ( ! strinarray( $location, $__GENERATED_WARNINGS{$_[0]} ) ) ;
+ }
+}
+
+# Log the specified message
+# __log_warning( text, file, lineno )
+sub __log_warning($$$) {
+ return 0 unless $_[0] ;
+ if ( ! exists $__GENERATED_WARNINGS{$_[0]} ) {
+ $__GENERATED_WARNINGS{$_[0]} = [] ;
+ }
+ my $location = ( $_[1] || '' ).':'.( ( $_[1] && $_[2] ) || '' ) ;
+ if ( ( $location ne ':' ) &&
+ ( ! strinarray( $location, $__GENERATED_WARNINGS{$_[0]} ) ) ) {
+ push @{$__GENERATED_WARNINGS{$_[0]}}, $location ;
+ }
+ return 0 ;
+}
+
+=pod
+
+=item * printwarningcount()
+
+Displays the count of warnings.
+
+=cut
+sub printwarningcount() {
+ if ( ( Bib2HTML::General::Verbose::currentlevel() >= 0 ) &&
+ ( $WARNING_COUNT > 0 ) ) {
+
+ # Display the warnings
+ if ( $SORT_WARNINGS ) {
+ my @msgs = () ;
+
+ while ( my ($key, $value) = each( %__GENERATED_WARNINGS ) ) {
+
+ if ( int(@{$value}) > 0 ) {
+
+ foreach my $location ( @{$value} ) {
+ my $file = extract_file_from_location( $location ) ;
+ my $lineno = extract_line_from_location( $location ) ;
+ push @msgs, { 'msg' => $key,
+ 'file' => $file,
+ 'line' => $lineno,
+ } ;
+ }
+ }
+ else {
+
+ push @msgs, { 'msg' => $key,
+ 'file' => '',
+ 'line' => 0,
+ } ;
+
+ }
+
+ }
+
+ @msgs = sort {
+ return -1 if ( $a->{'file'} lt $b->{'file'} ) ;
+ return 1 if ( $a->{'file'} gt $b->{'file'} ) ;
+ return -1 if ( $a->{'line'} < $b->{'line'} ) ;
+ return 1 if ( $a->{'line'} > $b->{'line'} ) ;
+ return ( $a->{'msg'} <=> $b->{'msg'} ) ;
+ } @msgs ;
+
+ foreach my $value ( @msgs ) {
+ my $msg = $value->{'msg'} || '???' ;
+ my $file = $value->{'file'} || '' ;
+ my $line = $value->{'line'} || 0 ;
+ print STDERR "Warning".
+ (($file)?
+ (" ($file".(($line>0)?
+ ":$line":"").")"): "").
+ ": $msg\n" ;
+ }
+
+ }
+
+ print STDERR "$WARNING_COUNT warning".(($WARNING_COUNT>1)?"s":"")."\n" ;
+ }
+}
+
+=pod
+
+=item * err()
+
+Displays an error and stop.
+Takes 3 args:
+
+=over
+
+=item * message (string)
+
+is the error message to display.
+
+=item * file (string)
+
+is the name of the file in which the error occurs.
+
+=item * line (integer)
+
+is the line where the error occurs.
+
+=back
+
+=cut
+sub err($$$) {
+ my $msg = $_[0] || '' ;
+ my $file = $_[1] || '' ;
+ my $line = $_[2] || 0 ;
+ printwarningcount() ;
+ $msg =~ s/\n+$// ;
+ die( "Error".
+ (($file)?
+ (" ($file".(($line>0)?
+ ":$line":"").")"): "").
+ ": $msg\n" ) ;
+}
+
+=pod
+
+=item * warm()
+
+Displays a warning.
+Takes 3 args:
+
+=over
+
+=item * message (string)
+
+is the warning message to display.
+
+=item * file (string)
+
+<is the name of the file in which the warning occurs.
+
+=item * line (integer)
+
+is the line where the warning occurs.
+
+=back
+
+=cut
+sub warm($$$) {
+ my $msg = $_[0] || '' ;
+ my $file = $_[1] || '' ;
+ my $line = $_[2] || 0 ;
+ if ( ! $WARNING_HAS_ERROR ) {
+ $msg =~ s/\n+$// ;
+ if ( __is_not_logged_warning( $msg, $file, $line ) ) {
+
+ __log_warning( $msg, $file, $line ) ;
+
+ $WARNING_COUNT ++ ;
+ if ( ( ! $SORT_WARNINGS ) &&
+ ( Bib2HTML::General::Verbose::currentlevel() >= 0 ) ) {
+ print STDERR "Warning".
+ (($file)?
+ (" ($file".(($line>0)?
+ ":$line":"").")"): "").
+ ": $msg\n" ;
+ }
+ }
+ }
+ else {
+ err( $msg, $file, $line ) ;
+ }
+}
+
+
+=pod
+
+=item * notempty()
+
+Replies the specified value if it was not empty.
+Otherwhise, generate a exception.
+
+Takes 2 args:
+
+=over
+
+=item * value (mixed)
+
+is the value to check
+
+=item * msg (string)
+
+is the error message
+
+=back
+
+=cut
+sub notempty {
+ confess( 'invalid use of function notempty()' )
+ unless ( $_[1] ) ;
+ if ( ( ! defined( $_[0] ) ) ||
+ ( length( "$_[0]" ) <= 0 ) ) {
+ confess( $_[1] ) ;
+ }
+ return $_[0] ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/HTML.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/HTML.pm
new file mode 100644
index 0000000000..50c1dbc03f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/HTML.pm
@@ -0,0 +1,1539 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::General::HTML - HTML support definitions
+
+=head1 DESCRIPTION
+
+Bib2HTML::General::HTML is a Perl module, which permits to support
+some HTML definitions. This is a fork of PhpDocGen::General::HTML.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in HTML.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::General::HTML;
+
+@ISA = ('Exporter');
+@EXPORT = qw(&get_html_entities &get_restricted_html_entities &translate_html_entities
+ &htmlcatdir &htmlcatfile &htmldirname &htmlfilename &htmltoroot &htmlpath
+ &htmlsplit &strip_html_tags &html_add_unsecable_spaces &html_uc &html_lc
+ &html_sc &split_html_tags &html_extract_tag_params &htmltolocalpath
+ &nl2br &br2nl &setAsValidHTML_small &setAsValidHTML &html_getinitiales
+ &html_ucwords &html_ucfirst &html_substr &html_split_to_chars &sortbyletters
+ &remove_html_accents );
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::Encode ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the HTML support functions
+my $VERSION = "4.0" ;
+
+# Translation table
+my %HTML_ENTITY_CODES = ( 'nbsp' => 160, #no-break space = non-breaking space
+ 'iexcl' => 161, #inverted exclamation mark, U+00A1 ISOnum
+ 'cent' => 162, #cent sign
+ 'pound' => 163, #pound sign
+ 'curren' => 164, #currency sign
+ 'yen' => 165, #yen sign = yuan sign
+ 'brvbar' => 166, #broken bar = broken vertical bar
+ 'sect' => 167, #section sign
+ 'uml' => 168, #diaeresis = spacing diaeresis,
+ 'copy' => 169, #copyright sign
+ 'ordf' => 170, #feminine ordinal indicator
+ 'laquo' => 171, #left-pointing double angle quotation mark
+ 'not' => 172, #not sign
+ 'shy' => 173, #soft hyphen = discretionary hyphen
+ 'reg' => 174, #registered sign = registered trade mark sign
+ 'macr' => 175, #macron = spacing macron = overline = APL overbar
+ 'deg' => 176, #degree sign
+ 'plusmn' => 177, #plus-minus sign = plus-or-minus sign
+ 'sup2' => 178, #superscript two = superscript digit two = squared
+ 'sup3' => 179, #superscript three = superscript digit three = cubed
+ 'acute' => 180, #acute accent = spacing acute
+ 'micro' => 181, #micro sign
+ 'para' => 182, #pilcrow sign = paragraph sign
+ 'middot' => 183, #middle dot = Georgian comma = Greek middle dot
+ 'cedil' => 184, #cedilla = spacing cedilla
+ 'sup1' => 185, #superscript one = superscript digit one
+ 'ordm' => 186, #masculine ordinal indicator
+ 'raquo' => 187, #right-pointing double angle quotation mark = right pointing guillemet
+ 'frac14' => 188, #vulgar fraction one quarter = fraction one quarter
+ 'frac12' => 189, #vulgar fraction one half = fraction one half
+ 'frac34' => 190, #vulgar fraction three quarters = fraction three quarters
+ 'iquest' => 191, #inverted question mark = turned question mark
+ 'Agrave' => 192, #latin capital letter A with grave = latin capital letter A grave
+ 'Aacute' => 193, #latin capital letter A with acute
+ 'Acirc' => 194, #latin capital letter A with circumflex
+ 'Atilde' => 195, #latin capital letter A with tilde
+ 'Auml' => 196, #latin capital letter A with diaeresis
+ 'Aring' => 197, #latin capital letter A with ring above = latin capital letter A ring
+ 'AElig' => 198, #latin capital letter AE = latin capital ligature AE
+ 'Ccedil' => 199, #latin capital letter C with cedilla
+ 'Egrave' => 200, #latin capital letter E with grave
+ 'Eacute' => 201, #latin capital letter E with acute
+ 'Ecirc' => 202, #latin capital letter E with circumflex
+ 'Euml' => 203, #latin capital letter E with diaeresis
+ 'Igrave' => 204, #latin capital letter I with grave
+ 'Iacute' => 205, #latin capital letter I with acute
+ 'Icirc' => 206, #latin capital letter I with circumflex
+ 'Iuml' => 207, #latin capital letter I with diaeresis
+ 'ETH' => 208, #latin capital letter ETH
+ 'Ntilde' => 209, #latin capital letter N with tilde
+ 'Ograve' => 210, #latin capital letter O with grave
+ 'Oacute' => 211, #latin capital letter O with acute
+ 'Ocirc' => 212, #latin capital letter O with circumflex
+ 'Otilde' => 213, #latin capital letter O with tilde
+ 'Ouml' => 214, #latin capital letter O with diaeresis
+ 'times' => 215, #multiplication sign
+ 'Oslash' => 216, #latin capital letter O with stroke = latin capital letter O slash
+ 'Ugrave' => 217, #latin capital letter U with grave
+ 'Uacute' => 218, #latin capital letter U with acute
+ 'Ucirc' => 219, #latin capital letter U with circumflex
+ 'Uuml' => 220, #latin capital letter U with diaeresis
+ 'Yacute' => 221, #latin capital letter Y with acute
+ 'THORN' => 222, #latin capital letter THORN
+ 'szlig' => 223, #latin small letter sharp s = ess-zed
+ 'agrave' => 224, #latin small letter a with grave = latin small letter a grave
+ 'aacute' => 225, #latin small letter a with acute
+ 'acirc' => 226, #latin small letter a with circumflex
+ 'atilde' => 227, #latin small letter a with tilde
+ 'auml' => 228, #latin small letter a with diaeresis
+ 'aring' => 229, #latin small letter a with ring above = latin small letter a ring
+ 'aelig' => 230, #latin small letter ae = latin small ligature ae
+ 'ccedil' => 231, #latin small letter c with cedilla
+ 'egrave' => 232, #latin small letter e with grave
+ 'eacute' => 233, #latin small letter e with acute
+ 'ecirc' => 234, #latin small letter e with circumflex
+ 'euml' => 235, #latin small letter e with diaeresis
+ 'igrave' => 236, #latin small letter i with grave
+ 'iacute' => 237, #latin small letter i with acute
+ 'icirc' => 238, #latin small letter i with circumflex
+ 'iuml' => 239, #latin small letter i with diaeresis
+ 'eth' => 240, #latin small letter eth
+ 'ntilde' => 241, #latin small letter n with tilde
+ 'ograve' => 242, #latin small letter o with grave
+ 'oacute' => 243, #latin small letter o with acute
+ 'ocirc' => 244, #latin small letter o with circumflex
+ 'otilde' => 245, #latin small letter o with tilde
+ 'ouml' => 246, #latin small letter o with diaeresis
+ 'divide' => 247, #division sign
+ 'oslash' => 248, #latin small letter o with stroke = latin small letter o slash
+ 'ugrave' => 249, #latin small letter u with grave
+ 'uacute' => 250, #latin small letter u with acute
+ 'ucirc' => 251, #latin small letter u with circumflex
+ 'uuml' => 252, #latin small letter u with diaeresis
+ 'yacute' => 253, #latin small letter y with acute
+ 'thorn' => 254, #latin small letter thorn
+ 'yuml' => 255, #latin small letter y with diaeresis
+ 'quot' => 34, #quotation mark = APL quote
+ 'amp' => 38, #ampersand
+ 'lt' => 60, #less-than sign
+ 'gt' => 62, #greater-than sign
+ 'OElig' => 338, #latin capital ligature OE
+ 'oelig' => 339, #latin small ligature oe
+ 'Scedil' => 'x015e', #latin capital letter S with cedil
+ 'scedil' => 'x015f', #latin small letter s with cedil
+ 'Tcedil' => 'x0162', #latin capital letter T with cedil
+ 'tcedil' => 'x0163', #latin small letter t with cedil
+ 'Yuml' => 376, #latin capital letter Y with diaeresis
+ 'circ' => 710, #modifier letter circumflex accent
+ 'tilde' => 732, #small tilde
+ 'Aucircle' => 'x0102', #latin capital letter A with small u on top
+ 'aucircle' => 'x0103', #latin small letter a with small u on top
+ 'Cacute' => 'x262', #latin capital letter C with acute
+ 'cacute' => 'x263', #latin small letter c with acute
+ 'Scaron' => 352, #latin capital letter S with caron
+ 'scaron' => 353, #latin small letter s with caron
+ 'Ccaron' => 268, #latin capital letter C with caron
+ 'ccaron' => 269, #latin small letter c with caron
+ 'Dcaron' => 270, #latin capital letter D with caron
+ 'dcaron' => 271, #latin small letter d with caron
+ 'Ecaron' => 282, #latin capital letter E with caron
+ 'ecaron' => 283, #latin small letter e with caron
+ 'Lcaron' => 317, #latin capital letter L with caron
+ 'lcaron' => 318, #latin small letter l with caron
+ 'Ncaron' => 327, #latin capital letter N with caron
+ 'ncaron' => 328, #latin small letter n with caron
+ 'Rcaron' => 344, #latin capital letter R with caron
+ 'rcaron' => 345, #latin small letter r with caron
+ 'Tcaron' => 356, #latin capital letter T with caron
+ 'tcaron' => 357, #latin small letter t with caron
+ 'Zcaron' => 381, #latin capital letter Z with caron
+ 'zcaron' => 382, #latin small letter z with caron
+ ) ;
+
+# The characters which are displayed for each HTML entity (except &amp; &gt; &lt; &quot; )
+my %HTML_ENTITY_CHARS = ( 'Ocirc' => 'Ô',
+ 'szlig' => 'ß',
+ 'micro' => 'µ',
+ 'para' => '¶',
+ 'not' => '¬',
+ 'sup1' => '¹',
+ 'oacute' => 'ó',
+ 'Uacute' => 'Ú',
+ 'middot' => '·',
+ 'ecirc' => 'ê',
+ 'pound' => '£',
+ 'scaron' => 'Å¡',
+ 'ntilde' => 'ñ',
+ 'igrave' => 'ì',
+ 'atilde' => 'ã',
+ 'thorn' => 'þ',
+ 'Euml' => 'Ë',
+ 'Ntilde' => 'Ñ',
+ 'Auml' => 'Ä',
+ 'plusmn' => '±',
+ 'raquo' => '»',
+ 'THORN' => 'Þ',
+ 'laquo' => '«',
+ 'Eacute' => 'É',
+ 'divide' => '÷',
+ 'Uuml' => 'Ü',
+ 'Aring' => 'Ã…',
+ 'ugrave' => 'ù',
+ 'Egrave' => 'È',
+ 'Acirc' => 'Â',
+ 'oslash' => 'ø',
+ 'ETH' => 'Ã',
+ 'iacute' => 'í',
+ 'Ograve' => 'Ã’',
+ 'Oslash' => 'Ø',
+ 'frac34' => '3/4',
+ 'Scaron' => 'Å ',
+ 'eth' => 'ð',
+ 'icirc' => 'î',
+ 'ordm' => 'º',
+ 'ucirc' => 'û',
+ 'reg' => '®',
+ 'tilde' => '~',
+ 'aacute' => 'á',
+ 'Agrave' => 'À',
+ 'Yuml' => 'Ÿ',
+ 'times' => '×',
+ 'deg' => '°',
+ 'AElig' => 'Æ',
+ 'Yacute' => 'Ã',
+ 'Otilde' => 'Õ',
+ 'circ' => '^',
+ 'sup3' => '³',
+ 'oelig' => 'Å“',
+ 'frac14' => '1/4',
+ 'Ouml' => 'Ö',
+ 'ograve' => 'ò',
+ 'copy' => '©',
+ 'shy' => '­',
+ 'iuml' => 'ï',
+ 'acirc' => 'â',
+ 'iexcl' => '¡',
+ 'Iacute' => 'Ã',
+ 'Oacute' => 'Ó',
+ 'ccedil' => 'ç',
+ 'frac12' => '1/2',
+ 'Icirc' => 'ÃŽ',
+ 'eacute' => 'é',
+ 'egrave' => 'è',
+ 'euml' => 'ë',
+ 'Ccedil' => 'Ç',
+ 'OElig' => 'Å’',
+ 'Atilde' => 'Ã',
+ 'ouml' => 'ö',
+ 'cent' => '¢',
+ 'Aacute' => 'Ã',
+ 'sect' => '§',
+ 'Ugrave' => 'Ù',
+ 'aelig' => 'æ',
+ 'ordf' => 'ª',
+ 'yacute' => 'ý',
+ 'Ecirc' => 'Ê',
+ 'auml' => 'ä',
+ 'macr' => '¯',
+ 'iquest' => '¿',
+ 'sup2' => '²',
+ 'Ucirc' => 'Û',
+ 'aring' => 'Ã¥',
+ 'Igrave' => 'Ì',
+ 'yen' => 'Â¥',
+ 'uuml' => 'ü',
+ 'otilde' => 'õ',
+ 'uacute' => 'ú',
+ 'yuml' => 'ÿ',
+ 'ocirc' => 'ô',
+ 'Iuml' => 'Ã',
+ 'agrave' => 'à',
+ ) ;
+
+
+# The mapping between the accentuated characters and the non-accentuated characters
+my %HTML_NO_ACCENT_ENTITY_CHARS = (
+ 'aacute' => 'a',
+ 'Aacute' => 'A',
+ 'aelig' => 'ae',
+ 'AElig' => 'ae',
+ 'acirc' => 'a',
+ 'Acirc' => 'A',
+ 'agrave' => 'a',
+ 'Agrave' => 'A',
+ 'atilde' => 'a',
+ 'Atilde' => 'A',
+ 'Aring' => 'A',
+ 'aring' => 'a',
+ 'aucircle' => 'a',
+ 'Aucircle' => 'A',
+ 'auml' => 'a',
+ 'Auml' => 'A',
+ 'Cacute' => 'C',
+ 'cacute' => 'c',
+ 'Ccaron' => 'C',
+ 'ccaron' => 'C',
+ 'ccedil' => 'c',
+ 'Ccedil' => 'C',
+ 'Dcaron' => 'D',
+ 'dcaron' => 'd',
+ 'Eacute' => 'E',
+ 'eacute' => 'e',
+ 'Ecaron' => 'E',
+ 'ecaron' => 'e',
+ 'ecirc' => 'e',
+ 'Ecirc' => 'E',
+ 'Egrave' => 'E',
+ 'egrave' => 'e',
+ 'eth' => 'd',
+ 'ETH' => 'D',
+ 'Euml' => 'E',
+ 'euml' => 'e',
+ 'Iacute' => 'i',
+ 'iacute' => 'i',
+ 'icirc' => 'i',
+ 'Icirc' => 'i',
+ 'Igrave' => 'I',
+ 'igrave' => 'i',
+ 'Iuml' => 'I',
+ 'iuml' => 'i',
+ 'Lcaron' => 'L',
+ 'lcaron' => 'l',
+ 'Ncaron' => 'N',
+ 'ncaron' => 'n',
+ 'ntilde' => 'n',
+ 'Ntilde' => 'N',
+ 'Oacute' => 'O',
+ 'oacute' => 'o',
+ 'ocirc' => 'o',
+ 'Ocirc' => 'O',
+ 'oelig' => 'oe',
+ 'OElig' => 'OE',
+ 'ograve' => 'o',
+ 'Ograve' => 'O',
+ 'Oslash' => 'O',
+ 'oslash' => 'o',
+ 'otilde' => 'o',
+ 'Otilde' => 'O',
+ 'Ouml' => 'O',
+ 'ouml' => 'o',
+ 'Rcaron' => 'R',
+ 'rcaron' => 'r',
+ 'scaron' => 's',
+ 'Scaron' => 'S',
+ 'scedil' => 's',
+ 'Scedil' => 'S',
+ 'szlig' => 'S',
+ 'Tcaron' => 'T',
+ 'tcaron' => 't',
+ 'tcedil' => 't',
+ 'Tcedil' => 'T',
+ 'thorn' => 't',
+ 'THORN' => 'T',
+ 'uacute' => 'u',
+ 'Uacute' => 'U',
+ 'Ucirc' => 'U',
+ 'ucirc' => 'u',
+ 'ugrave' => 'U',
+ 'Ugrave' => 'U',
+ 'uuml' => 'u',
+ 'Uuml' => 'U',
+ 'Yacute' => 'Y',
+ 'yacute' => 'y',
+ 'Yuml' => 'Y',
+ 'yuml' => 'y',
+ 'Zcaron' => 'Z',
+ 'zcaron' => 'z',
+ ) ;
+
+#------------------------------------------------------
+#
+# Predefined PHP variables support
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_restricted_html_entities()
+
+Replies the specified string in which some characters have been
+replaced by the corresponding HTML entities except for &amp;
+&quot; &lt; and &gt;
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub get_restricted_html_entities($) {
+ my $text = $_[0] || '' ;
+ foreach my $entity (keys %HTML_ENTITY_CHARS) {
+ if (($entity ne 'amp')&&
+ ($entity ne 'quot')&&
+ ($entity ne 'lt')&&
+ ($entity ne 'gt')) {
+ my $validchar = get_encoded_str($HTML_ENTITY_CHARS{$entity});
+ $text =~ s/\Q&#$HTML_ENTITY_CODES{$entity};\E/&$entity;/g ;
+ $text =~ s/\Q$validchar\E/&$entity;/g ;
+ }
+ }
+ return $text ;
+}
+
+=pod
+
+=item * get_html_entities()
+
+Replies the specified string in which some characters have been
+replaced by the corresponding HTML entities
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub get_html_entities($) {
+ my $text = $_[0] || '' ;
+
+ $text =~ s/\Q&\E/&amp;/g ;
+ $text =~ s/\Q<\E/&lt;/g ;
+ $text =~ s/\Q>\E/&gt;/g ;
+ $text =~ s/\Q\"\E/&quot;/g ;
+
+ return get_restricted_html_entities($text) ;
+}
+
+=pod
+
+=item * translate_html_entities()
+
+Replies the specified string in which each HTML entity was replaced
+by the corresponding character.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub translate_html_entities($) {
+ my $text = $_[0] || '' ;
+ $text =~ s/\Q&nbsp;\E/ /g ;
+ $text =~ s/\Q&quot;\E/\"/g ;
+ $text =~ s/\Q&lt;\E/</g ;
+ $text =~ s/\Q&gt;\E/>/g ;
+ $text =~ s/\Q&amp;\E/&/g ;
+ while (my ($entity,$charcode) = each(%HTML_ENTITY_CODES)) {
+ my $validchar = get_encoded_str($HTML_ENTITY_CHARS{$entity});
+ if ($validchar) {
+ $text =~ s/\Q&#$charcode;\E/$validchar/g ;
+ }
+ }
+ foreach my $entity (keys %HTML_ENTITY_CHARS) {
+ my $validchar = get_encoded_str($HTML_ENTITY_CHARS{$entity});
+ $text =~ s/\Q&$entity;\E/$validchar/g ;
+ }
+ return $text ;
+}
+
+=pod
+
+=item * htmlcatdir()
+
+Concatenate two or more directory names to form a complete path ending
+with a directory. But remove the trailing slash from the resulting
+string.
+Takes 2 args or more:
+
+=over
+
+=item * dir... (string)
+
+is a I<string> which correspond to a directory name to merge
+
+=back
+
+=cut
+sub htmlcatdir {
+ my $path = '' ;
+ $path = join('/', @_ ) if ( @_ ) ;
+ $path =~ s/\/{2,}/\//g ;
+ $path =~ s/\/$// ;
+ return $path ;
+}
+
+=pod
+
+=item * htmlcatfile()
+
+Concatenate one or more directory names and a filename to form a
+complete path ending with a filename
+Takes 2 args or more:
+
+=over
+
+=item * dir... (string)
+
+is a I<string> which correspond to a directory name to merge
+
+=item * file (string)
+
+is a I<string> which correspond to a file name to merge
+
+=back
+
+=cut
+sub htmlcatfile {
+ return '' unless @_ ;
+ my $file = pop @_;
+ return $file unless @_;
+ my $dir = htmlcatdir(@_);
+ $dir .= "/" unless substr($file,0,1) eq "/" ;
+ return $dir.$file;
+}
+
+=pod
+
+=item * htmldirname()
+
+Replies the path of the from the specified file
+Takes 1 arg:
+
+=over
+
+=item * path (string)
+
+is a I<string> which correspond to the path from which
+the dirname but be extracted
+
+=back
+
+=cut
+sub htmldirname($) {
+ my $dirname = $_[0] || '' ;
+ $dirname =~ s/\/+\s*$// ;
+ if ( $dirname =~ /^(.*?)\/[^\/]+$/ ) {
+ $dirname = ($1) ? $1 : "/" ;
+ }
+ else {
+ $dirname = "" ;
+ }
+ return $dirname ;
+}
+
+=pod
+
+=item * htmlfilename()
+
+Replies the filename of the from the specified file
+Takes 1 arg:
+
+=over
+
+=item * path (string)
+
+is a I<string> which correspond to the path from which
+the filename but be extracted
+
+=back
+
+=cut
+sub htmlfilename($) {
+ my $filename = $_[0] || '' ;
+ $filename =~ s/\/+\s*$// ;
+ if ( $filename =~ /^.*?\/([^\/]+)$/ ) {
+ $filename = $1 ;
+ }
+ return $filename ;
+}
+
+=pod
+
+=item * htmltoroot()
+
+Replies a relative path in wich each directory of the
+specified parameter was replaced by ..
+Takes 1 arg:
+
+=over
+
+=item * path (string)
+
+is a I<string> which correspond to the path to translate
+
+=back
+
+=cut
+sub htmltoroot($) {
+ my $dir = $_[0] || '' ;
+ $dir =~ s/\/\s*$// ;
+ $dir =~ s/[^\/]+/../g ;
+ return $dir ;
+}
+
+=pod
+
+=item * htmlpath()
+
+Replies a path in which all the OS path separators were replaced
+by the HTML path separator '/'
+Takes 1 arg:
+
+=over
+
+=item * path (string)
+
+is a I<string> which correspond to the path to translate
+
+=back
+
+=cut
+sub htmlpath($) {
+ my $path = $_[0] || '' ;
+ my $os_sep = "/" ;
+ my $p = File::Spec->catdir("a","b") ;
+ if ( $p =~ /a(.+)b/ ) {
+ $os_sep = $1 ;
+ }
+ $path =~ s/\Q$os_sep\E/\//g ;
+ return $path ;
+}
+
+=pod
+
+=item * htmltolocalpath()
+
+Replies a path in which all the HTML path separators '/' were replaced
+by the OS path separator
+Takes 1 arg:
+
+=over
+
+=item * path (string)
+
+is a I<string> which correspond to the path to translate
+
+=back
+
+=cut
+sub htmltolocalpath($) {
+ my $path = $_[0] || '' ;
+ my $os_sep = "/" ;
+ my $p = File::Spec->catdir("a","b") ;
+ if ( $p =~ /a(.+)b/ ) {
+ $os_sep = $1 ;
+ }
+ $path =~ s/\//$os_sep/g ;
+# if ( ( "$^O" ne 'MSWin32' ) &&
+# ( "$^O" ne 'os2' ) &&
+# ( "$^O" ne 'NetWare' ) &&
+# ( "$^O" ne 'dos' ) &&
+# ( "$^O" ne 'cygwin' ) &&
+# ( "$^O" ne 'MacOS' ) ) {
+# $path =~ s/\ /\\ /g ;
+# }
+ return $path ;
+}
+
+=pod
+
+=item * htmlsplit()
+
+Replies an array of directories which correspond to each
+parts of the specified path.
+Takes 1 arg:
+
+=over
+
+=item * path (string)
+
+is a I<string> which correspond to the path to split
+
+=back
+
+=cut
+sub htmlsplit($) {
+ my $path = $_[0] || '' ;
+ return split( /\//, $path ) ;
+}
+
+=pod
+
+=item * strip_html_tags()
+
+Removes the HTML tags from the specified string.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub strip_html_tags($) {
+ my $text = $_[0] || '' ;
+ my $res = '' ;
+ while ( ( $text ) &&
+ ( $text =~ /^(.*?)<(.*)$/ ) ) {
+ my ($prev,$next) = ($1,$2) ;
+ $res .= "$prev" ;
+ $text = $next ;
+ my $inside = 1 ;
+ while ( ( $inside ) && ( $text ) &&
+ ( $text =~ /^.*?(>|\"|\')(.*)$/ ) ) {
+ my ($sep,$next) = ($1,$2) ;
+ $text = $next ;
+ if ( $sep eq ">" ) {
+ $inside = 0 ;
+ }
+ else {
+ my $insidetext = 1 ;
+ while ( ( $insidetext ) && ( $text ) &&
+ ( $text =~ /^.*?((?:\\)|$sep)(.*)$/ ) ) {
+ my ($sepi,$rest) = ($1,$2) ;
+ if ( $sepi eq '\\' ) {
+ $text = substr($rest,1) ;
+ }
+ else {
+ $text = $rest ;
+ $insidetext = 0 ;
+ }
+ }
+ }
+ }
+ }
+ if ( $text ) {
+ $res .= $text ;
+ }
+ return $res ;
+}
+
+=pod
+
+=item * html_extract_tag_params()
+
+Replies the tag parameters that are given
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to parse.
+
+=back
+
+=cut
+sub html_extract_tag_params($) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my %params = ( ) ;
+ my @strings = () ;
+ remove_strings( \@strings, $text ) ;
+ $text =~ s/\s*=\s*/=/gm ;
+ my @parts = split( /\s+/, $text ) ;
+ foreach my $part ( @parts ) {
+ my @elts = split( /=/, $part ) ;
+ if ( @elts > 1 ) {
+ restore_strings( \@strings, $elts[1] ) ;
+ $params{lc($elts[0])} = removeslashes( $elts[1] ) ;
+ }
+ }
+ return \%params ;
+}
+
+=pod
+
+=item * split_html_tags()
+
+Replies an array in which each element
+is text or HTML tag.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to parse.
+
+=back
+
+=cut
+sub split_html_tags($) {
+ my $text = $_[0] || '' ;
+ my %res = () ;
+ while ( ( $text ) &&
+ ( $text =~ /^(.*?)<(.*)$/ ) ) {
+ my ($prev,$next) = ($1,$2) ;
+
+ add_value_entry( \%res, 'result', "$prev" ) ;
+
+ $text = $next ;
+ my $inside = 1 ;
+ my $tagcontent = '<' ;
+
+ while ( ( $inside ) && ( $text ) &&
+ ( $text =~ /^(.*?)(>|\"|\')(.*)$/ ) ) {
+ my ($inprev,$sep,$next) = ($1,$2,$3) ;
+
+ $tagcontent .= "$inprev$sep" ;
+ $text = $next ;
+ if ( $sep eq ">" ) {
+ $inside = 0 ;
+ }
+ else {
+ my $insidetext = 1 ;
+ while ( ( $insidetext ) && ( $text ) &&
+ ( $text =~ /^(.*?)((?:\\)|$sep)(.*)$/ ) ) {
+ my ($intprev,$sepi,$rest) = ($1,$2,$3) ;
+ $tagcontent .= "$intprev$sepi" ;
+ if ( $sepi eq '\\' ) {
+ $text = substr($rest,1) ;
+ }
+ else {
+ $text = $rest ;
+ $insidetext = 0 ;
+ }
+ }
+ }
+ }
+ add_value_entry( \%res, 'result', $tagcontent ) ;
+ }
+ if ( $text ) {
+ add_value_entry( \%res, 'result', $text ) ;
+ }
+ return $res{'result'} ;
+}
+
+sub __scan_html_text_and_apply($&) {
+ my $text = $_[0] || '' ;
+ my $res = '' ;
+ while ( ( $text ) &&
+ ( $text =~ /^(.*?)<(.*)$/ ) ) {
+ my ($prev,$next) = ($1,$2) ;
+
+ # Replacement
+ &{$_[1]}( $prev ) ;
+
+ $res .= "$prev<" ;
+ $text = $next ;
+ my $inside = 1 ;
+ while ( ( $inside ) && ( $text ) &&
+ ( $text =~ /^(.*?)(>|\"|\')(.*)$/ ) ) {
+ my ($inprev,$sep,$next) = ($1,$2,$3) ;
+ $res .= "$inprev$sep" ;
+ $text = $next ;
+ if ( $sep eq ">" ) {
+ $inside = 0 ;
+ }
+ else {
+ my $insidetext = 1 ;
+ while ( ( $insidetext ) && ( $text ) &&
+ ( $text =~ /^(.*?)((?:\\)|$sep)(.*)$/ ) ) {
+ my ($intprev,$sepi,$rest) = ($1,$2,$3) ;
+ $res .= "$intprev$sepi" ;
+ if ( $sepi eq '\\' ) {
+ $text = substr($rest,1) ;
+ }
+ else {
+ $text = $rest ;
+ $insidetext = 0 ;
+ }
+ }
+ }
+ }
+ }
+ if ( $text ) {
+
+ # Replacement
+ &{$_[1]}( $text ) ;
+
+ $res .= $text ;
+ }
+ return $res ;
+}
+
+=pod
+
+=item * html_add_unsecable_spaces()
+
+Replaces the spaces by unsecable spaces inside an HTML string
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub html_add_unsecable_spaces($) {
+ return __scan_html_text_and_apply( $_[0],
+ sub { $_[0] =~ s/[ \t\n\r]+/&nbsp;/g ;
+ } ) ;
+}
+
+=pod
+
+=item * html_uc()
+
+Upper cases the specified text.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub html_uc($) {
+ return __scan_html_text_and_apply( $_[0],
+ sub { $_[0] = __html_uc($_[0]) ;
+ } ) ;
+}
+
+sub __html_uc($) {
+ my $text = $_[0] || '' ;
+ my $res = '' ;
+ if ( $text ) {
+ while ( ( $text ) &&
+ ( $text =~ /^(.*?)&([^;]+);(.*)$/ ) ) {
+ (my $prev,my $tag,$text) = ($1,$2,$3) ;
+ $res .= uc( $prev ) ;
+ if ( ( $tag =~ /^[a-z]/ ) &&
+ ( exists $HTML_ENTITY_CODES{$tag} ) &&
+ ( exists $HTML_ENTITY_CODES{ucfirst($tag)} ) ) {
+ $tag = ucfirst($tag) ;
+ }
+ $res .= "&".$tag.";" ;
+ }
+ if ( $text ) {
+ $res .= uc( $text ) ;
+ }
+ }
+ return $res ;
+}
+
+=pod
+
+=item * html_lc()
+
+Lower cases the specified text.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub html_lc($) {
+ return __scan_html_text_and_apply( $_[0],
+ sub { $_[0] = __html_lc($_[0]) ;
+ } ) ;
+}
+
+sub __html_lc($) {
+ my $text = $_[0] || '' ;
+ my $res = '' ;
+ if ( $text ) {
+ while ( ( $text ) &&
+ ( $text =~ /^(.*?)&([^;]+);(.*)$/ ) ) {
+ (my $prev,my $tag,$text) = ($1,$2,$3) ;
+ $res .= lc( $prev ) ;
+ if ( ( $tag =~ /^[a-z]/ ) &&
+ ( exists $HTML_ENTITY_CODES{$tag} ) &&
+ ( exists $HTML_ENTITY_CODES{lcfirst($tag)} ) ) {
+ $tag = lcfirst($tag) ;
+ }
+ $res .= "&".$tag.";" ;
+ }
+ if ( $text ) {
+ $res .= lc( $text ) ;
+ }
+ }
+ return $res ;
+}
+
+=pod
+
+=item * html_ucwords()
+
+Upper cases the first letters of each words.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub html_ucwords($) {
+ return __scan_html_text_and_apply( $_[0],
+ sub { $_[0] = __html_ucwords($_[0]) ;
+ } ) ;
+}
+
+sub __html_ucwords($) {
+ my $text = $_[0] || '' ;
+ my $res = '' ;
+ while ( $text ) {
+ if ( $text =~ /^([_\-\s]*)&([^;]+);([^_\-\s]*)(.*)$/ ) {
+ (my $prev,my $tag,my $after,$text) = ($1,$2,$3,$4);
+ $res .= $1;
+ if ( ( $tag =~ /^[a-z]/ ) &&
+ ( exists $HTML_ENTITY_CODES{$tag} ) &&
+ ( exists $HTML_ENTITY_CODES{ucfirst($tag)} ) ) {
+ $tag = ucfirst($tag) ;
+ }
+ $res .= "&".$tag.";".$after ;
+ }
+ elsif ( $text =~ /^([_\-\s]*)([^_\-\s]+)(.*)$/ ) {
+ (my $prev,my $tag,$text) = ($1,$2,$3);
+ $res .= $1;
+ $res .= ucfirst($tag);
+ }
+ else {
+ $res .= ucwords($text);
+ $text = '';
+ }
+ }
+ return $res ;
+}
+
+=pod
+
+=item * html_ucfirst()
+
+Upper cases the first letters of the first word.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub html_ucfirst($) {
+ my $found = 0;
+ return __scan_html_text_and_apply( $_[0],
+ sub { $_[0] = __html_ucfirst($_[0],\$found) ;
+ } ) ;
+}
+
+sub __html_ucfirst($$) {
+ my $text = $_[0] || '' ;
+ if( !$_[1] ) {
+ return $text;
+ }
+ else {
+ my $res = '' ;
+ if ( $text =~ /^([_\-\s]*)&([^;]+);([^_\-\s]*)(.*)$/ ) {
+ (my $prev,my $tag,my $after,$text) = ($1,$2,$3,$4);
+ $res .= $1;
+ if ( ( $tag =~ /^[a-z]/ ) &&
+ ( exists $HTML_ENTITY_CODES{$tag} ) &&
+ ( exists $HTML_ENTITY_CODES{ucfirst($tag)} ) ) {
+ $tag = ucfirst($tag) ;
+ }
+ $res .= "&".$tag.";".$after.$text ;
+ }
+ elsif ( $text =~ /^([_\-\s]*)([^_\-\s]+)(.*)$/ ) {
+ (my $prev,my $tag,$text) = ($1,$2,$3);
+ $res .= $1;
+ $res .= ucfirst($tag).$text;
+ }
+ else {
+ $res .= ucwords($text);
+ }
+ $_[1] = 1;
+ return $res ;
+ }
+}
+
+=pod
+
+=item * html_sc()
+
+Translates the specified text into small caps
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub html_sc($) {
+ my $text = __scan_html_text_and_apply( $_[0],
+ sub { $_[0] = __html_sc($_[0]) ;
+ } ) ;
+ $text =~ s/<small><\/small>//g ;
+ $text =~ s/<\/small><small>//g ;
+ return $text ;
+}
+
+sub __html_sc($) {
+ my $text = $_[0] || '' ;
+ my $res = '' ;
+ if ( $text ) {
+ while ( ( $text ) &&
+ ( $text =~ /^(.*?)&([^;]+);(.*)$/ ) ) {
+ (my $prev,my $tag,$text) = ($1,$2,$3) ;
+ $prev =~ s/([a-z]+)/"<small>".uc($1)."<\/small>";/eg ;
+ $res .= $prev ;
+ if ( ( $tag =~ /^([a-z])/ ) &&
+ ( exists $HTML_ENTITY_CODES{$tag} ) &&
+ ( exists $HTML_ENTITY_CODES{ucfirst($tag)} ) ) {
+ $tag = ucfirst($tag) ;
+ }
+ $res .= "<small>&".$tag.";</small>" ;
+ }
+ if ( $text ) {
+ $text =~ s/([a-z]+)/"<small>".uc($1)."<\/small>";/eg ;
+ $res .= $text ;
+ }
+ }
+ return $res ;
+}
+
+=pod
+
+=item * nl2br()
+
+Translates newline characters into tags <BR>.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub nl2br($) {
+ my $text = $_[0] || '' ;
+ $text =~ s/[\n\r]/<BR>\n/g ;
+ return $text ;
+}
+
+=pod
+
+=item * br2nl()
+
+Translates tags <BR> into newline characters.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to translate.
+
+=back
+
+=cut
+sub br2nl($) {
+ my $text = $_[0] || '' ;
+ $text =~ s/<BR\s*\/?>[\n\r]*/\n/g ;
+ return $text ;
+}
+
+=pod
+
+=item * setAsValidHTML_small()
+
+Merge the "Valid HTML 4.1" small icon to the specified content.
+This icon must be copied by the calling generator as the file
+'path_to_root/valid-html401.gif'.
+Takes 3 args:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to update.
+
+=item * rootdir (string)
+
+is the relative path to the root directory.
+
+=item * valid (array)
+
+is an associative array which content all the validation flags.
+The keys are the validated formats: 'html', 'xhtml', 'css'.
+
+=back
+
+=cut
+sub setAsValidHTML_small($$@) {
+ my $t = \$_[0] ; shift ;
+ my $rootdir = shift ;
+ my ($html,$xhtml,$css) ;
+ foreach my $p (@_) {
+ $html = 1 if ( "$p" eq 'html') ;
+ $xhtml = 1 if ( "$p" eq 'xhtml') ;
+ $css = 1 if ( "$p" eq 'css') ;
+ }
+
+ if (($html)||($xhtml)||($css)) {
+ $$t .= "<p align=\"right\">" ;
+ if ($html) {
+ $$t .= join( '',
+ "<a href=\"http://validator.w3.org/check?uri=referer\">",
+ "<img border=\"0\" src=\"",
+ htmlcatfile($rootdir,"valid-html401.gif"),
+ "\" ",
+ "alt=\"Valid HTML 4.01!\" height=\"15\" width=\"44\">",
+ "</a>" ) ;
+ }
+ if ($css) {
+ $$t .= join( '',
+ "<a href=\"http://jigsaw.w3.org/css-validator/\">",
+ "<img style=\"border:0;width:44px;height:15px\" ",
+ "src=\"",
+ htmlcatfile($rootdir,"valid-css.gif"),
+ "\" alt=\"Valid CSS!\">",
+ "</a>" ) ;
+ }
+ $$t .= "</p>" ;
+ }
+}
+
+=pod
+
+=item * setAsValidHTML()
+
+Merge the "Valid HTML 4.1" small icon to the specified content.
+This icon must be copied by the calling generator as the directory
+'path_to_root/'.
+Takes 3 args:
+
+=over
+
+=item * text (string)
+
+is a I<string> which correspond to the text to update.
+
+=item * rootdir (string)
+
+is the relative path to the root directory.
+
+=item * valid (array)
+
+is an associative array which content all the validation flags.
+The keys are the validated formats: 'html', 'xhtml', 'css'.
+
+=back
+
+=cut
+sub setAsValidHTML($$@) {
+ my $t = \$_[0] ; shift ;
+ my $rootdir = shift ;
+ my ($html,$xhtml,$css) ;
+ foreach my $p (@_) {
+ $html = 1 if ( "$p" eq 'html') ;
+ $xhtml = 1 if ( "$p" eq 'xhtml') ;
+ $css = 1 if ( "$p" eq 'css') ;
+ }
+
+ if (($html)||($xhtml)||($css)) {
+ $$t .= "<p align=\"right\">" ;
+ if ($html) {
+ $$t .= join( '',
+ "<a href=\"http://validator.w3.org/check?uri=referer\">",
+ "<img border=\"0\" src=\"",
+ htmlcatfile($rootdir,"valid-html401.gif"),
+ "\" ",
+ "alt=\"Valid HTML 4.01!\" height=\"31\" width=\"88\">",
+ "</a>" ) ;
+ }
+ if ($css) {
+ $$t .= join( '',
+ "<a href=\"http://jigsaw.w3.org/css-validator/\">",
+ "<img style=\"border:0;width:88px;height:31px\" ",
+ "src=\"",
+ htmlcatfile($rootdir,"valid-css.gif"),
+ "\" alt=\"Valid CSS!\">",
+ "</a>" ) ;
+ }
+ $$t .= "</p>" ;
+ }
+}
+
+=pod
+
+=item * html_getinitiales()
+
+Replies the initiales of the specified text
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub html_getinitiales($) {
+ my $text = $_[0] || '' ;
+ return __scan_html_text_and_apply( $text,
+ sub { $_[0] = __html_getinitiales($_[0]) ;
+ } ) ;
+}
+
+# TODO: leave the '-' inside the returned initials.
+sub __html_getinitiales($) {
+ my $text = $_[0] || '' ;
+ my $res = '' ;
+ while ( $text ) {
+ if ( $text =~ /^[_\.\-\s]*&([^;]+);([\.\-])(.*)$/ ) {
+ # Name's initial starting with an accentuated letter
+ (my $tag,my $sep,$text) = ($1,$2,$3);
+ if ( exists $HTML_ENTITY_CODES{$tag} ) {
+ $res .= "&".$tag.";$sep" ;
+ }
+ }
+ elsif ( $text =~ /^[_\.\-\s]*([^&\s\-\._])([\.\-])(.*)$/ ) {
+ # Name's initial starting with an accentuated letter
+ (my $tag,my $sep,$text) = ($1,$2,$3);
+ $res .= "$tag$sep";
+ }
+ elsif ( $text =~ /^[_\.\-\s]*&([^;]+);[^\s\-\._]*(.*)$/ ) {
+ # Long name starting with an accentuated letter
+ (my $tag,$text) = ($1,$2);
+ if ( exists $HTML_ENTITY_CODES{$tag} ) {
+ $res .= "&".$tag.";." ;
+ }
+ }
+ elsif ( $text =~ /^[_\.\-\s]*([^&\s\-\._])[^\s\-\._]*(.*)$/ ) {
+ # Long name starting with a not-accentuated letter
+ (my $tag,$text) = ($1,$2);
+ $res .= $tag.".";
+ }
+ else {
+ $text = '';
+ }
+ }
+ return $res ;
+}
+
+=pod
+
+=item * html_substr()
+
+Replies a substring of the specified text
+Takes 3 args:
+
+=over
+
+=item * text (string)
+
+=item * start (optional integer)
+
+=item * length (optional integer)
+
+=back
+
+=cut
+sub html_substr($;$$) {
+ my $text = $_[0] || '' ;
+ my $startpos = $_[1] || 0;
+ my $length = $_[2] || -1;
+ return __scan_html_text_and_apply( $text,
+ sub { $_[0] = __html_substr($_[0],$startpos,$length) ;
+ } ) ;
+}
+
+sub __html_substr($$$) {
+ my ($text,$pos,$length) = ($_[0],$_[1],$_[2]);
+ my @chars = html_split_to_chars($text);
+ $pos = @chars + $pos if ($pos<0);
+ $pos = @chars if ($pos>@chars);
+ $length = @chars if ($length<0);
+ my @res = ();
+ for(my $i=$pos; ($i<@chars)&&($i<($pos+$length)); $i++) {
+ push @res, $chars[$i];
+ }
+ return join('',@res);
+}
+
+=pod
+
+=item * html_split_chars()
+
+Replies an array of the characters in the given HTML string.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+an HTML string without HTML tags
+
+=back
+
+=cut
+
+sub html_split_to_chars($) {
+ my @chars = ();
+ while ($_[0] =~ /((?:&[^;]+;)|(?:[^&]))/g) {
+ push @chars, "$1";
+ }
+ return @chars;
+}
+
+=pod
+
+=item * sortbyletters(@)
+
+Sort by letter the specified parameter and
+replies it.
+Takes 1 arg:
+
+=over
+
+=item * array (string)
+
+=back
+
+=cut
+sub sortbyletters(\@) {
+ return sort {
+ my $elt1 = remove_html_accents($a || "");
+ my $elt2 = remove_html_accents($b || "");
+ $elt1 =~ s/[^a-zA-Z0-9]//g;
+ $elt2 =~ s/[^a-zA-Z0-9]//g;
+ return ($elt1 cmp $elt2);
+ } @{$_[0]};
+}
+
+=pod
+
+=item * remove_html_accents($)
+
+Remove the accents from the given html strings.
+Takes 1 arg:
+
+=over
+
+=item * str (string)
+
+=back
+
+=cut
+sub remove_html_accents($) {
+ my $orig = shift | '';
+ my $trans = "$orig";
+ while (my ($html,$code) = each(%HTML_ENTITY_CODES)) {
+ $trans =~ s/\&\#\Q$code\E;/$HTML_NO_ACCENT_ENTITY_CHARS{$html}/gs;
+ }
+ while (my ($html,$letter) = each(%HTML_NO_ACCENT_ENTITY_CHARS)) {
+ $trans =~ s/\&\Q$html\E;/$letter/gs;
+ }
+ return "$trans";
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+phpdocgen.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Misc.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Misc.pm
new file mode 100644
index 0000000000..6354201a00
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Misc.pm
@@ -0,0 +1,1554 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::General::Misc - Miscellaneous definitions
+
+=head1 DESCRIPTION
+
+Bib2HTML::General::Misc is a Perl module, which proposes
+a set of miscellaneous functions.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Misc.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::General::Misc;
+
+@ISA = ('Exporter');
+@EXPORT = qw( &strinarray &mkdir_rec &add_value_entry
+ &isemptyhash &buildtree &removefctbraces
+ &addfctbraces &extract_file_from_location
+ &extract_line_from_location &formathashkeyname
+ &formatfctkeyname &isarray &ishash &isemptyarray
+ &hashcount &is_valid_regex &tohumanreadable
+ &readfileastext &valueinhash &issub &isnumber
+ &arabictoroman &romantoarabic &extract_first_words
+ &force_add_value_entry &tonumber &addslashes
+ &restore_strings &remove_strings &removeslashes
+ &array_slice &filecopy &ucwords
+ &integer2alphabetic &splittocolumn &uniq &trim
+ &splittocolumn_base &levenshtein
+ &levenshtein_ops &shell_to_regex);
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+
+use File::Spec ;
+use File::Copy ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the misc functions
+my $VERSION = "4.0" ;
+
+#------------------------------------------------------
+#
+# General purpose functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * splittocolumn_base()
+
+Replies the specified text splitted to the given column.
+This function treats the text line by line.
+Takes 3 args:
+
+=over
+
+=item * text (string)
+
+=item * column (integer)
+
+=item * header (optional string)
+
+is the text to merge in the begining of each line.
+
+=back
+
+=cut
+sub splittocolumn_base($$;$) {
+ my $source = shift || '' ;
+ my $size = shift || 0 ;
+
+ return "$source" unless (($source)&&($size>0)) ;
+
+ my $header = shift || '' ;
+
+ my @result = () ;
+
+ foreach my $line (split(/[\n\r\f]/, "$source")) {
+
+ my $result = '' ;
+ my $linesize = 0 ;
+ my $startline = 1 ;
+
+ foreach my $w (split(/[ \t]+/, $line)) {
+ if ($w) {
+
+ if ($startline) {
+ $linesize = length("$w")+length("$header") ;
+ $result .= "$header$w" ;
+ $startline = 0 ;
+
+ }
+ else {
+
+ if (($linesize+length($w)+1)>$size) {
+ $result .= "\n$header$w" ;
+ $linesize = length("$header")+length($w) ;
+ }
+ else {
+ $result .= " $w" ;
+ $linesize += length($w)+1 ;
+ }
+
+ }
+ }
+ }
+
+ push @result, "$result" ;
+
+ }
+
+ return join("\n",@result) ;
+}
+
+=pod
+
+=item * splittocolumn()
+
+Replies the specified text splitted to the given column.
+This function treats the text line by line.
+Takes 4 args:
+
+=over
+
+=item * text (string)
+
+=item * column (integer)
+
+=item * ident (integer)
+
+is the text which will be merged to each begining
+of lines.
+
+=item * firstindent (integer)
+
+if positive, indicates how mush the first line must be indented
+
+=back
+
+=cut
+sub splittocolumn($$$;$) {
+ my $source = shift || '' ;
+ my $size = shift || 0 ;
+
+ return "$source" unless (($source)&&($size>0)) ;
+
+ my $indent = shift || 0 ;
+ my $firstindent = shift ;
+ $firstindent = 0 unless (($firstindent)&&($firstindent>0)) ;
+
+ my ($indent_str,$first_indent) = ('','') ;
+
+ {
+ for(my $i=0; (($i<$indent)||($i<$firstindent)); $i++) {
+ $indent_str .= ' ' if ($i<$indent) ;
+ $first_indent .= ' ' if ($i<$firstindent) ;
+ }
+ }
+ my @result = () ;
+ my $veryfirstline = 1 ;
+
+ foreach my $line (split(/[\n\r\f]/, "$source")) {
+
+ my $result = '' ;
+ my $linesize = 0 ;
+ my $startline = 1 ;
+
+ foreach my $w (split(/[ \t]+/, $line)) {
+ if ($w) {
+
+ if ($startline) {
+ $linesize = length("$w") ;
+ if ($veryfirstline) {
+ $linesize += $firstindent ;
+ $result .= "$first_indent" ;
+ }
+ $result .= "$w" ;
+ $startline = 0 ;
+
+ }
+ else {
+
+ if (($linesize+length($w)+1)>$size) {
+ $result .= "\n$indent_str$w" ;
+ $linesize = $indent+length($w) ;
+ }
+ else {
+ $result .= " $w" ;
+ $linesize += length($w)+1 ;
+ }
+
+ }
+ }
+ }
+
+ push @result, "$result" ;
+ $veryfirstline = 0 ;
+
+ }
+
+ return join("\n",@result) ;
+}
+
+=pod
+
+=item * strinarray()
+
+Replies if the specified value is in an array.
+Takes 2 args:
+
+=over
+
+=item * str (string)
+
+is the string to search.
+
+=item * array (array ref)
+
+is the array in which the string will be searched.
+
+=back
+
+=cut
+sub strinarray($$) {
+ return 0 unless ( $_[1] ) && ( $_[0] ) ;
+ foreach my $g (@{$_[1]}) {
+ if ( $g eq $_[0] ) {
+ return 1 ;
+ }
+ }
+ return 0 ;
+}
+
+=pod
+
+=item * valueinhash()
+
+Replies if the specified value is a value of thez associative array.
+Takes 2 args:
+
+=over
+
+=item * str (string)
+
+is the string to search.
+
+=item * hash (hash ref)
+
+is the associative array in which the string will be searched.
+
+=back
+
+=cut
+sub valueinhash($$) {
+ return 0 unless ( $_[1] ) && ( $_[0] ) ;
+ foreach my $k (keys %{$_[1]}) {
+ if ( ( $_[1]->{$k} ) &&
+ ( $_[1]->{$k} eq $_[0] ) ) {
+ return 1 ;
+ }
+ }
+ return 0 ;
+}
+
+=pod
+
+=item * mkdir_rec()
+
+Creates recursively a directory.
+Takes 1 arg:
+
+=over
+
+=item * path (string)
+
+is the name of the directory to create.
+
+=back
+
+=cut
+sub mkdir_rec($) {
+ # Fix proposed by joezespak@yahoo.com:
+ # platform-independant paths
+ return 0 unless $_[0] ;
+ my $param = File::Spec->rel2abs($_[0]) ;
+ my @parts = File::Spec->splitdir( $param ) ;
+ my $current = "" ;
+ foreach my $r (@parts) {
+ # Fix by joezespak@yahoo.com:
+ # support of absolute paths
+ if ( $r ) {
+ $current = File::Spec->catdir($current,$r) ;
+ }
+ else {
+ $current = File::Spec->rootdir() ;
+ }
+ if ( ! -d "$current" ) {
+ if ( ! mkdir( "$current", 0777 ) ) {
+ return 0 ;
+ }
+ }
+ }
+ return 1 ;
+}
+
+=pod
+
+=item * isemptyhash()
+
+Replies if the specified hashtable was empty.
+Takes 1 arg:
+
+=over
+
+=item * hash (hash ref)
+
+is the hash table.
+
+=back
+
+=cut
+sub isemptyhash($) {
+ if ( ! $_[0] ) {
+ return (1==1) ;
+ }
+ else {
+ my @k = keys %{$_[0]} ;
+ return ($#k < 0) ;
+ }
+}
+
+=pod
+
+=item * isemptyarray()
+
+Replies if the specified array was empty.
+Takes 1 arg:
+
+=over
+
+=item * array (array ref)
+
+is the array.
+
+=back
+
+=cut
+sub isemptyarray($) {
+ if ( ! $_[0] ) {
+ return (1==1) ;
+ }
+ else {
+ return ($#{$_[0]} < 0) ;
+ }
+}
+
+=pod
+
+=item * hashcount()
+
+Replies the count of keys inside the specified hash.
+Takes 1 arg:
+
+=over
+
+=item * hash (hash ref)
+
+is the hash table.
+
+=back
+
+=cut
+sub hashcount($) {
+ if ( ! $_[0] ) {
+ return 0 ;
+ }
+ else {
+ my @k = keys %{$_[0]} ;
+ return (0 + @k) ;
+ }
+}
+
+=pod
+
+=item * ishash()
+
+Replies if the specified struct is an hash.
+Takes 1 arg:
+
+=over
+
+=item * object
+
+is the object to test.
+
+=back
+
+=cut
+sub ishash {
+ return 0 unless defined($_[0]) ;
+ my $r = ref( $_[0] ) ;
+ return ( $r eq "HASH" ) ;
+}
+
+=pod
+
+=item * issub()
+
+Replies if the specified parameter is a sub name.
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+is the name of a sub
+
+=back
+
+=cut
+sub issub($) {
+ return 0 unless defined($_[0]) ;
+ return defined( &{$_[0]} ) ;
+}
+
+=pod
+
+=item * isarray()
+
+Replies if the specified struct is an array.
+Takes 1 arg:
+
+=over
+
+=item * object
+
+is the object to test.
+
+=back
+
+=cut
+sub isarray {
+ return 0 unless defined($_[0]) ;
+ my $r = ref( $_[0] ) ;
+ return ( $r eq "ARRAY" ) ;
+}
+
+=pod
+
+=item * add_value_entry()
+
+Adds an entry to the specified hashtable. if the
+the value is not defined, adds as a scalar, else
+adds as a array entry.
+Takes 3 args:
+
+=over
+
+=item * hash (hash ref)
+
+is the hashtable.
+
+=item * key (string)
+
+is the key in which the value must be put.
+
+=item * value
+
+is the value.
+
+=back
+
+=cut
+sub add_value_entry($$$) {
+ if ( ( $_[0] ) && ( $_[1] ) &&
+ ( $_[2] ) ) {
+ if ( exists $_[0]{$_[1]} ) {
+ my $old = $_[0]{$_[1]} ;
+ my $r = ref( $old ) ;
+ if ( ! ( $r eq "ARRAY" ) ) {
+ delete $_[0]{$_[1]} ;
+ push( @{$_[0]{$_[1]}}, $old ) ;
+ }
+ push( @{$_[0]{$_[1]}}, $_[2] ) ;
+ }
+ else {
+ $_[0]{$_[1]} = $_[2] ;
+ }
+ }
+}
+
+=pod
+
+=item * force_add_value_entry()
+
+Adds an entry to the specified hashtable. if the
+the value is not defined, adds as a scalar, else
+adds as a array entry.
+Takes 3 args:
+
+=over
+
+=item * hash (hash ref)
+
+is the hashtable.
+
+=item * key (string)
+
+is the key in which the value must be put.
+
+=item * value
+
+is the value.
+
+=back
+
+=cut
+sub force_add_value_entry($$$) {
+ if ( ( $_[0] ) && ( $_[1] ) ) {
+ my $value = $_[2] || '' ;
+ if ( exists $_[0]{$_[1]} ) {
+ my $old = $_[0]{$_[1]} ;
+ my $r = ref( $old ) ;
+ if ( ! ( $r eq "ARRAY" ) ) {
+ delete $_[0]{$_[1]} ;
+ push( @{$_[0]{$_[1]}}, $old ) ;
+ }
+ push( @{$_[0]{$_[1]}}, $value ) ;
+ }
+ else {
+ $_[0]{$_[1]} = $value ;
+ }
+ }
+}
+
+=pod
+
+=item * buildtree()
+
+Updates the specified hashtable by
+adding the value at the specified keys.
+Takes 2 args:
+
+=over
+
+=item * hash (hash ref)
+
+is the tree.
+
+=item * keys (array ref)
+
+is the array of the keys.
+
+=item * name (string)
+
+is the classname.
+
+=back
+
+=cut
+sub buildtree($$$) {
+ return unless ( (isarray($_[1])) && $_[2] ) ;
+ my $ref = $_[0] || '' ;
+ foreach my $key (@{$_[1]}) {
+ if ( ! ( exists $$ref{$key} ) ) {
+ my %hash = () ;
+ $$ref{$key} = \%hash ;
+ }
+ $ref = $$ref{$key} ;
+ }
+ if ( ! ( exists $$ref{$_[2]} ) ) {
+ $$ref{$_[2]} = { } ;
+ }
+}
+
+=pod
+
+=item * removefctbraces()
+
+Replies a string without "()" at the end.
+Takes 1 arg:
+
+=over
+
+=item * str (string)
+
+is a string.
+
+=back
+
+=cut
+sub removefctbraces($) {
+ my $name = $_[0] || '' ;
+ if ( $name ) {
+ $name =~ s/\s*\(\s*\)\s*$// ;
+ }
+ return $name ;
+}
+
+=pod
+
+=item * addfctbraces()
+
+Replies a string with "()" at the end.
+Takes 1 arg:
+
+=over
+
+=item * str (string)
+
+is a string.
+
+=back
+
+=cut
+sub addfctbraces($) {
+ my $name = removefctbraces( $_[0] ) ;
+ return $name."()" ;
+}
+
+=pod
+
+=item * extract_file_from_location()
+
+Replies the file from the specified location.
+Takes 1 arg:
+
+=over
+
+=item * location (string)
+
+is the location inside the input stream.
+
+=back
+
+=cut
+sub extract_file_from_location($) {
+ return '' unless $_[0] ;
+ my $loc = $_[0] ;
+ my $file = "" ;
+ $loc =~ s/^(.*):[0-9]*/$file=$1;/e ;
+ return $file ;
+}
+
+=pod
+
+=item * extract_line_from_location()
+
+Replies the line number from the specified location.
+Takes 1 arg:
+
+=over
+
+=item * location (string)
+
+is the location inside the input stream.
+
+=back
+
+=cut
+sub extract_line_from_location($) {
+ return 0 unless $_[0] ;
+ my $loc = $_[0] ;
+ my $line = 0 ;
+ $loc =~ s/^.*:([0-9]*)/$line=$1;/e ;
+ if ( $line > 0 ) {
+ return $line ;
+ }
+ else {
+ return 0 ;
+ }
+}
+
+#------------------------------------------------------
+#
+# Formating of the name of the tokens
+#
+#------------------------------------------------------
+
+=pod
+
+=item * formathashkeyname()
+
+Replies a formatted hash key name.
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+is the string to format.
+
+=back
+
+=cut
+sub formathashkeyname($) {
+ return lc( $_[0] || '' ) ;
+}
+
+=pod
+
+=item * formatfctkeyname()
+
+Replies a formatted hash key name for functions.
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+is the string to format.
+
+=back
+
+=cut
+sub formatfctkeyname($) {
+ return addfctbraces( formathashkeyname( $_[0] || '' ) ) ;
+}
+
+=pod
+
+=item * is_valid_regex()
+
+Replies if the specified regular expression
+was well-formed.
+Takes 1 arg:
+
+=over
+
+=item * regex (string)
+
+is the regular expression to verify.
+
+=back
+
+=cut
+sub is_valid_regex($) {
+ return 0 unless $_[0] ;
+ return eval { "" =~ /$_[0]/; 1; } || 0 ;
+}
+
+=pod
+
+=item * tohumanreadable()
+
+Replies a string string that corresponds to
+the human readable form of the specified string.
+Takes 1 arg:
+
+=over
+
+=item * string (string)
+
+is the string to convert.
+
+=back
+
+=cut
+sub tohumanreadable($) {
+ my $string = $_[0] || '' ;
+ $string =~ s/\n/\\n/g;
+ $string =~ s/\r/\\r/g;
+ $string =~ s/\t/\\t/g;
+ $string =~ s/\"/\\\"/g;
+ $string =~ s/\'/\\\'/g;
+ return $string ;
+}
+
+=pod
+
+=item * readfileastext()
+
+Replies the content of a file as a string
+Takes 1 arg:
+
+=over
+
+=item * filename (string)
+
+is the name of the file to read
+
+=back
+
+=cut
+sub readfileastext($) {
+ my $string = "" ;
+ return $string unless $_[0] ;
+ open( READFILE_FID, "< $_[0]" )
+ or Bib2HTML::General::Error::syserr( "unable to open $_[0]: $!" ) ;
+ while ( my $line = <READFILE_FID> ) {
+ $string .= $line ;
+ }
+ close( READFILE_FID )
+ or Bib2HTML::General::Error::syserr( "unable to close $_[0]: $!" ) ;
+ return $string ;
+}
+
+=pod
+
+=item * isnumber()
+
+Replies if the parameter is a arabic or a roman number
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is the text to scan
+
+=back
+
+=cut
+sub isnumber($) {
+ return ( ( $_[0] ) &&
+ ( ( $_[0] =~ /^\s*[0-9]+\s*$/ ) ||
+ ( romantoarabic($_[0]) >= 0 ) ) ) ;
+}
+
+=pod
+
+=item * tonumber()
+
+Replies the integer value that correspond to the
+specified number. Replies undef if something wrong
+appends.
+Takes 1 arg:
+
+=over
+
+=item * number (string)
+
+is the text to translate
+
+=back
+
+=cut
+sub tonumber($) {
+ my $number = undef ;
+ if ( isnumber($_[0]) ) {
+ if ( $_[0] =~ /^\s*[0-9]+\s*$/ ) {
+ $number = $_[0] ;
+ $number =~ s/^\s+//m ;
+ $number =~ s/\s+$//m ;
+ }
+ else {
+ my $n = romantoarabic($_[0]) ;
+ if ( $n > 0 ) {
+ $number = $n ;
+ }
+ }
+ }
+ return $number ;
+}
+
+=pod
+
+=item * arabictoroman()
+
+Replies the roman number that correspond to the
+specified arabic number
+Takes 1 arg:
+
+=over
+
+=item * arabic (integer)
+
+is the number to convert
+
+=back
+
+=cut
+sub arabictoroman($) {
+ my $nb = $_[0] || 0 ;
+ my @CENT_TRANS_TBL = ( '', 'C', 'CC', 'CCC', 'CD', 'D', 'DC', 'DCC', 'DCCC', 'CM' ) ;
+ my @DEC_TRANS_TBL = ( '', 'X', 'XX', 'XXX', 'XL', 'L', 'LX', 'LXX', 'LXXX', 'XC' ) ;
+ my @UNIT_TRANS_TBL = ( '', 'I', 'II', 'III', 'IV', 'V', 'VI', 'VII', 'VIII', 'IX' ) ;
+ my $roman = "" ;
+ my $mille = int($nb / 1000) ;
+ my $cent = int(($nb % 1000) / 100) ;
+ my $dec = int(($nb % 100) / 10) ;
+ my $unit = $nb % 10 ;
+
+ while( $mille > 0 ) {
+ $roman .= "M" ;
+ $mille -- ;
+ }
+ $roman .= $CENT_TRANS_TBL[$cent] ;
+ $roman .= $DEC_TRANS_TBL[$dec] ;
+ $roman .= $UNIT_TRANS_TBL[$unit] ;
+ return $roman ;
+}
+
+=pod
+
+=item * romantoarabic()
+
+Replies the arabic number that correspond to the
+specified roman number
+Takes 1 arg:
+
+=over
+
+=item * roman (integer)
+
+is the number to convert
+
+=back
+
+=cut
+sub romantoarabic($) {
+ my $nb = $_[0] || '' ;
+ my @CENT_TRANS_TBL = ( '', 'C', 'CC', 'CCC', 'CD', 'D', 'DC', 'DCC', 'DCCC', 'CM' ) ;
+ my @DEC_TRANS_TBL = ( '', 'X', 'XX', 'XXX', 'XL', 'L', 'LX', 'LXX', 'LXXX', 'XC' ) ;
+ my @UNIT_TRANS_TBL = ( '', 'I', 'II', 'III', 'IV', 'V', 'VI', 'VII', 'VIII', 'IX' ) ;
+
+ my $roman = uc($nb) ;
+ my $arabic = 0 ;
+
+ if ( $roman =~ /^(M*)(.*)$/ ) {
+ $roman = $2 ;
+ $arabic = 1000 * length($1) ;
+ if ( ___romantoarabic($arabic,$roman,100,\@CENT_TRANS_TBL) ) {
+ if ( ___romantoarabic($arabic,$roman,10,\@DEC_TRANS_TBL) ) {
+ if ( ___romantoarabic($arabic,$roman,1,\@UNIT_TRANS_TBL) ) {
+ return $arabic ;
+ }
+ }
+ }
+ }
+ return -1 ;
+}
+
+sub ___romantoarabic($$$$) {
+ my ($max,$index,$after) = ('',-1,$_[1]) ;
+ for(my $i=1; $i<=$#{$_[3]};$i++) {
+ if ( $_[1] =~ /^($_[3][$i])(.*)$/ ) {
+ my ($nb,$reste) = ($1,$2) ;
+ if ( length($nb) > length($max) ) {
+ $max = $nb ;
+ $index = $i ;
+ $after = $reste ;
+ }
+ }
+ }
+ if ( $index > 0 ) {
+ $_[1] = $after ;
+ $_[0] += $_[2] * $index ;
+ return 1 ;
+ }
+ else {
+ return 0 ;
+ }
+}
+
+=pod
+
+=item * extract_first_words()
+
+Replies the first words of the specified string.
+Takes 2 args:
+
+=over
+
+=item * text (string)
+
+is the text from which the words must be extracted
+
+=item * len (integer)
+
+is the maximal length of the result
+
+=back
+
+=cut
+sub extract_first_words($$) {
+ my $index = $_[1] || 0 ;
+ my @words = split(/\s+/, ($_[0] || '')) ;
+ return '' unless @words ;
+ my ($result,$i) = ('',0) ;
+
+ while ( ( $i <= $#words ) && ( (length($result)+length($words[$i])) <= $index )) {
+ $result .= " " if ( $result ) ;
+ $result .= $words[$i] ;
+ $i ++ ;
+ }
+
+ if ( $i == 0 ) {
+ $result = substr($words[0],0,$index-3) ;
+ }
+ elsif ( $i < int(@words) ) {
+ if ( length($result) > $index ) {
+ $result = substr($result,0,$index-3) ;
+ }
+ $result .= "..." ;
+ }
+
+ return $result ;
+}
+
+=pod
+
+=item * addslahes()
+
+Replies a string in which the " are protected
+Takes 1 args:
+
+=over
+
+=item * text (string)
+
+is the text to translate
+
+=back
+
+=cut
+sub addslashes($) {
+ my $text = $_[0] || '' ;
+ $text =~ s/\\/\\\\/g ;
+ $text =~ s/"/\\"/g ;
+ return $text ;
+}
+
+=pod
+
+=item * removeslahes()
+
+Replies a string in which the " are unprotected
+Takes 1 args:
+
+=over
+
+=item * text (string)
+
+is the text to translate
+
+=back
+
+=cut
+sub removeslashes($) {
+ my $text = $_[0] || '' ;
+ $text =~ s/\\(.)/$1/g ;
+ return $text ;
+}
+
+=pod
+
+=item * remove_strings()
+
+Takes 2 args:
+
+=over
+
+=item * array (ref)
+
+=item * text (string)
+
+is the text to translate
+
+=back
+
+=cut
+sub remove_strings($$) {
+ my $delims= "\\\"|\\'" ;
+ my $count = int(@{$_[0]}) ;
+ while ( $_[1] =~ /($delims)/ ) {
+ my $delim = $1 ;
+ $_[1] =~ s/$delim((\\$delim|[^$delim])*)$delim/$_[0]->[$count++]="$1";"<<STRING".$count.">>"/ge;
+ }
+}
+
+=pod
+
+=item * restore_strings()
+
+Takes 2 args:
+
+=over
+
+=item * array (ref)
+
+=item * text (string)
+
+is the text to translate
+
+=back
+
+=cut
+sub restore_strings($$) {
+ $_[1] =~ s/<<STRING([0-9]+)>>/$_[0]->[$1-1]/eg ;
+}
+
+=pod
+
+=item * integer2alphabetic()
+
+Replies the string representation of the specified integer.
+Takes 1 arg.
+
+=cut
+sub integer2alphabetic($) {
+ my $value = $_[0] || 0 ;
+ my $q = chr( ord('a') + ( $value % 26 ) ) ;
+ while ( $value >= 26 ) {
+ $value = ($value/26)-1 ;
+ $q = chr( ord('a') + ( ($value % 26) % 26 ) ) . $q ;
+ }
+ return $q ;
+}
+
+=pod
+
+=item * array_slice()
+
+Slices an array content and insert the specified string
+Takes 3 args:
+
+=over
+
+=item * array (ref)
+
+=item * location (integer)
+
+is the index where insert the string
+
+=item * str (string)
+
+is the string to insert
+
+=back
+
+=cut
+sub array_slice($$$) {
+ return unless ( (isarray($_[0])) && ($_[1]>=0) ) ;
+ my $i=$#{$_[0]} ;
+ while ( $i >= $_[1] ) {
+ $_[0]->[$i+1] = $_[0]->[$i] ;
+ $i -- ;
+ }
+ $_[0]->[$_[1]] = $_[2] ;
+}
+
+=pod
+
+=item * filecopy()
+
+Copy a file
+Takes 2 args:
+
+=over
+
+=item * source (string)
+
+=item * target (string)
+
+=back
+
+=cut
+sub filecopy($$) {
+# if ( ! "$_[0]" ) {
+# $! = 2 ;
+# return 0 ;
+# }
+# if ( ! "$_[1]" ) {
+# $! = 2 ;
+# return 0 ;
+# }
+# if ( ! -f "$_[0]" ) {
+# $! = 2 ;
+# return 0 ;
+# }
+# local (*SOURCE,*TARGET) ;
+# open( *SOURCE, "< $_[0]" )
+# or return 0 ;
+# if ( ! open( *TARGET, "> $_[1]" ) ) {
+# my $msg = $! ;
+# close( *SOURCE ) ;
+# $! = $msg ;
+# return 0 ;
+# }
+# my ($tampon,$q,$w) ;
+# $q = sysread( *SOURCE, $tampon, 4096 ) ;
+# if ( ! defined( $q ) ) {
+# my $msg = $! ;
+# close( *TARGET ) ;
+# close( *SOURCE ) ;
+# unlink( $_[1] ) ;
+# $! = $msg ;
+# return 0 ;
+# }
+# while ( $q > 0 ) {
+# $w = syswrite( *TARGET, $tampon, $q ) ;
+# if ( ! defined( $w ) ) {
+# my $msg = $! ;
+# close( *TARGET ) ;
+# close( *SOURCE ) ;
+# unlink( $_[1] ) ;
+# $! = $msg ;
+# return 0 ;
+# }
+# $q = sysread( *SOURCE, $tampon, 4096 ) ;
+# if ( ! defined( $q ) ) {
+# my $msg = $! ;
+# close( *TARGET ) ;
+# close( *SOURCE ) ;
+# unlink( $_[1] ) ;
+# $! = $msg ;
+# return 0 ;
+# }
+# }
+# close( *TARGET ) ;
+# close( *SOURCE ) ;
+# return 1 ;
+
+ return copy("$_[0]","$_[1]") ;
+
+}
+
+=pod
+
+=item * ucwords()
+
+Upper case the first letter of each word.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub ucwords($) {
+ my $text = $_[0] || '' ;
+ $text =~ s/^([^\s\-_])/\u$1/g ;
+ $text =~ s/(?<=[\s\-_])([^\s\-_]+)/\u$1/g ;
+ return $text ;
+}
+
+
+=pod
+
+=item * uniq()
+
+Eliminates redundant values from sorted list of values input.
+Takes 1 arg:
+
+=over
+
+=item * items (list)
+
+The sorted list to be made uniq
+
+=back
+
+=cut
+sub uniq {
+ # Function added the 2003/03/17 by a patch from Norbert Preining
+ #
+ # Eliminates redundant values from sorted list of values input.
+ my $prev = undef;
+ my @out=();
+ foreach my $val (@_){
+ next if $prev && ($prev eq $val);
+ $prev = $val;
+ push(@out, $val);
+ }
+ return @out;
+}
+
+=pod
+
+=item * trim()
+
+Eliminates trailing spaces for each parameter.
+
+=cut
+sub trim {
+ foreach my $val (@_){
+ $val =~ s/^\s+// ;
+ $val =~ s/\s+$// ;
+ }
+}
+
+=pod
+
+=item * __matchlen()
+
+Returns the length of matching
+substrings at beginning of $a and $b.
+Takes 2 args:
+
+=over
+
+=item * str1 (string)
+
+=item * str2 (string)
+
+=back
+
+=cut
+sub __matchlen($$) {
+ my $c=0;
+ my $alen = length($_[0]);
+ my $blen = length($_[1]);
+ my $d = ($alen<$blen)?$alen:$blen;
+ while( (substr($_[0],$c,1) eq substr($_[1],$c,1))&&
+ ($c<$d) ) {
+ $c++;
+ }
+ return $c;
+}
+
+=pod
+
+=item * levenshtein_ops()
+
+Computes the levenshtein distance between two strings.
+A levenshtein distance corresponds to the adds, removes
+required to transform a string to obtain another one.
+Replies the actions to perform.
+Takes 2 args:
+
+=over
+
+=item * str1 (string)
+
+=item * str2 (string)
+
+=back
+
+=cut
+sub levenshtein_ops($$) {
+ my $alen = length($_[0]);
+ my $blen = length($_[1]);
+ my $aptr = 0;
+ my $bptr = 0;
+ my $stop = 0 ;
+
+ my @ops = ();
+
+ while((!$stop)&&($aptr<$alen)&&($bptr<$blen)) {
+ # Search for similar text at the start
+ my $matchlen = __matchlen(substr($_[0], $aptr), substr($_[1], $bptr));
+ if($matchlen>0) {
+ #
+ # Similar text found
+ #
+ push @ops, { '=' => substr($_[0], $aptr, $matchlen) };
+ $aptr += $matchlen;
+ $bptr += $matchlen;
+ }
+ else {
+ #
+ # Difference found
+ #
+ # search for the best next similar text
+ my $bestlen=0;
+ my @bestpos=(0,0);
+ my $bestfound = 0 ;
+ for(my $atmp=$aptr; (!$bestfound)&&($atmp<$alen); $atmp++) {
+ for(my $btmp=$bptr; $btmp<$blen; $btmp++) {
+ my $matchlen = __matchlen(substr($_[0], $atmp),
+ substr($_[1], $btmp));
+ if($matchlen>$bestlen) {
+ $bestlen = $matchlen;
+ @bestpos = ($atmp,$btmp);
+ }
+ $bestfound = ($matchlen>=$blen-$btmp) ;
+ }
+ }
+ if ($bestlen>0) {
+
+ my $adifflen = $bestpos[0] - $aptr;
+ my $bdifflen = $bestpos[1] - $bptr;
+
+ if($adifflen>0) {
+ push @ops, { '-' => substr($_[0], $aptr, $adifflen) };
+ $aptr += $adifflen;
+ }
+ if($bdifflen) {
+ push @ops, { '+' => substr($_[1], $bptr, $bdifflen) };
+ $bptr += $bdifflen;
+ }
+ push @ops, { '=' => substr($_[0], $aptr, $bestlen) };
+ $aptr += $bestlen;
+ $bptr += $bestlen;
+ }
+ else {
+ $stop = 1 ;
+ }
+ }
+ }
+ if($aptr<$alen) {
+ # b has too much stuff
+ push @ops, { '-' => substr($_[0], $aptr) };
+ }
+ if($bptr<$blen) {
+ # a has too little stuff
+ push @ops, { '+' => substr($_[1], $bptr) };
+ }
+ return @ops;
+}
+
+=pod
+
+=item * levenshtein()
+
+Computes the levenshtein distance between two strings.
+A levenshtein distance corresponds to the adds, removes
+required to transform a string to obtain another one.
+Replies the percent of similarity of the strings.
+Takes 2 args:
+
+=over
+
+=item * str1 (string)
+
+=item * str2 (string)
+
+=back
+
+=cut
+sub levenshtein($$) {
+ my @ops = &levenshtein_ops($_[0],$_[1]) ;
+ my $alen = length($_[0]);
+ my $blen = length($_[1]);
+ my $max = ($alen>$blen)?$alen:$blen ;
+ if ($max<=0) {
+ return 0 ;
+ }
+ my $count = 0 ;
+ foreach my $op (@ops) {
+ if ($op->{'='}) {
+ $count = $count + length($op->{'='}) ;
+ }
+ }
+ return ($count*100)/$max ;
+}
+
+=pod
+
+=item * shell_to_regex()
+
+Translate a string that contains shell's wildcards to
+its equivalent expressed with regular expressions.
+Takes 1 arg:
+
+=over
+
+=item * shell_string (string)
+
+=back
+
+=cut
+sub shell_to_regex($) {
+ my $shell_string = shift;
+ my $regex_string = '';
+ while ($shell_string =~ /^(.*?)([*?\[])(.*)$/) {
+ my ($prev,$sep,$after) = ($1,$2,$3);
+ if ($prev) {
+ $prev =~ s/\./\\./g;
+ $prev =~ s/\+/\\+/g;
+ $prev =~ s/\(/\\(/g;
+ $prev =~ s/\)/\\)/g;
+ $prev =~ s/\^/\\^/g;
+ $prev =~ s/\\/\\\\/g;
+ $prev =~ s/\$/\\\$/g;
+ $prev =~ s/\|/\\|/g;
+ $regex_string .= $prev;
+ }
+ if ($sep eq '*') {
+ $regex_string .= '.*';
+ }
+ elsif ($sep eq '?') {
+ $regex_string .= '.';
+ }
+ elsif ($sep eq '[') {
+ if ($after =~ /^([^\]]+)\](.*)$/) {
+ $after = $2;
+ $regex_string .= "[$1]";
+ }
+ else {
+ $regex_string .= '[';
+ }
+ }
+ $shell_string = $after;
+ }
+ if ($shell_string) {
+ $shell_string =~ s/\./\\./g;
+ $shell_string =~ s/\+/\\+/g;
+ $shell_string =~ s/\(/\\(/g;
+ $shell_string =~ s/\)/\\)/g;
+ $shell_string =~ s/\^/\\^/g;
+ $shell_string =~ s/\\/\\\\/g;
+ $shell_string =~ s/\$/\\\$/g;
+ $shell_string =~ s/\|/\\|/g;
+ $regex_string .= $shell_string;
+ }
+ return '^'.$regex_string.'$';
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Title.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Title.pm
new file mode 100644
index 0000000000..f0ce9a7196
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Title.pm
@@ -0,0 +1,145 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::General::Title - Utility functions for titles
+
+=head1 SYNOPSYS
+
+use Bib2HTML::General::Title ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::General::Title is a Perl module, which proposes
+functions to support the titles
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To use this package, say something like this:
+
+ use Bib2HTML::General::Title;
+
+...or something similar.
+
+=cut
+
+package Bib2HTML::General::Title;
+
+@ISA = ('Exporter');
+@EXPORT = qw( &get_title_keywords );
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use Bib2HTML::General::Misc ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the parser
+my $VERSION = "1.0" ;
+
+# The keywords that could be ignored
+my @IGNORABLE_WORDS = ( # English
+ 'the', 'a', 'an', 'in', 'on', 'inside', 'to',
+ 'and', 'by', 'for', 'based', 'of', 'his', 'her',
+ # French
+ 'la', 'le', 'les', 'dans', 'de', 'd', 'un', 'une',
+ 'vers', 'sur', 'et', 'pour', 'par', 'en',
+ ) ;
+
+# The forms of words that could be ignored
+my @IGNORABLE_WORD_FORMS = ( # English
+ '.*ing',
+ # French
+ ) ;
+
+#------------------------------------------------------
+#
+# Keyword API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_title_keywords()
+
+Replies the keywords of the specified title
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is the text to parse.
+
+=back
+
+=cut
+sub get_title_keywords($) : method {
+ my $text = $_[0] || '' ;
+ my @keywords = () ;
+ foreach my $word (split /[^a-zA-Z0-9\-\&\;]+/, $text) {
+ if ( ( ! strinarray( lc($word), \@keywords ) ) &&
+ ( ! strinarray( lc($word), \@IGNORABLE_WORDS ) ) ) {
+ my $i = $#IGNORABLE_WORD_FORMS ;
+ while ($i>=0) {
+ my $form = $IGNORABLE_WORD_FORMS[$i] ;
+ if ( lc($word) !~ /^$form$/ ) {
+ push @keywords, $word ;
+ $i = -1 ;
+ }
+ $i -- ;
+ }
+ }
+ }
+ return @keywords ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Verbose.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Verbose.pm
new file mode 100644
index 0000000000..7e2a0f31e5
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/General/Verbose.pm
@@ -0,0 +1,241 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::General::Verbose - Verbosing functions
+
+=head1 DESCRIPTION
+
+Bib2HTML::General::Verbose is a Perl module, which permits to display
+messages in a verbose mode.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Verbose.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::General::Verbose;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the verbosing functions
+my $VERSION = "1.0" ;
+# The current verbosing level ;
+my $CURRENT_VERBOSE_LEVEL = 0 ;
+
+#------------------------------------------------------
+#
+# Level management functions
+#
+#------------------------------------------------------
+
+#-------------
+=pod
+
+=item * setlevel()
+
+Changes the verbosing level.
+Takes 1 arg:
+
+=over
+
+=item * level (integer)
+
+is an I<integer> which is the requested verbose level.
+
+=back
+
+=cut
+sub setlevel($) {
+ $CURRENT_VERBOSE_LEVEL = $_[0] || 0 ;
+}
+
+
+#-------------
+=pod
+
+=item * currentlevel()
+
+Replies the current verbosing level.
+
+=cut
+sub currentlevel() {
+ return $CURRENT_VERBOSE_LEVEL ;
+}
+
+#------------------------------------------------------
+#
+# Output functions
+#
+#------------------------------------------------------
+
+#-------------
+=pod
+
+=item * verb()
+
+Displays the specified message if in verbose mode.
+Takes 2 args:
+
+=over
+
+=item * message (string)
+
+is an I<string> which is the message to display.
+
+=item * level (integer)
+
+is an I<integer> which is the required level of the message.
+
+=item * cr (optional boolean)
+
+indicates if the carriage return will be printed (default is true)
+
+=back
+
+=cut
+sub verb {
+ my $level = $_[1] || $CURRENT_VERBOSE_LEVEL ;
+ if ( Bib2HTML::General::Verbose::currentlevel() >= $level ) {
+ my $msg = $_[0] || '' ;
+ my $cr = defined($_[2]) ? $_[2] : 1 ;
+ $msg =~ s/\n$// ;
+ print $msg ;
+ print "\n" if $cr ;
+ }
+}
+
+#-------------
+=pod
+
+=item * one()
+
+Displays the specified message if in verbosing level
+greater or equal to 1.
+Takes 2 args:
+
+=over
+
+=item * message (string)
+
+is an I<string> which is the message to display.
+
+=item * ...
+
+optional parameters passed to verb()
+
+=back
+
+=cut
+sub one($) {
+ my $msg = $_[0] || '' ;
+ Bib2HTML::General::Verbose::verb($msg,1,$_[1]) ;
+}
+
+#-------------
+=pod
+
+=item * two()
+
+Displays the specified message if in verbosing level
+greater or equal to 2.
+Takes 2 args:
+
+=over
+
+=item * message (string)
+
+is an I<string> which is the message to display.
+
+=item * ...
+
+optional parameters passed to verb()
+
+=back
+
+=cut
+sub two($) {
+ my $msg = $_[0] || '' ;
+ Bib2HTML::General::Verbose::verb($msg,2,$_[1]) ;
+}
+
+#-------------
+=pod
+
+=item * three()
+
+Displays the specified message if in verbosing level
+greater or equal to 3.
+Takes 2 args:
+
+=over
+
+=item * message (string)
+
+is an I<string> which is the message to display.
+
+=item * ...
+
+optional parameters passed to verb()
+
+=back
+
+=cut
+sub three($) {
+ my $msg = $_[0] || '' ;
+ Bib2HTML::General::Verbose::verb($msg,3,$_[1]) ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/AbstractGenerator.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/AbstractGenerator.pm
new file mode 100644
index 0000000000..e19ee79173
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/AbstractGenerator.pm
@@ -0,0 +1,1226 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::AbstractGenerator - An abstract generator
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::AbstractGenerator is a Perl module, which permits to
+generate some document for a BibTeX database. This class must be
+overwrite.
+
+=head1 SYNOPSYS
+
+Bib2HTML::Generator::AbstractGenerator->new( content, output, info, titles,
+ lang, [params] ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::AbstractGenerator is a Perl module, which permits to
+generate some documents for a BibTeX database.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+Acceptable parameters to the constructor are:
+
+=over
+
+=item * content (hash)
+
+is the content of the bibliography to output.
+
+=item * output (string)
+
+is the output directory in which the HTML page must be put.
+
+=item * bib2html_data (hash)
+
+contains some information on Bib2HTML :
+
+=over
+
+=item VERSION
+
+is the version of Bib2HTML.
+
+=item BUG_URL
+
+is the URL where to submit a bug.
+
+=item URL
+
+is the URL of the main page of Bib2HTML.
+
+=item AUTHOR_EMAIL
+
+is the email of the author of Bib2HTML.
+
+=item AUTHOR
+
+is the nmae of the author of Bib2HTML.
+
+
+=item PERLSCRIPTDIR
+
+is the dorectory where is the Bib2HTML perl script.
+
+=back
+
+=item * titles (hash)
+
+is the titles of the pages:
+
+=over
+
+=item SHORT
+
+is the title shown in the window bar.
+
+=item LONG
+
+is the title shown in the default HTML pag.
+
+=back
+
+=item * lang (string)
+
+is the name of the language to use
+
+=item * show_bibtex (boolean)
+
+indicates if this parser must generate a verbatim of the BibTeX code
+
+=item * params (optional array)
+
+is the set of parameters passed to the generator.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in AbstractGenerator.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::AbstractGenerator;
+
+@ISA = ('Exporter');
+@EXPORT = qw( &display_supported_generators
+ &display_supported_languages
+ &display_supported_themes );
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+use File::Basename ;
+use File::Spec;
+
+use Bib2HTML::General::Misc;
+use Bib2HTML::General::HTML;
+use Bib2HTML::Generator::LangManager;
+use Bib2HTML::Generator::FileWriter;
+use Bib2HTML::Generator::StdOutWriter;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of abstract generator
+my $VERSION = "6.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$$;$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = { 'TARGET' => $_[1] || File::Spec->curdir(),
+ 'TARGET_NOT_REMOVABLE' => [],
+ 'CONTENT' => $_[0] || { },
+ 'BIB2HTML' => { 'VERSION' => $_[2]{'VERSION'} || "???",
+ 'BUG_URL' => $_[2]{'BUG_URL'} || "",
+ 'URL' => $_[2]{'URL'} || "",
+ 'AUTHOR_EMAIL' => $_[2]{'AUTHOR_EMAIL'} || "",
+ 'AUTHOR' => $_[2]{'AUTHOR'} || "",
+ 'PERLSCRIPTDIR' => $_[2]{'PERLSCRIPTDIR'} || "",
+ },
+ 'SHORT_TITLE' => $_[3]{'SHORT'},
+ 'LONG_TITLE' => $_[3]{'LONG'},
+ 'SHOW_BIBTEX' => $_[5],
+ 'CACHE' => { 'BUILT_ENTRY_AUTHOR_LIST' => {},
+ },
+ } ;
+
+ # Creates the language support
+ confess( 'you must supply the language' ) unless ($_[4]) ;
+ $self->{'LANG'} = Bib2HTML::Generator::LangManager->new($_[4]) ;
+
+ # Sets the constants according to the language
+ if ( ! $self->{'LONG_TITLE'} ) {
+ $self->{'LONG_TITLE'} = ( $self->{'SHORT_TITLE'} ?
+ $self->{'SHORT_TITLE'} :
+ $self->{'LANG'}->get('I18N_LANG_DEFAULT_TITLE') ) ;
+ }
+ if ( ! $self->{'SHORT_TITLE'} ) {
+ $self->{'SHORT_TITLE'} = $self->{'LONG_TITLE'} ;
+ }
+ $self->{'PLURIAL_TYPE_LABELS'} = { 'article' => $self->{'LANG'}->get('I18N_LANG_P_ARTICLE'),
+ 'inproceedings' => $self->{'LANG'}->get('I18N_LANG_P_INPROCEEDINGS'),
+ 'incollection' => $self->{'LANG'}->get('I18N_LANG_P_INCOLLECTION'),
+ 'book' => $self->{'LANG'}->get('I18N_LANG_P_BOOK'),
+ 'techreport' => $self->{'LANG'}->get('I18N_LANG_P_TECHREPORT'),
+ 'unpublished' => $self->{'LANG'}->get('I18N_LANG_P_UNPUBLISHED'),
+ 'booklet' => $self->{'LANG'}->get('I18N_LANG_P_BOOKLET'),
+ 'conference' => $self->{'LANG'}->get('I18N_LANG_P_PROCEEDINGS'),
+ 'proceedings' => $self->{'LANG'}->get('I18N_LANG_P_PROCEEDINGS'),
+ 'inbook' => $self->{'LANG'}->get('I18N_LANG_P_INBOOK'),
+ 'manual' => $self->{'LANG'}->get('I18N_LANG_P_MANUAL'),
+ 'mastersthesis' => $self->{'LANG'}->get('I18N_LANG_P_MASTERTHESIS'),
+ 'misc' => $self->{'LANG'}->get('I18N_LANG_P_MISC'),
+ 'phdthesis' => $self->{'LANG'}->get('I18N_LANG_P_PHDTHESIS'),
+ } ;
+ $self->{'SINGULAR_TYPE_LABELS'} = { 'article' => $self->{'LANG'}->get('I18N_LANG_S_ARTICLE'),
+ 'inproceedings' => $self->{'LANG'}->get('I18N_LANG_S_INPROCEEDINGS'),
+ 'incollection' => $self->{'LANG'}->get('I18N_LANG_S_INCOLLECTION'),
+ 'book' => $self->{'LANG'}->get('I18N_LANG_S_BOOK'),
+ 'techreport' => $self->{'LANG'}->get('I18N_LANG_S_TECHREPORT'),
+ 'unpublished' => $self->{'LANG'}->get('I18N_LANG_S_UNPUBLISHED'),
+ 'booklet' => $self->{'LANG'}->get('I18N_LANG_S_BOOKLET'),
+ 'conference' => $self->{'LANG'}->get('I18N_LANG_S_PROCEEDINGS'),
+ 'proceedings' => $self->{'LANG'}->get('I18N_LANG_S_PROCEEDINGS'),
+ 'inbook' => $self->{'LANG'}->get('I18N_LANG_S_INBOOK'),
+ 'manual' => $self->{'LANG'}->get('I18N_LANG_S_MANUAL'),
+ 'mastersthesis' => $self->{'LANG'}->get('I18N_LANG_S_MASTERTHESIS'),
+ 'misc' => $self->{'LANG'}->get('I18N_LANG_S_MISC'),
+ 'phdthesis' => $self->{'LANG'}->get('I18N_LANG_S_PHDTHESIS'),
+ } ;
+ $self->{'FORMATS'} = { 'name' => $self->{'LANG'}->get('I18N_LANG_FORMAT_NAME'),
+ 'names' => $self->{'LANG'}->get('I18N_LANG_FORMAT_NAMES'),
+ } ;
+
+ bless( $self, $class );
+
+ # Params
+ $self->{'GENERATOR_PARAMS'} = {} ;
+ if ( ( $_[6] ) && ( ! isemptyhash($_[6]) ) ) {
+ foreach my $param ( keys %{$_[6]} ) {
+ # Format the parameter's name
+ my $norm_param = lc($param) ;
+ $norm_param =~ s/_/-/g ;
+
+ # Get the current value and call the function to save it (eventually)
+ my $value = $self->last_param($_[6]->{"$param"} || '') ;
+ Bib2HTML::General::Error::syserr("unsupported generator parameter: ".lc("$norm_param"))
+ unless ($self->save_generator_parameter("$norm_param", $value));
+
+ # If this parameter was not saved, save it
+ $self->{'GENERATOR_PARAMS'}{"$norm_param"} = $value
+ unless ( exists $self->{'GENERATOR_PARAMS'}{"$norm_param"} ) ;
+
+ }
+ }
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Generation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * generate()
+
+Generates the HTML pages.
+You must NOT overwrite this method.
+
+=cut
+sub generate() : method {
+ my $self = shift ;
+ $self->pre_processing() ;
+ $self->do_processing() ;
+ $self->post_processing() ;
+}
+
+=pod
+
+=item * pre_processing()
+
+Pre_processing.
+
+=cut
+sub pre_processing() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ Bib2HTML::General::Verbose::three( "Doing the pre-processing...\n" ) ;
+ Bib2HTML::General::Verbose::verb( "\tReplace all <BIB2HTML>...\n", 4 ) ;
+ my $count = 0 ;
+ if ( ! isemptyhash( $self->{'CONTENT'}{'entries'} ) ) {
+ my @keys = keys %{$self->{'CONTENT'}{'entries'}} ;
+ foreach my $key ( @keys ) {
+
+ if ( ! isemptyhash( $self->{'CONTENT'}{'entries'}{$key}{'fields'} ) ) {
+
+ my @fields = keys %{$self->{'CONTENT'}{'entries'}{$key}{'fields'}} ;
+
+ foreach my $field ( @fields ) {
+ ( my $cnt,
+ $self->{'CONTENT'}{'entries'}{$key}{'fields'}{$field} ) =
+ $self->translate_bib2html_tags( $self->{'CONTENT'}{'entries'}{$key}{'fields'}{$field},
+ $key, $field, $rootdir ) ;
+ $count += $cnt ;
+ }
+
+ }
+
+ }
+ }
+
+ # Create the stream writer
+ my $writer;
+ if ($self->genparam('stdout')) {
+ $writer = Bib2HTML::Generator::StdOutWriter->new();
+ }
+ else {
+ $writer = Bib2HTML::Generator::FileWriter->new();
+ }
+ $self->set_stream_writer($writer);
+}
+
+=pod
+
+=item * create_output_directory()
+
+Create the output directory.
+
+=cut
+sub create_output_directory() : method {
+ my $self = shift;
+ my $writer = $self->get_stream_writer();
+ confess("no writer specified") unless ($writer);
+ $self->{'TARGET'} = $writer->create_output_directory($self->{'TARGET'},@{$self->{'TARGET_NOT_REMOVABLE'}});
+}
+
+=pod
+
+=item * set_unremovable_files(@)
+
+Force this generator to not remove the specified
+files when the output directory will be generated.
+
+=cut
+sub set_unremovable_files(@) : method {
+ my $self = shift;
+ @{$self->{'TARGET_NOT_REMOVABLE'}} = @_;
+}
+
+=pod
+
+=item * get_stream_writer()
+
+Replies the instance of the output stream writer.
+
+=cut
+sub get_stream_writer() : method {
+ my $self = shift ;
+ if (!$self->{'STREAM_WRITER'}) {
+ $self->{'STREAM_WRITER'} = new Bib2HTML::Generator::FileWriter->new();
+ }
+ return $self->{'STREAM_WRITER'};
+}
+
+=pod
+
+=item * set_stream_writer($)
+
+Set the instance of the output stream writer.
+Replies the old writer.
+Takes 1 arg:
+
+=over
+
+=item * writer (ref to Bib2HTML::Generator::Writer)
+
+is the instance of the writer.
+
+=back
+
+=cut
+sub set_stream_writer($) : method {
+ my $self = shift ;
+ my $writer = shift;
+ my $old_writer = $self->{'STREAM_WRITER'};
+ $self->{'STREAM_WRITER'} = $writer;
+ return $old_writer;
+}
+
+=pod
+
+=item * do_processing()
+
+Main processing.
+
+=cut
+sub do_processing() : method {
+ my $self = shift ;
+}
+
+=pod
+
+=item * post_processing()
+
+Post_processing.
+
+=cut
+sub post_processing() : method {
+ my $self = shift ;
+}
+
+=pod
+
+=item * translate_bib2html_tags()
+
+Replaces the Bib2HTML tags.
+Takes 4 args.
+
+=cut
+sub translate_bib2html_tags($$$$) : method {
+ my $self = shift ;
+ my $rootdir = $_[3] || confess( 'you must supply the root directory' );
+ my $text = $_[0] || '' ;
+ my $count = 0 ;
+ my $split = split_html_tags( $text ) ;
+ if ( defined( $split ) ) {
+ if ( isarray( $split ) ) {
+ $text = '' ;
+ my $inbib2html = undef ;
+ foreach my $case ( @{$split} ) {
+ if ( $case =~ /^<BIB2HTML\s*(.*)\s*>$/im ) {
+ $inbib2html = $self->html_extract_tag_params( $1 ) ;
+ }
+ elsif ( $case =~ /^<BIB2HTML\s*(.*)\s*\/>$/im ) {
+ $text .= $self->run_bib2html_post_action( $self->html_extract_tag_params( $1 ),
+ $_[1], $_[2], $rootdir ) ;
+ $count ++ ;
+ }
+ elsif ( $case =~ /^<\/BIB2HTML.*?>$/im ) {
+ if ( $inbib2html ) {
+ $text .= $self->run_bib2html_post_action( $inbib2html,
+ $_[1],
+ $_[2],
+ $rootdir ) ;
+ $count ++ ;
+ }
+ $inbib2html = undef ;
+ }
+ elsif ( ! defined( $inbib2html ) ) {
+ $text .= $case ;
+ }
+ }
+ }
+ }
+ return ( $count, $text ) ;
+}
+
+=pod
+
+=item * run_bib2html_post_action()
+
+Replies the text corresponding to the specified bib2html tag.
+Takes 4 args.
+
+=cut
+sub run_bib2html_post_action($$$$) : method {
+ my $self = shift ;
+ my $rootdir = $_[3] || confess( 'you must supply the root directory' );
+ my $currententry = $_[1] || confess( 'you must supply the current entry key' ) ;
+ my $currentfield = $_[2] || confess( 'you must supply the current field key' ) ;
+ if ( ( $_[0] ) && ( ! isemptyhash( $_[0] ) ) ) {
+ my $action = uc( $_[0]->{'action'} || '' ) ;
+
+ if ( $action eq 'CITE' ) {
+ my $label = $_[0]->{'label'} ;
+ my $key = $_[0]->{'key'} || '' ;
+ if ( $key ) {
+ my $bibtex = new Bib2HTML::Translator::BibTeXEntry() ;
+ if ( ! $label ) {
+ $label = $bibtex->citation_label( $key, $self->{'CONTENT'}{'entries'}{$key} ) ;
+ }
+ else {
+ $bibtex->save_citation_label( $key, $label ) ;
+ }
+ if ( exists $self->{'CONTENT'}{'entries'}{$key} ) {
+ my $filename = $self->filename('entry', $key ) ;
+
+ return $self->{'THEME'}->href( htmlcatfile($rootdir,$filename),
+ $label,
+ $self->browserframe('entry') ) ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "Can't found the entry key for a citation command inside the field '".$currentfield."'",
+ extract_file_from_location( $self->{'CONTENT'}{'entries'}{$currententry}{'location'} ),
+ extract_line_from_location( $self->{'CONTENT'}{'entries'}{$currententry}{'location'} ) ) ;
+ return "?" ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::warm( "Can't found the entry with the key '".$key."' for a citation command inside the field '".$currentfield."'",
+ extract_file_from_location( $self->{'CONTENT'}{'entries'}{$currententry}{'location'} ),
+ extract_line_from_location( $self->{'CONTENT'}{'entries'}{$currententry}{'location'} ) ) ;
+ return "?" ;
+ }
+ }
+
+ }
+ return '' ;
+}
+
+#------------------------------------------------------
+#
+# HTML buildings
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_all_authors()
+
+Replies the all authors from the specified list.
+
+=cut
+sub get_all_authors($) : method {
+ my $self = shift ;
+ my $parser = Bib2HTML::Translator::BibTeXName->new() ;
+ return $parser->splitnames( $_[0] ) ;
+}
+
+=pod
+
+=item * get_first_author()
+
+Replies the first author from the specified list.
+
+=cut
+sub get_first_author($) : method {
+ my $self = shift ;
+ my @authors = $self->get_all_authors( $_[0] ) ;
+ return $authors[0] ;
+}
+
+=pod
+
+=item * count_authors()
+
+Replies the number of authors inside the specified string
+
+=cut
+sub count_authors($) : method {
+ my $self = shift ;
+ my $parser = Bib2HTML::Translator::BibTeXName->new() ;
+ return $parser->countnames( $_[0] ) ;
+}
+
+=pod
+
+=item * get_entry_types()
+
+Replies an array of entry types
+
+=cut
+sub get_entry_types() : method {
+ my $self = shift ;
+ my @types = () ;
+ foreach my $entry (keys %{$self->{'CONTENT'}{'entries'}}) {
+ my $type = lc( $self->{'CONTENT'}{'entries'}{$entry}{'type'} ) ;
+ if ( ! strinarray($type,\@types) ) {
+ push( @types, $type ) ;
+ }
+ }
+ my @t = sortbyletters(@types);
+ return @t ;
+}
+
+=pod
+
+=item * get_entry_authors()
+
+Replies an array of entry authors
+
+=cut
+sub get_entry_authors() : method {
+ my $self = shift ;
+ if (%{$self->{'CACHE'}{'BUILT_ENTRY_AUTHOR_LIST'}}) {
+ return %{$self->{'CACHE'}{'BUILT_ENTRY_AUTHOR_LIST'}} ;
+ }
+ else {
+ my %authors = () ;
+ my $parser = Bib2HTML::Translator::BibTeXName->new() ;
+ my @entries = keys %{$self->{'CONTENT'}{'entries'}};
+ @entries = sortbyletters(@entries);
+ foreach my $entry (@entries) {
+ if ( $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'author'} ) {
+ my @auts = $self->get_all_authors($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'author'}) ;
+ foreach my $aut (@auts) {
+ if ( ! $aut->{'et al'} ) {
+ my $key = lc(remove_html_accents($parser->formatname( $aut, 'l f.' ))) ;
+ $key =~ s/[^a-zA-Z0-1]+//g ;
+ my $count = 0 ;
+ my $thekey = $key ;
+ while ( ( $count >= 0 ) && ( exists $authors{$thekey} ) ) {
+ if ( $parser->samenames($aut,$authors{$thekey}) ) {
+ $count = -1 ;
+ }
+ else {
+ $count ++ ;
+ $thekey = "${key}_${count}" ;
+ }
+ }
+ if ( $count >= 0 ) {
+ $authors{$thekey} = $aut ;
+ }
+ }
+ }
+ }
+ }
+ $self->{'CACHE'}{'BUILT_ENTRY_AUTHOR_LIST'} = \%authors ;
+ return %authors ;
+ }
+}
+
+=pod
+
+=item * get_all_entries_ayt()
+
+Replies an array of entries sorted by authors, year and title
+
+=cut
+sub get_all_entries_ayt() : method {
+ my $self = shift ;
+ my @keys = keys %{$self->{'CONTENT'}{'entries'}} ;
+ return ( sort {
+ my $result = &__compare_two_entries_ayt__($a,$b,$self) ;
+ return $result ;
+ } @keys ) ;
+}
+
+=pod
+
+=item * get_all_entries_yat()
+
+Replies an array of entries sorted by authors, year and title
+
+=cut
+sub get_all_entries_yat() : method {
+ my $self = shift ;
+ my @keys = keys %{$self->{'CONTENT'}{'entries'}} ;
+ return ( sort {
+ my $result = &__compare_two_entries_yat__($a,$b,$self) ;
+ return $result ;
+ } @keys ) ;
+}
+
+# Private function to compare two entries in the purpose
+# to sort the entries by author,year,title
+# WARNING: years have a decroissant order
+sub __compare_two_entries_ayt__($$$) {
+ confess( 'you must supply the left comparaison operand' ) unless $_[0] ;
+ confess( 'you must supply the right comparaison operand' ) unless $_[1] ;
+ my $self = $_[2] || confess( 'you must supply the generator object' ) ;
+ my $a1 = $self->get_first_author($self->__get_author_editor__($_[0],'') ) ;
+ my $a2 = $self->get_first_author($self->__get_author_editor__($_[1],'') ) ;
+
+ if ( (!$a1) && (!$a2) ) {
+ return 0 ;
+ }
+ elsif (!$a1) {
+ return 1 ;
+ }
+ elsif (!$a2) {
+ return -1 ;
+ }
+
+ my $y1 = $self->__get_year__( $_[0], 0 ) || 0 ;
+ my $y2 = $self->__get_year__( $_[1], 0 ) || 0 ;
+ my $t1 = $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'title'} || '' ;
+ my $t2 = $self->{'CONTENT'}{'entries'}{$_[1]}{'fields'}{'title'} || '' ;
+
+ if ( ( $a1->{'et al'} ) && ( $a2->{'et al'} ) ) {
+ return 0 ;
+ }
+ elsif ( $a1->{'et al'} ) {
+ return 1 ;
+ }
+ elsif ( $a1->{'et al'} ) {
+ return -1 ;
+ }
+ elsif ( $a1->{'last'} lt $a2->{'last'} ) {
+ return -1 ;
+ }
+ elsif ( $a1->{'last'} gt $a2->{'last'} ) {
+ return 1 ;
+ }
+ elsif ( $y1 < $y2 ) {
+ return 1 ;
+ }
+ elsif ( $y1 > $y2 ) {
+ return -1 ;
+ }
+ elsif ( $t1 lt $t2 ) {
+ return -1 ;
+ }
+ elsif ( $t1 gt $t2 ) {
+ return 1 ;
+ }
+ else {
+ return 0 ;
+ }
+}
+
+# Private function to compare two entries in the purpose
+# to sort the entries by year,author,title
+# WARNING: years have a decroissant order
+sub __compare_two_entries_yat__($$$) {
+ confess( 'you must supply the left comparaison operand' ) unless $_[0] ;
+ confess( 'you must supply the right comparaison operand' ) unless $_[1] ;
+ my $self = $_[2] || confess( 'you must supply the generator object' ) ;
+ my $a1 = $self->get_first_author($self->__get_author_editor__($_[0],'') ) ;
+ my $a2 = $self->get_first_author($self->__get_author_editor__($_[1],'') ) ;
+
+ if ( (!$a1) && (!$a2) ) {
+ return 0 ;
+ }
+ elsif (!$a1) {
+ return 1 ;
+ }
+ elsif (!$a2) {
+ return -1 ;
+ }
+
+ my $y1 = $self->__get_year__( $_[0], 0 ) || 0 ;
+ my $y2 = $self->__get_year__( $_[1], 0 ) || 0 ;
+ my $t1 = $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'title'} || '' ;
+ my $t2 = $self->{'CONTENT'}{'entries'}{$_[1]}{'fields'}{'title'} || '' ;
+ if ( $y1 < $y2 ) {
+ return 1 ;
+ }
+ elsif ( $y1 > $y2 ) {
+ return -1 ;
+ }
+ elsif ( ( $a1->{'et al'} ) && ( $a2->{'et al'} ) ) {
+ return 0 ;
+ }
+ elsif ( $a1->{'et al'} ) {
+ return 1 ;
+ }
+ elsif ( $a1->{'et al'} ) {
+ return -1 ;
+ }
+ elsif ( $a1->{'last'} lt $a2->{'last'} ) {
+ return -1 ;
+ }
+ elsif ( $a1->{'last'} gt $a2->{'last'} ) {
+ return 1 ;
+ }
+ elsif ( $t1 lt $t2 ) {
+ return -1 ;
+ }
+ elsif ( $t1 gt $t2 ) {
+ return 1 ;
+ }
+ else {
+ return 0 ;
+ }
+}
+
+# Private function to get the year of the specified entry
+sub __get_year__($$) {
+ my $self = shift ;
+ my $y = ( ( exists( $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'year'} ) ) &&
+ ( $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'year'} ) ) ?
+ tonumber($self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'year'}) : $_[1] ;
+ if ( ! defined( $y ) ) {
+ Bib2HTML::General::Error::warm( "the year field of '$_[0]' is not well-formatted: \"".
+ $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'year'}.
+ "\". It must be a number. Assume none.",
+ extract_file_from_location( $self->{'CONTENT'}{'entries'}{$_[0]}{'location'} ),
+ extract_line_from_location( $self->{'CONTENT'}{'entries'}{$_[0]}{'location'} ) ) ;
+ $y = $_[1] ;
+ }
+ return $y ;
+}
+
+# Private function to get the author of the specified entry
+sub __get_author_editor__($$) {
+ my $self = shift ;
+ my $a = ( ( exists( $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'author'} ) ) &&
+ ( $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'author'} ) ) ?
+ $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'author'} : $_[1] ;
+ if ( ! $a ) {
+ $a = ( ( exists( $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'editor'} ) ) &&
+ ( $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'editor'} ) ) ?
+ $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'editor'} : $_[1] ;
+ }
+ if ( ! defined( $a ) ) {
+ Bib2HTML::General::Error::warm( "the author field of '$_[0]' is not well-formatted: \"".
+ $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'author'}.
+ "\". Assume none.",
+ extract_file_from_location( $self->{'CONTENT'}{'entries'}{$_[0]}{'location'} ),
+ extract_line_from_location( $self->{'CONTENT'}{'entries'}{$_[0]}{'location'} ) ) ;
+ $a = $_[1] ;
+ }
+ return $a ;
+}
+
+#------------------------------------------------------
+#
+# Information
+#
+#------------------------------------------------------
+
+=pod
+
+=item * display_supported_generators()
+
+Display the list of supported generators.
+Takes 2 args:
+
+=over
+
+=item * perldir (string)
+
+is the path to the directory where the Perl packages
+are stored.
+
+=item * default (string)
+
+is the name of the default generator
+
+=back
+
+=cut
+sub display_supported_generators($$) {
+ my $path = $_[0] || confess( 'you must specify the pm path' ) ;
+ my $default = $_[1] || '' ;
+ my @pack = split /\:\:/, __PACKAGE__ ;
+ pop @pack ;
+ @pack = ( File::Spec->splitdir($path), @pack ) ;
+ my $glob = File::Spec->catfile(@pack, '*');
+ $glob =~ s/ /\\ /g;
+ foreach my $file ( glob($glob) ) {
+ my $name = basename($file) ;
+ if ( $name =~ /^(.+)Gen\.pm$/ ) {
+ $name = $1 ;
+ print join( '',
+ "$name",
+ ( $default && ( $default eq $name ) ) ?
+ " (default)" : "",
+ "\n" ) ;
+ }
+ }
+}
+
+=pod
+
+=item * display_supported_languages()
+
+Display the list of supported languages.
+Takes 2 args:
+
+=over
+
+=item * perldir (string)
+
+is the path to the directory where the Perl packages
+are stored.
+
+=item * default (string)
+
+is the name of the default language
+
+=back
+
+=cut
+sub display_supported_languages($$) {
+ Bib2HTML::Generator::LangManager::display_supported_languages($_[0],$_[1]);
+}
+
+=pod
+
+=item * display_supported_themes()
+
+Display the list of supported themes.
+Takes 2 args:
+
+=over
+
+=item * perldir (string)
+
+is the path to the directory where the Perl packages
+are stored.
+
+=item * default (string)
+
+is the name of the default theme
+
+=back
+
+=cut
+sub display_supported_themes($$) {
+ my $path = $_[0] || confess( 'you must specify the pm path' ) ;
+ my $default = $_[1] || '' ;
+ my @pack = split /\:\:/, __PACKAGE__ ;
+ pop @pack ;
+ push @pack, 'Theme' ;
+ @pack = ( File::Spec->splitdir($path), @pack ) ;
+ my $glob = File::Spec->catfile(@pack, '*');
+ $glob =~ s/ /\\ /g;
+ foreach my $file ( glob($glob) ) {
+ my $name = basename($file) ;
+ if ( $name =~ /^(.+)\.pm$/ ) {
+ $name = $1 ;
+ print join( '',
+ "$name",
+ ( $default && ( $default eq $name ) ) ?
+ " (default)" : "",
+ "\n" ) ;
+ }
+ }
+}
+
+=pod
+
+=item * save_generator_parameter()
+
+Replies if the specified generator parameter was supported.
+This function was called each time a generator parameter was
+given to this generator. By default, simply updatethe
+given parameter value (second parameter).
+You could do some stuff before
+saving (splitting...). Replies false is the parameter was
+not recognized. Don't forget to call inherited functions.
+Takes 2 args:
+
+=over
+
+=item * param_name (string)
+
+is the name of the parameter.
+
+=item * param_value (byref string)
+
+is the value of the parameter.
+
+=back
+
+=cut
+sub save_generator_parameter($$) {
+ my $self = shift ;
+ if ( $_[0] eq 'stdout' ) {
+ $_[1] = 1 ;
+ return 1 ;
+ }
+ return undef ;
+}
+
+=pod
+
+=item * display_supported_generator_params()
+
+Display the list of supported generator parameters.
+Child classes must override this method.
+
+=cut
+sub display_supported_generator_params() {
+ my $self = shift ;
+ print "supported generator parameters:\n" ;
+
+ $self->show_supported_param('stdout',
+ 'If specified, the generated contents will be print on to the standard output.' );
+
+}
+
+=pod
+
+=item * show_supported_param()
+
+Display the help about one generator parameter.
+Takes 3 args:
+
+=over
+
+=item * name (string)
+
+is the name of the parameter
+
+=item * comment (string)
+
+is the comment for the parameter
+
+=item * type (optional string)
+
+is the type of the value that will be affected to
+the parameter. If not present, no value needed.
+
+=back
+
+=cut
+sub show_supported_param($$;$) {
+ my $self = shift ;
+ print " ".($_[0]||'?') ;
+ if ( $_[2] ) {
+ print " = ".$_[2] ;
+ }
+ print "\n" ;
+ my $t = splittocolumn_base($_[1]||'',
+ 55,
+ "\t\t") ;
+ print $t ;
+ if ( $t !~ /\n\r$/ ) {
+ print "\n" ;
+ }
+}
+
+=pod
+
+=item * merge_params()
+
+Merges the specified parameter value with the given join.
+Takes 2 args:
+
+=over
+
+=item * join (string)
+
+=item * value (mixed)
+
+=back
+
+=cut
+sub merge_params($) {
+ my $self = shift ;
+ return join($_[0],@{$_[1]})
+ if ( isarray($_[1]) ) ;
+ return $_[1] ;
+}
+
+=item * last_param()
+
+Replies the last occurrence of a generator parameter value.
+Takes 1 args:
+
+=over
+
+=item * value (mixed)
+
+=back
+
+=cut
+sub last_param {
+ my $self = shift ;
+ return $_[0]->[$#{$_[0]}]
+ if ( isarray($_[0]) ) ;
+ return $_[0] ;
+}
+
+=item * first_param()
+
+Replies the first occurrence of a generator parameter value.
+Takes 1 args:
+
+=over
+
+=item * value (mixed)
+
+=back
+
+=cut
+sub first_param {
+ my $self = shift ;
+ return $_[0]->[0]
+ if ( isarray($_[0]) ) ;
+ return $_[0] ;
+}
+
+#------------------------------------------------------
+#
+# Formatting backend
+#
+#------------------------------------------------------
+
+=pod
+
+=item * formatnames_url_backend()
+
+This method is called each time the BibTeXNames module
+must format an author's name with a URL.
+Takes 2 args:
+
+=over
+
+=item * author's data (hash)
+
+=item * label (string)
+
+=item * rootdir (string)
+
+=back
+
+=cut
+sub formatnames_url_backend($$$) {
+ my $self = shift ;
+ return $_[1] || '' ;
+}
+
+#------------------------------------------------------
+#
+# Utility
+#
+#------------------------------------------------------
+
+
+=pod
+
+=item * copythisfile()
+
+Copy a file.
+Takes 2 args:
+
+=over
+
+=item * source (string)
+
+=item * target (string)
+
+=back
+
+=cut
+sub copythisfile($$) {
+ my $self = shift ;
+ my $source = $_[0] || '' ;
+ my $target = $_[1] || '' ;
+
+ Bib2HTML::General::Error::syserr( "you must give a source file to copy\n" )
+ unless ( $source ) ;
+ Bib2HTML::General::Error::syserr( "you must give a target file to copy\n" )
+ unless ( $target ) ;
+
+ my $sbase = basename($source) ;
+ my $sdir = dirname($source) ;
+ my $tbase = basename($target) ;
+ my $tdir = dirname($target) ;
+
+ Bib2HTML::General::Verbose::two( "Copying $sbase..." ) ;
+ Bib2HTML::General::Verbose::three( "\tfrom $sdir" ) ;
+ if ( $tbase ne $sbase ) {
+ Bib2HTML::General::Verbose::three( "\tto $target" ) ;
+ }
+ else {
+ Bib2HTML::General::Verbose::three( "\tto $tdir" ) ;
+ }
+
+ filecopy( "$source",
+ "$target" )
+ or Bib2HTML::General::Error::syswarm( "$source: $!\n" );
+
+ return 1 ;
+}
+
+=pod
+
+=item * isgenparam()
+
+Replies if the specified string corresponds to a
+generator parameter.
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+=back
+
+=cut
+sub isgenparam($) {
+ my $self = shift ;
+ return ( ( $_[0] ) &&
+ ( exists $self->{'GENERATOR_PARAMS'}{lc($_[0])} ) ) ;
+}
+
+=pod
+
+=item * genparam()
+
+Replies the specified generator parameter value.
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+=back
+
+=cut
+sub genparam($) {
+ my $self = shift ;
+ if ( ( $_[0] ) &&
+ ( exists $self->{'GENERATOR_PARAMS'}{lc($_[0])} ) &&
+ ( $self->{'GENERATOR_PARAMS'}{lc($_[0])} ) ) {
+ return $self->{'GENERATOR_PARAMS'}{lc($_[0])} ;
+ }
+ else {
+ return undef ;
+ }
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/DomainGen.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/DomainGen.pm
new file mode 100644
index 0000000000..e2abf52174
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/DomainGen.pm
@@ -0,0 +1,564 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::DomainGen - An HTML generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::DomainGen ;
+
+my $gen = Bib2HTML::Generator::DomainGen->new( data, output, info, titles,
+ lang, theme ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::DomainGen is a Perl module, which permits to
+generate HTML pages for the BibTeX database.
+In addition to the features of Bib2HTML::Generator::ExtendedGen, this
+generator supports the following bibtex fields:
+
+=over
+
+=item * domain
+
+is a string that identify the first domain in which
+the document was located.
+
+=item * nddomain
+
+is a string that identify the second domain in which
+the document was located.
+
+=item * rddomain
+
+is a string that identify the third domain in which
+the document was located.
+
+=item * domains
+
+is column-separated list of domains in which
+the document was located.
+
+=back
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::DomainGen;
+
+ my $gen = Bib2HTML::Generator::DomainGen->new( { }, "./bib",
+ { 'BIB2HTML_VERSION' => "0.1",
+ },
+ { 'SHORT' => "This is the title",
+ 'LONG' => "This is the title",
+ },
+ "English",
+ "Simple"
+ ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * content (hash)
+
+see ExtendedGen help.
+
+=item * output (string)
+
+see ExtendedGen help.
+
+=item * bib2html_data (hash)
+
+see ExtendedGen help.
+
+=item * titles (hash)
+
+see ExtendedGen help.
+
+=item * lang (string)
+
+see ExtendedGen help.
+
+=item * theme (string)
+
+see ExtendedGen help.
+
+=item * show_bibtex (boolean)
+
+See ExtendedGen.pm
+
+=item * params (optional array)
+
+see ExtendedGen help.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in DomainGen.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::DomainGen;
+
+@ISA = ('Bib2HTML::Generator::ExtendedGen');
+@EXPORT = qw( );
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use Bib2HTML::Generator::ExtendedGen ;
+use Bib2HTML::General::HTML ;
+use Bib2HTML::General::Misc ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of this generator
+my $VERSION = "4.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$$$;$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+
+ my @langs = ();
+ if (isarray($_[4])) {
+ foreach my $l (@{$_[4]}) {
+ if ($l !~ /_[a-zA-Z0-9]+Gen$/) {
+ push @langs, $l."_DomainGen";
+ }
+ push @langs, $l;
+ }
+ }
+ else {
+ @langs = ( $_[4] );
+ if ($_[4] !~ /_[a-zA-Z0-9]+Gen$/) {
+ unshift @langs, $_[4]."_DomainGen";
+ }
+ }
+
+ $_[4] = \@langs;
+
+ my $self = $class->SUPER::new(@_) ;
+
+ $self->{'FILENAMES'}{'domain-tree'} = 'domain-tree.html';
+
+ bless( $self, $class );
+
+ $self->addNavigationButton($self->filename('domain-tree'),
+ 'I18N_LANG_DOMAINS');
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Generation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * do_processing()
+
+Main processing.
+
+=cut
+sub do_processing() : method {
+ my $self = shift ;
+
+ # Call inherited generation method
+ $self->SUPER::do_processing() ;
+
+ # Generates the domain pages
+ $self->generate_domain_tree() ;
+}
+
+=pod
+
+=item * generate_domain_tree()
+
+Generates domain-tree.html
+
+=cut
+sub generate_domain_tree() : method {
+ my $self = shift ;
+ my $filename = $self->filename('domain-tree');
+ return unless ($self->is_restricted_file("$filename"));
+ my $rootdir = "." ;
+ $filename = htmlcatfile($rootdir,$filename) ;
+ my $bar = $self->{'THEME'}->get_navigation_bar( $filename,
+ { 'tree' => 0,
+ 'index' => $self->{'__INDEX_GENERATED__'},
+ 'userdef' => $self->getNavigationButtons('I18N_LANG_DOMAINS'),
+ },
+ $rootdir ) ;
+ my $content = join('',
+ $bar,
+ $self->{'THEME'}->partseparator(),
+ $self->generate_domain_tree_content($rootdir),
+ $self->{'THEME'}->partseparator(),
+ $bar,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->get_copyright($rootdir) ) ;
+
+ $self->{'THEME'}->create_html_body_page( $filename,
+ $content,
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'html') ;
+}
+
+#------------------------------------------------------
+#
+# Overwriteable Generation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * generate_domain_tree_content()
+
+Generates and replies the content of domain-tree.html.
+Takes 1 arg:
+
+=over
+
+=item * rootdir (string)
+
+=back
+
+=cut
+sub generate_domain_tree_content($) : method {
+ my $self = shift ;
+ my $rootdir = shift ;
+ my @entries = $self->get_all_entries_ayt() ;
+ my $content = $self->{'THEME'}->title($self->{'LANG'}->get('I18N_LANG_DOMAIN_TREE')) ;
+
+ # Build the tree
+ my %tree = () ;
+ foreach my $entry (@entries) {
+
+ # Search the domains of the entry
+ my @domains = $self->get_all_domains_for($entry) ;
+
+ if ( @domains ) {
+
+ # Generate the entry data
+ my $entrylabel = $self->get_short_entry_description("$entry",$rootdir) ;
+
+ # Register the entry inside the tree
+ foreach my $domain (@domains) {
+ my @parts = htmlsplit($domain) ;
+ my $t = \%tree ;
+
+ # Creates categories inside the tree
+ # $t is a reference to the current leaf
+ foreach my $part (@parts) {
+ $part =~ s/[ \t\n\r]+/&nbsp;/g ;
+ $part = $self->{'THEME'}->strong("$part");
+ $t->{"$part"} = {}
+ unless ( exists $t->{"$part"} ) ;
+ $t = $t->{"$part"} ;
+ }
+
+ # Adds the entry into the new category
+ $t->{"$entrylabel"} = {} ;
+ }
+ }
+ }
+
+ # Generate the HTML representation of the tree
+ $content .= $self->{'THEME'}->get_tree( \%tree, $rootdir, $self->{'LANG'}->get('I18N_LANG_KEYWORDS') ) ;
+
+ return $content ;
+}
+
+#------------------------------------------------------
+#
+# Domain API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_all_domain_for()
+
+Replies the array of the domains for the specified entry
+Takes 1 arg:
+
+=over
+
+=item * entry (string)
+
+is the identifier of the entry.
+
+=back
+
+=cut
+sub get_all_domains_for($) : method {
+ my $self = shift ;
+ my @domains = () ;
+
+ if ( $self->{'CONTENT'}{'entries'}{$_[0]} ) {
+ my $domain1 = $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'domain'} || '' ;
+ my $domain2 = $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'nddomain'} || '' ;
+ my $domain3 = $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'rddomain'} || '' ;
+ my $alldomains = $self->{'CONTENT'}{'entries'}{$_[0]}{'fields'}{'domains'} || '' ;
+
+ if ( $alldomains ) {
+ @domains = split(':', $alldomains) ;
+ }
+ if ( ($domain1) && (!strinarray("$domain1",\@domains)) ) {
+ unshift @domains, "$domain1" ;
+ }
+ if ( ($domain2) && (!strinarray("$domain2",\@domains)) ) {
+ unshift @domains, "$domain2" ;
+ }
+ if ( ($domain3) && (!strinarray("$domain3",\@domains)) ) {
+ unshift @domains, "$domain3" ;
+ }
+
+ }
+ return @domains ;
+}
+
+=pod
+
+=item * get_all_documents_for_domain()
+
+Replies the array of the documents keys which
+are in the specified domain.
+Takes 1 arg:
+
+=over
+
+=item * domain (string)
+
+is the identifier of the domain.
+
+=back
+
+=cut
+sub get_all_documents_for_domain($) : method {
+ my $self = shift ;
+ my @documents = () ;
+
+ foreach my $entry (keys %{$self->{'CONTENT'}{'entries'}}) {
+
+ my $domain1 = $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'domain'} || '' ;
+ my $domain2 = $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'nddomain'} || '' ;
+ my $domain3 = $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'rddomain'} || '' ;
+ my $alldomains = $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'domains'} || '' ;
+
+ my @domains = () ;
+ if ( $alldomains ) {
+ @domains = split(':', $alldomains) ;
+ }
+ if ( ( @domains ) && ( strinarray($_[0], \@domains) ) ) {
+ push @documents, $entry ;
+ }
+ elsif ( ($domain1) && ($domain1 eq $_[0]) ) {
+ push @documents, $entry ;
+ }
+ elsif ( ($domain2) && ($domain2 eq $_[0]) ) {
+ push @documents, $entry ;
+ }
+ elsif ( ($domain3) && ($domain3 eq $_[0]) ) {
+ push @documents, $entry ;
+ }
+
+ }
+ return @documents ;
+}
+
+=pod
+
+=item * get_short_entry_description()
+
+Replies a short entry description.
+Takes 2 args:
+
+=over
+
+=item * entry (string)
+
+is the entry key.
+
+=item * rootdir (string)
+
+is the root directory.
+
+=back
+
+=cut
+sub get_short_entry_description($$) : method {
+ my $self = shift ;
+ my $entry = $_[0] || confess('you must supply the entry key') ;
+ my $rootdir = $_[1] || confess('you must supply the root directory') ;
+ my $biblabeller = Bib2HTML::Translator::BibTeXEntry->new() ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+
+ # Generate the entry data
+ my $filename = $self->filename('entry',$entry) ;
+ my $name = $translator->formatnames( $self->__get_author_editor__($entry,''),
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'} ) ;
+ $name =~ s/[ \t\n\r]+/&nbsp;/g ;
+ my $title = $self->{'THEME'}->entry_title( extract_first_words( $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'title'},
+ 40 ) ) ;
+ $title =~ s/[ \t\n\r]+/&nbsp;/g ;
+ my $year = $self->__get_year__( $entry, '' ) ;
+ my $entrylabel = join( '',
+ "[",
+ $self->{'THEME'}->href( htmlcatfile($rootdir,$filename),
+ $biblabeller->citation_label($entry,$self->{'CONTENT'}{'entries'}{$entry}),
+ $self->browserframe('overview-summary') ),
+ "]&nbsp;",
+ $name,
+ ",&nbsp;",
+ $title,
+ ( $year ? "&nbsp;(". $year .")" : '' )
+ ) ;
+
+ return $entrylabel ;
+}
+
+#------------------------------------------------------
+#
+# Entry Generation
+#
+#------------------------------------------------------
+
+=pod
+
+=item * generate_entry_content()
+
+Generates the HTML entry-???.html
+Overwrite this method.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the BibTeX key of the current bibliographical entry
+
+=item * entry (hash ref)
+
+is the description of the current bibliographical entry
+
+=item * url (string)
+
+is the URL of the current entry
+
+=item * rootdir (string)
+
+is the path to the root.
+
+=item * entry_title (ref string)
+
+must be filled with the title of the entry.
+
+=item * user_fields (array)
+
+is the field predefined by the user. It must be an
+array of associative arrays (one for each generable field).
+
+=cut
+sub generate_entry_content($$$$$) {
+ my $self = shift ;
+ my @content = @{$_[5]} ;
+ my ($key,$entry,$url,$rootdir) = ($_[0],$_[1],$_[2],$_[3]) ;
+ my ($title,$aut_ed_flg,$note_req) = ($_[4],$_[6],$_[7]) ;
+
+ # Call the inherited method
+ my $result = $self->SUPER::generate_entry_content($key,$entry,$url,$rootdir,$title,\@content,$aut_ed_flg,$note_req) ;
+
+ # Generates the domains of the entry
+ my @domains = $self->get_all_domains_for("$key");
+
+ if ( @domains ) {
+
+ my $content = '' ;
+ my %tree = () ;
+
+ foreach my $domain (@domains) {
+ my @entries = $self->get_all_documents_for_domain("$domain") ;
+
+ $domain =~ s/[ \t\n\r]+/&nbsp;/g ;
+ $domain = $self->{'THEME'}->strong("$domain");
+
+ # Adds the entry into the new category
+ foreach my $entry (@entries) {
+ my $label = $self->get_short_entry_description($entry,$rootdir);
+ $tree{"$domain"}{"$label"} = {} ;
+ }
+ }
+
+ $content = $self->{'THEME'}->get_tree( \%tree, $rootdir ) ;
+ push @{$result}, $self->{'THEME'}->build_onecolumn_array( $self->{'LANG'}->get('I18N_LANG_ARTICLESINSAMEDOMAINS'),
+ [ $content ] ) ;
+
+ }
+
+ return $result ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/ExtendedGen.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/ExtendedGen.pm
new file mode 100644
index 0000000000..8eafff69aa
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/ExtendedGen.pm
@@ -0,0 +1,714 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::ExtendedGen - An HTML generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::ExtendedGen ;
+
+my $gen = Bib2HTML::Generator::ExtendedGen->new( data, output, info, titles,
+ lang, theme ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::ExtendedGen is a Perl module, which permits to
+generate HTML pages for the BibTeX database.
+In addition to the features of Bib2HTML::Generator::HTMLGen, this
+generator supports the following bibtex fields:
+
+=over
+
+=item * isbn
+
+is the ISBN number.
+
+=item * issn
+
+is the ISSN number.
+
+=item * readers
+
+is the list of people who read this entry. The format
+is similar as for the author field.
+
+=item * abstract
+
+is the abstract of the document.
+
+=item * keywords
+
+are the keywords associated to the document.
+
+=item * localfile
+
+is the local path to a electronic version of
+the document. This document could be dowload
+from the generated webpage.
+
+=back
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::ExtendedGen;
+
+ my $gen = Bib2HTML::Generator::ExtendedGen->new( { }, "./bib",
+ { 'BIB2HTML_VERSION' => "0.1",
+ },
+ { 'SHORT' => "This is the title",
+ 'LONG' => "This is the title",
+ },
+ "English",
+ "Simple"
+ ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * content (hash)
+
+See HTMLGen.pm.
+
+=item * output (string)
+
+See HTMLGen.pm.
+
+=item * bib2html_data (hash)
+
+See HTMLGen.pm.
+
+=item * titles (hash)
+
+See HTMLGen.pm.
+
+=item * lang (string)
+
+See HTMLGen.pm.
+
+=item * theme (string)
+
+See HTMLGen.pm.
+
+=item * show_bibtex (boolean)
+
+See HTMLGen.pm
+
+=item * params (optional array)
+
+is the set of parameters passed to the generator.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in ExtendedGen.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::ExtendedGen;
+
+@ISA = ('Bib2HTML::Generator::HTMLGen');
+@EXPORT = qw( );
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use File::Basename ;
+
+use Bib2HTML::Generator::HTMLGen ;
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::HTML ;
+use Bib2HTML::General::Verbose ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of this generator
+my $VERSION = "5.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$$$;$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+
+ my @langs = ();
+ if (isarray($_[4])) {
+ foreach my $l (@{$_[4]}) {
+ if ($l !~ /_[a-zA-Z0-9]+Gen$/) {
+ push @langs, $l."_ExtendedGen";
+ }
+ push @langs, $l;
+ }
+ }
+ else {
+ @langs = ( $_[4] );
+ if ($_[4] !~ /_[a-zA-Z0-9]+Gen$/) {
+ unshift @langs, $_[4]."_ExtendedGen";
+ }
+ }
+
+ $_[4] = \@langs;
+
+ my $self = $class->SUPER::new(@_) ;
+ $self->{'EXTEND_FILES_TO_COPY'} = [] ;
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Background tasks
+#
+#------------------------------------------------------
+
+
+=pod
+
+=item * pre_processing()
+
+Pre_processing.
+
+=cut
+sub pre_processing() : method {
+ my $self = shift ;
+
+ # Call inherited copying method
+ $self->SUPER::pre_processing() ;
+
+ foreach my $key (keys %{$self->{'CONTENT'}{'entries'}}) {
+ my $entry = $self->{'CONTENT'}{'entries'}{"$key"};
+ if ((exists $entry->{'fields'}{'pdf'})&&
+ (!exists $entry->{'fields'}{'localfile'})) {
+ $self->addLocalFileFromPDF($key,$entry->{'fields'}{'pdf'}, $entry->{'fields'});
+ }
+ }
+}
+
+sub addLocalFileFromPDF($$$) {
+ my $self = shift;
+ my $key = shift;
+ my $url = shift;
+
+ my $filename = undef;
+
+ if ( $url =~ /^file:\s*(.*?)\s*$/i) {
+ $filename = "$1";
+ }
+ elsif ( ( $url !~ /^http:/i ) &&
+ ( $url !~ /^ftp:/i ) &&
+ ( $url !~ /^https:/i ) &&
+ ( $url !~ /^gopher:/i ) &&
+ ( $url !~ /^mailto:/i ) ) {
+ $filename = "$url" ;
+ }
+
+ if ($filename) {
+ Bib2HTML::General::Verbose::one ("The 'pdf' field of $key was replaced by the 'localfile' field.");
+ $_[0]->{'localfile'} = "$filename";
+ delete $_[0]->{'pdf'};
+ }
+}
+
+=pod
+
+=item * copy_files()
+
+Overwrite this method.
+
+=cut
+sub copy_files() : method {
+ my $self = shift ;
+
+ # Call inherited copying method
+ $self->SUPER::copy_files() ;
+
+ # Copy the Extended's files
+ my @source = File::Spec->splitdir($self->{'BIB2HTML'}{'PERLSCRIPTDIR'}) ;
+ @source = ( @source, split(/\:\:/, __PACKAGE__) ) ;
+ pop @source ;
+
+ # Copy icons
+ $self->copythisfile( File::Spec->catfile(@source,"drive.png"),
+ File::Spec->catfile($self->{'TARGET'},"drive.png") ) ;
+
+ # Copy registered electronic documents
+ foreach my $file (@{$self->{'EXTEND_FILES_TO_COPY'}}) {
+ if ($self->is_restricted_file($file->{'target'})) {
+ if ( ! mkdir_rec( dirname( $file->{'target'} ) ) ) {
+ Bib2HTML::General::Error::syswarm( $file->{'target'}.": $!\n" );
+ }
+ elsif ( ! $self->copythisfile( $file->{'source'}, $file->{'target'} ) ) {
+ Bib2HTML::General::Error::syswarm( $file->{'source'}.": $!\n" );
+ }
+ }
+ }
+}
+
+=pod
+
+=item * register_file_to_copy()
+
+Register a file which must be copied.
+Takes 2 args:
+
+=over
+
+=item * source (string)
+
+=item * target (string)
+
+=back
+
+=cut
+sub register_file_to_copy($$) : method {
+ my $self = shift;
+ push @{$self->{'EXTEND_FILES_TO_COPY'}},
+ { 'source' => $_[0],
+ 'target' => $_[1],
+ } ;
+}
+
+#------------------------------------------------------
+#
+# Entry Generation
+#
+#------------------------------------------------------
+
+=pod
+
+=item * generate_entry_content()
+
+Generates the HTML entry-???.html
+Overwrite this method.
+Takes 5 args:
+
+=over
+
+=item * key (string)
+
+is the BibTeX key of the current bibliographical entry
+
+=item * entry (hash ref)
+
+is the description of the current bibliographical entry
+
+=item * url (string)
+
+is the URL of the current entry
+
+=item * rootdir (string)
+
+is the path to the root.
+
+=item * entry_title (ref string)
+
+must be filled with the title of the entry.
+
+=item * user_fields (array)
+
+is the field predefined by the user. It must be an
+array of associative arrays (one for each generable field).
+
+=cut
+sub generate_entry_content($$$$$) {
+ my $self = shift ;
+ my @content = @{$_[5]} ;
+ my ($key,$entry,$url,$rootdir) = ($_[0],$_[1],$_[2],$_[3]) ;
+ my ($title,$aut_ed_flg,$note_req) = ($_[4],$_[6],$_[7]) ;
+
+ #
+ # Prepare the additional fields which are supported by
+ # this generator.
+ # There new fields must be displayed inside the
+ # first generated array of attributes.
+ #
+ # ISBN
+ if ( exists $entry->{'fields'}{'isbn'} ) {
+ push @content, { 'name' => $self->{'LANG'}->get('I18N_LANG_FIELD_ISBN'),
+ 'explanation' => $entry->{'fields'}{'isbn'} || "-",
+ } ;
+ }
+ # ISSN
+ if ( exists $entry->{'fields'}{'issn'} ) {
+ push @content, { 'name' => $self->{'LANG'}->get('I18N_LANG_FIELD_ISSN'),
+ 'explanation' => $entry->{'fields'}{'issn'} || "-",
+ } ;
+ }
+ # URL
+ if ( exists $entry->{'fields'}{'url'} ) {
+ my $url = $entry->{'fields'}{'url'} ;
+ if ( $url ) {
+ $url =~ s/\\(.)/$1/g unless ($self->isgenparam('backslash'));
+ if ( ( $url !~ /^http:/i ) &&
+ ( $url !~ /^ftp:/i ) &&
+ ( $url !~ /^file:/i ) &&
+ ( $url !~ /^https:/i ) &&
+ ( $url !~ /^gopher:/i ) &&
+ ( $url !~ /^mailto:/i ) ) {
+ $url = "http://".$url ;
+ }
+ }
+ push @content, { 'name' => $self->{'LANG'}->get('I18N_LANG_FIELD_URL'),
+ 'explanation' => ( $url ) ?
+ $self->{'THEME'}->href( $url,
+ $url,
+ "_top" ) : "-",
+ } ;
+ }
+ # ADSURL - ASTROPHYSICS REFERENCE CITATION LIBRARY
+ if ( exists $entry->{'fields'}{'adsurl'} ) {
+ my $url = $entry->{'fields'}{'adsurl'} ;
+ if ( $url ) {
+ $url =~ s/\\(.)/$1/g unless ($self->isgenparam('backslash'));
+ if ( ( $url !~ /^http:/i ) &&
+ ( $url !~ /^ftp:/i ) &&
+ ( $url !~ /^file:/i ) &&
+ ( $url !~ /^https:/i ) &&
+ ( $url !~ /^gopher:/i ) &&
+ ( $url !~ /^mailto:/i ) ) {
+ $url = "http://".$url ;
+ }
+ }
+ push @content, { 'name' => $self->{'LANG'}->get('I18N_LANG_FIELD_ADSURL'),
+ 'explanation' => ( $url ) ?
+ $self->{'THEME'}->href( $url,
+ $url,
+ "_top" ) : "-",
+ } ;
+ }
+ # DOI - ACM URL
+ if ( exists $entry->{'fields'}{'doi'} ) {
+ my $url = $entry->{'fields'}{'doi'} ;
+ if ( $url ) {
+ $url =~ s/\\(.)/$1/g unless ($self->isgenparam('backslash'));
+ if ( ( $url !~ /^http:/i ) &&
+ ( $url !~ /^ftp:/i ) &&
+ ( $url !~ /^file:/i ) &&
+ ( $url !~ /^https:/i ) &&
+ ( $url !~ /^gopher:/i ) &&
+ ( $url !~ /^mailto:/i ) ) {
+ $url = "http://".$url ;
+ }
+ }
+ push @content, { 'name' => $self->{'LANG'}->get('I18N_LANG_FIELD_DOI'),
+ 'explanation' => ( $url ) ?
+ $self->{'THEME'}->href( $url,
+ $url,
+ "_top" ) : "-",
+ } ;
+ }
+ # PDF file
+ if ( exists $entry->{'fields'}{'pdf'} ) {
+ my $pdf = $entry->{'fields'}{'pdf'} ;
+ if ( $pdf ) {
+ $pdf =~ s/\\(.)/$1/g unless ($self->isgenparam('backslash'));
+ if ( ( $pdf =~ /^http:/i ) ||
+ ( $pdf =~ /^ftp:/i ) ||
+ ( $pdf =~ /^file:/i ) ||
+ ( $pdf =~ /^https:/i ) ||
+ ( $pdf =~ /^gopher:/i ) ||
+ ( $pdf =~ /^mailto:/i ) ) {
+ $pdf = $self->{'THEME'}->href($pdf,
+ get_html_entities($pdf),
+ "_top") ;
+ }
+ }
+ push @content, { 'name' => $self->{'LANG'}->get('I18N_LANG_FIELD_PDFFILE'),
+ 'explanation' => ( $pdf ) ? "$pdf" : "-",
+ } ;
+ }
+ # Readers' names
+ if ( exists $entry->{'fields'}{'readers'} ) {
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ push @content, { 'name' => $self->{'LANG'}->get('I18N_LANG_FIELD_READERS'),
+ 'explanation' => $translator->formatnames($entry->{'fields'}{'readers'},
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'},
+ -1) || "-",
+ } ;
+ }
+
+ #
+ # Call the inherited generating method
+ # which permits to create the first array
+ # of attributes
+ #
+ my $result = $self->SUPER::generate_entry_content($key,$entry,$url,$rootdir,$title,\@content,$aut_ed_flg,$note_req) ;
+
+ my $sliceindex = 2 ;
+
+ #
+ # Generates additional information which are
+ # specified to this extended generator
+ #
+ # Box for abstract and keywords
+ if ( ( exists $entry->{'fields'}{'abstract'} ) ||
+ ( exists $entry->{'fields'}{'keywords'} ) ) {
+
+ my ($abstract,$title) = ('','') ;
+ if ( exists $entry->{'fields'}{'abstract'} ) {
+ $title = $self->{'LANG'}->get('I18N_LANG_FIELD_ABSTRACT') ;
+ $abstract = $entry->{'fields'}{'abstract'} ;
+ }
+ if ( exists $entry->{'fields'}{'keywords'} ) {
+ if ( $title ) {
+ $title = $self->{'LANG'}->get('I18N_LANG_FIELD_ABSTRACT_KEYWORDS') ;
+ $abstract .= "<BR><BR>\n" ;
+ }
+ else {
+ $title = $self->{'LANG'}->get('I18N_LANG_FIELD_KEYWORDS_TITLE') ;
+ }
+ $abstract .= $self->{'THEME'}->small($self->{'LANG'}->get('I18N_LANG_FIELD_KEYWORDS', $entry->{'fields'}{'keywords'} ) ) ;
+ }
+ my $r = $self->{'THEME'}->build_onecolumn_array( $title,
+ [ $abstract ] ) ;
+ array_slice( $result, $sliceindex, $r ) ;
+ $sliceindex ++ ;
+
+ }
+
+ # Downloadable file
+ if ( ( ( exists $entry->{'fields'}{'localfile'} ) ||
+ ( $self->isgenparam('doc-repository') ) ) &&
+ ( ! $self->isgenparam('nodownload') ) ) {
+
+ # Compute the source path of the PDF document
+ my ($abs,$rel,$turl,$drepos) = ($self->genparam('absolute-source'),
+ $self->genparam('relative-source'),
+ $self->genparam('target-url'),
+ $self->genparam('doc-repository')) ;
+
+ my ($sourcefilename,$targetfilename,$targeturl) ;
+
+ # Does it is an URL?
+ if ($turl) {
+ $targeturl = htmlcatdir( $turl, File::Spec->splitdir( $entry->{'fields'}{'localfile'} ) ) ;
+ }
+ # Does it have an absolute filename?
+ elsif ( $rel ) {
+ my @path = File::Spec->splitdir($entry->{'dirname'}) ;
+ push @path, File::Spec->splitdir("$rel") ;
+ $sourcefilename = File::Spec->catfile(@path,
+ htmltolocalpath( $entry->{'fields'}{'localfile'} ) ) ;
+ }
+ # Does it have a relative filename?
+ elsif ( $abs ) {
+ my @path = File::Spec->splitdir("$abs") ;
+ $sourcefilename = File::Spec->catfile( @path,
+ htmltolocalpath( $entry->{'fields'}{'localfile'} ) ) ;
+ }
+ # Default location
+ else {
+ my @path = File::Spec->splitdir($entry->{'dirname'}) ;
+ $sourcefilename = File::Spec->catfile(@path,
+ htmltolocalpath( $entry->{'fields'}{'localfile'} ) ) ;
+ }
+
+ # Does the document repository exists?
+ if ($drepos) {
+ my @exts = ('pdf','PDF','ps','PS');
+ my $i = 0;
+ do {
+ $sourcefilename = File::Spec->catfile( File::Spec->splitdir("$drepos"), $key.".".$exts[$i] ) ;
+ $i ++;
+ }
+ while (( ! -f "$sourcefilename" )&&($i<@exts));
+ $sourcefilename = undef unless ( -f "$sourcefilename" );
+ }
+
+ if ($sourcefilename) {
+ if ( (!$drepos) && ( exists $entry->{'fields'}{'localfile'} ) ) {
+ my @path = htmlsplit( $entry->{'fields'}{'localfile'} ) ;
+ $targeturl = htmlcatfile( 'e-documents', @path ) ;
+ }
+ else {
+ $targeturl = htmlcatfile( 'e-documents', basename($sourcefilename) ) ;
+ }
+ $targetfilename = File::Spec->catdir( $self->{'TARGET'}, $targeturl ) ;
+ }
+
+ if ( (!$sourcefilename) || ( -f "$sourcefilename" ) ) {
+
+ # Register the PDF document to copy
+ # The real copy will be made during the copy_files() call.
+ if (($sourcefilename)&&($targetfilename)) {
+ $self->register_file_to_copy( "$sourcefilename", "$targetfilename" ) ;
+ }
+
+ if ($targeturl) {
+ my $alttext = '';
+ if ($sourcefilename) {
+ $alttext = basename("$sourcefilename");
+ }
+
+ # Generate the HTML code which permits to download the document
+ my $r = $self->{'THEME'}->par( $self->{'LANG'}->get( 'I18N_LANG_FIELD_DOWNLOAD',
+ $self->{'THEME'}->href( $targeturl,
+ "<IMG align='middle' src='".
+ htmlcatdir($rootdir,'drive.png').
+ "' alt='".
+ $alttext.
+ "' border='0'>",
+ "_top" ) ) ) ;
+ array_slice( $result, $sliceindex, $r ) ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::syswarm( "$sourcefilename: $!\n" );
+ }
+ }
+
+ return $result ;
+}
+
+#------------------------------------------------------
+#
+# Generator helpers
+#
+#------------------------------------------------------
+
+=pod
+
+=item * save_generator_parameter()
+
+Replies if the specified generator parameter was supported.
+This function was called each time a generator parameter was
+given to this generator. By default, simply updatethe
+given parameter value (second parameter).
+You could do some stuff before
+saving (splitting...). Replies false is the parameter was
+not recognized. Don't forget to call inherited functions.
+Takes 2 args:
+
+=over
+
+=item * param_name (string)
+
+is the name of the parameter.
+
+=item * param_value (byref string)
+
+is the value of the parameter.
+
+=back
+
+=cut
+sub save_generator_parameter($$) {
+ my $self = shift ;
+ # all the following parameters will be saved by AbstractGenerator::new
+ return 1 if ( strinarray($_[0],
+ ['absolute-source',
+ 'nodownload',
+ 'doc-repository',
+ 'relative-source',
+ 'target-url',
+ 'backslash']) ) ;
+ return $self->SUPER::save_generator_parameter($_[0],$_[1]) ;
+}
+
+=pod
+
+=item * display_supported_generator_params()
+
+Display the list of supported generator parameters.
+
+=cut
+sub display_supported_generator_params() {
+ my $self = shift ;
+ $self->SUPER::display_supported_generator_params() ;
+
+ $self->show_supported_param('absolute-source',
+ 'is the absolute path where the '.
+ 'downloadable articles could be '.
+ 'found',
+ 'path') ;
+
+ $self->show_supported_param('backslash',
+ 'if presents, indicates that '.
+ 'backslashes will be removed from '.
+ 'the link fields (url,ftp...).') ;
+
+ $self->show_supported_param('doc-repository',
+ 'if presents, indicates the path to '.
+ 'the direction where the electronical '.
+ 'documents was stored. The documents '.
+ 'must have the same name as the '.
+ 'BibTeX key.') ;
+
+ $self->show_supported_param('nodownload',
+ 'if presents, indicates that no '.
+ 'link to the electronic documents '.
+ 'will be generated. By extension, '.
+ 'if presents no copy will be made.') ;
+
+ $self->show_supported_param('relative-source',
+ 'is the path where the downloadable '.
+ 'articles could be found, relatively '.
+ 'to the .bib file location.',
+ 'path') ;
+
+ $self->show_supported_param('target-url',
+ 'is the base URL where document '.
+ 'could be download. If presents, '.
+ 'the document will not be copied.',
+ 'url') ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/FileWriter.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/FileWriter.pm
new file mode 100644
index 0000000000..d79d5495e2
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/FileWriter.pm
@@ -0,0 +1,307 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::FileWriter - An output stream writer
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::FileWriter is a Perl module, which permits to
+output streams into files.
+
+=head1 SYNOPSYS
+
+Bib2HTML::Generator::FileWriter->new( ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::FileWriter is a Perl module, which permits to
+output streams into files.
+
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in FileWriter.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::FileWriter;
+
+@ISA = ('Bib2HTML::Generator::Writer');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use File::Path;
+use File::Spec;
+
+use Bib2HTML::Generator::Writer;
+use Bib2HTML::General::Misc;
+use Bib2HTML::General::Error;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of abstract generator
+my $VERSION = "1.0" ;
+
+# Opened streams
+my @opened_streams = ();
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = $class->SUPER::new() ;
+ bless( $self, $class );
+ return $self;
+}
+
+=pod
+
+=item * openstream($)
+
+Open the output stream.
+Takes 1 param:
+
+=over
+
+=item * filename (string)
+
+is the name of the output file.
+
+=back
+
+=cut
+sub openstream($) {
+ my $self = shift;
+ my $filename = shift || confess( 'you must supply the root directory' ) ;
+ confess('output stream already opened') if ($self->{'opened'});
+ my $streamname = '';
+
+ do {
+ my $count = int(rand(5));
+ $streamname = $filename;
+ $streamname =~ s/[^a-zA-Z]//g;
+ for(my $i=0; $i<$count; $i++) {
+ my $c = rand(26);
+ $streamname .= chr(ord('A')+$c);
+ }
+ }
+ while (strinarray("$streamname",\@opened_streams));
+
+ local *OUTPUTFILE;
+ *OUTPUTFILE = $streamname;
+ my $r = open( OUTPUTFILE, "> $filename" );
+ if ($r) {
+ $self->{'opened'} = "$streamname";
+ push @opened_streams, "$streamname";
+ }
+ return $r;
+}
+
+=pod
+
+=item * out($)
+
+Put a string into the output stream.
+Takes 1 param:
+
+=over
+
+=item * str (string)
+
+is the string to output.
+
+=back
+
+=cut
+sub out($) {
+ my $self = shift;
+ my $str = shift || '';
+ if ($self->{'opened'}) {
+ local *OUTPUTFILE;
+ *OUTPUTFILE = $self->{'opened'};
+ print OUTPUTFILE ("$str");
+ return 1;
+ }
+ else {
+ return undef;
+ }
+}
+
+=pod
+
+=item * closestream()
+
+Close the currently opened stream.
+
+=cut
+sub closestream() {
+ my $self = shift;
+ if ($self->{'opened'}) {
+ local *OUTPUTFILE;
+ *OUTPUTFILE = $self->{'opened'};
+ close(OUTPUTFILE);
+ @opened_streams = grep {($self->{opened} ne $_)} @opened_streams;
+ delete $self->{'opened'};
+ return 1;
+ }
+ else {
+ return undef;
+ }
+}
+
+=pod
+
+=item * create_output_directory()
+
+Create the output directory if required.
+Replies the output filename (directory).
+Takes n params:
+
+=over
+
+=item * output (string)
+
+is the output directory to create.
+
+=item * exceptions (list of strings)
+
+is the list of the file in the existing output directory
+to not remove.
+
+=back
+
+=cut
+sub create_output_directory($@) {
+ my $self = shift;
+ my $output = shift ;
+ if ( ! $output ) {
+ $output = File::Spec->catdir( ".", "bib2html" ) ;
+ }
+ if ( ! -d "$output" ) {
+ mkdir( "$output", 0777 )
+ or Bib2HTML::General::Error::syserr( "$output: $!\n" );
+ }
+ else {
+ $self->_clear_output_directory("$output", @_);
+ }
+ return "$output" ;
+}
+
+=pod
+
+=item * _clear_output_directory()
+
+Clear the content of the output directory.
+
+=cut
+sub _clear_output_directory($@) {
+ my $self = shift;
+ my $output = shift ;
+ my @protect = ();
+
+ foreach my $expr (@_) {
+ push @protect, shell_to_regex($expr);
+ }
+
+ local *DIR;
+ opendir(*DIR,"$output")
+ or Bib2HTML::General::Error::syserr( "The output directory '$output".
+ "' can't be opened: $!\n" ) ;
+ while (my $subfile = readdir(*DIR)) {
+ if (($subfile ne File::Spec->curdir())&&($subfile ne File::Spec->updir())) {
+ my $valid = 1;
+
+ foreach my $expr (@protect) {
+ if ($subfile =~ /$expr/) {
+ $valid = undef;
+ last;
+ }
+ }
+
+ if ($valid) {
+ my $fullpath = File::Spec->catfile("$output","$subfile");
+
+ if ( -d "$fullpath" ) {
+ rmtree( "$fullpath" )
+ or Bib2HTML::General::Error::syserr( "The directory '$fullpath".
+ "' can't be deleted: $!\n" ) ;
+ }
+ else {
+ unlink( "$fullpath" )
+ or Bib2HTML::General::Error::syserr( "The file '$fullpath".
+ "' can't be deleted: $!\n" ) ;
+ }
+ }
+ }
+ }
+ closedir(*DIR);
+}
+
+=pod
+
+=item * is_file_creation_allowed()
+
+Replies if this writer allows to create files.
+
+=cut
+sub is_file_creation_allowed() {
+ my $self = shift;
+ return 1;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/HTMLGen.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/HTMLGen.pm
new file mode 100644
index 0000000000..55ec802ab7
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/HTMLGen.pm
@@ -0,0 +1,2334 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::HTMLGen - A basic HTML generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::HTMLGen ;
+
+my $gen = Bib2HTML::Generator::HTMLGen->new( content, output, info, titles,
+ lang, theme, params ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::HTMLGen is a Perl module, which permits to
+generate HTML pages for the BibTeX database.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::HTMLGen;
+
+ my $gen = Bib2HTML::Generator::HTMLGen->new( { }, "./bib",
+ { 'BIB2HTML_VERSION' => "0.1",
+ },
+ { 'SHORT' => "This is the title",
+ 'LONG' => "This is the title",
+ },
+ "English",
+ "Simple", ""
+ ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * content (hash)
+
+see AbstractGenerator help.
+
+=item * output (string)
+
+see AbstractGenerator help.
+
+=item * bib2html_data (hash)
+
+see AbstractGenerator help.
+
+=item * titles (hash)
+
+see AbstractGenerator help.
+
+=item * lang (string)
+
+see AbstractGenerator help.
+
+=item * theme (string)
+
+is the name of the theme to use
+
+=item * show_bibtex (boolean)
+
+indicates if this parser must generate a verbatim of the BibTeX code
+
+=item * params (optional array)
+
+is the set of parameters passed to the generator.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in HTMLGen.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::HTMLGen;
+
+@ISA = ('Bib2HTML::Generator::AbstractGenerator');
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Carp ;
+use File::Spec ;
+use File::Basename;
+
+use Bib2HTML::Generator::AbstractGenerator;
+use Bib2HTML::General::Misc;
+use Bib2HTML::General::HTML;
+use Bib2HTML::General::Title;
+use Bib2HTML::General::Error;
+use Bib2HTML::General::Encode;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of this generator
+my $VERSION = "6.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$$$;$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+
+ my @langs = ();
+ if (isarray($_[4])) {
+ foreach my $l (@{$_[4]}) {
+ if ($l !~ /_[a-zA-Z0-9]+Gen$/) {
+ push @langs, $l."_HTMLGen";
+ }
+ push @langs, $l;
+ }
+ }
+ else {
+ @langs = ( $_[4] );
+ if ($_[4] !~ /_[a-zA-Z0-9]+Gen$/) {
+ unshift @langs, $_[4]."_HTMLGen";
+ }
+ }
+
+ my $self = $class->SUPER::new($_[0], #content
+ $_[1], #output
+ $_[2], #bib2html info
+ $_[3], #titles
+ \@langs, #lang
+ $_[6], #show bibtex
+ $_[7], #params
+ ) ;
+ bless( $self, $class );
+
+ $self->{'__INDEX_GENERATED__'} = 0 ; # index not generated
+
+ # Filenames patterns
+ $self->{'FILENAMES'} = { 'overview-frame' => 'overview-frame.html',
+ 'overview-summary' => 'overview-summary.html',
+ 'allelements' => 'allelements-frame.html',
+ 'type-overview' => 'type-#1.html',
+ 'entry' => 'entry-#1.html',
+ 'overview-tree' => 'overview-tree.html',
+ 'main_index' => "index.html",
+ 'index' => "index-#1.html",
+ 'author-overview' => 'author-#1.html',
+ } ;
+ $self->{'ENTRY_FILENAMES'} = {} ;
+ $self->{'AUTHOR_FILENAMES'} = {} ;
+
+ # HTML frames identifiers
+ $self->{'FRAMES'} = { 'overview-frame' => 'typeFrame',
+ 'overview-summary' => 'mainFrame',
+ 'allelements' => 'entryFrame',
+ 'type-overview' => 'entryFrame',
+ 'entry' => 'mainFrame',
+ 'overview-tree' => 'mainFrame',
+ 'main_index' => "_top",
+ 'index' => "mainFrame",
+ } ;
+
+ # Storage area for the buttons added into the navigation bar
+ $self->{'USER_NAVIGATION_BUTTONS'} = [] ;
+
+ # Creates the theme support
+ my $theme = $_[5] || confess( 'you must supply the theme' ) ;
+ if ( $theme !~ /\:\:/ ) {
+ $theme = "Bib2HTML::Generator::Theme::".$theme ;
+ }
+ eval "require $theme ;" ;
+ if ( $@ ) {
+ Bib2HTML::General::Error::syserr( "Unable to find the theme class: $theme\n$@\n" ) ;
+ }
+ $self->{'THEME'} = ($theme)->new( $self,
+ $self->{'BIB2HTML'},
+ $self->{'TARGET'},
+ $self->{'SHORT_TITLE'},
+ $self->{'LANG'} ) ;
+
+ # Create an instance of a XML generator
+ if ($self->genparam('xml-verbatim')) {
+ require Bib2HTML::Generator::XMLGen ;
+ $self->{'XML_GENERATOR'} = Bib2HTML::Generator::XMLGen->new($_[0], #content
+ $_[1], #output
+ $_[2], #bib2html info
+ $_[3], #titles
+ $_[4], #lang
+ $_[6], #show bibtex
+ $_[7], #params
+ ) ;
+ }
+
+ return $self;
+}
+
+
+=pod
+
+=item * save_generator_parameter()
+
+Replies if the specified generator parameter was supported.
+This function was called each time a generator parameter was
+given to this generator. By default, simply update the
+given parameter value (second parameter).
+You could do some stuff before
+saving (splitting...). Replies false is the parameter was
+not recognized. Don't forget to call inherited functions.
+Takes 2 args:
+
+=over
+
+=item * param_name (string)
+
+is the name of the parameter.
+
+=item * param_value (byref string)
+
+is the value of the parameter.
+
+=back
+
+=cut
+sub save_generator_parameter($$) {
+ # Patch by Norbert Preining added the 2003/03/17
+ # Patch by Norbert Preining added the 2003/03/27
+ # Patch by Aurel Gabris added the 2006/04/10
+ my $self = shift ;
+ if ( ( $_[0] eq 'author-regexp' ) ||
+ ( $_[0] eq 'max-names-overview' ) ||
+ ( $_[0] eq 'max-titlelength-overview' ) ||
+ ( $_[0] eq 'max-names-list') ||
+ ( $_[0] eq 'html-encoding' ) ) {
+ # will be saved by PARENT::new
+ return 1 ;
+ }
+ elsif ( $_[0] eq 'newtype' ) {
+ # extracts new type definitions
+ $_[1] = $self->merge_params(',',$_[1]) ;
+ my @ntypedef = split /\s*,\s*/, "$_[1]" ;
+ # adds each extracted definition
+ foreach my $td (@ntypedef) {
+ if ( $td !~ /^\s*(.+?)\s*:\s*(.+?)\s*:\s*(.+?)\s*$/ ) {
+ Bib2HTML::General::Error::syserr("syntax error for generator parameter ".
+ "'newtype' for \"$td\"" ) ;
+ }
+ else {
+ my @foo = (lc($1),$2,$3) ;
+ Bib2HTML::General::Verbose::one(join('',
+ "\tadd BibTeX type: ".$foo[0].",\n",
+ "\t singular: ".($foo[1]||'')."\n",
+ "\t plurial: ".($foo[2]||''))) ;
+ $self->{'SINGULAR_TYPE_LABELS'}{$foo[0]} = $foo[1] ;
+ $self->{'PLURIAL_TYPE_LABELS'}{$foo[0]} = $foo[2] ;
+ }
+ }
+ return 1 ;
+ }
+ elsif ( $_[0] eq 'type-matching' ) {
+ # Normalize the syntax of this parameter's value
+ my $val = $self->merge_params(',',$_[1]) ;
+ $val =~ s/\=>/,/g ;
+ $val =~ s/\->/,/g ;
+ $val =~ s/>/,/g ;
+ # Check the syntax of this parameter's value
+ my @foo = split /\s*,\s*/, "$val" ;
+ if ((@foo)&&((@foo%2)==0)) {
+ $_[1] = {} ;
+ while (@foo) {
+ my $a = shift @foo ;
+ my $b = shift @foo ;
+ $_[1]->{"$a"} = "$b" ;
+ }
+ }
+ else {
+ # Die on error if the syntax was invalid
+ Bib2HTML::General::Error::syserr("invalid value for the generator parameter 'type-matching'") ;
+ }
+ return 1 ;
+ }
+ elsif ( $_[0] eq 'restrict' ) {
+ # extracts output filename restrictions
+ $_[1] = $self->merge_params(',',$_[1]) ;
+ my @restricts = split /\s*,\s*/, "$_[1]" ;
+ # adds each extracted definition
+ $self->{'FILE_RESTRICTIONS'} = [];
+ foreach my $res (@restricts) {
+ push @{$self->{'FILE_RESTRICTIONS'}}, shell_to_regex($res);
+ }
+ return 1 ;
+ }
+ elsif ( ( $_[0] eq 'xml-verbatim' ) ||
+ ( $_[0] eq 'show-journalparams-overview' ) ||
+ ( $_[0] eq 'hideindex' ) ) {
+ $_[1] = 1 ;
+ return 1 ;
+ }
+ else {
+ return $self->SUPER::save_generator_parameter($_[0],$_[1]) ;
+ }
+}
+
+=pod
+
+=item * display_supported_generator_params()
+
+Display the list of supported generator parameters.
+
+=cut
+sub display_supported_generator_params() {
+ # Patch by Norbert Preining added the 2003/03/17
+ # Patch by Norbert Preining added the 2003/03/27
+ # Patch by Aurel Gabris added the 2006/04/10
+ my $self = shift ;
+ $self->SUPER::display_supported_generator_params() ;
+
+ $self->show_supported_param('author-regexp',
+ 'A regexp (case-insensitive) against which '.
+ 'the lastname of '.
+ 'an author is matched. If the author '.
+ 'matches, (s)he is included in the '.
+ 'overview window author list.' );
+
+ $self->show_supported_param('hideindex',
+ 'If present, the generator will hide the index pages.' );
+
+ $self->show_supported_param('html-encoding',
+ 'String, the character encoding used in the HTML pages '.
+ '("UTF8", "ISO-8859-1"...).' );
+
+ $self->show_supported_param('max-names-overview',
+ 'Integer, max number of authors on '.
+ 'the overview page.' );
+
+ $self->show_supported_param('max-names-list',
+ 'Integer, max number of authors on the '.
+ 'listing in the lower left window.' );
+
+ $self->show_supported_param('max-titlelength-overview',
+ 'Integer, max length of title on '.
+ 'the overview page.' );
+
+ $self->show_supported_param('newtype',
+ 'A comma separated list of new type, with singular and '.
+ 'plural form, format: '.
+ 'type:Singular:Plural[,type:Singular:Plural...]' );
+
+ $self->show_supported_param('restrict',
+ 'A comma separated list of strings containing shell-like wildcards. They '.
+ 'corresponds to the pattern filenames that are available to be generated.' );
+
+ $self->show_supported_param('show-journalparams-overview',
+ 'If specified, show journal parameters instead '.
+ 'of type for articles on the overview page.' );
+
+ $self->show_supported_param('type-matching',
+ 'A coma separated list of items which inititalizes an '.
+ 'associative array of type entry mappings. '.
+ 'For example \'incollection,article,inproceedings,article\' '.
+ 'means that all the BibTeX\'s \'@incollection\' entries will be '.
+ 'considered as \'@article\' entries. Same thing for the '.
+ '\'@inproceedings\'.' );
+
+ $self->show_supported_param('xml-verbatim',
+ 'If present, each entry\'s page will contains the '.
+ 'XML entry as verbatim.' );
+}
+
+#------------------------------------------------------
+#
+# Generation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * set_stream_writer($)
+
+Set the instance of the output stream writer.
+Replies the old writer.
+Takes 1 arg:
+
+=over
+
+=item * writer (ref to Bib2HTML::Generator::Writer)
+
+is the instance of the writer.
+
+=back
+
+=cut
+sub set_stream_writer($) : method {
+ my $self = shift ;
+ my $writer = shift;
+ my $old_writer = $self->SUPER::set_stream_writer($writer);
+ if ($self->{'THEME'}) {
+ $self->{'THEME'}->set_stream_writer($writer);
+ }
+ return $old_writer;
+}
+
+
+=pod
+
+=item * pre_processing()
+
+Pre_processing.
+
+=cut
+sub pre_processing() : method {
+ my $self = shift ;
+
+ # Set the HTML encoding
+ if (!$self->{'GENERATOR_PARAMS'}{'html-encoding'}) {
+ $self->{'GENERATOR_PARAMS'}{'html-encoding'} = get_default_encoding();
+ }
+ set_default_encoding($self->{'GENERATOR_PARAMS'}{'html-encoding'});
+ $self->{'THEME'}->set_html_encoding($self->{'GENERATOR_PARAMS'}{'html-encoding'});
+
+ # Call inherited generation method
+ $self->SUPER::pre_processing() ;
+
+ # Create the output directory
+ $self->create_output_directory();
+}
+
+=pod
+
+=item * do_processing()
+
+Main processing.
+
+=cut
+sub do_processing() : method {
+ my $self = shift ;
+
+ # Call inherited generation method
+ $self->SUPER::do_processing() ;
+
+ # Generates each part of the document
+
+ if (!$self->genparam('hideindex')) {
+ $self->{'__INDEX_GENERATED__'} = $self->generate_indexes() ;
+ }
+ else {
+ $self->{'__INDEX_GENERATED__'} = undef;
+ }
+ $self->generate_index() ;
+ $self->generate_overviewframe() ;
+ $self->generate_allelementframe() ;
+ $self->generate_typeoverviews() ;
+ $self->generate_authoroverviews() ;
+ $self->generate_overviewtree() ;
+ $self->generate_overview() ;
+ $self->generate_entries() ;
+}
+
+=pod
+
+=item * post_processing()
+
+Post_processing.
+
+=cut
+sub post_processing() : method {
+ my $self = shift ;
+ # Call inherited generation method
+ $self->SUPER::post_processing() ;
+ # Copy resource files
+ my $writer = $self->{'THEME'}->get_stream_writer();
+ if ($writer->is_file_creation_allowed()) {
+ $self->copy_files() ;
+ }
+}
+
+=pod
+
+=item * is_restricted_file($)
+
+Replies if the specified filename is inside the
+restriction list. If the restriction list was empty,
+this function replies true.
+Takes 1 arg:
+
+=over
+
+=item * filename (string)
+
+is the filename to treat.
+
+=back
+
+=cut
+sub is_restricted_file($) : method {
+ my $self = shift;
+ my $filename = shift;
+ $filename = basename($filename);
+ return 1 unless ($self->{'FILE_RESTRICTIONS'});
+ foreach my $pattern (@{$self->{'FILE_RESTRICTIONS'}}) {
+ if ($filename =~ /$pattern/) {
+ return 1;
+ }
+ }
+ return undef;
+}
+
+=pod
+
+=item * generate_entries()
+
+Generates the HTML pages for each entry
+
+=cut
+sub generate_entries() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my @entries = $self->get_all_entries_ayt() ;
+ my $i = $#entries ;
+ while ( $i >= 0 ) {
+ # Compute entry constants
+ my $filename = $self->filename('entry',$entries[$i]) ;
+
+ Bib2HTML::General::Verbose::three( "Generates entry '".$entries[$i]."'\n" ) ;
+
+ next unless ($self->is_restricted_file("$filename"));
+
+ my $type = $self->{'CONTENT'}{'entries'}{$entries[$i]}{'type'} ;
+ my $url = htmlcatfile($rootdir,$filename) ;
+ my $bar = $self->{'THEME'}->get_navigation_bar( $filename,
+ { 'index' => $self->{'__INDEX_GENERATED__'},
+ 'previous' => '',
+ 'next' => '',
+ 'userdef' => $self->getNavigationButtons(),
+ },
+ $rootdir ) ;
+
+ # Generate the header
+ my $content = $bar.$self->{'THEME'}->partseparator() ;
+
+ # Calls the content building function
+ my $fct = "generate_entry_content_$type" ;
+ my $entrytitle = '' ;
+ if ( my $funcref = $self->can( $fct ) ) {
+ $content .= join( '', @{ $self->$funcref( $entries[$i],
+ $self->{'CONTENT'}{'entries'}{$entries[$i]},
+ $url,$rootdir,$entrytitle,[]) } ) ;
+ }
+ else {
+ Bib2HTML::General::Error::warm("I don't know how to generate a '\@".$type.
+ "' for the entry '".$entries[$i]."'. Assume '\@misc'",
+ extract_file_from_location( $_[1]{'location'} ),
+ extract_line_from_location( $_[1]{'location'} ) ) ;
+ $content .= join( '', @{ $self->generate_entry_content_misc( $entries[$i],
+ $self->{'CONTENT'}{'entries'}{$entries[$i]},
+ $url,$rootdir,$entrytitle,[]) } ) ;
+ }
+
+ # Generate the footer
+ $content .= join( '',
+ $self->{'THEME'}->partseparator(),
+ $bar,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->get_copyright() ) ;
+
+ # Output to the file
+ $self->{'THEME'}->create_html_body_page( $url,
+ $content,
+ $entrytitle||$self->{'SHORT_TITLE'},
+ $rootdir,
+ 'html') ;
+ }
+ continue {
+ $i -- ;
+ }
+}
+
+=pod
+
+=item * generate_index()
+
+Generates the HTML index.html
+
+=cut
+sub generate_index() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my $filename = $self->filename('main_index');
+
+ Bib2HTML::General::Verbose::three( "Generates the main index file\n" ) ;
+
+ return unless ($self->is_restricted_file("$filename"));
+
+ my $content = $self->{'THEME'}->get_html_index($rootdir);
+ $self->{'THEME'}->create_html_page( htmlcatfile($rootdir,$filename),
+ $content,
+ $self->{'SHORT_TITLE'},
+ $rootdir ) ;
+}
+
+=pod
+
+=item * generate_overviewframe()
+
+Generates the HTML overview-frame.html
+Dont overwrite this method.
+
+=cut
+sub generate_overviewframe : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my $filename = $self->filename('overview-frame');
+
+ Bib2HTML::General::Verbose::three( "Generates the overview frame\n" ) ;
+
+ return unless ($self->is_restricted_file("$filename"));
+
+ my $content = join( '',
+ $self->{'THEME'}->frame_subpart( '',
+ [ $self->{'THEME'}->ext_href( 'allelements',
+ $self->{'LANG'}->get('I18N_LANG_ALL_ELEMENTS'),
+ $rootdir ),
+ ],
+ $rootdir ),
+ $self->generate_overviewframe_content($rootdir)
+ ) ;
+
+ $self->{'THEME'}->create_html_body_page( htmlcatfile($rootdir,$filename),
+ $self->{'THEME'}->frame_window( $self->{'SHORT_TITLE'},
+ $content ),
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'small', 'html') ;
+}
+
+=pod
+
+=item * generate_allelementframe()
+
+Generates the HTML allelements-frame.html
+
+=cut
+sub generate_allelementframe() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my $filename = $self->filename('allelements');
+
+ Bib2HTML::General::Verbose::three( "Generates the all-element frame\n" ) ;
+
+ return unless ($self->is_restricted_file("$filename"));
+
+ my @entries = $self->get_all_entries_yat() ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ my $biblabeller = Bib2HTML::Translator::BibTeXEntry->new() ;
+ my $currentyear = '' ;
+ my $content = '' ;
+ my @current = () ;
+
+ foreach my $entry (@entries) {
+ my $year = $self->__get_year__( $entry, '' ) ;
+ if ( "$currentyear" ne "$year" ) {
+ if ( @current ) {
+ $content .= $self->{'THEME'}->frame_subpart( $currentyear || $self->{'LANG'}->get('I18N_LANG_NO_DATE'),
+ \@current,
+ $rootdir ) ;
+ }
+ $currentyear = $year ;
+ @current = () ;
+ }
+
+ my $biblabel = '' ;
+ if ( exists( $self->{'CONTENT'}{'entries'}{$entry} ) ) {
+ my $filename = $self->filename('entry',$entry) ;
+ $biblabel = join( '',
+ '[',
+ $self->{'THEME'}->href( htmlcatfile($rootdir,$filename),
+ $biblabeller->citation_label( $entry,
+ $self->{'CONTENT'}{'entries'}{$entry} ),
+ $self->browserframe('entry') ),
+ ']&nbsp;' ) ;
+ }
+ $biblabel .= $translator->formatnames( $self->__get_author_editor__($entry,''),
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'},
+ exists($self->{'GENERATOR_PARAMS'}{'max-names-list'})?$self->{'GENERATOR_PARAMS'}{'max-names-list'}:1 ) ;
+
+ push @current, $biblabel ;
+ }
+
+ if ( @current ) {
+ $content .= $self->{'THEME'}->frame_subpart( $currentyear || $self->{'LANG'}->get('I18N_LANG_NO_DATE'),
+ \@current,
+ $rootdir ) ;
+ }
+
+ $self->{'THEME'}->create_html_body_page( htmlcatfile($rootdir,$filename),
+ $self->{'THEME'}->frame_window( $self->{'LANG'}->get('I18N_LANG_ALL_ELEMENTS'),
+ $content ),
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'small', 'html') ;
+}
+
+=pod
+
+=item * generate_typeoverviews()
+
+Generates the HTML type-???.html
+
+=cut
+sub generate_typeoverviews() : method {
+ # Patch by Norbert Preining added the 2003/03/27
+ my $self = shift ;
+ my $rootdir = "." ;
+ my @entries = $self->get_all_entries_yat() ;
+ my @types = $self->get_entry_types() ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ my $biblabeller = Bib2HTML::Translator::BibTeXEntry->new() ;
+ my %typematching = () ;
+
+ if ( exists($self->{'GENERATOR_PARAMS'}{'type-matching'}) ) {
+ %typematching = %{$self->{'GENERATOR_PARAMS'}{'type-matching'}};
+ }
+ if ( @types > 0 ) {
+ foreach my $type (@types) {
+ if ( ! exists( $typematching{$type} ) ) {
+ $typematching{$type} = $type;
+ }
+ }
+ my @sortedtypes = values %typematching;
+ @sortedtypes = uniq(sortbyletters(@sortedtypes));
+ foreach my $type (@sortedtypes) {
+ my $url = $self->filename('type-overview',$type) ;
+ Bib2HTML::General::Verbose::three( "Generates type overview for '$type'\n" ) ;
+ next unless ($self->is_restricted_file("$url"));
+ my ($currentyear,$writeentry) = ('',0) ;
+ my @current = () ;
+ my $content = '' ;
+
+ foreach my $entry (@entries) {
+ my $year = $self->__get_year__( $entry, '' ) ;
+ if ( $typematching{$self->{'CONTENT'}{'entries'}{$entry}{'type'}} eq $type ) {
+ if ( "$currentyear" ne "$year" ) {
+ if ( @current ) {
+ $content .= $self->{'THEME'}->frame_subpart( $currentyear,
+ \@current,
+ $rootdir ) ;
+ }
+ $currentyear = $year ;
+ @current = () ;
+ }
+ my $biblabel = '' ;
+ if ( exists( $self->{'CONTENT'}{'entries'}{$entry} ) ) {
+ my $filename = $self->filename('entry',$entry) ;
+ $biblabel = join( '',
+ '[',
+ $self->{'THEME'}->href( htmlcatfile($rootdir,$filename),
+ $biblabeller->citation_label( $entry,
+ $self->{'CONTENT'}{'entries'}{$entry} ),
+ $self->browserframe('entry') ),
+ ']&nbsp;' ) ;
+ }
+ $biblabel .= $translator->formatnames( $self->__get_author_editor__($entry,''),
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'},
+ exists($self->{'GENERATOR_PARAMS'}{'max-names-list'})?$self->{'GENERATOR_PARAMS'}{'max-names-list'}:1) ;
+ push @current, $biblabel ;
+ }
+ }
+
+ if ( @current ) {
+ $content .= $self->{'THEME'}->frame_subpart( $currentyear,
+ \@current,
+ $rootdir ) ;
+ }
+
+ $self->{'THEME'}->create_html_body_page( htmlcatfile($rootdir,$url),
+ $self->{'THEME'}->frame_window( $self->{'PLURIAL_TYPE_LABELS'}{$type},
+ $content,
+ $self->{'THEME'}->ext_href( 'allelements',
+ $self->{'LANG'}->get('I18N_LANG_ALL_ELEMENTS'),
+ $rootdir )),
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'small', 'html') ;
+ }
+
+ }
+}
+
+=pod
+
+=item * generate_authoroverviews()
+
+Generates the HTML author-???.html
+
+=cut
+sub generate_authoroverviews() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ my $biblabeller = Bib2HTML::Translator::BibTeXEntry->new() ;
+ my @entries = $self->get_all_entries_yat() ;
+ my %authors = $self->get_entry_authors() ;
+
+ if ( !isemptyhash(\%authors) ) {
+ foreach my $author (keys %authors) {
+ my $url = $self->filename('author-overview',$author) ;
+ Bib2HTML::General::Verbose::three( "Generates author overview for '$author'\n" ) ;
+ next unless ($self->is_restricted_file("$url"));
+ my @current = () ;
+ my ($content,$currentyear) = ('','') ;
+
+ foreach my $entry (@entries) {
+
+ if ( $translator->isauthorin($authors{$author},
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'author'}) ) {
+
+ my $year = $self->__get_year__( $entry, '' ) ;
+ if ( "$currentyear" ne "$year" ) {
+ if ( @current ) {
+ $content .= $self->{'THEME'}->frame_subpart( $currentyear,
+ \@current,
+ $rootdir ) ;
+ }
+ $currentyear = $year ;
+ @current = () ;
+ }
+ my $biblabel = '' ;
+ if ( exists( $self->{'CONTENT'}{'entries'}{$entry} ) ) {
+ my $filename = $self->filename('entry',$entry) ;
+ $biblabel = join( '',
+ '[',
+ $self->{'THEME'}->href( htmlcatfile($rootdir,$filename),
+ $biblabeller->citation_label( $entry,
+ $self->{'CONTENT'}{'entries'}{$entry} ),
+ $self->browserframe('entry') ),
+ ']&nbsp;' ) ;
+ }
+ $biblabel .= $translator->formatnames( $self->__get_author_editor__($entry,''),
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'} ) ;
+ push @current, $biblabel ;
+ }
+
+ }
+
+
+
+ if ( @current ) {
+ $content .= $self->{'THEME'}->frame_subpart( $currentyear,
+ \@current,
+ $rootdir ) ;
+ }
+
+ $self->{'THEME'}->create_html_body_page( htmlcatfile($rootdir,$url),
+ $self->{'THEME'}->frame_window( $translator->formatname($authors{$author},'l, f.'),
+ $content,
+ $self->{'THEME'}->ext_href( 'allelements',
+ $self->{'LANG'}->get('I18N_LANG_ALL_ELEMENTS'),
+ $rootdir )),
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'small', 'html') ;
+ }
+ }
+}
+
+=pod
+
+=item * generate_overview()
+
+Generates the HTML overview-summary.html
+Dont overwrite this method.
+
+=cut
+sub generate_overview() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my $filename = $self->filename('overview-summary') ;
+ Bib2HTML::General::Verbose::three( "Generates overview summary\n" ) ;
+ return unless ($self->is_restricted_file("$filename"));
+ $filename = htmlcatfile($rootdir,$filename) ;
+ my $bar = $self->{'THEME'}->get_navigation_bar( $filename,
+ { 'overview' => 1,
+ 'index' => $self->{'__INDEX_GENERATED__'},
+ 'userdef' => $self->getNavigationButtons(),
+ },
+ $rootdir ) ;
+ my $content = join('',
+ $bar,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->title($self->{'LONG_TITLE'}),
+ $self->generate_overview_content($rootdir),
+ $self->{'THEME'}->partseparator(),
+ $bar,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->get_copyright($rootdir) ) ;
+
+ $self->{'THEME'}->create_html_body_page( $filename,
+ $content,
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'html' ) ;
+}
+
+=pod
+
+=item * generate_overviewtree()
+
+Generates the HTML overview-tree.html
+Dont overwrite this method.
+
+=cut
+sub generate_overviewtree() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my $filename = $self->filename('overview-tree') ;
+ Bib2HTML::General::Verbose::three( "Generates overview tree\n" ) ;
+ return unless ($self->is_restricted_file("$filename"));
+ $filename = htmlcatfile($rootdir,$filename) ;
+ my $bar = $self->{'THEME'}->get_navigation_bar( $filename,
+ { 'tree' => 1,
+ 'index' => $self->{'__INDEX_GENERATED__'},
+ 'userdef' => $self->getNavigationButtons(),
+ },
+ $rootdir ) ;
+ my $content = join('',
+ $bar,
+ $self->{'THEME'}->partseparator(),
+ $self->generate_overviewtree_content($rootdir),
+ $self->{'THEME'}->partseparator(),
+ $bar,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->get_copyright($rootdir) ) ;
+
+ $self->{'THEME'}->create_html_body_page( $filename,
+ $content,
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'html') ;
+}
+
+=pod
+
+=item * generate_indexes()
+
+Generates the HTML index-???.html
+Dont overwrite this method.
+
+=cut
+sub generate_indexes() : method {
+ my $self = shift ;
+ my $rootdir = "." ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ my %indexentries = () ;
+
+ Bib2HTML::General::Verbose::two( "Build the indexes\n" ) ;
+ my @entries = $self->get_all_entries_ayt() ;
+ foreach my $entry (@entries) {
+
+ # Builds the comment for this entry
+ my $filename = $self->filename('entry',$entry) ;
+ my $url = htmlcatfile($rootdir,$filename) ;
+ my $year = $self->__get_year__( $entry, '' ) ;
+ my $entrycomment = join( '',
+ $self->{'LANG'}->get('I18N_LANG_SMALL_IN',
+ $translator->formatnames( $self->__get_author_editor__($entry,''),
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'},
+ -1 )),
+ "<BR>\n",
+ $self->{'THEME'}->entry_title( $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'title'} ),
+ ( $year ? " (".$year.")" : '' ) ) ;
+
+ # Adds the authors
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'author'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the authors\n" ) ;
+ my @authors = $self->get_all_authors($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'author'}) ;
+ foreach my $author (@authors) {
+ my %desc = ( 'url' => $url,
+ 'label' => $translator->formatname( $author, $self->{'FORMATS'}{'name'} ),
+ 'comment' => $entrycomment,
+ 'short-comment' => $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_AUTHOR'),
+ ) ;
+ my $sorttag = lc(remove_html_accents($author->{'last'}));
+ push @{$indexentries{$sorttag}}, \%desc ;
+ }
+ }
+
+ # Adds the editors
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'editor'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the editors\n" ) ;
+ my @editors = $self->get_all_authors($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'editor'}) ;
+ foreach my $editor (@editors) {
+ my %desc = ( 'url' => $url,
+ 'label' => $translator->formatname( $editor, $self->{'FORMATS'}{'name'} ),
+ 'comment' => $entrycomment,
+ 'short-comment' => $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_EDITOR'),
+ ) ;
+ my $sorttag = lc(remove_html_accents($editor->{'last'}));
+ push @{$indexentries{$sorttag}}, \%desc ;
+ }
+ }
+
+ # Adds the title keywords
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'title'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the titles\n" ) ;
+ $self->_add_sentence_keywords( \%indexentries,
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'title'},
+ $url, $entrycomment,
+ $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_TITLE')) ;
+ }
+
+ # Adds the booktitle
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'booktitle'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the booktitles\n" ) ;
+ $self->_add_sentence_keywords( \%indexentries,
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'booktitle'},
+ $url, $entrycomment,
+ $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_BOOKTITLE')) ;
+ }
+
+ # Adds the journal
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'journal'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the journal\n" ) ;
+ $self->_add_sentence_keywords( \%indexentries,
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'journal'},
+ $url, $entrycomment,
+ $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_ARTICLE')) ;
+ }
+
+ # Adds the publisher
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'publisher'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the publisher\n" ) ;
+ $self->_add_sentence_keywords( \%indexentries,
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'publisher'},
+ $url, $entrycomment,
+ $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_PUBLISHER')) ;
+ }
+
+ # Adds the school
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'school'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the school\n" ) ;
+ $self->_add_sentence_keywords( \%indexentries,
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'school'},
+ $url, $entrycomment,
+ $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_SCHOOL')) ;
+ }
+
+ # Adds the institution
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'institution'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the institution\n" ) ;
+ $self->_add_sentence_keywords( \%indexentries,
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'institution'},
+ $url, $entrycomment,
+ $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_INSTITUTION')) ;
+ }
+
+ # Adds the howpublished
+ if ( exists $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'howpublished'} ) {
+ Bib2HTML::General::Verbose::three( "\tinclude the howpublished\n" ) ;
+ $self->_add_sentence_keywords( \%indexentries,
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'howpublished'},
+ $url, $entrycomment,
+ $self->{'LANG'}->get('I18N_LANG_INDEX_COMMENT_HOWPUBLISHED')) ;
+ }
+
+ # Calls the overwritable function to adds entries
+ $self->generate_index_content(\%indexentries,$entry,$url,$entrycomment,$rootdir) ;
+
+ }
+
+ # Builds the list of letters
+ Bib2HTML::General::Verbose::three( "\tgets the index letters\n" ) ;
+ my @words = keys %indexentries;
+ @words = sortbyletters(@words) ;
+ my $letterlist = "" ;
+ my $lastletter = "" ;
+ my $maxcount = 0 ;
+
+ foreach my $word (@words) {
+ $word =~ /^(.)/ ;
+ my $letter = lc($1) ;
+ if ( ! ( $letter eq $lastletter ) ) {
+ $lastletter = $letter ;
+ $letterlist .= $self->{'THEME'}->href( htmlcatfile($rootdir,
+ $self->filename('index',$maxcount)),
+ uc( $letter ),
+ $self->browserframe('index') ) ;
+ $maxcount ++ ;
+ }
+ }
+
+ if ( isemptyhash(\%indexentries) ) {
+ return 0 ;
+ }
+
+ # Ouputs the indexes
+ my $nav = "" ;
+ my $content = '' ;
+ my @letterentries = () ;
+ my $count = 0 ;
+ my $currentfile = "" ;
+ $lastletter = "" ;
+ $self->{'__INDEX_GENERATED__'} = 1 ;
+
+ foreach my $word (@words) {
+ $word =~ /^(.)/ ;
+ my $letter = lc($1) ;
+ if ( ! ( $letter eq $lastletter ) ) {
+ #
+ # The first letter has changed
+ #
+ if ( $currentfile ) {
+ # finish to write the previous file
+ $content = join( '',
+ $nav,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->format_index_page( $letterlist,
+ $lastletter,
+ \@letterentries ),
+ $self->{'THEME'}->partseparator(),
+ $nav,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->get_copyright($rootdir) ) ;
+ $self->{'THEME'}->create_html_body_page( $currentfile,
+ $content,
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'html') ;
+ }
+ Bib2HTML::General::Verbose::three( "\tgenerates the index content for '$letter'\n" ) ;
+ $lastletter = $letter ;
+ # begin to write the file for the current letter
+ $currentfile = $self->{'THEME'}->filename('index',$count) ;
+ unless ($self->is_restricted_file("$currentfile")) {
+ $currentfile = '';
+ }
+ if ($currentfile) {
+ $nav = $self->{'THEME'}->get_navigation_bar( $currentfile,
+ { 'index' => (($count > 0) && ($self->{'__INDEX_GENERATED__'})),
+ 'previous' => ( ( $count > 0 ) ? htmlcatfile($rootdir,
+ $self->{'THEME'}->filename('index',($count-1))) : "" ),
+ 'next' => ( ($count<($maxcount-1)) ? htmlcatfile($rootdir,
+ $self->{'THEME'}->filename('index',($count+1))) : "" ),
+ 'notree' => ( isemptyhash( $self->{'CONTENT'}{'entries'} ) ),
+ 'userdef' => $self->getNavigationButtons(),
+ },
+ $rootdir ) ;
+ }
+ $count ++ ;
+ @letterentries = () ;
+ }
+
+ @letterentries = ( @letterentries, @{$indexentries{$word}} ) ;
+ }
+
+ if ( $currentfile ) {
+ # Really finish the last file
+ $content = join( '',
+ $nav,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->format_index_page( $letterlist,
+ $lastletter,
+ \@letterentries ),
+ $self->{'THEME'}->partseparator(),
+ $nav,
+ $self->{'THEME'}->partseparator(),
+ $self->{'THEME'}->get_copyright($rootdir) ) ;
+ $self->{'THEME'}->create_html_body_page( $currentfile,
+ $content,
+ $self->{'SHORT_TITLE'},
+ $rootdir,
+ 'html') ;
+ }
+
+ Bib2HTML::General::Verbose::three( "\tindexes finished\n" ) ;
+
+ return 1 ;
+}
+
+#------------------------------------------------------
+#
+# Overwritable Generation API
+#
+#------------------------------------------------------
+
+my %__FIELD_TO_LANG_TRANS_TBL = ( 'editor' => 'EDITORS',
+ 'booktitle' => 'IN',
+ 'author' => 'AUTHORS',
+ ) ;
+
+=pod
+
+=item * MAKE_REQUIRED()
+
+Add a required parameter into the specified array.
+
+=cut
+sub MAKE_REQUIRED(\@$$;$$) {
+ my $self = shift ;
+ my $LABEL = 'I18N_LANG_FIELD_';
+ if ( exists $__FIELD_TO_LANG_TRANS_TBL{lc("$_[2]")} ) {
+ $LABEL .= $__FIELD_TO_LANG_TRANS_TBL{lc("$_[2]")} ;
+ }
+ else {
+ $LABEL .= uc($_[2]) ;
+ }
+ my $val = $_[1]->{'fields'}{"$_[2]"} || "-" ;
+ $val = "$_[3]$val" if ($_[3]) ;
+ $val .= "$_[4]" if ($_[4]) ;
+ push @{$_[0]}, { 'name' => $self->{'LANG'}->get("$LABEL"),
+ 'explanation' => "$val",
+ } ;
+}
+
+=pod
+
+=item * MAKE_OPTIONAL()
+
+Add a optional parameter into the specified array.
+
+=cut
+sub MAKE_OPTIONAL(\@$$;$$) {
+ my $self = shift ;
+ if ((exists $_[1]->{'fields'}{"$_[2]"})&&
+ ($_[1]->{'fields'}{"$_[2]"})) {
+ my $LABEL = 'I18N_LANG_FIELD_';
+ if ( exists $__FIELD_TO_LANG_TRANS_TBL{lc("$_[2]")} ) {
+ $LABEL .= $__FIELD_TO_LANG_TRANS_TBL{lc("$_[2]")} ;
+ }
+ else {
+ $LABEL .= uc($_[2]) ;
+ }
+ my $val = $_[1]{'fields'}{"$_[2]"} ;
+ $val = "$_[3]$val" if ($_[3]) ;
+ $val .= "$_[4]" if ($_[4]) ;
+ push @{$_[0]}, { 'name' => $self->{'LANG'}->get("$LABEL"),
+ 'explanation' => "$val",
+ } ;
+ }
+}
+
+=pod
+
+=item * generate_entry_content_article()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_article($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_REQUIRED(\@content,$_[1],'journal') ;
+
+ $self->MAKE_OPTIONAL(\@content,$_[1],'volume') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'number') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'pages') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content);
+}
+
+=pod
+
+=item * generate_entry_content_book()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_book($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_REQUIRED(\@content,$_[1],'publisher') ;
+
+ $self->MAKE_OPTIONAL(\@content,$_[1],'series') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'volume') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'number') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'edition') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content,1);
+}
+
+=pod
+
+=item * generate_entry_content_booklet()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_booklet($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'howpublished') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ # The following fields are not required in BibTeX specification
+ $self->MAKE_OPTIONAL(\@content,$_[1],'publisher') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'series') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'volume') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'number') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'edition') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content);
+}
+
+=pod
+
+=item * generate_entry_content_inbook()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_inbook($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'howpublished') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ # The following fields are not required in BibTeX specification
+ $self->MAKE_OPTIONAL(\@content,$_[1],'publisher') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'series') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'volume') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'number') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'edition') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content);
+}
+
+=pod
+
+=item * generate_entry_content_incollection()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_incollection($$$$$) : method {
+ my $self = shift ;
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content(@_);
+}
+
+=pod
+
+=item * generate_entry_content_inproceedings()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_inproceedings($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_REQUIRED(\@content,$_[1],'booktitle') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'series') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'editor') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'volume') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'number') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'pages') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'organization') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'publisher') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'type') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content);
+}
+
+=pod
+
+=item * generate_entry_content_manual()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_manual($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'edition') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'organization') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content);
+}
+
+=pod
+
+=item * generate_entry_content_mastersthesis()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_mastersthesis($$$$$) : method {
+ my $self = shift ;
+ return $self->generate_entry_content_phdthesis(@_) ;
+}
+
+=pod
+
+=item * generate_entry_content_phdthesis()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_phdthesis($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'type') ;
+ $self->MAKE_REQUIRED(\@content,$_[1],'school') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content);
+}
+
+=pod
+
+=item * generate_entry_content_proceedings()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_proceedings($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'series') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'volume') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'number') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'organization') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'publisher') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content, 1);
+}
+
+=pod
+
+=item * generate_entry_content_techreport()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_techreport($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'number') ;
+ $self->MAKE_REQUIRED(\@content,$_[1],'institution') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'address') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'type') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content);
+}
+
+=pod
+
+=item * generate_entry_content_unpublished()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_unpublished($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+ my @content = () ;
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content,undef,1);
+}
+
+=pod
+
+=item * generate_entry_content_misc()
+
+See generate_entry_content()
+
+=cut
+sub generate_entry_content_misc($$$$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+
+ my @content = () ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'howpublished') ;
+ $self->MAKE_OPTIONAL(\@content,$_[1],'year') ;
+
+ #key,entry,url,rootdir,title,[user_fields,aut_ed,note]
+ return $self->generate_entry_content($key,$_[1],$url,$rootdir,$_[4],\@content,1);
+}
+
+=pod
+
+=item * generate_entry_content()
+
+Generates the HTML entry-???.html
+Overwrite this method.
+Takes 6 args:
+
+=over
+
+=item * key (string)
+
+is the BibTeX key of the current bibliographical entry
+
+=item * entry (hash ref)
+
+is the description of the current bibliographical entry
+
+=item * url (string)
+
+is the URL of the current entry
+
+=item * rootdir (string)
+
+is the path to the root.
+
+=item * entry_title (ref string)
+
+must be filled with the title of the entry.
+
+=item * user_fields (array)
+
+is the field predefined by the user. It must be an
+array of associative arrays (one for each generable field).
+
+=item * aut_ed_flg (optional boolean)
+
+indicates if the author and the editor fields are mutual
+alternatives.
+
+=item * note_req (optional boolean)
+
+indicates if the field 'note' was required.
+
+=cut
+sub generate_entry_content($$$$$;$$) : method {
+ my $self = shift ;
+ my ($key,$url,$rootdir) = ($_[0],$_[2],$_[3]) ;
+ my ($aut_ed_flg,$note_req) = ($_[6],$_[7]) ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ my $biblabeller = Bib2HTML::Translator::BibTeXEntry->new() ;
+
+ # Compute the publication year
+ my $date = $self->__get_year__( $_[0], '' ) ;
+ if ( $date ) {
+ if ( exists $_[1]{'fields'}{'month'} ) {
+ $date = $self->{'THEME'}->format_date($_[1]{'fields'}{'month'},$date) ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::warm("You must specify a year for the entry '".$key."'",
+ extract_file_from_location( $_[1]{'location'} ),
+ extract_line_from_location( $_[1]{'location'} ) ) ;
+ }
+
+ #
+ # Build the main tabular
+ #
+ my @content = () ;
+ # The fields 'author' and 'editor' are mutual alternatives
+ if ($aut_ed_flg) {
+ push @content, { 'name' => $_[1]{'fields'}{'author'} ?
+ $self->{'LANG'}->get('I18N_LANG_FIELD_AUTHORS') :
+ $self->{'LANG'}->get('I18N_LANG_FIELD_EDITORS'),
+ 'explanation' => $translator->formatnames_withurl(($_[1]{'fields'}{'author'}||
+ $_[1]{'fields'}{'editor'})||'',
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'},
+ $self,
+ -1,
+ $rootdir) || "-",
+ } ;
+ }
+ else {
+ # Only the field 'author' is required
+ $self->MAKE_REQUIRED(\@content,$_[1],'author') ;
+ }
+
+ # Finish to build the tabular
+ $self->MAKE_REQUIRED(\@content,$_[1],'title', '&laquo;&nbsp;<i>', '&nbsp;&raquo;</i>') ;
+ #$self->MAKE_REQUIRED(\@content,$_[1],'date') ;
+ push @content, @{$_[5]} ;
+
+ if (($aut_ed_flg)&&
+ (exists $_[1]{'fields'}{'author'})&&
+ ($_[1]{'fields'}{'author'})&&
+ (exists $_[1]{'fields'}{'editor'})&&
+ ($_[1]{'fields'}{'editor'})) {
+ $self->MAKE_OPTIONAL(\@content,$_[1],'editor') ;
+ }
+
+ if ($note_req) {
+ $self->MAKE_REQUIRED(\@content,$_[1],'note') ;
+ }
+ else {
+ $self->MAKE_OPTIONAL(\@content,$_[1],'note') ;
+ }
+
+ # Compute the user comments
+ my $annote = '' ;
+ if ( ( exists $_[1]{'fields'}{'annote'} ) ||
+ ( exists $_[1]{'fields'}{'comments'} ) ) {
+ $annote = $self->{'THEME'}->section( $self->{'LANG'}->get('I18N_LANG_FIELD_ANNOTATION'),
+ ($_[1]{'fields'}{'annote'}||'').
+ ($_[1]{'fields'}{'comments'}||''),
+ $rootdir ) ;
+ }
+
+ # What is the title of this entry?
+ my $title = '['.$biblabeller->citation_label($key,$_[1]).'] &nbsp;' ;
+ if ( ! $_[1]{'fields'}{'title'} ) {
+ Bib2HTML::General::Error::warm( "Can't found the title for the entry with key '".$key."'",
+ extract_file_from_location( $_[1]{'location'} ),
+ extract_line_from_location( $_[1]{'location'} ) ) ;
+ }
+ $title .= ucfirst($_[1]{'fields'}{'title'}) || '' ;
+ # Replies the title to the calling function
+ $_[4] = translate_html_entities(strip_html_tags($title)) ;
+ $_[4] =~ s/\s+/ /g;
+
+ # Computes the BibTeX verbatim part
+ my $bibtex_verb = '' ;
+ if ( $self->{'SHOW_BIBTEX'} ) {
+
+ my $e = new Bib2HTML::Translator::BibTeXEntry() ;
+ $bibtex_verb = $e->bibtex_build_entry_html($_[1]{'type'},"$key",
+ $_[1]{'original-fields'},
+ $self->{'CONTENT'}{'constants'},
+ 80) ;
+
+ if ( $bibtex_verb ) {
+ $bibtex_verb = $self->{'THEME'}->section( $self->{'LANG'}->get('I18N_LANG_FIELD_BIBTEX_VERBATIM'),
+ "<PRE><CODE>".
+ "$bibtex_verb".
+ "</CODE></PRE>",
+ $rootdir ) ;
+ }
+
+ }
+
+ # Computes the XML verbatim part
+ my $xml_verb = '' ;
+ if (( $self->genparam('xml-verbatim') )&&( $self->{'XML_GENERATOR'} )) {
+
+ $xml_verb = get_html_entities($self->{'XML_GENERATOR'}->create_the_standalone_xml_entry("$key")) ;
+
+ if ( $xml_verb ) {
+ $xml_verb = $self->{'THEME'}->section( $self->{'LANG'}->get('I18N_LANG_FIELD_XML_VERBATIM'),
+ "<PRE><CODE>".
+ "$xml_verb".
+ "</CODE></PRE>",
+ $rootdir ) ;
+ }
+
+ }
+
+ # Generates each main parts of the entry page
+ return [ $self->{'THEME'}->subtitle($title), # title
+ $self->{'THEME'}->build_twocolumn_array( $key." ". # main tabular
+ $self->{'THEME'}->small("(".
+ $self->{'SINGULAR_TYPE_LABELS'}{$_[1]{'type'}}.
+ ")"),
+ \@content ),
+ $annote, # user comments
+ $bibtex_verb, # BibTeX verbatim part
+ $xml_verb, # XML verbatim part
+ ] ;
+}
+
+=pod
+
+=item * copy_files()
+
+Generates the HTML pages.
+Overwrite this method.
+
+=cut
+sub copy_files() : method {
+ my $self = shift ;
+ my @source = File::Spec->splitdir($self->{'BIB2HTML'}{'PERLSCRIPTDIR'}) ;
+ @source = ( @source, split(/\:\:/, __PACKAGE__) ) ;
+ pop @source ;
+
+ # Copy icons
+ $self->copythisfile( File::Spec->catfile(@source,"valid-html401.gif"),
+ File::Spec->catfile($self->{'TARGET'},"valid-html401.gif") ) ;
+ $self->copythisfile( File::Spec->catfile(@source,"valid-css.gif"),
+ File::Spec->catfile($self->{'TARGET'},"valid-css.gif") ) ;
+ $self->copythisfile( File::Spec->catfile(@source,"loupe.gif"),
+ File::Spec->catfile($self->{'TARGET'},"loupe.gif") ) ;
+
+ # Copy the theme files
+ $self->{'THEME'}->copy_files() ;
+}
+
+=pod
+
+=item * copythisfile()
+
+Copy a file.
+Takes 2 args:
+
+=over
+
+=item * source (string)
+
+=item * target (string)
+
+=back
+
+=cut
+sub copythisfile($$) {
+ my $self = shift ;
+ my $source = $_[0] || '' ;
+ my $target = $_[1] || '' ;
+
+ Bib2HTML::General::Error::syserr( "you must give a source file to copy\n" )
+ unless ( $source ) ;
+ Bib2HTML::General::Error::syserr( "you must give a target file to copy\n" )
+ unless ( $target ) ;
+
+ my $sbase = basename("$target") ;
+
+ if ($self->is_restricted_file("$sbase")) {
+ $self->SUPER::copythisfile("$source","$target");
+ }
+
+ return 1 ;
+}
+
+=pod
+
+=item * generate_index_content()
+
+Generates the HTML index-???.html
+Overwrite this method.
+Takes 5 args:
+
+=over
+
+=item * entries (hash ref)
+
+is the associative array that this method must
+update to add some entry inside the index.
+
+=item * entry (hash ref)
+
+is the description of the current bibliographical entry
+
+=item * url (string)
+
+is the URL of the current entry
+
+=item * comment (string)
+
+is the comment associated to the current entry
+
+=item * rootdir (string)
+
+is the path to the root.
+
+=cut
+sub generate_index_content(\%$$$$) : method {
+ my $self = shift ;
+ my ($entry,$url,$comment,$rootdir) = ($_[1],$_[2],$_[3],$_[4]) ;
+}
+
+=pod
+
+=item * generate_overviewtree_content()
+
+Generates the HTML overview-tree.html.
+Overwrite this method.
+Takes 1 arg:
+
+=over
+
+=item * rootdir (string)
+
+is the path to the root.
+
+=back
+
+=cut
+sub generate_overviewtree_content($) : method {
+ my $self = shift ;
+ my $rootdir = shift ;
+ my @entries = $self->get_all_entries_ayt() ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ my $biblabeller = Bib2HTML::Translator::BibTeXEntry->new() ;
+ my $content = $self->{'THEME'}->title($self->{'LANG'}->get('I18N_LANG_ENTRY_TYPE_TREE')) ;
+
+ # Build the tree
+ my %tree = () ;
+ foreach my $entry (@entries) {
+ my $type = $self->{'CONTENT'}{'entries'}{$entry}{'type'} ;
+ if ( $self->{'PLURIAL_TYPE_LABELS'}{$type} ) {
+ my $typelabel = $self->{'THEME'}->strong($self->{'PLURIAL_TYPE_LABELS'}{$type}) ;
+ $typelabel =~ s/[ \t\n\r]+/&nbsp;/g ;
+ my $filename = $self->filename('entry',$entry) ;
+ my $name = $translator->formatnames( $self->__get_author_editor__($entry,''),
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'} ) ;
+ $name =~ s/[ \t\n\r]+/&nbsp;/g ;
+ my $title = $self->{'THEME'}->entry_title( extract_first_words( $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'title'},
+ 40 ) ) ;
+ $title =~ s/[ \t\n\r]+/&nbsp;/g ;
+ my $year = $self->__get_year__( $entry, '' ) ;
+ my $entrylabel = join( '',
+ "[",
+ $self->{'THEME'}->href( htmlcatfile($rootdir,$filename),
+ $biblabeller->citation_label($entry,$self->{'CONTENT'}{'entries'}{$entry}),
+ $self->browserframe('overview-summary') ),
+ "]&nbsp;",
+ $name,
+ ",&nbsp;",
+ $title,
+ ( $year ? "&nbsp;(". $year .")" : '' )
+ ) ;
+ $tree{$typelabel}{$entrylabel} = {} ;
+ }
+ }
+ # Generate the HTML representation of the tree
+ if ( $self->{'THEME'}->can('get_tree') ) {
+ $content .= $self->{'THEME'}->get_tree( \%tree, $rootdir, $self->{'LANG'}->get('I18N_LANG_DOCUMENTS') ) ;
+ }
+ else {
+ # Display the tree
+ if ( ! isemptyhash( \%tree ) ) {
+ my $treecontent = '' ;
+ foreach my $type (sortbyletters @{keys %tree}) {
+ if ( ! isemptyhash( $tree{$type} ) ) {
+ my $subs = '' ;
+ foreach my $entry (sortbyletters @{keys %{$tree{$type}}}) {
+ $subs .= $self->{'THEME'}->get_tree_leaf( $entry, $rootdir ) ;
+ }
+ $treecontent .= $self->{'THEME'}->get_tree_node( $type, $subs, $rootdir ) ;
+ }
+ }
+ if ( $treecontent ) {
+ $content .= $self->{'THEME'}->get_tree_node( '', $treecontent, $rootdir ) ;
+ }
+ }
+ }
+
+ return $content ;
+}
+
+=pod
+
+=item * generate_overview_content()
+
+Generates the HTML overview-summary.html.
+Overwrite this method.
+Takes 1 arg:
+
+=over
+
+=item * rootdir (string)
+
+is the path to the root.
+
+=back
+
+=cut
+sub generate_overview_content($) : method {
+ # Patch by Aurel Gabris added the 2006/04/10
+ my $self = shift ;
+ my $rootdir = shift ;
+ my $content = '' ;
+ my @entries = $self->get_all_entries_yat() ;
+ my $translator = Bib2HTML::Translator::BibTeXName->new() ;
+ my $currentyear = '' ;
+ my @tab = () ;
+
+ foreach my $entry (@entries) {
+ my $year = $self->__get_year__( $entry, '' ) ;
+ if ( "$currentyear" ne "$year" ) {
+ # Display tab
+ if ( @tab ) {
+ $content .= $self->{'THEME'}->build_twocolumn_array( $currentyear||
+ $self->{'LANG'}->get('I18N_LANG_NO_DATE'),
+ \@tab ) ;
+ }
+ @tab = () ;
+ $currentyear = $year ;
+ }
+ my $filename = $self->filename('entry',$entry) ;
+ push @tab, { 'name' => $self->{'THEME'}->href( htmlcatfile($rootdir,$filename),
+ $translator->formatnames( $self->__get_author_editor__($entry,''),
+ $self->{'FORMATS'}{'name'},
+ $self->{'FORMATS'}{'names'},
+ $self->genparam('max-names-overview')||1),
+ $self->browserframe('overview-summary') ),
+ 'explanation' => join( '',
+ $self->{'THEME'}->entry_title( extract_first_words( $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'title'},
+ $self->genparam('max-titlelength-overview')||70 ) ),
+ "<BR>\n",
+ (exists($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'journal'}) &&
+ exists($self->{'GENERATOR_PARAMS'}{'show-journalparams-overview'})) ?
+ $self->{'THEME'}->small($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'journal'}).(exists($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'volume'})?" ".$self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'volume'}.(exists($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'pages'})?", ".$self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'pages'}.(exists($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'year'})?" (".$self->{'CONTENT'}{'entries'}{$entry}{'fields'}{'year'}.")":""):""):""):
+ $self->{'THEME'}->small("(".
+ $self->{'SINGULAR_TYPE_LABELS'}{$self->{'CONTENT'}{'entries'}{$entry}{'type'}}.
+ ")") ),
+ } ;
+ }
+ if ( @tab ) {
+ # Display tab
+ $content .= $self->{'THEME'}->build_twocolumn_array( $currentyear||
+ $self->{'LANG'}->get('I18N_LANG_NO_DATE'),
+ \@tab ) ;
+ }
+ return $content ;
+}
+
+=pod
+
+=item * generate_overviewframe_content()
+
+Generates the HTML overview-frame.html.
+Overwrite this method.
+Takes 1 arg:
+
+=over
+
+=item * rootdir (string)
+
+is the path to the rootdirectory.
+
+=back
+
+=cut
+sub generate_overviewframe_content($) : method {
+ my $self = shift ;
+ my $rootdir = $_[0] || confess( 'you must supply the root directory' );
+ my @lines = () ;
+
+ # Generates the list of types
+ my @types = $self->get_entry_types() ;
+ my %typematching;
+ if ( exists($self->{'GENERATOR_PARAMS'}{'type-matching'}) ) {
+ %typematching = %{$self->{'GENERATOR_PARAMS'}{'type-matching'}};
+ }
+
+ if ( @types > 0 ) {
+ # fill emtpy type matching slots
+ foreach my $type (@types) {
+ if ( ! exists( $typematching{$type} ) ) {
+ $typematching{$type} = $type;
+ }
+ }
+ my @thevals = values %typematching;
+ foreach my $type (uniq(sort(@thevals))) {
+ if ( $self->{'PLURIAL_TYPE_LABELS'}{$type} ) {
+ my $url = $self->filename('type-overview',$type) ;
+ push @lines, $self->{'THEME'}->href( htmlcatfile($rootdir,$url),
+ $self->{'PLURIAL_TYPE_LABELS'}{$type},
+ $self->browserframe('allelements') ) ;
+ }
+ else {
+ confess( "You must supply a label for the entry type '$type'" ) ;
+ }
+ }
+ }
+
+ my $subframe = $self->{'THEME'}->frame_subpart( $self->{'LANG'}->get('I18N_LANG_FRAME_TITLE_TYPES'),
+ \@lines,
+ $rootdir ) ;
+
+ # Generates the list of authors
+ my $subframe2 ;
+ my %authors = $self->get_entry_authors() ;
+ my $parser = Bib2HTML::Translator::BibTeXName->new() ;
+ @lines = () ;
+ my @authors = keys %authors;
+ @authors = sortbyletters(@authors);
+ foreach my $author (@authors) {
+ if ( exists($self->{'GENERATOR_PARAMS'}{'author-regexp'}) ) {
+ if (! ( $parser->formatname($authors{$author}, 'l') =~ /$self->{'GENERATOR_PARAMS'}{'author-regexp'}/i)) { next };
+ }
+ my $url = $self->filename('author-overview',$author) ;
+ push @lines, $self->{'THEME'}->href( htmlcatfile($rootdir,$url),
+ $parser->formatname($authors{$author}, 'l, f.'),
+ $self->browserframe('allelements') ) ;
+ }
+ $subframe2 = $self->{'THEME'}->frame_subpart( $self->{'LANG'}->get('I18N_LANG_FRAME_TITLE_AUTHORS'),
+ \@lines,
+ $rootdir ) ;
+
+ return join('',$subframe,$subframe2) ;
+}
+
+#------------------------------------------------------
+#
+# Formatting backend
+#
+#------------------------------------------------------
+
+=pod
+
+=item * formatnames_url_backend()
+
+This method is called each time the BibTeXNames module
+must format an author's name with a URL.
+Takes 2 args:
+
+=over
+
+=item * author's data (hash)
+
+=item * label (string)
+
+=item * rootdir (string)
+
+=back
+
+=cut
+sub formatnames_url_backend($$$) {
+ my $self = shift ;
+ confess( 'you must supply the author\'s data' ) unless $_[0] ;
+ my $rootdir = $_[2] || confess( 'you must supply the root directory' );
+ my $data = $_[0] ;
+ my $label = $_[1] || '' ;
+ my $url = '' ;
+
+ if ($label) {
+ my $texname = Bib2HTML::Translator::BibTeXName->new() ;
+ # Search for the first author which corresponds to
+ # the specified one.
+ my %authors = $self->get_entry_authors() ;
+
+ my $k = undef ;
+ while ((!$k)&&(my $authorkey = each(%authors))) {
+ if ($texname->samenames($authors{$authorkey},$data)) {
+ $k = $authorkey ;
+ }
+ }
+ # Compute the filename for this author
+ if ($k) {
+ my $filename = $self->filename('author-overview',$k) ;
+ $url = $self->{'THEME'}->href($filename) ;
+ $url = $self->{'THEME'}->href( (($rootdir) ?
+ htmlcatfile($rootdir,$filename) :
+ $filename),
+ $label,
+ $self->browserframe('allelements') ) ;
+ }
+ }
+ if (!$url) {
+ $url = "$label";
+ }
+ return $url ;
+}
+
+#------------------------------------------------------
+#
+# Helpers
+#
+#------------------------------------------------------
+
+=pod
+
+=item * _add_sentence_keywords()
+Takes 5 args.
+
+=cut
+sub _add_sentence_keywords($$$$$) : method {
+ my $self = shift ;
+ my @words = get_title_keywords( $_[1] ) ;
+ foreach my $word (@words) {
+ if ( $word !~ /^[A-Z]+$/ ) {
+ $word = ucfirst($word) ;
+ }
+ my %desc = ( 'url' => $_[2],
+ 'label' => $word,
+ 'comment' => $_[3],
+ 'short-comment' => $_[4],
+ ) ;
+ my $sorttag = lc(remove_html_accents($word));
+ push @{$_[0]->{$sorttag}}, \%desc ;
+ }
+}
+
+#------------------------------------------------------
+#
+# Getters
+#
+#------------------------------------------------------
+
+=pod
+
+=item * filename()
+
+Replies the filename of the specified section.
+Takes 1 arg:
+
+=over
+
+=item * section (string)
+
+is the name of the section.
+
+=back
+
+=cut
+sub filename($) : method {
+ my $self = shift ;
+ my $section = $_[0] || '' ;
+
+ # Does the specified request already encountered?
+ if ( ($section) &&
+ ($section eq 'entry') &&
+ ($_[1]) &&
+ ($self->{'ENTRY_FILENAMES'}{$_[1]}) ) {
+ return $self->{'ENTRY_FILENAMES'}{$_[1]} ;
+ }
+ elsif ( ($section) &&
+ ($section eq 'author-overview') &&
+ ($_[1]) &&
+ ($self->{'AUTHOR_FILENAMES'}{$_[1]}) ) {
+ return $self->{'AUTHOR_FILENAMES'}{$_[1]} ;
+ }
+
+ # Compute a new filename
+ my $fn = $self->{'FILENAMES'}{$section} ;
+ confess( "filename not found for '$section'" ) unless $fn ;
+ my $i = 1 ;
+ while ( $fn =~ /\#\Q$i\E/ ) {
+ my $val = (defined($_[$i])) ? $_[$i] : '' ;
+ $fn =~ s/\#$i/$val/g ;
+ $i ++ ;
+ }
+
+ # Make sure that the filename could be supported by most of the
+ # operating systems
+ $fn =~ s/:/-/g if ($fn);
+
+ # Save the filename
+ if ( ($section) &&
+ ($section eq 'entry') &&
+ ($_[1]) ) {
+ $self->{'ENTRY_FILENAMES'}{$_[1]} = $fn ;
+ }
+ elsif ( ($section) &&
+ ($section eq 'author-overview') &&
+ ($_[1]) ) {
+ $self->{'AUTHOR_FILENAMES'}{$_[1]} = $fn ;
+ }
+
+ return $fn ;
+}
+
+=pod
+
+=item * browserframe()
+
+Replies the frame used for the specified section.
+Takes 1 arg:
+
+=over
+
+=item * section (string)
+
+is the name of the section.
+
+=back
+
+=cut
+sub browserframe($) : method {
+ my $self = shift ;
+ my $section = $_[0] || '' ;
+ my $fr = $self->{'FRAMES'}{$section} ;
+ confess( "frame not found for '$section'" ) unless $fr ;
+ return $fr ;
+}
+
+
+=pod
+
+=item * getNavigationButtons()
+
+Replies the additional buttons for the navigation bar.
+Takes 1 arg:
+
+=over
+
+=item * exception (optional mixed)
+
+is the list of label to not reply.
+
+=back
+
+=cut
+sub getNavigationButtons : method {
+ my $self = shift ;
+ my @buttons = () ;
+ if ( int(@_) > 0 ) {
+ if ( isarray($_[0]) ) {
+ foreach my $button (@{$self->{'USER_NAVIGATION_BUTTONS'}}) {
+ if ( ! strinarray($button->{'label'},$_[0]) ) {
+ push @buttons, $button ;
+ }
+ }
+ }
+ else {
+ foreach my $button (@{$self->{'USER_NAVIGATION_BUTTONS'}}) {
+ if ( ! strinarray($button->{'label'},\@_) ) {
+ push @buttons, $button ;
+ }
+ }
+ }
+ }
+ else {
+ @buttons = @{$self->{'USER_NAVIGATION_BUTTONS'}} ;
+ }
+ return \@buttons ;
+}
+
+=pod
+
+=item * addNavigationButton()
+
+Adds an additional button for the navigation bar.
+Takes 2 args:
+
+=over
+
+=item * url (string)
+
+is the URL for the new button
+
+=item * key (string)
+
+is the language string identifier that corresponds
+to the label of the button.
+
+=back
+
+=cut
+sub addNavigationButton($$) : method {
+ my $self = shift ;
+ my $url = $_[0] || '' ;
+ my $label = $_[1] || '' ;
+ return unless (($url)&&($label)) ;
+ push @{$self->{'USER_NAVIGATION_BUTTONS'}}, { 'url' => "$url",
+ 'label' => "$label",
+ } ;
+}
+
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang.pm
new file mode 100644
index 0000000000..803c950ce1
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang.pm
@@ -0,0 +1,319 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::Lang - A Language support for the generators
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::Lang ;
+
+my $gen = Bib2HTML::Generator::Lang->new( name, defs ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::Lang is a Perl module, which proposes
+a generic language support for all the generators.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::Lang;
+
+ my $gen = Bib2HTML::Generator::Lang->new( 'English',
+ '/usr/lib/bib2html/Langs/English' ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * name (string)
+
+is the name of the current language.
+
+=item * defs_path (string)
+
+is the filename of the file which contains the definitions.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Lang.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::Lang;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+
+use Carp ;
+
+use Bib2HTML::General::Error ;
+use Bib2HTML::Release ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of language support
+my $VERSION = "3.0" ;
+
+# Language definitions
+my %LANG_DEFS = ( ) ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $filename = $_[1];
+ my $self = { 'defs' => {},
+ 'name' => $_[0] || 'unknow',
+ } ;
+ bless( $self, $class );
+
+ foreach my $key (keys %LANG_DEFS) {
+ $self->{'defs'}->{$key} = $LANG_DEFS{$key} ;
+ }
+
+ %{$self->{'defs'}} = $self->loadScript("$filename");
+
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Getters
+#
+#------------------------------------------------------
+
+sub get_final_copyright() {
+ my $final_copyright = 1998;
+ my $soft_release = getVersionDate();
+ if ($soft_release =~ /^([0-9]+)\/[0-9]+\/[0-9]+$/) {
+ if ($1<=98) {
+ $final_copyright = 2000 + $1;
+ }
+ elsif ($1==99) {
+ $final_copyright = 1999;
+ }
+ else {
+ $final_copyright = $1;
+ }
+ }
+
+ if ($final_copyright!=1998) {
+ $final_copyright = "1998-$final_copyright";
+ }
+
+ return $final_copyright;
+}
+
+sub replace_function_calls($) {
+ my $str = shift;
+ $str =~ s/\{\{\*([a-zA-Z0-9_]+)\}\}/{local *s=$1;&s();}/eg;
+ return $str;
+}
+
+sub loadScript($) {
+ my $self = shift;
+ my $filename = shift;
+
+ my %defs = ();
+
+ if (($filename)&&(-r "$filename")) {
+ local *LANG_FILE;
+ open *LANG_FILE, "<$filename"
+ or Bib2HTML::General::Error::syserr( "Unable to find the language file '$filename': $!\n" );
+
+ my $lastkey = undef;
+ while (my $line = <LANG_FILE>) {
+ if ($lastkey) {
+ $line =~ s/^\s+//;
+ if ($line =~ /^(.*?)\s*\\\s*$/) {
+ $line = $1;
+ $defs{'$lastkey'} .= ' ' if ($defs{'$lastkey'});
+ $defs{"$lastkey"} .= replace_function_calls("$line");
+ }
+ else {
+ $line =~ s/\s+$//;
+ $defs{'$lastkey'} .= ' ' if ($defs{'$lastkey'});
+ $defs{"$lastkey"} .= replace_function_calls("$line");
+ $lastkey = undef;
+ }
+ }
+ else {
+ if (($line)&&($line =~ /^\s*([a-aA-Z0-9_\-:]+)\s*=\s*(.*)?\s*$/)) {
+ my ($key,$value) = ($1,$2);
+ if ($value =~ /^(.*?)\s*\\\s*$/) {
+ $value = $1;
+ $lastkey = $key;
+ }
+ else {
+ $value =~ s/\s+$//;
+ }
+ $defs{"$key"} = replace_function_calls("$value");
+ }
+ }
+ }
+
+ close *LANG_FILE;
+ }
+
+ return %defs;
+}
+
+=pod
+
+=item * get()
+
+Replies the specified string according to the language.
+Takes at least 1 arg:
+
+=over
+
+=item * id (string)
+
+is the id of the string.
+
+=item * param1 (string)
+
+is a string which must replace the string "#1" in the language definition.
+
+=item * param2 (string)
+
+is a string which must replace the string "#2" in the language definition.
+
+=item ...
+
+=back
+
+=cut
+sub get($) : method {
+ my $self = shift ;
+ my $id = shift || confess( 'you must supply the id' ) ;
+ my $str = ( ( exists $self->{'defs'}{$id} ) ?
+ $self->{'defs'}{$id} : '' ) ;
+ Bib2HTML::General::Error::syserr( "the string id '$id' is not defined ".
+ "for the current language '".$self->{'name'}."'" ) unless $str ;
+ if ( @_ ) {
+ for(my $i=0; $i<=$#_; $i++ ) {
+ my $j = $i+1 ;
+ my $s = $_[$i] || "#$j" ;
+ $str =~ s/#$j/$s/g ;
+ }
+ }
+ return $str ;
+}
+
+=pod
+
+=item * _get_noerror()
+
+Replies the specified string according to the language.
+Takes at least 1 arg:
+
+=over
+
+=item * id (string)
+
+is the id of the string.
+
+=item * param1 (string)
+
+is a string which must replace the string "#1" in the language definition.
+
+=item * param2 (string)
+
+is a string which must replace the string "#2" in the language definition.
+
+=item ...
+
+=back
+
+=cut
+sub _get_noerror($) : method {
+ my $self = shift ;
+ my $id = shift || confess( 'you must supply the id' ) ;
+ my $str = ( ( exists $self->{'defs'}{$id} ) ?
+ $self->{'defs'}{$id} : '' ) ;
+ return undef unless $str ;
+ if ( @_ ) {
+ for(my $i=0; $i<=$#_; $i++ ) {
+ my $j = $i+1 ;
+ my $s = $_[$i] || "#$j" ;
+ $str =~ s/#$j/$s/g ;
+ }
+ }
+ return $str ;
+}
+
+=pod
+
+=item * getname()
+
+Replies the name of the current language.
+
+=cut
+sub getname() : method {
+ my $self = shift ;
+ return $self->{'name'} ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English
new file mode 100644
index 0000000000..050a32be41
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English
@@ -0,0 +1,86 @@
+# English support for the generators.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_BIB2HTML_COPYRIGHT = This document was generated by #1.<BR>\
+ Copyright &copy; {{*get_final_copyright}} #2 (under the #3)
+I18N_LANG_DEFAULT_TITLE = BibTeX
+I18N_LANG_DOCUMENTS = Documents
+I18N_LANG_FIELD_ADDRESS = Address
+I18N_LANG_FIELD_ADSURL = Link to ADS
+I18N_LANG_FIELD_ABSTRACT = Abstract
+I18N_LANG_FIELD_ABSTRACT_KEYWORDS = Abstract &amp; Keywords
+I18N_LANG_FIELD_ANNOTATION = Annotation
+I18N_LANG_FIELD_AUTHORS = Author(s)
+I18N_LANG_FIELD_CHAPTER = Chapter of
+I18N_LANG_FIELD_DATE = Date
+I18N_LANG_FIELD_DOI = Document on Internet
+I18N_LANG_FIELD_DOWNLOAD = Download the complete article: #1
+I18N_LANG_FIELD_EDITION = Edition
+I18N_LANG_FIELD_EDITORS = Editor(s)
+I18N_LANG_FIELD_HOWPUBLISHED = How published
+I18N_LANG_FIELD_IN = In
+I18N_LANG_FIELD_INSTITUTION = Institution
+I18N_LANG_FIELD_ISBN = ISBN number
+I18N_LANG_FIELD_ISSN = ISSN number
+I18N_LANG_FIELD_JOURNAL = Journal
+I18N_LANG_FIELD_KEYWORDS = <strong>Keywords</strong>: #1
+I18N_LANG_FIELD_KEYWORDS_TITLE = Keywords
+I18N_LANG_FIELD_NOTE = Note
+I18N_LANG_FIELD_NUMBER = Number
+I18N_LANG_FIELD_ORGANIZATION = Organization
+I18N_LANG_FIELD_PAGES = Page(s)
+I18N_LANG_FIELD_PDFFILE = PDF
+I18N_LANG_FIELD_PUBLISHER = Publisher
+I18N_LANG_FIELD_READERS = Reader(s)
+I18N_LANG_FIELD_SCHOOL = School
+I18N_LANG_FIELD_SERIES = Series
+I18N_LANG_FIELD_TITLE = Title
+I18N_LANG_FIELD_TYPE = Type
+I18N_LANG_FIELD_URL = URL
+I18N_LANG_FIELD_VOLUME = Volume
+I18N_LANG_FIELD_YEAR = Year
+I18N_LANG_FORMAT_NAME = l{ (v)}{ f.}{, j}
+I18N_LANG_FORMAT_NAMES = { and }{, }
+I18N_LANG_KEYWORDS = Key-words
+I18N_LANG_P_ARTICLE = Articles
+I18N_LANG_P_BOOK = Books
+I18N_LANG_P_BOOKLET = Not-sponsored books
+I18N_LANG_P_INBOOK = Book parts
+I18N_LANG_P_INCOLLECTION = In a collection
+I18N_LANG_P_INPROCEEDINGS = In proceedings
+I18N_LANG_P_MANUAL = Technical manuals
+I18N_LANG_P_MASTERTHESIS = Master's thesis
+I18N_LANG_P_MISC = 'Miscellaneous documents'
+I18N_LANG_P_PHDTHESIS = PhD thesis
+I18N_LANG_P_PROCEEDINGS = Conference proceedings
+I18N_LANG_P_TECHREPORT = Technical reports
+I18N_LANG_P_UNPUBLISHED = Unpublished
+I18N_LANG_S_ARTICLE = Article
+I18N_LANG_S_BOOK = Book
+I18N_LANG_S_BOOKLET = Not-sponsored book
+I18N_LANG_S_INBOOK = Book part
+I18N_LANG_S_INCOLLECTION = In a collection
+I18N_LANG_S_INPROCEEDINGS = In proceedings
+I18N_LANG_S_MANUAL = Technical manual
+I18N_LANG_S_MASTERTHESIS = Master's thesis
+I18N_LANG_S_MISC = 'Miscellaneous document'
+I18N_LANG_S_PHDTHESIS = PhD thesis
+I18N_LANG_S_PROCEEDINGS = Conference proceedings
+I18N_LANG_S_TECHREPORT = Technical report
+I18N_LANG_S_UNPUBLISHED = Unpublished
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.HTMLGen b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.HTMLGen
new file mode 100644
index 0000000000..798491eb2a
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.HTMLGen
@@ -0,0 +1,54 @@
+# English support for the generator HTMLGen.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_ALL_ELEMENTS = All Elements
+I18N_LANG_ARTICLESINSAMEDOMAINS = Documents in the same domains
+I18N_LANG_FIELD_BIBTEX_VERBATIM = BibTeX code
+I18N_LANG_FIELD_XML_VERBATIM = XML code
+I18N_LANG_DEFAULT_TITLE = Bibliography
+I18N_LANG_DOMAIN_TREE = Domain Tree
+I18N_LANG_DOMAINS = Domains
+I18N_LANG_ENTRY_TYPE_TREE = Hierarchical list by entry type
+I18N_LANG_FRAME_TITLE_AUTHORS = Authors
+I18N_LANG_FRAME_TITLE_TYPES = Types
+I18N_LANG_FRAMES = Frames
+I18N_LANG_INDEX = Index
+I18N_LANG_INDEX_COMMENT_ARTICLE = article
+I18N_LANG_INDEX_COMMENT_AUTHOR = author
+I18N_LANG_INDEX_COMMENT_BOOKTITLE = booktitle
+I18N_LANG_INDEX_COMMENT_EDITOR = editor
+I18N_LANG_INDEX_COMMENT_HOWPUBLISHED = publication mean
+I18N_LANG_INDEX_COMMENT_INSTITUTION = institution
+I18N_LANG_INDEX_COMMENT_PUBLISHER = publisher
+I18N_LANG_INDEX_COMMENT_SCHOOL = school
+I18N_LANG_INDEX_COMMENT_TITLE = title
+I18N_LANG_NEXT = Next
+I18N_LANG_NO_DATE = Not dated
+I18N_LANG_NO_FRAME = No Frame
+I18N_LANG_NO_FRAME_ALERT = <H2>Frame Alert</H2>\
+ <P>This document is designed to be\
+ viewed using the frames feature. If\
+ you see this message, you are using a\
+ non-frame-capable web client.<BR>\
+ Link to <A HREF="#1">Non-frame version.</A>.<BR>#2
+I18N_LANG_OVERVIEW = Overview
+I18N_LANG_PREV = Prev
+I18N_LANG_TREE = Tree
+I18N_LANG_SMALL_IN = in:&nbsp;#1
+I18N_LANG_SUBMIT_BUG = Submit a bug
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.Theme.Dyna b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.Theme.Dyna
new file mode 100644
index 0000000000..03fce9ef60
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/English.Theme.Dyna
@@ -0,0 +1,22 @@
+# English support for the Dyna theme.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_THEME_SUMMARY_BAR = SUMMARY: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_DETAIL_BAR = DETAIL: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_TREE_ROOT = Root
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French
new file mode 100644
index 0000000000..bfbf3e5818
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French
@@ -0,0 +1,86 @@
+# French support for the generators.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_BIB2HTML_COPYRIGHT = Ce document a &eacute;t&eacute; g&eacute;n&eacute;r&eacute; \
+ par #1.<BR>Copyright &copy; {{*get_final_copyright}} #2 (licence #3)
+I18N_LANG_DEFAULT_TITLE = BibTeX
+I18N_LANG_DOCUMENTS = Documents
+I18N_LANG_FIELD_ADDRESS = Adresse
+I18N_LANG_FIELD_ADSURL = Lien vers ADS
+I18N_LANG_FIELD_ABSTRACT = R&eacute;sum&eacute;
+I18N_LANG_FIELD_ABSTRACT_KEYWORDS = R&eacute;sum&eacute; &amp; Mots-cl&eacute;s
+I18N_LANG_FIELD_ANNOTATION = Annotation
+I18N_LANG_FIELD_AUTHORS = Auteur(s)
+I18N_LANG_FIELD_CHAPTER = Chapitre de
+I18N_LANG_FIELD_DATE = Date
+I18N_LANG_FIELD_DOI = Document sur Internet
+I18N_LANG_FIELD_DOWNLOAD = T&eacute;l&eacute;charger une version compl&egrave;te de ce document&nbsp;: #1
+I18N_LANG_FIELD_EDITION = &Eacute;dition
+I18N_LANG_FIELD_EDITORS = R&eacute;dacteur(s) en chef
+I18N_LANG_FIELD_HOWPUBLISHED = Moyen de publication
+I18N_LANG_FIELD_IN = In
+I18N_LANG_FIELD_INSTITUTION = Institution
+I18N_LANG_FIELD_ISBN = Num&eacute;ro ISBN
+I18N_LANG_FIELD_ISSN = Num&eacute;ro ISSN
+I18N_LANG_FIELD_JOURNAL = Journal
+I18N_LANG_FIELD_KEYWORDS = <strong>Mots-cl&eacute;s</strong>: #1
+I18N_LANG_FIELD_KEYWORDS_TITLE = Mots-cl&eacute;s
+I18N_LANG_FIELD_NOTE = Note
+I18N_LANG_FIELD_NUMBER = Num&eacute;ro
+I18N_LANG_FIELD_ORGANIZATION = Organisation
+I18N_LANG_FIELD_PAGES = Page(s)
+I18N_LANG_FIELD_PDFFILE = PDF
+I18N_LANG_FIELD_PUBLISHER = &Eacute;diteur
+I18N_LANG_FIELD_READERS = Lecteur(s)
+I18N_LANG_FIELD_SCHOOL = &Eacute;cole
+I18N_LANG_FIELD_SERIES = S&eacute;rie(s)
+I18N_LANG_FIELD_TITLE = Titre
+I18N_LANG_FIELD_TYPE = Type
+I18N_LANG_FIELD_URL = URL
+I18N_LANG_FIELD_VOLUME = Volume
+I18N_LANG_FIELD_YEAR = Ann&eacute;e
+I18N_LANG_FORMAT_NAME = l{ (v)}{ f.}{, j}
+I18N_LANG_FORMAT_NAMES = { et }{, }
+I18N_LANG_KEYWORDS = Mots-clés
+I18N_LANG_P_ARTICLE = Articles
+I18N_LANG_P_BOOK = Livres
+I18N_LANG_P_BOOKLET = Livres sans éditeur
+I18N_LANG_P_INBOOK = Parties de livre
+I18N_LANG_P_INCOLLECTION = Articles dans des collections
+I18N_LANG_P_INPROCEEDINGS = Articles dans des actes de conf&eacute;rences
+I18N_LANG_P_MANUAL = Manuels techniques
+I18N_LANG_P_MASTERTHESIS = M&eacute;moire d'ing&eacute;nieur
+I18N_LANG_P_MISC = 'Documents divers'
+I18N_LANG_P_PHDTHESIS = M&eacute;moires de recherche
+I18N_LANG_P_PROCEEDINGS = Actes de conférences
+I18N_LANG_P_TECHREPORT = Documentations techniques
+I18N_LANG_P_UNPUBLISHED = Non publi&eacute;s
+I18N_LANG_S_ARTICLE = Article
+I18N_LANG_S_BOOK = Livre
+I18N_LANG_S_BOOKLET = Livre sans éditeur
+I18N_LANG_S_INBOOK = Partie de livre
+I18N_LANG_S_INCOLLECTION = Article dans une collection
+I18N_LANG_S_INPROCEEDINGS = Article dans des actes de conf&eacute;rence
+I18N_LANG_S_MANUAL = Manuel technique
+I18N_LANG_S_MASTERTHESIS = M&eacute;moire d'ingénieur
+I18N_LANG_S_MISC = 'Document divers'
+I18N_LANG_S_PHDTHESIS = M&eacute;moire de recherche
+I18N_LANG_S_PROCEEDINGS = Actes de confi&eacute;rence
+I18N_LANG_S_TECHREPORT = Rapport technique
+I18N_LANG_S_UNPUBLISHED = Non publi&eacute;
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.HTMLGen b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.HTMLGen
new file mode 100644
index 0000000000..3da9bb32b9
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.HTMLGen
@@ -0,0 +1,55 @@
+# French support for the generator HTMLGen.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_ALL_ELEMENTS = Tous les &eacute;l&eacute;ments
+I18N_LANG_ARTICLESINSAMEDOMAINS = Documents dans le m&ecirc;me domaine
+I18N_LANG_FIELD_BIBTEX_VERBATIM = Code BibTeX
+I18N_LANG_FIELD_XML_VERBATIM = Code XML
+I18N_LANG_DEFAULT_TITLE = Bibliographie
+I18N_LANG_DOMAIN_TREE = Arbre des domaines
+I18N_LANG_DOMAINS = Domaines
+I18N_LANG_ENTRY_TYPE_TREE = Liste hi&eacute;rarchique par type d'entr&eacute;e
+I18N_LANG_FRAME_TITLE_AUTHORS = Auteurs
+I18N_LANG_FRAME_TITLE_TYPES = Types
+I18N_LANG_FRAMES = Frames
+I18N_LANG_INDEX = Index
+I18N_LANG_INDEX_COMMENT_ARTICLE = article
+I18N_LANG_INDEX_COMMENT_AUTHOR = auteur
+I18N_LANG_INDEX_COMMENT_BOOKTITLE = title de livre
+I18N_LANG_INDEX_COMMENT_EDITOR = r&eacute;dacteur en chef
+I18N_LANG_INDEX_COMMENT_HOWPUBLISHED = moyen de publication
+I18N_LANG_INDEX_COMMENT_INSTITUTION = institution
+I18N_LANG_INDEX_COMMENT_PUBLISHER = &eacute;diteur
+I18N_LANG_INDEX_COMMENT_SCHOOL = &eacute;cole
+I18N_LANG_INDEX_COMMENT_TITLE = titre
+I18N_LANG_NEXT = Suivant
+I18N_LANG_NO_DATE = Non dat&eacute;
+I18N_LANG_NO_FRAME = Pas de Frame
+I18N_LANG_NO_FRAME_ALERT = <H2>Support des cadres</H2>\
+ <P>Ce document est con&ccedil; pour &ecirc;tre \
+ visualis&eacute; avec des cadres (frames). \
+ Le fait de lire ce message indique que vous \
+ utilis&eacute; un navigateur ne supportant \
+ pas les frames.<BR> Lien vers la <A HREF="#1">\
+ version sans frame.</A>.<BR>\n#2
+I18N_LANG_OVERVIEW = Page principale
+I18N_LANG_PREV = Pr&eacute;d
+I18N_LANG_TREE = Arbre
+I18N_LANG_SMALL_IN = in:&nbsp;#1
+I18N_LANG_SUBMIT_BUG = Soumettre un bug
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.Theme.Dyna b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.Theme.Dyna
new file mode 100644
index 0000000000..0004c6ab3c
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/French.Theme.Dyna
@@ -0,0 +1,22 @@
+# French support for the Dyna theme.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_THEME_SUMMARY_BAR = R&Eacute;SUM&Eacute;: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_DETAIL_BAR = D&Eacute;TAIL: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_TREE_ROOT = Racine
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian
new file mode 100644
index 0000000000..e5f962412f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian
@@ -0,0 +1,86 @@
+# Italian support for the generators.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_BIB2HTML_COPYRIGHT = Documento generato da #1.<BR>\
+ Copyright &copy; {{{*get_final_copyright}} #2 (sotto la #3)
+I18N_LANG_DEFAULT_TITLE = BibTeX
+I18N_LANG_DOCUMENTS = Documenti
+I18N_LANG_FIELD_ADDRESS = Indirizzo
+I18N_LANG_FIELD_ADSURL = Collegamento al ADS
+I18N_LANG_FIELD_ABSTRACT = Abstract
+I18N_LANG_FIELD_ABSTRACT_KEYWORDS = Abstract &amp; Parole chiave
+I18N_LANG_FIELD_ANNOTATION = Annotazione
+I18N_LANG_FIELD_AUTHORS = Autore
+I18N_LANG_FIELD_CHAPTER = Capitolo di
+I18N_LANG_FIELD_DATE = Data
+I18N_LANG_FIELD_DOI = Documento sul Internet
+I18N_LANG_FIELD_DOWNLOAD = Scarica articolo completo: #1
+I18N_LANG_FIELD_EDITION = Edizione
+I18N_LANG_FIELD_EDITORS = Curatore
+I18N_LANG_FIELD_HOWPUBLISHED = Modalità di pubblicazione
+I18N_LANG_FIELD_IN = In
+I18N_LANG_FIELD_INSTITUTION = Istituzione
+I18N_LANG_FIELD_ISBN = Numero ISBN
+I18N_LANG_FIELD_ISSN = Numero ISSN
+I18N_LANG_FIELD_JOURNAL = Rivista
+I18N_LANG_FIELD_KEYWORDS = <strong>Parole chiave</strong>: #1
+I18N_LANG_FIELD_KEYWORDS_TITLE = Parole chiave
+I18N_LANG_FIELD_NOTE = Nota
+I18N_LANG_FIELD_NUMBER = Numero
+I18N_LANG_FIELD_ORGANIZATION = Organizzazione
+I18N_LANG_FIELD_PAGES = Pagine
+I18N_LANG_FIELD_PDFFILE = PDF
+I18N_LANG_FIELD_PUBLISHER = Editore
+I18N_LANG_FIELD_READERS = Lettori
+I18N_LANG_FIELD_SCHOOL = Scuola
+I18N_LANG_FIELD_SERIES = Serie
+I18N_LANG_FIELD_TITLE = Titolo
+I18N_LANG_FIELD_TYPE = Tipo
+I18N_LANG_FIELD_URL = URL
+I18N_LANG_FIELD_VOLUME = Volume
+I18N_LANG_FIELD_YEAR = Anno
+I18N_LANG_FORMAT_NAME = l{ (v)}{ f.}{, j}
+I18N_LANG_FORMAT_NAMES = { e }{, }
+I18N_LANG_KEYWORDS = Parole chiavi
+I18N_LANG_P_ARTICLE = Articoli
+I18N_LANG_P_BOOK = Libri
+I18N_LANG_P_BOOKLET = Libretti
+I18N_LANG_P_INBOOK = Parte di libro
+I18N_LANG_P_INCOLLECTION = In raccolte
+I18N_LANG_P_INPROCEEDINGS = In atti
+I18N_LANG_P_MANUAL = Manuali tecnici
+I18N_LANG_P_MASTERTHESIS = Tesi di master
+I18N_LANG_P_MISC = 'Documenti vari'
+I18N_LANG_P_PHDTHESIS = Tesi di dottorato
+I18N_LANG_P_PROCEEDINGS = Atti di conferenze
+I18N_LANG_P_TECHREPORT = Rapporti tecnici
+I18N_LANG_P_UNPUBLISHED = Non pubblicati
+I18N_LANG_S_ARTICLE = articolo
+I18N_LANG_S_BOOK = libro
+I18N_LANG_S_BOOKLET = libretto
+I18N_LANG_S_INBOOK = parte di libro
+I18N_LANG_S_INCOLLECTION = parte di una raccolta
+I18N_LANG_S_INPROCEEDINGS = parte di atti
+I18N_LANG_S_MANUAL = manuale tecnico
+I18N_LANG_S_MASTERTHESIS = tesi di master
+I18N_LANG_S_MISC = 'documenti vari'
+I18N_LANG_S_PHDTHESIS = tesi di dottorato
+I18N_LANG_S_PROCEEDINGS = atti di conferenze
+I18N_LANG_S_TECHREPORT = rapporto tecnico
+I18N_LANG_S_UNPUBLISHED = non pubblicato
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.HTMLGen b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.HTMLGen
new file mode 100644
index 0000000000..393907d803
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.HTMLGen
@@ -0,0 +1,56 @@
+# Italian support for the generators.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_ALL_ELEMENTS = Tutti i documenti
+I18N_LANG_ARTICLESINSAMEDOMAINS = Documenti negli stessi domini
+I18N_LANG_FIELD_BIBTEX_VERBATIM = Codice BibTeX
+I18N_LANG_FIELD_XML_VERBATIM = Codice XML
+I18N_LANG_DEFAULT_TITLE = Bibliografia
+I18N_LANG_DOMAIN_TREE = Albero dei domini
+I18N_LANG_DOMAINS = Domini
+I18N_LANG_ENTRY_TYPE_TREE = Elenco gerarchico per tipo di documento
+I18N_LANG_FRAME_TITLE_AUTHORS = Autori
+I18N_LANG_FRAME_TITLE_TYPES = Tipi
+I18N_LANG_FRAMES = Frame
+I18N_LANG_INDEX = Indice
+I18N_LANG_INDEX_COMMENT_ARTICLE = Articolo
+I18N_LANG_INDEX_COMMENT_AUTHOR = Autore
+I18N_LANG_INDEX_COMMENT_BOOKTITLE = Titolo
+I18N_LANG_INDEX_COMMENT_EDITOR = Curatore
+I18N_LANG_INDEX_COMMENT_HOWPUBLISHED = Modalità di pubblicazione
+I18N_LANG_INDEX_COMMENT_INSTITUTION = Istituzione
+I18N_LANG_INDEX_COMMENT_PUBLISHER = Editore
+I18N_LANG_INDEX_COMMENT_SCHOOL = Scuola
+I18N_LANG_INDEX_COMMENT_TITLE = Titolo
+I18N_LANG_NEXT = Successivo
+I18N_LANG_NO_DATE = Non datati
+I18N_LANG_NO_FRAME = Pagina unica
+I18N_LANG_NO_FRAME_ALERT = <H2>Attenzione</H2>\
+ <P>Questo documento è destinato ad \
+ essere visualizzato usando i frame. \
+ Se visualizzate questo messaggio \
+ state utilizzando un client che non \
+ supporta i frame.<BR>\
+ Si veda la <A HREF="#1">Versione senza \
+ frame.</A>.<BR>\n#2
+I18N_LANG_OVERVIEW = Per anno
+I18N_LANG_PREV = Precedente
+I18N_LANG_TREE = Per tipo
+I18N_LANG_SMALL_IN = in:&nbsp;#1
+I18N_LANG_SUBMIT_BUG = Segnalazione bug
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.Theme.Dyna b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.Theme.Dyna
new file mode 100644
index 0000000000..c715bf6c18
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Italian.Theme.Dyna
@@ -0,0 +1,22 @@
+# Italian support for the Dyna theme.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_THEME_SUMMARY_BAR = RIASSUNTO: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_DETAIL_BAR = DETTAGLIO: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_TREE_ROOT = Radice
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese
new file mode 100644
index 0000000000..a668ef8033
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese
@@ -0,0 +1,86 @@
+# Portuguese support for the generators.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_BIB2HTML_COPYRIGHT = Este documento foi gerado por #1.<BR>\
+ Copyright &copy; {{*get_final_copyright}} #2 (licen&ccedil;a #3)
+I18N_LANG_DEFAULT_TITLE = BibTeX
+I18N_LANG_DOCUMENTS = Documentos
+I18N_LANG_FIELD_ADDRESS = Endere&ccedil;o
+I18N_LANG_FIELD_ADSURL = Liga&ccedil;&atilde;o ao ADS
+I18N_LANG_FIELD_ABSTRACT = Resumo
+I18N_LANG_FIELD_ABSTRACT_KEYWORDS = Resumo &amp; Palavras-chave
+I18N_LANG_FIELD_ANNOTATION = Anota&ccedil;&otilde;es
+I18N_LANG_FIELD_AUTHORS = Autor(es)
+I18N_LANG_FIELD_CHAPTER = Cap&iacute;tulo de
+I18N_LANG_FIELD_DATE = Data
+I18N_LANG_FIELD_DOI = Original no Internet
+I18N_LANG_FIELD_DOWNLOAD = Obter o artigo completo: #1
+I18N_LANG_FIELD_EDITION = Edi&ccedil;&atilde;o
+I18N_LANG_FIELD_EDITORS = Editor(es)
+I18N_LANG_FIELD_HOWPUBLISHED = Publicado como
+I18N_LANG_FIELD_IN = Em
+I18N_LANG_FIELD_INSTITUTION = Institui&ccedil;&atilde;o
+I18N_LANG_FIELD_ISBN = N&uacute;mero ISBN
+I18N_LANG_FIELD_ISSN = N&uacute;mero ISSN
+I18N_LANG_FIELD_JOURNAL = Journal
+I18N_LANG_FIELD_KEYWORDS = <strong>Palavras-chave</strong>: #1
+I18N_LANG_FIELD_KEYWORDS_TITLE = Palavras-chave
+I18N_LANG_FIELD_NOTE = Nota
+I18N_LANG_FIELD_NUMBER = N&uacute;mero
+I18N_LANG_FIELD_ORGANIZATION = Organiza&ccedil;&atilde;o
+I18N_LANG_FIELD_PAGES = P&aacute;gina(s)
+I18N_LANG_FIELD_PDFFILE = PDF
+I18N_LANG_FIELD_PUBLISHER = Editora
+I18N_LANG_FIELD_READERS = Leitor(es)
+I18N_LANG_FIELD_SCHOOL = Escola
+I18N_LANG_FIELD_SERIES = S&eacute;ries
+I18N_LANG_FIELD_TITLE = Título
+I18N_LANG_FIELD_TYPE = Tipo
+I18N_LANG_FIELD_URL = URL
+I18N_LANG_FIELD_VOLUME = Volume
+I18N_LANG_FIELD_YEAR = Ano
+I18N_LANG_FORMAT_NAME = l{ (v)}{ f.}{, j}
+I18N_LANG_FORMAT_NAMES = { e }{, }
+I18N_LANG_KEYWORDS = Palavras-chaves
+I18N_LANG_P_ARTICLE = Artigos
+I18N_LANG_P_BOOK = Livros
+I18N_LANG_P_BOOKLET = Livros sem editor
+I18N_LANG_P_INBOOK = Partes de livros
+I18N_LANG_P_INCOLLECTION = Artigos numa colec&ccedil;&atilde;o
+I18N_LANG_P_INPROCEEDINGS = Artigos em actas de confer&ecirc;ncias
+I18N_LANG_P_MANUAL = Manuais t&eacute;cnicos
+I18N_LANG_P_MASTERTHESIS = Teses de mestrado
+I18N_LANG_P_MISC = 'Documentos diversos'
+I18N_LANG_P_PHDTHESIS = Teses de doutoramento
+I18N_LANG_P_PROCEEDINGS = Actas de confer&ecirc;ncias
+I18N_LANG_P_TECHREPORT = Relat&oacute;rios t&eacute;cnicos
+I18N_LANG_P_UNPUBLISHED = N&atilde;o publicados
+I18N_LANG_S_ARTICLE = Artigo
+I18N_LANG_S_BOOK = Livro
+I18N_LANG_S_BOOKLET = Livros sem editor
+I18N_LANG_S_INBOOK = Parte de livro
+I18N_LANG_S_INCOLLECTION = Artigo numa colec&ccedil;&atilde;o
+I18N_LANG_S_INPROCEEDINGS = Artigo em actas de confer&ecirc;ncias
+I18N_LANG_S_MANUAL = Manual t&eacute;cnico
+I18N_LANG_S_MASTERTHESIS = Tese de mestrado
+I18N_LANG_S_MISC = 'Documentos diverso'
+I18N_LANG_S_PHDTHESIS = Tese de doutoramento
+I18N_LANG_S_PROCEEDINGS = Actas de confer&ecirc;ncia
+I18N_LANG_S_TECHREPORT = Relat&oacute;rio t&eacute;cnico
+I18N_LANG_S_UNPUBLISHED = N&atilde;o publicado
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.HTMLGen b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.HTMLGen
new file mode 100644
index 0000000000..86f4a9b2e5
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.HTMLGen
@@ -0,0 +1,56 @@
+# Portuguese support for the generators.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_ALL_ELEMENTS = Todos os Elementos
+I18N_LANG_ARTICLESINSAMEDOMAINS = Documentos nos mesmos dom&iacute;nios
+I18N_LANG_FIELD_BIBTEX_VERBATIM = C&oacute;digo BibTeX
+I18N_LANG_FIELD_XML_VERBATIM = C&oacute;digo XML
+I18N_LANG_DEFAULT_TITLE = Bibliografia
+I18N_LANG_DOMAIN_TREE = &Aacute;rvore de dom&iacute;nios
+I18N_LANG_DOMAINS = Dom&iacute;nios
+I18N_LANG_ENTRY_TYPE_TREE = Lista hier&aacute;rquiaca por tipo de entrada
+I18N_LANG_FRAME_TITLE_AUTHORS = Autores
+I18N_LANG_FRAME_TITLE_TYPES = Tipos
+I18N_LANG_FRAMES = <em>Frames</em>
+I18N_LANG_INDEX = &Iacute;ndice
+I18N_LANG_INDEX_COMMENT_ARTICLE = artigo
+I18N_LANG_INDEX_COMMENT_AUTHOR = autor
+I18N_LANG_INDEX_COMMENT_BOOKTITLE = T&iacute;tulo de livro
+I18N_LANG_INDEX_COMMENT_EDITOR = editor
+I18N_LANG_INDEX_COMMENT_HOWPUBLISHED = meio de publica&ccedil;&atilde;o
+I18N_LANG_INDEX_COMMENT_INSTITUTION = institui&ccdeil;&atilde;o
+I18N_LANG_INDEX_COMMENT_PUBLISHER = editor
+I18N_LANG_INDEX_COMMENT_SCHOOL = escola
+I18N_LANG_INDEX_COMMENT_TITLE = t&iacute;tulo
+I18N_LANG_NEXT = Pr&oacute;ximo
+I18N_LANG_NO_DATE = N&atilde;o datado
+I18N_LANG_NO_FRAME = Sem <em>Frames</em>
+I18N_LANG_NO_FRAME_ALERT = <H2>Alerta de Frames</H2>\
+ <P>Este documento foi concebido para ser \
+ visualizado usando a funcionalidade \
+ de <en>frames</em>. A visualiza&ccedil,&atilde;o desta \
+ mensagem indica que est&aacute; a usar um <em>browser</em> \
+ que n&atilde;o suport <em>frames</em>.<BR>\
+ <em>Link</em> para uma <A HREF="#1">vers&atilde;o \
+ sem <em>frames</em></A>.<BR>#2
+I18N_LANG_OVERVIEW = P&aacute;gina&nbsp;principal
+I18N_LANG_PREV = Anterior
+I18N_LANG_TREE = &Aacute;rvore
+I18N_LANG_SMALL_IN = em:&nbsp;#1
+I18N_LANG_SUBMIT_BUG = Submeter um relat&oacute;rio de erro
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.Theme.Dyna b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.Theme.Dyna
new file mode 100644
index 0000000000..bf372b5d5b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Portuguese.Theme.Dyna
@@ -0,0 +1,22 @@
+# Portuguese support for the Dyna theme.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_THEME_SUMMARY_BAR = SUM&Aacute;RIO: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_DETAIL_BAR = DETALHE: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_TREE_ROOT = Raiz
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish
new file mode 100644
index 0000000000..752bafbafa
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish
@@ -0,0 +1,87 @@
+# Spanish support for the generators.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+# Sebastian Rodriguez <sebastian.rodriguez@utbm.fr>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_BIB2HTML_COPYRIGHT = Este documento fue generado por #1.<BR>\
+ Copyright &copy; {{*get_final_copyright}} #2 (Bajo #3)
+I18N_LANG_DEFAULT_TITLE = BibTeX
+I18N_LANG_DOCUMENTS = Documentos
+I18N_LANG_FIELD_ADDRESS = Direcci&oacute;n
+I18N_LANG_FIELD_ADSURL = Acoplamiento al ADS
+I18N_LANG_FIELD_ABSTRACT = Resumen
+I18N_LANG_FIELD_ABSTRACT_KEYWORDS = Resumen y Palabras Claves
+I18N_LANG_FIELD_ANNOTATION = Comentario
+I18N_LANG_FIELD_AUTHORS = Autor(es)
+I18N_LANG_FIELD_CHAPTER = Capitulo de
+I18N_LANG_FIELD_DATE = Fecha
+I18N_LANG_FIELD_DOI = Documento en Internet
+I18N_LANG_FIELD_DOWNLOAD = Descargar el articulo completo: #1
+I18N_LANG_FIELD_EDITION = Edici&oacute;n
+I18N_LANG_FIELD_EDITORS = Redactor en Jefe
+I18N_LANG_FIELD_HOWPUBLISHED = How published
+I18N_LANG_FIELD_IN = En
+I18N_LANG_FIELD_INSTITUTION = Instituci&oacute;n
+I18N_LANG_FIELD_ISBN = N&uacute;mero ISBN
+I18N_LANG_FIELD_ISSN = N&uacute;mero ISSN
+I18N_LANG_FIELD_JOURNAL = Revista
+I18N_LANG_FIELD_KEYWORDS = <strong>Palabras claves</strong>: #1
+I18N_LANG_FIELD_KEYWORDS_TITLE = Palabras claves
+I18N_LANG_FIELD_NOTE = Nota
+I18N_LANG_FIELD_NUMBER = N&uacute;mero
+I18N_LANG_FIELD_ORGANIZATION = Organizaci&oacute;n
+I18N_LANG_FIELD_PAGES = P&aacute;gina(s)
+I18N_LANG_FIELD_PDFFILE = PDF
+I18N_LANG_FIELD_PUBLISHER = Editor
+I18N_LANG_FIELD_READERS = Lectore(s)
+I18N_LANG_FIELD_SCHOOL = Escuela
+I18N_LANG_FIELD_SERIES = Serie
+I18N_LANG_FIELD_TITLE = T&iacute;tulo
+I18N_LANG_FIELD_TYPE = Tipo
+I18N_LANG_FIELD_URL = URL
+I18N_LANG_FIELD_VOLUME = Volumen
+I18N_LANG_FIELD_YEAR = A&ntilde;o
+I18N_LANG_FORMAT_NAME = l{ (v)}{ f.}{, j}
+I18N_LANG_FORMAT_NAMES = { y }{, }
+I18N_LANG_KEYWORDS = Palabras claves
+I18N_LANG_P_ARTICLE = Articulos
+I18N_LANG_P_BOOK = Libros
+I18N_LANG_P_BOOKLET = Libros Sin Sponsord
+I18N_LANG_P_INBOOK = Partes de Libros
+I18N_LANG_P_INCOLLECTION = En colecci&oacute;n
+I18N_LANG_P_INPROCEEDINGS = En proceedings
+I18N_LANG_P_MANUAL = Manuales T&eacute;cnicos
+I18N_LANG_P_MASTERTHESIS = Tesis de Master
+I18N_LANG_P_MISC = 'Documentos miscel&aacute;neos'
+I18N_LANG_P_PHDTHESIS = Tesis Doctorales
+I18N_LANG_P_PROCEEDINGS = Conference proceedings
+I18N_LANG_P_TECHREPORT = Reportes T&eacute;cnicos
+I18N_LANG_P_UNPUBLISHED = In&eacute;dito
+I18N_LANG_S_ARTICLE = Articulo
+I18N_LANG_S_BOOK = Libro
+I18N_LANG_S_BOOKLET = Not-sponsored book
+I18N_LANG_S_INBOOK = Parte de Libro
+I18N_LANG_S_INCOLLECTION = En una colecci&oacute;n
+I18N_LANG_S_INPROCEEDINGS = En proceedings
+I18N_LANG_S_MANUAL = Manual T&eacute;cnico
+I18N_LANG_S_MASTERTHESIS = T&eacute;sis de Master
+I18N_LANG_S_MISC = 'Documento Miscelaneo'
+I18N_LANG_S_PHDTHESIS = T&eacute;sis Doctoral
+I18N_LANG_S_PROCEEDINGS = Conference proceedings
+I18N_LANG_S_TECHREPORT = Reporte T&eacute;cnico
+I18N_LANG_S_UNPUBLISHED = In&eacute;dito
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.HTMLGen b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.HTMLGen
new file mode 100644
index 0000000000..5b11ef3f82
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.HTMLGen
@@ -0,0 +1,55 @@
+# Spanish support for the generator HTMLGen.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+# Sebastian Rodriguez <sebastian.rodriguez@utbm.fr>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_ALL_ELEMENTS = Todos los Elemnetos
+I18N_LANG_ARTICLESINSAMEDOMAINS = Documentos en el mismo dominio
+I18N_LANG_FIELD_BIBTEX_VERBATIM = BibTeX
+I18N_LANG_FIELD_XML_VERBATIM = XML
+I18N_LANG_DEFAULT_TITLE = Bibliograf&iacute;a
+I18N_LANG_DOMAIN_TREE = Domain Tree
+I18N_LANG_DOMAINS = Dominios
+I18N_LANG_ENTRY_TYPE_TREE = Lista por tipos de Entada
+I18N_LANG_FRAME_TITLE_AUTHORS = Autores
+I18N_LANG_FRAME_TITLE_TYPES = Tipos
+I18N_LANG_FRAMES = Frames
+I18N_LANG_INDEX = Indice
+I18N_LANG_INDEX_COMMENT_ARTICLE = artiuclo
+I18N_LANG_INDEX_COMMENT_AUTHOR = autor
+I18N_LANG_INDEX_COMMENT_BOOKTITLE = titulo del libro
+I18N_LANG_INDEX_COMMENT_EDITOR = Redactor jefe
+I18N_LANG_INDEX_COMMENT_HOWPUBLISHED = forma de publicaci&oacute;n
+I18N_LANG_INDEX_COMMENT_INSTITUTION = instituci&oacute;n
+I18N_LANG_INDEX_COMMENT_PUBLISHER = Editor
+I18N_LANG_INDEX_COMMENT_SCHOOL = escuela
+I18N_LANG_INDEX_COMMENT_TITLE = titulo
+I18N_LANG_NEXT = Siguiente
+I18N_LANG_NO_DATE = Sin Fecha
+I18N_LANG_NO_FRAME = No Frame
+I18N_LANG_NO_FRAME_ALERT = <H2>Frame Alert</H2>\
+ <P>Este documento fue dise&ntilde;ando para ser \
+ visualizado usando Frames. Si esta viendo este \
+ mensaje, esta usando un web browser sin soporte \
+ para los Frames.<BR>Vinculo a <A HREF="#1">la \
+ versi&oacute;n sin Frames.</A>.<BR>#2
+I18N_LANG_OVERVIEW = Visi&oacute;n General
+I18N_LANG_PREV = Anterior
+I18N_LANG_TREE = Tree
+I18N_LANG_SMALL_IN = en:&nbsp;#1
+I18N_LANG_SUBMIT_BUG = Reportar un bug
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.Theme.Dyna b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.Theme.Dyna
new file mode 100644
index 0000000000..6db9ef0498
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Lang/Spanish.Theme.Dyna
@@ -0,0 +1,23 @@
+# Spanish support for the Dyna theme.
+#
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+# Sebastian Rodriguez <sebastian.rodriguez@utbm.fr>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+I18N_LANG_THEME_SUMMARY_BAR = RESUMEN: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_DETAIL_BAR = DETALLE: &nbsp;#1&nbsp;|&nbsp;#2&nbsp;|&nbsp;#3
+I18N_LANG_THEME_TREE_ROOT = Raíz
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/LangManager.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/LangManager.pm
new file mode 100644
index 0000000000..03b67db383
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/LangManager.pm
@@ -0,0 +1,382 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::LangManager - A Language support for the generators
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::LangManager ;
+
+my $gen = Bib2HTML::Generator::LangManager->new( names ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::LangManager is a Perl module, which proposes
+a generic language support for all the generators.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::LangManager;
+
+ my $gen = Bib2HTML::Generator::LangManager->new( [ 'English_HTMLGen',
+ 'English' ] ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * names (array of strings)
+
+is the ordred list of the desired language files.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in LangManager.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::LangManager;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+
+use Carp ;
+use File::Basename ;
+use File::Spec ;
+
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::Verbose ;
+use Bib2HTML::Generator::Lang ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of language support
+my $VERSION = "4.0" ;
+
+# Default language
+my $DEFAULT_LANGUAGE = "English";
+
+#------------------------------------------------------
+#
+# Static functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * set_default_language()
+
+Set the default language.
+Takes 1 arg:
+
+=over
+
+=item * default (string)
+
+is the name of the default language.
+
+=back
+
+=cut
+sub set_default_lang($) {
+ $DEFAULT_LANGUAGE = "$_[0]";
+}
+
+=pod
+
+=item * display_supported_languages()
+
+Display the list of supported languages.
+Takes 2 args:
+
+=over
+
+=item * perldir (string)
+
+is the path to the directory where the Perl packages
+are stored.
+
+=item * default (string)
+
+is the name of the default language
+
+=back
+
+=cut
+sub display_supported_languages($$) {
+ my $path = $_[0] || confess( 'you must specify the pm path' ) ;
+ my $default = $_[1] || '' ;
+ my @pack = split /\:\:/, __PACKAGE__ ;
+ pop @pack ;
+ push @pack, 'Lang' ;
+ @pack = ( File::Spec->splitdir($path), @pack ) ;
+ my $glob = File::Spec->catfile(@pack, '*');
+ $glob =~ s/ /\\ /g;
+ foreach my $file ( glob($glob) ) {
+ my $name = basename($file) ;
+ if ( ( $name !~ /[._-][a-zA-Z0-9]+Gen$/ ) &&
+ ( $name !~ /\.perl$/ ) && # For Perl scripts
+ ( $name !~ /\.pl$/ ) && # For Perl scripts
+ ( $name !~ /\.pm$/ ) && # For Perl modules
+ ( $name !~ /~$/ ) ) { # For backup files
+ print join( '',
+ "$name",
+ ( $default && ( $default eq $name ) ) ?
+ " (default)" : "",
+ "\n" ) ;
+ }
+ }
+}
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+
+ # Compute the list of the desired languages
+ my @desired_langs;
+ if (isarray($_[0])) {
+ @desired_langs = @{$_[0]};
+ }
+ else {
+ @desired_langs = ( $_[0] );
+ }
+ push @desired_langs, "$DEFAULT_LANGUAGE";
+
+ # Build the directory filename where are located the
+ # language files
+ my @pack = split /\:\:/, __PACKAGE__ ;
+ pop @pack ;
+ push @pack, 'Lang' ;
+
+ # Get the language directory
+ my $directory_path = undef;
+ foreach my $path (@INC) {
+ my $fullpath = File::Spec->catfile($path,@pack);
+ if (-d "$fullpath") {
+ $directory_path = $path;
+ last;
+ }
+ }
+
+ @pack = ( File::Spec->splitdir($directory_path), @pack);
+
+ # Search for and load the desired languages
+ my @lang_objs = ();
+ my @real_desired_langs = ();
+ foreach my $desired_lang (@desired_langs) {
+ $desired_lang =~ s/[-_.=,:;!~\s]/./g;
+ my $filename = File::Spec->catfile(@pack,$desired_lang);
+ if (-r "$filename") {
+ my $obj = Bib2HTML::Generator::Lang->new($desired_lang,"$filename");
+ my $found = undef;
+ foreach my $ex_lang (@lang_objs) {
+ if ($ex_lang->getname() eq $desired_lang) {
+ $found = 1;
+ last;
+ }
+ }
+ if (!$found) {
+ push @lang_objs, $obj;
+ push @real_desired_langs,$desired_lang;
+ }
+ }
+ elsif (Bib2HTML::General::Verbose::currentlevel()>=2) {
+ Bib2HTML::General::Error::syswarm( "'$filename' language file was not found or can't be red\n" );
+ }
+ }
+
+ # Check for one language found
+ Bib2HTML::General::Error::syserr( "Unable to find the language class\n" ) unless (@lang_objs);
+
+ my $self = { 'langs' => (@lang_objs ? \@lang_objs : []),
+ 'desired_langs' => \@real_desired_langs,
+ 'lang_directory' => \@pack,
+ } ;
+
+ bless( $self, $class );
+ return $self;
+}
+
+=pod
+
+=item * registerLang($)
+
+Register a language file.
+The name of the new language files must respect the following pattern:
+<lang_dir>/<lang_name>.<extension>
+where <lang_dir> is the predefined directory where language files
+are stored, <lang_name> is the name of the language, and
+<extension> is a string specified to this function.
+Takes at least 1 arg:
+
+=over
+
+=item * extension (string)
+
+is the extension of the language file.
+
+=back
+
+=cut
+sub registerLang($) {
+ my $self = shift;
+ my $extension = shift;
+
+ foreach my $desired_lang (@{$self->{'desired_langs'}}) {
+ $desired_lang =~ s/[-_.=,:;!~\s]/./g;
+ my $realname = $desired_lang.".".$extension;
+ my $filename = File::Spec->catfile(@{$self->{'lang_directory'}},"$realname");
+ if (-r "$filename") {
+ my $obj = Bib2HTML::Generator::Lang->new("$realname","$filename");
+
+ my $found = 0;
+ foreach my $ex_lang (@{$self->{'langs'}}) {
+ if ($ex_lang->getname() eq $realname) {
+ $found = 1;
+ last;
+ }
+ }
+
+ if (!$found) {
+ unshift @{$self->{'langs'}}, $obj;
+ unshift @{$self->{'desired_langs'}}, $realname;
+ }
+ }
+ }
+}
+
+#------------------------------------------------------
+#
+# Getters
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get()
+
+Replies the specified string according to the language.
+Takes at least 1 arg:
+
+=over
+
+=item * id (string)
+
+is the id of the string.
+
+=item * param1 (string)
+
+is a string which must replace the string "#1" in the language definition.
+
+=item * param2 (string)
+
+is a string which must replace the string "#2" in the language definition.
+
+=item ...
+
+=back
+
+=cut
+sub get($) : method {
+ my $self = shift ;
+ my $id = $_[0] || confess( 'you must supply the id' ) ;
+
+ my $lgs = '';
+
+ foreach my $l (@{$self->{'langs'}}) {
+ my $n = $l->_get_noerror(@_);
+ if ($n) {
+ return $n;
+ }
+ if ($lgs) {
+ $lgs .= ", ";
+ }
+ $lgs .= "'".$l->{'name'}."'";
+ }
+
+ Bib2HTML::General::Error::syserr( "the string id '$id' is not defined ".
+ "for all the current languages: $lgs" );
+ return undef;
+}
+
+=pod
+
+=item * getname()
+
+Replies the name of the current language.
+
+=cut
+sub getname() : method {
+ my $self = shift ;
+ foreach my $l (@{$self->{'langs'}}) {
+ my $n = $l->getname() ;
+ if ($n !~ /_[a-zA-Z0-9]+Gen$/) {
+ return $n;
+ }
+ }
+ return "unknow";
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SQLGen.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SQLGen.pm
new file mode 100644
index 0000000000..2a2e80f2cd
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SQLGen.pm
@@ -0,0 +1,746 @@
+# Copyright (C) 2004-07 Stephane Galland <galland@arakhne.org>
+# Copyright (C) 2011 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::SQLGen - A basic SQL generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::SQLGen ;
+
+my $gen = Bib2HTML::Generator::SQLGen->new( content, output, info, titles,
+ lang, theme, params ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::SQLGen is a Perl module, which permits to
+generate SQL scripts for the BibTeX database.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::SQLGen;
+
+ my $gen = Bib2HTML::Generator::SQLGen->new( { }, "./bib.sql",
+ { 'BIB2HTML_VERSION' => "0.1",
+ },
+ { 'SHORT' => "This is the title",
+ 'LONG' => "This is the title",
+ },
+ "English",
+ "Simple", ""
+ ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * content (hash)
+
+see AbstractGenerator help.
+
+=item * output (string)
+
+see AbstractGenerator help.
+
+=item * bib2html_data (hash)
+
+see AbstractGenerator help.
+
+=item * titles (hash)
+
+see AbstractGenerator help.
+
+=item * lang (string)
+
+see AbstractGenerator help.
+
+=item * theme (string)
+
+is the name of the theme to use
+
+=item * show_bibtex (boolean)
+
+indicates if this parser must generate a verbatim of the BibTeX code
+
+=item * params (optional array)
+
+is the set of parameters passed to the generator.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in SQLGen.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::SQLGen;
+
+@ISA = ('Bib2HTML::Generator::AbstractGenerator');
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use constant TRUE => (1==1);
+use constant FALSE => (1==0);
+use Carp ;
+use File::Spec ;
+use File::Basename ;
+
+use Bib2HTML::Generator::AbstractGenerator;
+use Bib2HTML::General::Misc;
+use Bib2HTML::General::Error;
+use Bib2HTML::General::HTML;
+use Bib2HTML::General::Encode;
+use Bib2HTML::Translator::BibTeXName;
+
+use Bib2HTML::Generator::SqlEngine::MySql;
+use Bib2HTML::Generator::SqlEngine::PgSql;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of this generator
+my $VERSION = "3.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$$$;$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+
+ my @langs = ();
+ if (isarray($_[4])) {
+ foreach my $l (@{$_[4]}) {
+ if ($l !~ /_[a-zA-Z0-9]+Gen$/) {
+ push @langs, $l."_SQLGen";
+ }
+ push @langs, $l;
+ }
+ }
+ else {
+ @langs = ( $_[4] );
+ if ($_[4] !~ /_[a-zA-Z0-9]+Gen$/) {
+ unshift @langs, $_[4]."_SQLGen";
+ }
+ }
+
+ my $self = $class->SUPER::new($_[0], #content
+ $_[1], #output
+ $_[2], #bib2html info
+ $_[3], #titles
+ \@langs, #lang
+ $_[6], #show bibtex
+ $_[7], #params
+ ) ;
+
+ $self->{'sql_identifiers'}{'identity'} = 0;
+ $self->{'current_sql_engine_instance'} = undef;
+
+ bless( $self, $class );
+
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Generation parameters
+#
+#------------------------------------------------------
+
+=pod
+
+=item * save_generator_parameter()
+
+Replies if the specified generator parameter was supported.
+This function was called each time a generator parameter was
+given to this generator. By default, simply update the
+given parameter value (second parameter).
+You could do some stuff before
+saving (splitting...). Replies false is the parameter was
+not recognized. Don't forget to call inherited functions.
+Takes 2 args:
+
+=over
+
+=item * param_name (string)
+
+is the name of the parameter.
+
+=item * param_value (byref string)
+
+is the value of the parameter.
+
+=back
+
+=cut
+sub save_generator_parameter($$) {
+ my $self = shift ;
+ if ( ( $_[0] eq 'sql-encoding' ) ) {
+ # will be saved by PARENT::new
+ return 1 ;
+ }
+ elsif ( ( $_[0] eq 'sql-engine' ) ) {
+ # will be saved by PARENT::new
+ return 1 ;
+ }
+ else {
+ return $self->SUPER::save_generator_parameter($_[0],$_[1]) ;
+ }
+}
+
+=pod
+
+=item * display_supported_generator_params()
+
+Display the list of supported generator parameters.
+
+=cut
+sub display_supported_generator_params() {
+ my $self = shift ;
+ $self->SUPER::display_supported_generator_params() ;
+
+ $self->show_supported_param('sql-encoding',
+ 'String, the character encoding used in the SQL script '.
+ '("UTF8", "ISO-8859-1"...).' );
+ $self->show_supported_param('sql-engine',
+ 'String, the name of the SQL engine for which the '.
+ 'SQL script should be generated '.
+ '("mysql", "pgsql"...).' );
+}
+
+#------------------------------------------------------
+#
+# Generation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * pre_processing()
+
+Pre_processing.
+
+=cut
+sub pre_processing() : method {
+ my $self = shift ;
+
+ # Set the HTML encoding
+ if (!$self->{'GENERATOR_PARAMS'}{'sql-encoding'}) {
+ $self->{'GENERATOR_PARAMS'}{'sql-encoding'} = get_default_encoding();
+ }
+ set_default_encoding($self->{'GENERATOR_PARAMS'}{'sql-encoding'});
+
+ # Set the default SQL engine
+ if (!$self->{'GENERATOR_PARAMS'}{'sql-engine'}) {
+ $self->{'GENERATOR_PARAMS'}{'sql-engine'} = "mysql";
+ }
+ else {
+ $self->{'GENERATOR_PARAMS'}{'sql-engine'} = lc($self->{'GENERATOR_PARAMS'}{'sql-engine'});
+ }
+
+ if ($self->{'GENERATOR_PARAMS'}{'sql-engine'} eq 'mysql') {
+ $self->{'current_sql_engine_instance'} = new Bib2HTML::Generator::SqlEngine::MySql();
+ }
+ elsif ($self->{'GENERATOR_PARAMS'}{'sql-engine'} eq 'pgsql') {
+ $self->{'current_sql_engine_instance'} = new Bib2HTML::Generator::SqlEngine::PgSql();
+ }
+ else {
+ Bib2HTML::General::Error::syserr("unsupported SQL engine: ".$self->{'GENERATOR_PARAMS'}{'sql-engine'});
+ }
+
+ # Call inherited generation method
+ $self->SUPER::pre_processing() ;
+}
+
+=pod
+
+=item * do_processing()
+
+Main processing.
+
+=cut
+sub do_processing() : method {
+ my $self = shift ;
+
+ # Call inherited generation method
+ $self->SUPER::do_processing() ;
+
+ # Generates each part of the document
+ my $t = '' ;
+
+ # Generates the schema of the database
+ $self->create_SQLSCHEMA($t) ;
+
+ # Generates the content for each entries
+ $self->create_SQLENTRIES($t) ;
+
+ # Create file
+ $self->create_FILE($t) ;
+}
+
+
+sub quotesql($) {
+ my $self = shift;
+ my $v = shift;
+ my $sqlEngine = $self->{'current_sql_engine_instance'};
+ return $sqlEngine->quotesql($v);
+}
+
+
+=pod
+
+=item * create_SQLSCHEMA()
+
+Generates the SQL schema.
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content to fill
+
+=back
+
+=cut
+sub create_SQLSCHEMA($) : method {
+ my $self = shift ;
+ my $sqlEngine = $self->{'current_sql_engine_instance'};
+ $_[0] .= $sqlEngine->createSchema();
+}
+
+=pod
+
+=item * create_SQLENTRIES()
+
+Generates the SQL pages for each entry
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content to fill
+
+=back
+
+=cut
+sub create_SQLENTRIES($) : method {
+ my $self = shift ;
+ my @entries = $self->get_all_entries_ayt() ;
+ my $i = $#entries ;
+ my $sqlEngine = $self->{'current_sql_engine_instance'};
+
+ while ( $i >= 0 ) {
+ # Compute entry constants
+ my $type = $self->{'CONTENT'}{'entries'}{$entries[$i]}{'type'} ;
+ my $fields = $self->{'CONTENT'}{'entries'}{$entries[$i]}{'fields'};
+ my $entry = '';
+
+ # Insert the entry's type
+ if ((!$self->{'GENERATION'}{'types'})||
+ (!strinarray($type,$self->{'GENERATION'}{'types'}))) {
+ $entry .= $sqlEngine->insertInto(
+ 'bibtex_entrytype',
+ { 'type' => $type });
+ push @{$self->{'GENERATION'}{'types'}}, "$type";
+ }
+
+ # Insert the entry
+ $entry .= $sqlEngine->insertInto(
+ 'bibtex_entry',
+ { 'entry_key' => $entries[$i],
+ 'year' => $fields->{'year'}||0,
+ 'title' => $fields->{'title'}||'',
+ 'type' => $type});
+ delete $fields->{'year'};
+ delete $fields->{'title'};
+
+ if (exists $fields->{'author'}) {
+ $self->create_SQLAUTHORS($entries[$i],$fields->{'author'},$entry);
+ delete $fields->{'author'};
+ }
+
+ if (exists $fields->{'editor'}) {
+ $self->create_SQLEDITORS($entries[$i],$fields->{'editor'},$entry);
+ delete $fields->{'editor'};
+ }
+
+ if ((exists $fields->{'domain'})||
+ (exists $fields->{'nddomain'})||
+ (exists $fields->{'rddomain'})||
+ (exists $fields->{'domains'})) {
+ $self->create_SQLDOMAINS($entries[$i],
+ join(':',
+ ($fields->{'domain'}||''),
+ ($fields->{'nddomain'}||''),
+ ($fields->{'rddomain'}||''),
+ ($fields->{'domains'}||'')),
+ $entry);
+ delete $fields->{'domain'};
+ delete $fields->{'nddomain'};
+ delete $fields->{'rddomain'};
+ delete $fields->{'domains'};
+ }
+
+ # Fields
+ foreach my $field (keys %{$fields}) {
+ $self->create_SQLFIELD($entries[$i],
+ "$field", $fields->{"$field"},
+ $entry);
+ }
+
+ $_[0] .= $entry ;
+ $i -- ;
+ }
+}
+
+=pod
+
+=item * create_SQLAUTHORS()
+
+Generates the SQL pages for the authors
+Takes 3 args:
+
+=over
+
+=item * entry_key (string)
+
+is the BibTeX key of the entry.
+
+=item * authors (string)
+
+is the list of authors.
+
+=item * content (string)
+
+is the content to fill.
+
+=back
+
+=cut
+sub create_SQLAUTHORS($$$) : method {
+ my $self = shift;
+ my $entry_key = shift;
+ my $sauthors = shift;
+
+ my $sqlEngine = $self->{'current_sql_engine_instance'};
+ my $translator = Bib2HTML::Translator::BibTeXName->new();
+ my @names = $translator->splitnames($sauthors);
+ my $idxauthor = 0;
+
+ my %insertedAuthors = ();
+
+ for(my $idxname=0; $idxname<@names; $idxname++) {
+ my $name = $names[$idxname];
+ if (!$name->{'et al'}) {
+ my $author_key = html_lc($translator->formatname($name,'l,i.'));
+
+ my $id;
+ if ((!$self->{'GENERATION'}{'authors'})||
+ (!$self->{'GENERATION'}{'authors'}{"sqlid_$author_key"})) {
+ $self->{'sql_identifiers'}{'identity'}++;
+ $_[0] .= $sqlEngine->insertInto(
+ 'bibtex_identity',
+ { 'identifier' => $self->{'sql_identifiers'}{'identity'},
+ 'name' => translate_html_entities($name->{'last'}),
+ 'firstname' => translate_html_entities($name->{'first'}),
+ 'von' => translate_html_entities($name->{'von'}),
+ 'junior' => translate_html_entities($name->{'jr'})});
+ $self->{'GENERATION'}{'authors'}{"sqlid_$author_key"} = $self->{'sql_identifiers'}{'identity'};
+ $id = $self->{'sql_identifiers'}{'identity'};
+ }
+ else {
+ $id = $self->{'GENERATION'}{'authors'}{"sqlid_$author_key"};
+ }
+
+ my $etal = ((($idxname+1)<@names)&&($names[$idxname+1]->{'et al'}));
+
+ if ($insertedAuthors{"||$entry_key||$id||"}) {
+ Bib2HTML::General::Error::syswarm("Duplicate author '$id' for entry '$entry_key'");
+ }
+ else {
+ $_[0] .= $sqlEngine->insertInto(
+ 'bibtex_authors',
+ { 'entry_key' => $entry_key,
+ 'author_id' => $id,
+ 'order_id' => $idxauthor,
+ 'etal' => ($etal ? "true" : "false")});
+ $insertedAuthors{"||$entry_key||$id||"} = TRUE;
+ $idxauthor++;
+ }
+ }
+ }
+}
+
+=pod
+
+=item * create_SQLEDITORS()
+
+Generates the SQL pages for the editors
+Takes 3 args:
+
+=over
+
+=item * entry_key (string)
+
+is the BibTeX key of the entry.
+
+=item * editors (string)
+
+is the list of editors.
+
+=item * content (string)
+
+is the content to fill.
+
+=back
+
+=cut
+sub create_SQLEDITORS($$$) : method {
+ my $self = shift;
+ my $entry_key = shift;
+ my $seditors = shift;
+
+ my $sqlEngine = $self->{'current_sql_engine_instance'};
+ my $translator = Bib2HTML::Translator::BibTeXName->new();
+ my @names = $translator->splitnames($seditors);
+ my $idxeditor = 0;
+
+ for(my $idxname=0; $idxname<@names; $idxname++) {
+ my $name = $names[$idxname];
+ if (!$name->{'et al'}) {
+ my $editor_key = html_lc($translator->formatname($name,'l,i.'));
+
+ my $id;
+ if ((!$self->{'GENERATION'}{'authors'})||
+ (!$self->{'GENERATION'}{'authors'}{"sqlid_$editor_key"})) {
+ $self->{'sql_identifiers'}{'identity'}++;
+ $_[0] .= $sqlEngine->insertInto(
+ 'bibtex_identity',
+ { 'identifier' => $self->{'sql_identifiers'}{'identity'},
+ 'name' => translate_html_entities($name->{'last'}),
+ 'firstname' => translate_html_entities($name->{'first'}),
+ 'von' => translate_html_entities($name->{'von'}),
+ 'junior' => translate_html_entities($name->{'jr'})});
+ $self->{'GENERATION'}{'authors'}{"sqlid_$editor_key"} = $self->{'sql_identifiers'}{'identity'};
+ $id = $self->{'sql_identifiers'}{'identity'};
+ }
+ else {
+ $id = $self->{'GENERATION'}{'authors'}{"sqlid_$editor_key"};
+ }
+
+ my $etal = ((($idxname+1)<@names)&&($names[$idxname+1]->{'et al'}));
+
+ $_[0] .= $sqlEngine->insertInto(
+ 'bibtex_editors',
+ { 'entry_key' => $entry_key,
+ 'editor_id' => $id,
+ 'order_id' => $idxeditor,
+ 'etal' => ($etal ? "true" : "false")});
+
+ $idxeditor++;
+ }
+ }
+}
+
+=pod
+
+=item * create_SQLDOMAINS()
+
+Generates the SQL pages for the entry's domains
+Takes 3 args:
+
+=over
+
+=item * entry_key (string)
+
+is the BibTeX key of the entry.
+
+=item * domains (string)
+
+is the list of domains separated by ':'.
+
+=item * content (string)
+
+is the content to fill.
+
+=back
+
+=cut
+sub create_SQLDOMAINS($$$) : method {
+ my $self = shift;
+ my $entry_key = shift;
+ my $sdomains = shift;
+
+ my $sqlEngine = $self->{'current_sql_engine_instance'};
+ my @domains = split(/\s*:\s*/,$sdomains);
+
+ foreach my $domain (@domains) {
+ $domain =~ s/^\s+//;
+ $domain =~ s/\s+$//;
+ if ($domain) {
+ my $domain_key = $domain;
+ $domain_key =~ s/\s//g;
+ $domain_key = html_lc($domain_key);
+
+ my $id;
+ if ((!$self->{'GENERATION'}{'domains'})||
+ (!$self->{'GENERATION'}{'domains'}{"$domain_key"})) {
+ if (!$self->{'GENERATION'}{'domains'}) {
+ $id = 1;
+ }
+ else {
+ $id = %{$self->{'GENERATION'}{'domains'}} + 1;
+ }
+ $_[0] .= $sqlEngine->insertInto(
+ 'bibtex_domain',
+ { 'identifier' => $id,
+ 'name' => translate_html_entities($domain)});
+ $self->{'GENERATION'}{'domains'}{"$domain_key"} = $id;
+ }
+ else {
+ $id = $self->{'GENERATION'}{'domains'}{"$domain_key"};
+ }
+
+ $_[0] .= $sqlEngine->insertInto(
+ 'bibtex_entrydomain',
+ { 'entry_key' => $entry_key,
+ 'domain_id' => $id});
+ }
+ }
+}
+
+=pod
+
+=item * create_SQLFIELD()
+
+Generates the SQL pages for the entry's field
+Takes 4 args:
+
+=over
+
+=item * entry_key (string)
+
+is the BibTeX key of the entry.
+
+=item * field_name (string)
+
+is the name of the field to add.
+
+=item * field_value (string)
+
+is the value of the field to add.
+
+=item * content (string)
+
+is the content to fill.
+
+=back
+
+=cut
+sub create_SQLFIELD($$$$) : method {
+ my $self = shift;
+ my $entry_key = shift;
+ my $field_name = shift;
+ my $field_value = shift;
+
+ my $sqlEngine = $self->{'current_sql_engine_instance'};
+
+ if ($self->{'GENERATION'}{'field_id'}) {
+ $self->{'GENERATION'}{'field_id'}++;
+ }
+ else {
+ $self->{'GENERATION'}{'field_id'} = 1;
+ }
+
+ $_[0] .= $sqlEngine->insertInto(
+ 'bibtex_field',
+ { 'identifier' => $self->{'GENERATION'}{'field_id'},
+ 'entry_key' => $entry_key,
+ 'name' => translate_html_entities("$field_name"),
+ 'value' => translate_html_entities("$field_value")});
+}
+
+=pod
+
+=item * create_FILE
+
+Creates the SQL file.
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content of the SQL file.
+
+=back
+
+=cut
+sub create_FILE($) : method {
+ my $self = shift ;
+ Bib2HTML::General::Verbose::two( "Writing ".$self->{'TARGET'}."..." ) ;
+
+ my $writer = $self->get_stream_writer();
+
+ $writer->openstream($self->{'TARGET'});
+ $writer->out($_[0]||'') ;
+ $writer->closestream() ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 2004-07 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+(c) Copyright 2011 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/MySql.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/MySql.pm
new file mode 100644
index 0000000000..d899321740
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/MySql.pm
@@ -0,0 +1,214 @@
+# Copyright (C) 2011 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::SqlEngine::MySql - SQL Generator utilities for MySQL
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::SqlEngine::MySql;
+
+@ISA = ('');
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Carp ;
+
+use Bib2HTML::General::Error;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of this file
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = {};
+ bless( $self, $class );
+ return $self;
+}
+
+sub quotesql($) : method {
+ my $self = shift;
+ my $s = $_[0];
+ $s =~ s/\'/\\\'/g;
+ return $s;
+}
+
+
+sub createSchema() : method {
+ my $self = shift;
+ my $schema = '';
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_entrytype;",
+ "CREATE TABLE bibtex_entrytype (",
+ " type varchar(50) NOT NULL,",
+ " PRIMARY KEY(type)",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_domain;",
+ "CREATE TABLE bibtex_domain (",
+ " identifier int(10) NOT NULL,",
+ " name varchar(100) NOT NULL,",
+ " PRIMARY KEY(identifier)",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_entry;",
+ "CREATE TABLE bibtex_entry (",
+ " entry_key varchar(50) NOT NULL,",
+ " year int(5) NOT NULL default 1900,",
+ " title text NOT NULL,",
+ " type varchar(50) NOT NULL,",
+ " crossref varchar(50),",
+ " PRIMARY KEY(entry_key),",
+ " FOREIGN KEY(type) REFERENCES bibtex_entrytype(type) ON DELETE CASCADE,",
+ " FOREIGN KEY(crossref) REFERENCES bibtex_entry(entry_key) ON DELETE SET NULL",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_field;",
+ "CREATE TABLE bibtex_field (",
+ " identifier int(10) NOT NULL,",
+ " name varchar(100) NOT NULL,",
+ " value text,",
+ " entry_key varchar(50) NOT NULL,",
+ " PRIMARY KEY(identifier),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_identity;",
+ "CREATE TABLE bibtex_identity (",
+ " identifier int(10) NOT NULL,",
+ " name varchar(100) NOT NULL,",
+ " firstname varchar(100) NOT NULL,",
+ " von varchar(20),",
+ " junior varchar(20),",
+ " PRIMARY KEY(identifier)",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_authors;",
+ "CREATE TABLE bibtex_authors (",
+ " entry_key varchar(50) NOT NULL,",
+ " author_id int(10) NOT NULL,",
+ " order_id int(5) NOT NULL DEFAULT 1,",
+ " etal boolean NOT NULL DEFAULT false,",
+ " PRIMARY KEY(entry_key,author_id),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE,",
+ " FOREIGN KEY(author_id) REFERENCES bibtex_identity(identifier) ON DELETE CASCADE",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_editors;",
+ "CREATE TABLE bibtex_editors (",
+ " entry_key varchar(50) NOT NULL,",
+ " editor_id int(10) NOT NULL,",
+ " order_id int(5) NOT NULL DEFAULT 1,",
+ " etal boolean NOT NULL DEFAULT false,",
+ " PRIMARY KEY(entry_key,editor_id),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE,",
+ " FOREIGN KEY(editor_id) REFERENCES bibtex_identity(identifier) ON DELETE CASCADE",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_entrydomain;",
+ "CREATE TABLE bibtex_entrydomain (",
+ " entry_key varchar(50) NOT NULL,",
+ " domain_id int(10) NOT NULL,",
+ " PRIMARY KEY(entry_key,domain_id),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE,",
+ " FOREIGN KEY(domain_id) REFERENCES bibtex_domain(identifier) ON DELETE CASCADE",
+ ");\n");
+
+ return $schema;
+}
+
+sub insertInto($) : method {
+ my $self = shift;
+ my $table = shift || Bib2HTML::General::Error::syserr('table name parameter is mandatory');
+ my $values = shift;
+ my $query = '';
+
+ my $sqlFields = '';
+ my $sqlValues = '';
+ foreach my $field (keys %{$values}) {
+ if ($sqlFields) {
+ $sqlFields .= ',';
+ }
+ $sqlFields .= $field;
+ if ($sqlValues) {
+ $sqlValues .= ',';
+ }
+ $sqlValues .= "'";
+ $sqlValues .= $self->quotesql($values->{$field});
+ $sqlValues .= "'";
+ }
+
+ $query .= "INSERT INTO ";
+ $query .= $table;
+ $query .= ' (';
+ $query .= $sqlFields;
+ $query .= ') VALUES (';
+ $query .= $sqlValues;
+ $query .= ");\n";
+
+ return $query;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 2004-07 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+(c) Copyright 2011 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/PgSql.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/PgSql.pm
new file mode 100644
index 0000000000..5560a10067
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/SqlEngine/PgSql.pm
@@ -0,0 +1,214 @@
+# Copyright (C) 2011 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::SqlEngine::PgSql - SQL Generator utilities for PostgreSQL
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::SqlEngine::PgSql;
+
+@ISA = ('');
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Carp ;
+
+use Bib2HTML::General::Error;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of this file
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = {};
+ bless( $self, $class );
+ return $self;
+}
+
+sub quotesql($) : method {
+ my $self = shift;
+ my $s = $_[0];
+ $s =~ s/\'/\\\'/g;
+ return $s;
+}
+
+
+sub createSchema() : method {
+ my $self = shift;
+ my $schema = '';
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_entrytype;",
+ "CREATE TABLE bibtex_entrytype (",
+ " type varchar(50) NOT NULL,",
+ " PRIMARY KEY(type)",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_domain;",
+ "CREATE TABLE bibtex_domain (",
+ " identifier integer NOT NULL,",
+ " name varchar(100) NOT NULL,",
+ " PRIMARY KEY(identifier)",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_entry;",
+ "CREATE TABLE bibtex_entry (",
+ " entry_key varchar(50) NOT NULL,",
+ " year integer NOT NULL default 1900,",
+ " title text NOT NULL,",
+ " type varchar(50) NOT NULL,",
+ " crossref varchar(50),",
+ " PRIMARY KEY(entry_key),",
+ " FOREIGN KEY(type) REFERENCES bibtex_entrytype(type) ON DELETE CASCADE,",
+ " FOREIGN KEY(crossref) REFERENCES bibtex_entry(entry_key) ON DELETE SET NULL",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_field;",
+ "CREATE TABLE bibtex_field (",
+ " identifier integer NOT NULL,",
+ " name varchar(100) NOT NULL,",
+ " value text,",
+ " entry_key varchar(50) NOT NULL,",
+ " PRIMARY KEY(identifier),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_identity;",
+ "CREATE TABLE bibtex_identity (",
+ " identifier integer NOT NULL,",
+ " name varchar(100) NOT NULL,",
+ " firstname varchar(100) NOT NULL,",
+ " von varchar(20),",
+ " junior varchar(20),",
+ " PRIMARY KEY(identifier)",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_authors;",
+ "CREATE TABLE bibtex_authors (",
+ " entry_key varchar(50) NOT NULL,",
+ " author_id integer NOT NULL,",
+ " order_id integer NOT NULL DEFAULT 1,",
+ " etal boolean NOT NULL DEFAULT false,",
+ " PRIMARY KEY(entry_key,author_id),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE,",
+ " FOREIGN KEY(author_id) REFERENCES bibtex_identity(identifier) ON DELETE CASCADE",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_editors;",
+ "CREATE TABLE bibtex_editors (",
+ " entry_key varchar(50) NOT NULL,",
+ " editor_id integer NOT NULL,",
+ " order_id integer NOT NULL DEFAULT 1,",
+ " etal boolean NOT NULL DEFAULT false,",
+ " PRIMARY KEY(entry_key,editor_id),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE,",
+ " FOREIGN KEY(editor_id) REFERENCES bibtex_identity(identifier) ON DELETE CASCADE",
+ ");\n");
+
+ $schema .= join("\n",
+ "DROP TABLE IF EXISTS bibtex_entrydomain;",
+ "CREATE TABLE bibtex_entrydomain (",
+ " entry_key varchar(50) NOT NULL,",
+ " domain_id integer NOT NULL,",
+ " PRIMARY KEY(entry_key,domain_id),",
+ " FOREIGN KEY(entry_key) REFERENCES bibtex_entry(entry_key) ON DELETE CASCADE,",
+ " FOREIGN KEY(domain_id) REFERENCES bibtex_domain(identifier) ON DELETE CASCADE",
+ ");\n");
+
+ return $schema;
+}
+
+sub insertInto($) : method {
+ my $self = shift;
+ my $table = shift || Bib2HTML::General::Error::syserr('table name parameter is mandatory');
+ my $values = shift;
+ my $query = '';
+
+ my $sqlFields = '';
+ my $sqlValues = '';
+ foreach my $field (keys %{$values}) {
+ if ($sqlFields) {
+ $sqlFields .= ',';
+ }
+ $sqlFields .= $field;
+ if ($sqlValues) {
+ $sqlValues .= ',';
+ }
+ $sqlValues .= "'";
+ $sqlValues .= $self->quotesql($values->{$field});
+ $sqlValues .= "'";
+ }
+
+ $query .= "INSERT INTO ";
+ $query .= $table;
+ $query .= ' (';
+ $query .= $sqlFields;
+ $query .= ') VALUES (';
+ $query .= $sqlValues;
+ $query .= ");\n";
+
+ return $query;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 2004-07 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+(c) Copyright 2011 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/StdOutWriter.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/StdOutWriter.pm
new file mode 100644
index 0000000000..fa814fb96e
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/StdOutWriter.pm
@@ -0,0 +1,163 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::StdOutWriter - An output stream writer
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::StdOutWriter is a Perl module, which permits to
+output streams into the standard output.
+
+=head1 SYNOPSYS
+
+Bib2HTML::Generator::StdOutWriter->new( ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::SydOutWriter is a Perl module, which permits to
+output streams into the standard output.
+
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in StdOutWriter.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::StdOutWriter;
+
+@ISA = ('Bib2HTML::Generator::Writer');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use Bib2HTML::Generator::Writer;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of abstract generator
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = $class->SUPER::new() ;
+ bless( $self, $class );
+ return $self;
+}
+
+=pod
+
+=item * openstream($)
+
+Open the output stream.
+Takes 1 param:
+
+=over
+
+=item * filename (string)
+
+is the name of the output file.
+
+=back
+
+=cut
+sub openstream($) {
+ my $self = shift;
+ my $filename = shift || confess( 'you must supply the root directory' ) ;
+ confess('output stream already opened') if ($self->{'opened'});
+ $self->{'opened'} = $filename;
+}
+
+=pod
+
+=item * out($)
+
+Put a string into the output stream.
+Takes 1 param:
+
+=over
+
+=item * str (string)
+
+is the string to output.
+
+=back
+
+=cut
+sub out($) {
+ my $self = shift;
+ my $str = shift || '';
+ print STDOUT ("$str");
+ return 1;
+}
+
+=pod
+
+=item * closestream()
+
+Close the currently opened stream.
+
+=cut
+sub closestream() {
+ my $self = shift;
+ delete $self->{'opened'};
+ return 1;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme.pm
new file mode 100644
index 0000000000..8513ec79da
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme.pm
@@ -0,0 +1,1418 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::Theme - A theme for the HTML generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::Theme ;
+
+my $gen = Bib2HTML::Generator::Theme->new( generator,
+ bib2html,
+ target,
+ title,
+ lang ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::Theme is a Perl module, which proposes
+a documentation theme for the HTML generator of bib2html.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::Theme;
+
+ my $gen = Bib2HTML::Generator::Theme->new( $generator,
+ { 'VERSION' => '0.11' },
+ './bib_output',
+ 'Title',
+ $lang ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * parent (object ref)
+
+is a reference to the current HTML generator.
+
+=item * bib2html (hash)
+
+contains some data about bib2html.
+
+=item * target (string)
+
+The directory in which the documentation must be put.
+
+=item * title (string)
+
+is the title of the documentation.
+
+=item * lang (object ref)
+
+is a reference to the language object.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Theme.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::Theme;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+
+use Carp ;
+use File::Spec ;
+
+use Bib2HTML::General::Verbose ;
+use Bib2HTML::General::Error ;
+use Bib2HTML::General::HTML ;
+use Bib2HTML::General::Misc ;
+use Bib2HTML::Generator::FileWriter ;
+use Bib2HTML::Generator::StdOutWriter ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of theme
+my $VERSION = "2.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = { 'PARENT' => $_[0] || confess( 'you must supply the parent object' ),
+ 'BIB2HTML' => $_[1] || '',
+ 'TARGET_DIR' => $_[2] || confess( 'you must supply the target directory' ),
+ 'TITLE' => $_[3] || '',
+ 'LANG' => $_[4] || confess( 'you must supply the language object' ),
+ } ;
+
+ my $simpleclass = $class;
+ if ($class =~ /^.*::(.+?)$/) {
+ $simpleclass = "$1";
+ }
+
+ # Register lang files
+ if ($self->{'LANG'}) {
+ $self->{'LANG'}->registerLang("Theme.$simpleclass");
+ }
+
+ bless( $self, $class );
+ return $self;
+}
+
+=pod
+
+=item * copy_files()
+
+Copies some files from the bib2html distribution directly inside the
+HTML documentation tree.
+
+=cut
+sub copy_files() : method {
+ my $self = shift ;
+}
+
+=pod
+
+=item * get_stream_writer()
+
+Replies the instance of the output stream writer.
+
+=cut
+sub get_stream_writer() : method {
+ my $self = shift ;
+ if (!$self->{'STREAM_WRITER'}) {
+ $self->{'STREAM_WRITER'} = new Bib2HTML::Generator::FileWriter->new();
+ }
+ return $self->{'STREAM_WRITER'};
+}
+
+=pod
+
+=item * set_stream_writer($)
+
+Set the instance of the output stream writer.
+Replies the old writer.
+Takes 1 arg:
+
+=over
+
+=item * writer (ref to Bib2HTML::Generator::Writer)
+
+is the instance of the writer.
+
+=back
+
+=cut
+sub set_stream_writer($) : method {
+ my $self = shift ;
+ my $writer = shift;
+ my $old_writer = $self->{'STREAM_WRITER'};
+ $self->{'STREAM_WRITER'} = $writer;
+ return $old_writer;
+}
+
+#------------------------------------------------------
+#
+# Filename API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * ext_href()
+
+Replies a hyperlink according to the parameters
+Takes 3 args:
+
+=over
+
+=item * section (string)
+
+is the id of the section.
+
+=item * label (string)
+
+is the label of the hyperlink
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub ext_href($$$) : method {
+ my $self = shift ;
+ my $section = shift || confess( 'you must supply the section id' ) ;
+ my $label = shift || '' ;
+ my $rootdir = shift || confess( 'you must supply the root directory' ) ;
+ return $self->href( htmlcatfile($rootdir,$self->filename($section,@_)),
+ $label,
+ $self->browserframe($section) ) ;
+}
+
+=pod
+
+=item * ext_wt_href()
+
+Replies a hyperlink according to the parameters (without target)
+Takes 3 args:
+
+=over
+
+=item * section (string)
+
+is the id of the section.
+
+=item * label (string)
+
+is the label of the hyperlink
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub ext_wt_href($$$) : method {
+ my $self = shift ;
+ my $section = shift || confess( 'you must supply the section id' ) ;
+ my $label = shift || '' ;
+ my $rootdir = shift || confess( 'you must supply the root directory' ) ;
+ return $self->href( htmlcatfile($rootdir,$self->filename($section,@_)),
+ $label ) ;
+}
+
+=pod
+
+=item * filename()
+
+Replies the filename of the specified section.
+Takes 1 arg:
+
+=over
+
+=item * section (string)
+
+is the name of the section.
+
+=back
+
+=cut
+sub filename : method {
+ my $self = shift ;
+ return $self->{'PARENT'}->filename(@_) ;
+}
+
+=pod
+
+=item * browserframe()
+
+Replies the frame used for the specified section.
+Takes 1 arg:
+
+=over
+
+=item * section (string)
+
+is the name of the section.
+
+=back
+
+=cut
+sub browserframe : method {
+ my $self = shift ;
+ return $self->{'PARENT'}->browserframe(@_) ;
+}
+
+#------------------------------------------------------
+#
+# Page API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_copyright()
+
+Replies a string that represents the copyright of this translator.
+
+=over
+
+=item * rootdir (string)
+
+is the path to the root directory
+
+=back
+
+=cut
+sub get_copyright($) : method {
+ my $self = shift ;
+ my $rootdir = $_[0] ;
+ return join( '',
+ $self->par( $self->small( $self->href( $self->{'BIB2HTML'}{'BUG_URL'},
+ $self->{'LANG'}->get( 'I18N_LANG_SUBMIT_BUG'), "_top" ) ) ),
+ $self->par( $self->small( $self->{'LANG'}->get( 'I18N_LANG_BIB2HTML_COPYRIGHT',
+ $self->href( $self->{'BIB2HTML'}{'URL'},
+ "bib2html ".$self->{'BIB2HTML'}{'VERSION'},
+ "_top" ),
+ $self->href( "mailto:".$self->{'BIB2HTML'}{'AUTHOR_EMAIL'},
+ $self->{'BIB2HTML'}{'AUTHOR'} ),
+ $self->href( "http://www.gnu.org/copyleft/gpl.html",
+ "GNU General Public License",
+ "_top" ) ) ) )
+ ) ;
+}
+
+=pod
+
+=item * get_html_index()
+
+Replies the content of the main index.html
+Takes 1 arg:
+
+=over
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub get_html_index($) {
+ my $self = shift ;
+ my $rootdir = $_[0] || confess( 'you must supply the root directory' ) ;
+ return join( '',
+ "<FRAMESET cols=\"20%,80%\">\n",
+ "<FRAMESET rows=\"30%,70%\">\n",
+ "<FRAME src=\"",
+ htmlcatfile($rootdir,$self->filename('overview-frame')),
+ "\" name=\"",
+ $self->browserframe('overview-frame'),
+ "\">\n<FRAME src=\"",
+ htmlcatfile($rootdir,$self->filename('allelements')),
+ "\" name=\"",
+ $self->browserframe('allelements'),
+ "\">\n</FRAMESET>\n<FRAME src=\"",
+ htmlcatfile($rootdir,$self->filename('overview-summary')),
+ "\" name=\"",
+ $self->browserframe('overview-summary'),
+ "\">\n<NOFRAMES>\n",
+ $self->{'LANG'}->get('I18N_LANG_NO_FRAME_ALERT',
+ $self->filename('overview-summary'),
+ ''),
+ "</NOFRAMES>\n",
+ "</FRAMESET>\n" ) ;
+}
+
+=pod
+
+=item * create_html_page()
+
+Creates an HTML page without a <BODY>.
+Takes 3 args:
+
+=over
+
+=item * filename (string)
+
+is the name of the file in which the page
+must be created.
+
+=item * content (string)
+
+is the content of the page.
+
+=item * title (string)
+
+is the title of the page.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=item * frameset (boolean)
+
+must be true if the generated page must respect the w3c frameset definition,
+otherwhise it will respect the w3c transitional definition
+
+=back
+
+=cut
+sub create_html_page($$$$$) : method {
+ my $self = shift ;
+ my $rootdir = $_[3] || confess( 'you must supply the root directory' ) ;
+ confess( 'you must supply the filename' ) unless $_[0] ;
+ my $filename = File::Spec->catfile( $self->{'TARGET_DIR'}, htmlpath($_[0]) ) ;
+ Bib2HTML::General::Verbose::two( "Writing $filename..." ) ;
+
+ my $writer = $self->get_stream_writer();
+
+ $writer->openstream("$filename")
+ or Bib2HTML::General::Error::syserr( "$filename: $!\n" );
+
+ my $header ;
+ if ( $_[4] ) {
+ $header = "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Frameset//EN\" \"http://www.w3.org/TR/REC-html40/frameset.dtd\">" ;
+ }
+ else {
+ $header = "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/REC-html40/loose.dtd\">" ;
+ }
+
+ $writer->out(join( '',
+ $header,
+ "\n\n<!-- Generated by bib2html ".$self->{'BIB2HTML'}{'VERSION'},
+ " on ",
+ "".localtime(),
+ " -->\n\n",
+ "<HTML>\n<HEAD>\n<TITLE>",
+ $_[2] || '',
+ "</TITLE>\n",
+ "<META http-equiv=\"Content-Type\" ",
+ "content=\"text/html; charset=",
+ $self->get_html_encoding(),#ISO-8859-1
+ "\">\n",
+ $self->get_html_header($rootdir),
+ "</HEAD>\n",
+ $_[1] || '',
+ "</HTML>" ) ) ;
+
+ $writer->closestream() ;
+}
+
+=pod
+
+=item * get_html_encoding()
+
+Replies the HTML encoding of each page
+(by default ISO-8859-1).
+
+=cut
+sub get_html_encoding() : method {
+ my $self = shift ;
+ return $self->{'html_encoding'} || "ISO-8859-1" ;
+}
+
+=pod
+
+=item * set_html_encoding($)
+
+Set the HTML encoding of each page
+Takes 1 arg:
+
+=over
+
+=item * encoding (string)
+
+is the new encoding
+
+=back
+
+=cut
+sub set_html_encoding($) : method {
+ my $self = shift ;
+ my $encoding = shift;
+ $self->{'html_encoding'} = $encoding if ($encoding) ;
+}
+
+=pod
+
+=item * get_html_header()
+
+Replies the HTML header of each page.
+Takes 1 arg:
+
+=over
+
+=item * rootdir (string)
+
+is the path to the root directory
+
+=back
+
+=cut
+sub get_html_header($) : method {
+ my $self = shift ;
+ return '' ;
+}
+
+=pod
+
+=item * create_html_body_page()
+
+Creates an HTML page with a <BODY>.
+Takes 3 args:
+
+=over
+
+=item * filename (string)
+
+is the name of the file in which the page
+must be created.
+
+=item * content (string)
+
+is the content of the page.
+
+=item * title (string)
+
+is the title of the page.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub create_html_body_page($$$$@) : method {
+ my $self = shift ;
+ my $filename = shift ;
+ my $content = shift ;
+ my $title = shift ;
+ my $rootdir = shift || confess( "the rootdir must be supplied" ) ;
+ $content = join( '',
+ "<BODY",
+ ( $self->{'BACKGROUND_COLOR'} ?
+ " BGCOLOR=\"" .
+ $self->{'BACKGROUND_COLOR'} .
+ "\"" : '' ),
+ ">\n",
+ $content ) ;
+ my $small ;
+ if ((@_)&&("$_[0]" eq 'small')) {
+ shift @_ ;
+ $small = 1 ;
+ }
+ $self->mergeValidHTMLIcons($content,$rootdir,$small,@_) ;
+ $content .= "\n</BODY>\n",
+ $self->create_html_page( "$filename",
+ "$content",
+ "$title",
+ "$rootdir",
+ 0 ) ;
+}
+
+=pod
+
+=item * getMyValidHTML()
+
+Replies the list of W3C protocols for which this theme
+was validated. You must override this method.
+
+=cut
+sub getMyValidHTML() {
+ my $self = shift ;
+ return () ;
+}
+
+sub mergeValidHTMLIcons($$$@) {
+ my $self = shift ;
+ if (int(@_)>3) {
+
+ #
+ # A protocol is displayed as supported only if
+ # the generator AND the theme support it, or
+ # if the protocol was CSS and was supported
+ # by the theme only (We assume that the generators
+ # does not use any CSS syntax)
+ #
+ my @themevalid = $self->getMyValidHTML() ;
+ my @valid = () ;
+ for(my $i=3; $i<int(@_); $i++) {
+ if (strinarray("$_[$i]",\@themevalid)) {
+ push @valid, "$_[$i]" ;
+ }
+ }
+ if (strinarray('css',\@themevalid)) {
+ push @valid, 'css' ;
+ }
+
+ if ($_[2]) {
+ setAsValidHTML_small($_[0],$_[1],@valid) ;
+ }
+ else {
+ setAsValidHTML($_[0],$_[1],@valid) ;
+ }
+ }
+}
+
+#------------------------------------------------------
+#
+# Paragraph API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * frame_subpart()
+
+Replies a subpart of a frame
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the part.
+
+=item * text (array)
+
+is the content of the frame.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub frame_subpart($$$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+=pod
+
+=item * frame_window()
+
+Replies a frame
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the frame.
+
+=item * text (string)
+
+is the content of the frame.
+
+=item * prefix (optional string)
+
+is a string which is put before the title
+
+=back
+
+=cut
+sub frame_window($$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+=pod
+
+=item * partseparator()
+
+Replies a part separator.
+
+=cut
+sub partseparator($) {
+ my $self = shift ;
+ return "<HR>\n" ;
+}
+
+=pod
+
+=item * title()
+
+Formats a page title
+Takes 2 args:
+
+=over
+
+=item * text (string)
+
+=item * text_before (optional boolean)
+
+indicates if some text are before this title
+
+=back
+
+=cut
+sub title($) {
+ my $self = shift ;
+ my $text = $_[0] || confess( 'you must specify the text' ) ;
+ return
+ ($_[1] ? $self->partseparator() : '') .
+ "<center><h2>$text</h2></center>\n\n" ;
+}
+
+=pod
+
+=item * subtitle()
+
+Formats a page subtitle
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=item * text_before (optional boolean)
+
+indicates if some text are before this title
+
+=back
+
+=cut
+sub subtitle($) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ if ( ! $text ) {
+ Bib2HTML::General::Error::syswarm( 'a title was expected' ) ;
+ }
+ return
+ ($_[1] ? "<hr>\n" : '').
+ "<h2>$text</h2>\n" ;
+}
+
+=pod
+
+=item * strong()
+
+Formats a keyword
+Takes 2 args:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub strong($) {
+ my $self = shift ;
+ my $text = $_[0] || confess( 'you must specify the text' ) ;
+ return "<b>$text</b>" ;
+}
+
+=pod
+
+=item * entry_title()
+
+Formats the title of an BibTeX entry.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub entry_title($) {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ if ( ! $title ) {
+ Bib2HTML::General::Error::syswarm( 'a title was expected' ) ;
+ }
+ return join( '',
+ "&quot;<i><b>",
+ $title,
+ "</b></i>&quot;" ) ;
+}
+
+=pod
+
+=item * format_date()
+
+Formats a date.
+Takes 2 args:
+
+=over
+
+=item * month (string)
+
+=item * year (string)
+
+=back
+
+=cut
+sub format_date($$) {
+ my $self = shift ;
+ my $month = $_[0] || '' ;
+ my $year = $_[1] || confess( 'you must supply the year' ) ;
+ return ($month?"$month&nbsp;":"")."$year" ;
+}
+
+=pod
+
+=item * href()
+
+Replies a hyperlink.
+Takes 3 args:
+
+=over
+
+=item * url (string)
+
+is the URL to link to
+
+=item * label (string)
+
+is the label of the hyperlink
+
+=item * target (optional string)
+
+is the frame target.
+
+=back
+
+=cut
+sub href($$) {
+ my $self = shift ;
+ my $url = $_[0] || confess( 'you must specify the URL' ) ;
+ my $label = $_[1] ;
+ return '' unless ($label) ;
+ return join( '',
+ "<A HREF=\"",
+ $url,
+ "\"",
+ ( $_[2] ? " target=\"$_[2]\"" : "" ),
+ ">",
+ $label,
+ "</A>" ) ;
+}
+
+=pod
+
+=item * small()
+
+Replies a text with a small size.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub small($) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ return join( '',
+ "<FONT SIZE=\"-1\">",
+ $text,
+ "</FONT>\n" ) ;
+}
+
+=pod
+
+=item * tiny()
+
+Replies a text with a tiny size.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub tiny($) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ return join( '',
+ "<FONT SIZE=\"-2\">",
+ $text,
+ "</FONT>\n" ) ;
+}
+
+=pod
+
+=item * par()
+
+Replies a paragraph.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub par($) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ return join( '',
+ "<P>",
+ $text,
+ "</P>\n" ) ;
+}
+
+=pod
+
+=item * get_tree_node()
+
+Replues the HTML string for the specified tree.
+a list.
+Takes 2 args:
+
+=over
+
+=item * node (string)
+
+is the string that is the root of the tree.
+
+=item * subs (string)
+
+is an HTML string that describes the children.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub get_tree_node($$$) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my $sub = $_[1] || '' ;
+ $sub = "<ul>$sub</ul>" ;
+ if ( $text ) {
+ return "<li type=\"circle\">".$text.$sub."</li>\n" ;
+ }
+ else {
+ return "$sub\n" ;
+ }
+}
+
+=pod
+
+=item * get_tree_leaf()
+
+Replies a line of a tree which will be displayed inside
+a list.
+Takes 1 args:
+
+=over
+
+=item * node (string)
+
+is the string that is the root of the tree.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub get_tree_leaf($$) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ return join( '',
+ "<li type=\"circle\">",
+ $text,
+ "</li>\n" ) ;
+}
+
+=pod
+
+=item * get_tree()
+
+Creates a tree.
+Takes 2 or 3 args:
+
+=over
+
+=item * tree (hash)
+
+is the tree
+
+=item * rootdir (string)
+
+is the path to the root directory
+
+=item * root label (optional string)
+
+is the label of the root node
+
+=back
+
+=cut
+sub get_tree($$;$) : method {
+ my $self = shift ;
+ my $tree = $_[0] || confess( "you must supply the tree" ) ;
+ my $rootdir = $_[1] || confess( 'you must supply the root directory' ) ;
+ my $content = $self->__get_default_tree__($tree,$rootdir) ;
+ if ( $content ) {
+ return "<ul>$content</ul>\n" ;
+ }
+ else {
+ return "$content" ;
+ }
+}
+
+sub __get_default_tree__($$) {
+ my $self = shift ;
+ my $tree = $_[0] || confess( "you must supply the tree" ) ;
+ my $rootdir = $_[1] || confess( 'you must supply the root directory' ) ;
+ my $content = '' ;
+
+ my @c = keys %{$tree};
+ @c = sortbyletters(@c);
+ foreach my $children (@c) {
+
+ if ( isemptyhash($tree->{"$children"}) ) {
+ # leaf
+ $content .= $self->get_tree_leaf("$children",$rootdir) ;
+ }
+ else {
+ # node
+ my $sub = $self->__get_default_tree__($tree->{"$children"},$rootdir) ;
+ $content .= $self->get_tree_node("$children",$sub,$rootdir) ;
+ }
+
+ }
+
+ return $content ;
+}
+
+=pod
+
+=item * get_navigation_bar()
+
+Replies the navigation bar.
+Takes 3 args:
+
+=over
+
+=item * url (string)
+
+is the url of the generated page.
+
+=item * params (hash ref)
+
+is a set of parameters used to generate the bar.
+
+=item * root (string)
+
+is the root directory for the generated documentation.
+
+=back
+
+=cut
+sub get_navigation_bar($$$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+=pod
+
+=item * section()
+
+Replies a section
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the new section.
+
+=item * content (string)
+
+is the content of the new section
+
+=item * root (string)
+
+is the root directory for the generated documentation.
+
+=back
+
+=cut
+sub section($$$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+#------------------------------------------------------
+#
+# Array API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * build_onecolumn_array()
+
+Replies an one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_onecolumn_array($$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+=pod
+
+=item * build_twocolumn_array()
+
+Replies an two-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_twocolumn_array($$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+=pod
+
+=item * build_small_array()
+
+Replies an small one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_small_array($$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+=pod
+
+=item * build_tiny_array()
+
+Replies a tiny one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_tiny_array($$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+=pod
+
+=item * build_threecolumn_array()
+
+Replies an two-column array.
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=item * anchor (string)
+
+is the name of the anchor.
+
+=back
+
+=cut
+sub build_threecolumn_array($$$) : method {
+ my $self = shift ;
+ confess( 'you must overwrite this method' ) ;
+}
+
+#------------------------------------------------------
+#
+# Index API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * format_index_page()
+
+Replies a formatted page for the index.
+Takes 3 args:
+
+=over
+
+=item * letterlist (string)
+
+is the list of letters of the index.
+
+=item * letter (string)
+
+is the current letter.
+
+=item * content (array ref)
+
+is the content of the page.
+
+=back
+
+=cut
+sub format_index_page($$$) : method {
+ my $self = shift ;
+ my $letterlist = $_[0] || '' ;
+ my $letter = notempty( $_[1], 'you must supply the index letter for this page' ) ;
+
+ my $content = join( '',
+ ( $letterlist ?
+ $letterlist.$self->partseparator() : '' ),
+ "<H2>",
+ uc($letter),
+ "</H2>\n",
+ "<DL>" ) ;
+
+ my $previouslabel = '' ;
+ my @currententry = () ;
+
+ foreach my $entry (@{$_[2]}) {
+ if ( "$previouslabel" eq $entry->{'label'} ) {
+ # Caching this entry for futher display
+ push @currententry, $entry ;
+ }
+ else {
+ # Generate the page content
+ $self->__generate_index_entry(\@currententry,$content,$entry);
+ }
+
+ $previouslabel = $entry->{'label'} ;
+ }
+
+ if ( @currententry ) {
+ $self->__generate_index_entry(\@currententry,$content);
+ }
+
+ $content .= join( '',
+ "</DL>",
+ ( $letterlist ?
+ $self->partseparator().$letterlist : '' ) ) ;
+
+ return $content ;
+}
+
+sub __generate_index_entry($$;$) {
+ my $self = shift ;
+
+ # Generates the previous entries
+ if ( @{$_[0]} == 1 ) {
+ $_[1] .= join( '',
+ "<DT>",
+ $self->href( $_[0]->[0]{'url'},
+ $_[0]->[0]{'label'} ),
+ ( $_[0]->[0]{'short_comment'} ?
+ " - ".$_[0]->[0]{'short_comment'} :
+ '' ),
+ "</DT><DD>",
+ $_[0]->[0]{'comment'},
+ "&nbsp;</DD>\n" ) ;
+ }
+ elsif ( @{$_[0]} > 1 ) {
+ $_[1] .= join( '',
+ "<DT>",
+ $_[0]->[0]{'label'},
+ "</DT><DD><UL>" ) ;
+ foreach my $entry_to_display (@{$_[0]}) {
+ $_[1] .= join( '',
+ "<LI>",
+ $entry_to_display->{'comment'},
+ $self->href( $entry_to_display->{'url'},
+ "<IMG src=\"./loupe.gif\" alt=\"\" ".
+ "border=\"0\" align=\"center\">" ),
+ "</LI>\n"
+ ) ;
+ }
+ $_[1] .= "</UL></DD>\n" ;
+ }
+ # Prepare the caching for this entry
+ if ( $_[2] ) {
+ @{$_[0]} = ( $_[2] ) ;
+ }
+}
+
+#------------------------------------------------------
+#
+# Filename API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_math_start_tag()
+
+Replies the HTML balise which starts the math mode.
+
+=cut
+sub get_math_start_tag() : method {
+ my $self = shift ;
+ return "<math>" ;
+}
+
+=pod
+
+=item * get_math_stop_tag()
+
+Replies the HTML balise which stops the math mode.
+
+=cut
+sub get_math_stop_tag() : method {
+ my $self = shift ;
+ return "</math>" ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna.pm
new file mode 100644
index 0000000000..3c9d051214
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna.pm
@@ -0,0 +1,1401 @@
+# Copyright (C) 2002-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::Theme::DynaTheme - A theme for the HTML generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::Theme::DynaTheme ;
+
+my $gen = Bib2HTML::Generator::Theme::DynaTheme->new( bib2html,
+ target,
+ title,
+ phpgen,
+ webgen ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::Theme::DynaTheme is a Perl module, which proposes
+a documentation theme for the HTML generator of bib2html. This theme generates
+something like javadoc.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::Theme::DynaTheme;
+
+ my $gen = Bib2HTML::Generator::Theme::DynaTheme->new( { 'VERSION' => '0.11' },
+ "./phpdoc",
+ "Title",
+ 1, 1 ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * bib2html (hash)
+
+contains some data about bib2html.
+
+=item * target (string)
+
+The directory in which the documentation must be put.
+
+=item * title (string)
+
+is the title of the documentation.
+
+=item * phpgen (boolean)
+
+indicates if the PHP doc was generated
+
+=item * webgen (boolean)
+
+indicates if the WEB doc was generated
+
+=item * lang (object ref)
+
+is a reference to the language object.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Html.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::Theme::Dyna;
+
+@ISA = ('Bib2HTML::Generator::Theme');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+
+use Carp ;
+
+use Bib2HTML::Generator::Theme ;
+use Bib2HTML::General::Verbose ;
+use Bib2HTML::General::Error ;
+use Bib2HTML::General::HTML ;
+use Bib2HTML::General::Misc ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of Dyna theme
+my $VERSION = "4.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$$$) {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = $class->SUPER::new( @_ ) ;
+
+ $self->{'COPY_FILES'} = [ 'stylesheet.css',
+ 'minus.gif',
+ 'plus.gif',
+ 'child.gif',
+ 'lastchild.gif',
+ 'samechild.gif',
+ 'emptychild.gif',
+ ] ;
+
+ $self->{'FRAME_TREE_ID_COUNT'} = 0 ;
+ $self->{'TREE_ID_COUNT'} = 0 ;
+
+ bless( $self, $class );
+
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Validation
+#
+#------------------------------------------------------
+
+=pod
+
+=item * getMyValidHTML()
+
+Replies the list of W3C protocols for which this theme
+was validated. You must override this method.
+
+=cut
+sub getMyValidHTML() {
+ my $self = shift ;
+ return ( 'html', 'css' ) ;
+}
+
+#------------------------------------------------------
+#
+# Main structure
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_html_header()
+
+Replies the HTML header of each page.
+Takes 1 arg:
+
+=over
+
+=item * rootdir (string)
+
+is the path to the root directory
+
+=back
+
+=cut
+sub get_html_header($) : method {
+ my $self = shift ;
+ my $rootdir = $_[0] || confess( 'you must supply the root directory' ) ;
+ return join( '',
+ "<link REL ='stylesheet' TYPE='text/css' HREF='",
+ htmlcatfile($rootdir,"stylesheet.css"),
+ "' TITLE='Style'>\n",
+
+ # JavaScript
+ "<script language='JavaScript1.2' type=\"text/javascript\">\n<!--\n",
+ "function swaptreecontent(elID) {\n",
+ " b = document.getElementById(elID).innerHTML;\n",
+ " a = document.getElementById(elID + \"off__\").innerHTML;\n",
+ " if (a.length == 0) {",
+ " document.getElementById(elID).innerHTML = \"\";\n",
+ " } else {\n",
+ " document.getElementById(elID).innerHTML = a;\n",
+ " }\n",
+ " document.getElementById(elID + \"off__\").innerHTML = b;\n",
+ "}\n\n",
+ "function swaptreeicon(elID) {\n",
+ " a = document.getElementById(elID + \"plusminus\").src;\n",
+ " if (a.indexOf(\"minus.gif\") != -1) a = \"",
+ htmlcatfile($rootdir,"plus.gif"),
+ "\";\n",
+ " else a = \"",
+ htmlcatfile($rootdir,"minus.gif"),
+ "\";\n",
+ " document.getElementById(elID + \"plusminus\").src = a;\n",
+ "}\n\n",
+ "function swaptree(elID) {\n",
+ " swaptreecontent(elID);\n",
+ " swaptreeicon(elID);\n",
+ "}\n\n",
+ "function swaptree2(elID1,elID2) {\n",
+ " swaptreecontent(elID1);\n",
+ " swaptreecontent(elID2);\n",
+ " swaptreeicon(elID1);\n",
+ "}\n",
+ "//-->\n</script>\n" ) ;
+}
+
+
+#------------------------------------------------------
+#
+# Structural element API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_tree_node()
+
+Replues the HTML string for the specified tree.
+a list.
+Takes 2 args:
+
+=over
+
+=item * node (string)
+
+is the string that is the root of the tree.
+
+=item * subs (string)
+
+is an HTML string that describes the children.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub get_tree_node($$$) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ $text =~ s/[ \t\n\r]+/&nbsp;/g ;
+ return $self->SUPER::get_tree_node($text,$_[1],$_[2]) ;
+}
+
+=pod
+
+=item * get_tree_leaf()
+
+Replies a line of a tree which will be displayed inside
+a list.
+Takes 1 args:
+
+=over
+
+=item * node (string)
+
+is the string that is the root of the tree.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub get_tree_leaf($$) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ $text =~ s/[ \t\n\r]+/&nbsp;/g ;
+ return $self->SUPER::get_tree_leaf($text,$_[1]) ;
+}
+
+=pod
+
+=item * get_tree()
+
+Creates a tree.
+Takes 2 or 3 args:
+
+=over
+
+=item * tree (hash)
+
+is the tree
+
+=item * rootdir (string)
+
+is the path to the root directory
+
+=item * root label (optional string)
+
+is the label of the root node
+
+=back
+
+=cut
+sub get_tree($$;$) : method {
+ my $self = shift ;
+ my $tree = $_[0] || confess( "you must supply the tree" ) ;
+ my $rootdir = $_[1] || confess( 'you must supply the root directory' ) ;
+ my $defaultRootLabel = $self->{'LANG'}->get('I18N_LANG_THEME_TREE_ROOT');
+ my $rootlabel = $_[2] || $defaultRootLabel;
+ $tree = { $rootlabel => $tree } ;
+ return $self->__get_dyna_tree__( $tree, $rootdir ) ;
+}
+
+sub __get_dyna_tree__($$) {
+ my $self = shift ;
+ my $rootdir = $_[1] || confess( 'you must supply the root directory' ) ;
+ my ($prevs,$lines,$max) = $self->__get_dyna_tree_rec__(@_) ;
+
+ my $content = '' ;
+ foreach my $prev (@{$prevs}) {
+ $content .= join( '',
+ "<DIV id=\"",
+ $prev,
+ "off__\" style=\"visibility : hidden; position: absolute\"></DIV>\n" ) ;
+ }
+
+ my $tblheader = "<TABLE border='0' cellspacing='0' cellpadding='0' width='100%'>\n" ;
+ my $tblfooter = "</TABLE>\n" ;
+
+ my $tablecontent = "" ;
+ foreach my $line (@{$lines}) {
+ my $iddata = pop @{$line} ;
+ my $count = $max ;
+ my $linecontent = '' ;
+
+ while (@{$line}) {
+ my $cell = shift @{$line} ;
+
+ if (($cell)&&("$cell" eq "[-]")) {
+ # Add a collapse button
+ confess( 'empty id when collapsable node' ) unless $iddata->{'open'} ;
+ $count -- ;
+ $linecontent .= join( '',
+ "<TD valign='middle' align='left' width='11' height='17'>",
+ $self->href( "javascript:swaptree('".$iddata->{'open'}."')",
+ "<img src=\"".
+ htmlcatfile($rootdir,"minus.gif").
+ "\" alt=\"-\" ".
+ "id=\"".$iddata->{'open'}."plusminus\" width=\"11\" ".
+ "height=\"11\" border=\"0\">" ),
+ "</TD>" ) ;
+ }
+ elsif (($cell)&&($cell eq '[ ]')) {
+ # Add a white space
+ $count -- ;
+ $linecontent .= join( '',
+ "<TD valign='top' align='left' width='11' height='17'>",
+ "<IMG src=\"",
+ htmlcatfile($rootdir,"emptychild.gif"),
+ "\" alt=\" \" width=\"11\" ",
+ "height=\"17\" border=\"0\">",
+ "</TD>" ) ;
+ }
+ elsif (($cell)&&($cell eq '[+]')) {
+ # Add a tee
+ $count -- ;
+ $linecontent .= join( '',
+ "<TD valign='top' align='left' width='11' height='17'>",
+ "<IMG src=\"",
+ htmlcatfile($rootdir,"child.gif"),
+ "\" alt=\"+\" width=\"11\" ",
+ "height=\"17\" border=\"0\">",
+ "</TD>" ) ;
+ }
+ elsif (($cell)&&($cell eq '[|]')) {
+ # Add a vertical bar
+ $count -- ;
+ $linecontent .= join( '',
+ "<TD valign='top' align='left' height='17'>",
+ "<IMG src=\"",
+ htmlcatfile($rootdir,"samechild.gif"),
+ "\" alt=\"|\" width=\"11\" ",
+ "height=\"17\" border=\"0\">",
+ "</TD>" ) ;
+ }
+ elsif (($cell)&&($cell eq '[\\]')) {
+ # Add a corner
+ $count -- ;
+ $linecontent .= join( '',
+ "<TD valign='top' align='left' width='11' height='17'>",
+ "<IMG src=\"",
+ htmlcatfile($rootdir,"lastchild.gif"),
+ "\" alt=\"\\\" width=\"11\" ",
+ "height=\"17\" border=\"0\">",
+ "</TD>" ) ;
+ }
+ elsif (($cell)&&($count>0)) {
+ # Add a text
+ $linecontent .= join( '',
+ "<TD colspan='$count' width='100%' valign='middle' align='left' class='TreeText' height='17'>",
+ $cell,
+ "</TD>" ) ;
+ $count = 0 ;
+ }
+
+ }
+
+ # Add the line
+ if ($linecontent !~ /^\s*$/m) {
+
+ # Test if a table header was needed
+ $tablecontent = "$tblheader" unless ($tablecontent) ;
+
+ # Add the line
+ $tablecontent .= "<TR>$linecontent</TR>" ;
+
+ # Close the table if on a block bound
+ if ((!isemptyarray($iddata->{'closes'}))||
+ ($iddata->{'open'})) {
+ $content .= "$tablecontent$tblfooter" ;
+ $tablecontent = "" ;
+ }
+
+ # Put the block's open/close actions
+ if (!isemptyarray($iddata->{'closes'})) {
+ for(my $i=0; $i<@{$iddata->{'closes'}}; $i++) {
+ $content .= "</DIV>" ;
+ }
+ }
+ if ( $iddata->{'open'} ) {
+ $content .= "<DIV id=\"".$iddata->{'open'}."\">" ;
+ }
+
+ }
+
+ }
+
+ if ($tablecontent) {
+ $content .= "$tablecontent$tblfooter" ;
+ }
+
+ return $content ;
+}
+
+sub __get_dyna_tree_rec__($$) {
+ my $self = shift ;
+ my $rootdir = $_[1] || confess( 'you must supply the root directory' ) ;
+ my @content = () ;
+ my @prev = () ;
+ my $max = 0 ;
+
+ if ( ! isemptyhash( $_[0] ) ) {
+
+ my @keys = keys %{$_[0]};
+ @keys = sortbyletters(@keys) ;
+
+ for(my $i=0; $i<=$#keys; $i++) {
+ my $nodename = $keys[$i] ;
+ my $oid = '' ;
+
+ # Gets the children
+ my ($child_prev,$child_content,$child_max) = $self->__get_dyna_tree_rec__( $_[0]->{$nodename}, $rootdir ) ;
+
+ # Computes the collpasing icon
+ my $collaps = '' ;
+ if ( ! isemptyarray( $child_content ) ) {
+ $collaps = '[-]' ;
+ # Computes the tags just before the tree
+ # This tag permits to undisplay the $id area
+ $self->{'FRAME_TREE_ID_COUNT'} ++ ;
+ $oid = "treeoverviewid".$self->{'FRAME_TREE_ID_COUNT'} ;
+ push @prev, $oid ;
+ }
+ push @prev, @{$child_prev} ;
+
+ # Adds this node to the array
+ push @content, [ "$collaps", "&nbsp;$nodename", { 'open' => $oid,
+ 'closes' => [] } ] ;
+ $max = 2 ;
+
+ # Adds the children
+ my @subcontent = () ;
+ my $found = 0 ;
+ for(my $j=$#{$child_content}; $j>=0; $j--) {
+ my $next = $child_content->[$j][0] ;
+ my $icon = '[ ]' ;
+ if ( $found ) {
+ if ( ( ! $next ) || ( $next eq '[-]' ) ) {
+ $icon = '[+]' ;
+ }
+ else {
+ $icon = '[|]' ;
+ }
+ }
+ elsif ( ( ! $next ) || ( $next eq '[-]' ) ) {
+ $found = 1 ;
+ $icon = '[\\]' ;
+ }
+ unshift @subcontent, [ $icon, @{$child_content->[$j]} ] ;
+ if ( $max < (@{$child_content->[$j]}-1) ) {
+ $max = @{$child_content->[$j]}-1 ;
+ }
+ }
+ push @content, @subcontent ;
+ if ( $oid ) {
+ push( @{$content[$#content]->[$#{$content[$#content]}]->{'closes'}},
+ $oid ) ;
+ }
+ }
+
+ }
+
+ return (\@prev,\@content,$max) ;
+}
+
+=pod
+
+=item * build_linked_tree()
+
+Creates a tree with links between nodes.
+Takes 1 arg:
+
+=over
+
+=item * tree (array)
+
+is the tree
+
+=item * rootdir (string)
+
+is the path to the root directory
+
+=back
+
+=cut
+sub build_linked_tree($$) : method {
+ my $self = shift ;
+ my $tree = $_[0] || confess( "you must supply the tree" ) ;
+ my $rootdir = $_[1] || confess( 'you must supply the root directory' ) ;
+ my $content = "" ;
+ if ( $#{$tree} >= 0 ) {
+ my $end = '' ;
+ for(my $i=0; $i<=$#{$tree}; $i++ ) {
+ my $class = $tree->[$i] ;
+
+ $self->{'FRAME_TREE_ID_COUNT'} ++ ;
+ my $id1 = "classtreeid".$self->{'FRAME_TREE_ID_COUNT'} ;
+ $self->{'FRAME_TREE_ID_COUNT'} ++ ;
+ my $id2 = "classtreeid".$self->{'FRAME_TREE_ID_COUNT'} ;
+
+ $content .= join( '',
+ "<DIV id=\"",
+ $id1,
+ "off__\" style=\"visibility : hidden; position: absolute\"></DIV>\n",
+ "<DIV id=\"",
+ $id2,
+ "off__\" style=\"visibility : hidden; position: absolute\"></DIV>\n",
+
+ "<TABLE border=0 cellspacing=2 cellpadding=0>",
+ "<TR><TD>" ) ;
+
+ if ( $i < $#{$tree} ) {
+ $content .= join( '',
+ $self->href( "javascript:swaptree2('".$id1."','".$id2."')",
+ "<img src=\"".
+ htmlcatfile($rootdir,"minus.gif").
+ "\" alt=\"-\" ".
+ "id=\"".$id1."plusminus\" width=\"11\" ".
+ "height=\"11\" border=\"0\">" ),
+ "</TD><TD>&nbsp;" ) ;
+ }
+
+ $content .= join( '',
+ $class,
+ "</TD></TR>",
+ "<TR><TD valign='top' align='right'>" ) ;
+
+ if ( $i < $#{$tree} ) {
+ $content .= join( '',
+ "<DIV id=\"",
+ $id2,
+ "\">",
+ "<IMG src=\"",
+ htmlcatfile($rootdir,"lastchild.gif"),
+ "\" alt=\"-\" width=\"11\" ",
+ "height=\"17\" border=\"0\">",
+ "</DIV>" ) ;
+ }
+
+ $content .= join( '',
+ "</TD><TD class='TreeText' valign='middle' align='left'><DIV id=\"",
+ $id1,
+ "\">") ;
+
+ $end .= "</DIV></TD></TR></TABLE>" ;
+
+ }
+
+ $content .= $end ;
+
+ }
+ return $content ;
+}
+
+=pod
+
+=item * build_detail_section_title()
+
+Replies title of an detail section.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the section.
+
+=item * label (string)
+
+is the label of the title bar.
+
+=back
+
+=cut
+sub build_detail_section_title($$) : method {
+ my $self = shift ;
+ return join( '',
+ "<A NAME=\"",
+ $_[1] || '',
+ "\"></A>",
+ "<P></P><TABLE BORDER='1' CELLPADDING='3' CELLSPACING='0' WIDTH='100%'>",
+ "<THEAD><TR><TD CLASS='largetabletitle'>",
+ $_[0] || '',
+ "</TD></TR></THEAD></TABLE><BR>\n" ) ;
+}
+
+=pod
+
+=item * build_class_detail()
+
+Replies the detail for a class.
+Takes 3 args:
+
+=over
+
+=item * classname (string)
+
+is the name of the class
+
+=item * extends (string)
+
+is the name of extended class.
+
+=item * explanation (string)
+
+is the description of the function.
+
+=item * details (string)
+
+contains some details on this function.
+
+=back
+
+=cut
+sub build_class_detail($$$$) : method {
+ my $self = shift ;
+ my $classname = $_[0] || confess( 'you must supply the classname' ) ;
+ my $extends = $_[1] || '' ;
+ my $explanation = $_[2] || '' ;
+ my $details = $_[3] || '' ;
+ return join( '',
+ "<DL>\n<DT>",
+ $self->{'LANG'}->get('I18N_LANG_CLASS'),
+ " <B>$classname</B>",
+ ( $extends ? "<DT>".
+ $self->{'LANG'}->get('I18N_LANG_EXTENDS').
+ " $extends</DL>\n" : '' ),
+ "<P>",
+ $explanation,
+ "</P>\n",
+ $details,
+ "</DL>\n" ) ;
+}
+
+=pod
+
+=item * build_function_detail()
+
+Replies the detail for a function.
+Takes 5 args:
+
+=over
+
+=item * key_name (string)
+
+is the keyname of the function.
+
+=item * name (string)
+
+is the name of the function.
+
+=item * signature (string)
+
+is the signature of the function.
+
+=item * explanation (string)
+
+is the description of the function.
+
+=item * details (string)
+
+contains some details on this function.
+
+=back
+
+=cut
+sub build_function_detail($$$$) : method {
+ my $self = shift ;
+ my $kname = $_[0] || confess( 'you must supply the keyname' ) ;
+ my $name = $_[1] || confess( 'you must supply the name' ) ;
+ my $signature = $_[2] || confess( 'you must supply the signature' ) ;
+ my $explanation = $_[3] || confess( 'you must supply the explanation' ) ;
+ my $details = $_[4] || '' ;
+ return join( '',
+ "<A NAME=\"",
+ $kname,
+ "\"></A><H3>",
+ $name,
+ "</H3>\n<PRE>\n",
+ $signature,
+ "</PRE>\n<DL><DD><P>",
+ $explanation,
+ "</P>\n",
+ $details,
+ "</DD></DL>"
+ ) ;
+}
+
+=pod
+
+=item * build_detail_part()
+
+Replies a detail part.
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the section.
+
+=item * separator (string)
+
+is the separator of the elements.
+
+=item * elements (array ref)
+
+is the whole of the elements.
+
+=back
+
+=cut
+sub build_detail_part($$$) : method {
+ my $self = shift ;
+ if ( $#{$_[2]} >= 0 ) {
+ my $content = join( '',
+ "<DL><DT><B>$_[0]:</B></DT><DD>"
+ ) ;
+ my $i = 0 ;
+ $content .= "<UL>" if ( $_[1] =~ /<li>/i ) ;
+ foreach my $e (@{$_[2]}) {
+ if ( $_[1] =~ /<li>/i ) {
+ $content .= "<LI>" ;
+ }
+ elsif ( $i > 0 ) {
+ $content .= $_[1] ;
+ }
+ $content .= $e ;
+ $content .= "</LI>" if ( $_[1] =~ /<li>/i ) ;
+ $i ++ ;
+ }
+ $content .= "</UL>" if ( $_[1] =~ /<li>/i ) ;
+ $content .= "</DD></DL>\n" ;
+ return $content ;
+ }
+ else {
+ return "" ;
+ }
+}
+
+#------------------------------------------------------
+#
+# Paragraph API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * frame_subpart()
+
+Replies a subpart of a frame
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the part.
+
+=item * text (array)
+
+is the content of the frame.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub frame_subpart($$$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $rootdir = $_[2] || confess( 'you must supply the root directory' ) ;
+ $self->{'FRAME_TREE_ID_COUNT'} ++ ;
+ my $id = "treeid".$self->{'FRAME_TREE_ID_COUNT'} ;
+
+ my $content = "<P></P><DIV id=\"".$id."off__\" style=\"visibility : hidden; position: absolute\"></DIV>\n" ;
+
+ $content .= $self->href( "javascript:swaptree('".$id."')",
+ "<img src=\"".
+ htmlcatfile($rootdir,"minus.gif").
+ "\" alt=\"-\" ".
+ "id=\"".$id."plusminus\" width=\"11\" ".
+ "height=\"11\" border=\"0\">" ) ;
+ $content .= join( '',
+ ( $title ? '&nbsp;'.html_add_unsecable_spaces($title)."<BR>\n" : '' ),
+ "<div id=\"",
+ $id,
+ "\">" ) ;
+
+ if ( ( isarray($_[1]) ) && ( ! isemptyarray($_[1]) ) ) {
+ for(my $i=0; $i<=$#{$_[1]}; $i++) {
+ my $item = html_add_unsecable_spaces( $_[1][$i] ) ;
+ $content .= join( '',
+ "<TABLE border=0 cellspacing=0 cellpadding=0>",
+ "<TR><TD valign='top' align='right'><img src=\"",
+ htmlcatfile($rootdir,
+ ($i==$#{$_[1]}) ?
+ "lastchild.gif" : "child.gif"),
+ "\" alt=\"-\" width=\"11\" ",
+ "height=\"17\" border=\"0\"></TD><TD class='TreeText' valign='middle' align='left'>&nbsp;",
+ $item,
+ "</TD></TR></TABLE>\n" ) ;
+ }
+ }
+ $content .= "</DIV>\n\n" ;
+ return $content ;
+}
+
+=pod
+
+=item * frame_window()
+
+Replies a frame
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the frame.
+
+=item * text (string)
+
+is the content of the frame.
+
+=back
+
+=cut
+sub frame_window($$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $text = $_[1] || '' ;
+ return join( '',
+ ( $title ? "<H2>$title</H2>\n\n" : '' ),
+ $text ) ;
+}
+
+=pod
+
+=item * small()
+
+Replies a text with a small size.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub small($) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ return join( '',
+ "<SPAN CLASS='small'>",
+ $text,
+ "</SPAN>\n" ) ;
+}
+
+=pod
+
+=item * tiny()
+
+Replies a text with a tiny size.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub tiny($) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ return join( '',
+ "<SPAN CLASS='tiny'>",
+ $text,
+ "</SPAN>\n" ) ;
+}
+
+=pod
+
+=item * section()
+
+Replies a section
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the new section.
+
+=item * content (string)
+
+is the content of the new section
+
+=item * root (string)
+
+is the root directory for the generated documentation.
+
+=back
+
+=cut
+sub section($$$) : method {
+ my $self = shift ;
+ my $title = $_[0] || confess( 'you must specify the title' ) ;
+ my $content = $_[1] || '' ;
+ my $rootdir = $_[2] || confess( 'you must specify the root directory' ) ;
+ return join( '',
+ "<P></P>",
+ "<TABLE BORDER='0' WIDTH='100%' ",
+ "CELLPADDING='1' CELLSPACING='0'>\n",
+ "<TR><TD CLASS='tabletitle'>",
+ $title,
+ "</TD></TR>\n",
+ "<TR><TD>",
+ $content,
+ "</TD></TR></TABLE>\n" ) ;
+}
+
+#------------------------------------------------------
+#
+# Array API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * build_onecolumn_array()
+
+Replies an one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_onecolumn_array($$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $content = '' ;
+ if ( ( isarray($_[1]) ) && ( ! isemptyarray($_[1]) ) ) {
+ foreach my $cell (@{$_[1]}) {
+ $content .= join( '',
+ "<TR><TD>",
+ $cell,
+ "</TD></TR>\n" ) ;
+ }
+ }
+ return join( '',
+ "<P></P><TABLE BORDER='1' CELLPADDING='3' CELLSPACING='0' WIDTH='100%'>",
+ "<THEAD>",
+ "<TR><TD CLASS='tabletitle'><B>",
+ $title,
+ "</B></TD></TR>",
+ "</THEAD>\n<TBODY>",
+ $content,
+ "</TBODY>\n</TABLE>\n\n" ) ;
+}
+
+=pod
+
+=item * build_twocolumn_array()
+
+Replies an two-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_twocolumn_array($$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $content = '' ;
+ if ( ( isarray($_[1]) ) && ( ! isemptyarray($_[1]) ) ) {
+ for(my $i=0; $i<=$#{$_[1]}; $i++) {
+ if ( ( ishash($_[1][$i]) ) && ( ! isemptyhash($_[1][$i]) ) ) {
+ $content .= join( '',
+ "<TR><TD valign='top' align='left' width='20%'>",
+ $_[1][$i]->{'name'},
+ "</TD><TD valign='top' align='left' width='80%'>",
+ $_[1][$i]->{'explanation'},
+ "</TD></TR>" ) ;
+ }
+ }
+ }
+ return join( '',
+ "<P></P><TABLE BORDER='1' CELLPADDING='3' CELLSPACING='0' WIDTH='100%'>",
+ "<THEAD>",
+ "<TR><TD CLASS='tabletitle' COLSPAN='2'><B>",
+ $title,
+ "</B></TD></TR>",
+ "</THEAD>\n<TBODY>",
+ $content,
+ "</TBODY>\n</TABLE>\n\n" ) ;
+}
+
+=pod
+
+=item * build_small_array()
+
+Replies an small one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_small_array($$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $content = '' ;
+ if ( ( isarray($_[1]) ) && ( ! isemptyarray($_[1]) ) ) {
+ foreach my $cell (@{$_[1]}) {
+ $content .= join( '',
+ "<TR><TD>",
+ $cell,
+ "</TD></TR>\n" ) ;
+ }
+ }
+ return join( '',
+ "<P></P><TABLE BORDER='1' CELLPADDING='3' CELLSPACING='0' WIDTH='100%'>",
+ "<THEAD>",
+ "<TR><TD CLASS='smalltabletitle'><B>",
+ $title,
+ "</B></TD></TR>",
+ "</THEAD>\n<TBODY CLASS='smalltable'>",
+ $content,
+ "</TBODY>\n</TABLE>\n\n" ) ;
+}
+
+=pod
+
+=item * build_tiny_array()
+
+Replies a tiny one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_tiny_array($$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $content = '' ;
+ if ( ( isarray($_[1]) ) && ( ! isemptyarray($_[1]) ) ) {
+ foreach my $cell (@{$_[1]}) {
+ $content .= join( '',
+ "<TR><TD>",
+ $cell,
+ "</TD></TR>\n" ) ;
+ }
+ }
+ return join( '',
+ "<P></P><TABLE BORDER='1' CELLPADDING='3' CELLSPACING='0' WIDTH='100%'>",
+ "<THEAD>",
+ "<TR><TD CLASS='tinytabletitle'><B>",
+ $title,
+ "</B></TD></TR>",
+ "</THEAD>\n<TBODY CLASS='tinytable'>",
+ $content,
+ "</TBODY>\n</TABLE>\n\n" ) ;
+}
+
+=pod
+
+=item * build_threecolumn_array()
+
+Replies an two-column array.
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=item * anchor (string)
+
+is the name of the anchor.
+
+=back
+
+=cut
+sub build_threecolumn_array($$$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $content = '' ;
+ if ( ( isarray($_[1]) ) && ( ! isemptyarray($_[1]) ) ) {
+ for(my $i=0; $i<=$#{$_[1]}; $i++) {
+ if ( ( ishash($_[1][$i]) ) && ( ! isemptyhash($_[1][$i]) ) ) {
+ $content .= join( '',
+ "<TR><TD valign='top' align='left'>",
+ $_[1][$i]->{'type'},
+ "</TD><TD WIDTH='100%' valign='top' align='left'>",
+ $_[1][$i]->{'name'},
+ "<BR>\n",
+ $_[1][$i]->{'explanation'},
+ "</TD></TR>" ) ;
+ }
+ }
+ }
+ return join( '',
+ "<P></P><TABLE BORDER='1' CELLPADDING='3' CELLSPACING='0' WIDTH='100%'>",
+ "<THEAD>",
+ "<TR><TD CLASS='tabletitle' COLSPAN='3'><B>",
+ $title,
+ "</B></TD></TR>",
+ "</THEAD>\n<TBODY>",
+ $content,
+ "</TBODY>\n</TABLE>\n\n" ) ;
+}
+
+#------------------------------------------------------
+#
+# Navigation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_navigation_bar()
+
+Replies the navigation bar.
+Takes 3 args:
+
+=over
+
+=item * url (string)
+
+is the url of the generated page.
+
+=item * params (hash ref)
+
+is a set of parameters used to generate the bar.
+
+=item * root (string)
+
+is the root directory for the generated documentation.
+
+=back
+
+=cut
+sub get_navigation_bar($$$) : method {
+ my $self = shift ;
+ my $thispage = $_[0] || confess( 'the url must be provided' ) ;
+ my $rootdir = $_[2] || confess( "the rootdir must be supplied" ) ;
+ confess( 'params is not an associative aray' ) unless (ishash($_[1])) ;
+
+ my $overview = "<b>".$self->{'LANG'}->get('I18N_LANG_OVERVIEW')."</b>" ;
+ my $tree = "<b>".$self->{'LANG'}->get('I18N_LANG_TREE')."</b>" ;
+ my $index = "<b>".$self->{'LANG'}->get('I18N_LANG_INDEX')."</b>" ;
+ my $newbuttons = '';
+
+ my $prev = html_uc( $self->{'LANG'}->get('I18N_LANG_PREV') ) ;
+ my $next = html_uc( $self->{'LANG'}->get('I18N_LANG_NEXT') ) ;
+
+ if ( ! $_[1]{'overview'} ) {
+ $overview = $self->ext_wt_href('overview-summary',$overview,$rootdir) ;
+ }
+ if ( ! $_[1]{'tree'} ) {
+ $tree = $self->ext_wt_href('overview-tree',$tree,$rootdir) ;
+ }
+ if ( $_[1]{'index'} ) {
+ $index = $self->href( htmlcatfile( $rootdir,
+ $self->filename('index',0) ),
+ $index,
+ $self->browserframe('index') ) ;
+ }
+ if ( $_[1]{'previous'} ) {
+ $prev = $self->href($_[1]{'previous'},$prev) ;
+ }
+ if ( $_[1]{'next'} ) {
+ $next = $self->href($_[1]{'next'},$next) ;
+ }
+
+ if ( $_[1]{'notree'} ) {
+ $tree = "" ;
+ }
+ else {
+ $tree = "<td BGCOLOR=\"#EEEEFF\">&nbsp;$tree&nbsp;</td>\n" ;
+ }
+
+ # new buttons
+ if ( ( $_[1]{'userdef'} ) &&
+ ( ! isemptyarray($_[1]->{'userdef'}) ) ) {
+ foreach my $button (@{$_[1]->{'userdef'}}) {
+ if ( ($button->{'url'}) && ($button->{'label'}) ) {
+ my $str = $self->href($button->{'url'},
+ $self->{'LANG'}->get($button->{'label'})) ;
+ $newbuttons .= "<td BGCOLOR=\"#EEEEFF\">&nbsp;<B>$str</B>&nbsp;</td>\n" ;
+ }
+ }
+ }
+
+ my $content = join( '',
+ "<table BORDER=\"0\" WIDTH=\"100%\" ",
+ "CELLPADDING=\"1\" CELLSPACING=\"0\">\n",
+ "<tr>\n",
+ "<td COLSPAN=2 BGCOLOR=\"#EEEEFF\">\n",
+ # First row
+ "<table BORDER=\"0\" CELLPADDING=\"0\" ",
+ "CELLSPACING=\"3\">\n",
+ "<tr ALIGN=\"center\" VALIGN=\"top\">\n",
+ "<td BGCOLOR=\"#EEEEFF\">&nbsp;$overview&nbsp;</td>\n",
+ $tree,
+ $newbuttons,
+ "<td BGCOLOR=\"#EEEEFF\">&nbsp;$index&nbsp;</td>\n",
+ "</tr>\n</table>\n",
+ "</td>\n",
+ # Name of the doc
+ "<td ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><em><b>",
+ $self->{'TITLE'},
+ "</b></em></td>\n</tr>\n",
+ # Second row
+ "<tr>\n",
+ "<td BGCOLOR=\"white\"><font SIZE=\"-2\">",
+ "$prev&nbsp;&nbsp;$next",
+ "</font></td>\n",
+ "<td BGCOLOR=\"white\"><font SIZE=\"-2\">",
+ $self->ext_href('main_index',"<b>".
+ uc( $self->{'LANG'}->get('I18N_LANG_FRAMES') ).
+ "</b>",$rootdir),
+ "&nbsp;&nbsp;",
+ $self->href($thispage,"<b>".
+ uc( $self->{'LANG'}->get('I18N_LANG_NO_FRAME') ).
+ "</b>",
+ $self->browserframe('main_index')),
+ "&nbsp;</font></td>\n",
+ "</tr>\n",
+ "</table>\n"
+ ) ;
+}
+
+#------------------------------------------------------
+#
+# Filename API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * copy_files()
+
+Copies some files from the bib2html distribution directly inside the
+HTML documentation tree.
+
+=cut
+sub copy_files() : method {
+ my $self = shift ;
+ $self->SUPER::copy_files() ;
+ my @pack = File::Spec->splitdir( __FILE__ ) ;
+ pop @pack ;
+ push @pack, 'Dyna' ;
+ foreach my $file (@{$self->{'COPY_FILES'}}) {
+ Bib2HTML::General::Verbose::two( "Copying $file..." ) ;
+ Bib2HTML::General::Verbose::three( "\tfrom ".File::Spec->catdir(@pack) ) ;
+ Bib2HTML::General::Verbose::three( "\tto ".$self->{'TARGET_DIR'} ) ;
+ my $from = File::Spec->catfile(@pack, $file) ;
+ filecopy( $from,
+ File::Spec->catfile($self->{'TARGET_DIR'},$file) )
+ or Bib2HTML::General::Error::syserr( "$from: $!\n" );
+ }
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 2002-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/child.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/child.gif
new file mode 100644
index 0000000000..a78d0c9559
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/child.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/emptychild.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/emptychild.gif
new file mode 100644
index 0000000000..84d1e5d9a3
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/emptychild.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/lastchild.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/lastchild.gif
new file mode 100644
index 0000000000..9ba960473c
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/lastchild.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/minus.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/minus.gif
new file mode 100644
index 0000000000..f502662bcc
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/minus.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/plus.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/plus.gif
new file mode 100644
index 0000000000..eeca02ce00
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/plus.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/samechild.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/samechild.gif
new file mode 100644
index 0000000000..c9e0f4da03
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/samechild.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/stylesheet.css b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/stylesheet.css
new file mode 100644
index 0000000000..4258c83fb4
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Dyna/stylesheet.css
@@ -0,0 +1,180 @@
+BODY {
+ background-color : #F0F0F0;
+ color : #000000;
+ font-family : Arial, Tahoma, Helvetica, sans-serif;
+ font-size : 10pt;
+ margin-left : 1em;
+ margin-right : 1em;
+
+}
+
+MATH {
+ background-color : #F0F0F0;
+ color : #000000;
+ font-family : default;
+ font-family: Times New Roman;
+ font-size : 12pt;
+}
+
+A:LINK, A:VISITED {
+ color : #000099;
+}
+
+A:HOVER {
+ background-color : #FFFFFF;
+ color : #00009F;
+}
+
+H1 {
+ color : Black;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 16pt;
+ padding-bottom : 5px;
+ padding-top : 5px;
+ padding-left : 5px;
+}
+
+H2 {
+ color : Black;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 14pt;
+ margin-top : 2em;
+}
+
+H3 {
+ color : Navy;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 12pt;
+ margin-top :1em;
+}
+
+H4 {
+ color : Navy;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 11pt;
+ background-color : #E6E6FA;
+ padding-bottom : 2px;
+ padding-top : 2px;
+ padding-left : 2px;
+}
+
+H5 {
+ color : Navy;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 10pt;
+ font-weight : 900;
+ margin-bottom : -1em;
+}
+
+H6 {
+ color : #000000;
+ font-family : Arial, Helvetica, sans-serif;
+ font-size : 10pt;
+ font-weight : 800;
+ margin-bottom : -1em;
+}
+
+BLOCKQUOTE {
+ margin-left : 0;
+}
+
+CAPTION {
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-weight : 800;
+}
+
+TH {
+ background-color : #FFFFFF;
+}
+
+TD {
+ background-color : #F0F0F0;
+ font-size : 10pt;
+}
+
+CODE {
+ font-size: 8pt;
+}
+
+SPAN.functionlinenumber {
+ font-size : 10pt;
+ font-weight : 600;
+ color : #000000;
+}
+
+SPAN.small {
+ font-size : 8pt;
+}
+
+SPAN.tiny {
+ font-size : 8pt;
+}
+
+UL {
+ margin: 7px;
+ padding: 5px;
+ padding-left: 5px;
+}
+
+LI {
+ text-indent: -15px;
+ padding-bottom: 2px;
+ padding-left: 14px;
+}
+
+TD.largetabletitle {
+ color : Navy;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 12pt;
+ background-color : #E6E6FA;
+ padding-bottom : 2px;
+ padding-top : 2px;
+ padding-left : 2px;
+}
+
+TD.tabletitle {
+ color : Navy;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 11pt;
+ background-color : #E6E6FA;
+ padding-bottom : 2px;
+ padding-top : 2px;
+ padding-left : 2px;
+}
+
+TD.smalltabletitle {
+ color : Navy;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 10pt;
+ background-color : #E8E8FD;
+ padding-bottom : 2px;
+ padding-top : 2px;
+ padding-left : 2px;
+}
+
+TD.tinytabletitle {
+ color : Navy;
+ font-family : Verdana, Tahoma, Arial, Helvetica, sans-serif;
+ font-size : 8pt;
+ background-color : #E8E8FD;
+ padding-bottom : 2px;
+ padding-top : 2px;
+ padding-left : 2px;
+}
+
+TD.TreeText {
+ font-family : Arial, Tahoma, Helvetica, sans-serif;
+ font-size : 10pt;
+ padding-bottom : 0px;
+ padding-top : 0px;
+ padding-left : 0px;
+ padding-right : 0px;
+}
+
+TBODY.smalltable {
+ font-size : 8pt;
+}
+
+TBODY.tinytable {
+ font-size : 8pt;
+}
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Simple.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Simple.pm
new file mode 100644
index 0000000000..9f96969d9f
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Theme/Simple.pm
@@ -0,0 +1,678 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::Theme::Simple - A theme for the HTML generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::Theme::Simple ;
+
+my $gen = Bib2HTML::Generator::Theme::Simple->new( generator,
+ bib2html,
+ target,
+ title,
+ lang ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::Theme::Simple is a Perl module, which proposes
+a documentation theme for the HTML generator of bib2html.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::Theme::Simple;
+
+ my $gen = Bib2HTML::Generator::Theme::Simple->new( $generator,
+ { 'VERSION' => '0.11' },
+ './bib_output',
+ 'Title',
+ $lang ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * parent (object ref)
+
+is a reference to the current HTML generator.
+
+=item * bib2html (hash)
+
+contains some data about bib2html.
+
+=item * target (string)
+
+The directory in which the documentation must be put.
+
+=item * title (string)
+
+is the title of the documentation.
+
+=item * lang (object ref)
+
+is a reference to the language object.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Simple.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::Theme::Simple;
+
+@ISA = ('Bib2HTML::Generator::Theme');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+
+use Carp ;
+use File::Spec ;
+
+use Bib2HTML::Generator::Theme ;
+use Bib2HTML::General::Verbose ;
+use Bib2HTML::General::Error ;
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::HTML ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of theme
+my $VERSION = "5.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = $class->SUPER::new( @_ ) ;
+
+ $self->{'BACKGROUND_COLOR'} = '#FFFFFF' ;
+
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Validation
+#
+#------------------------------------------------------
+
+=pod
+
+=item * getMyValidHTML()
+
+Replies the list of W3C protocols for which this theme
+was validated. You must override this method.
+
+=cut
+sub getMyValidHTML() {
+ my $self = shift ;
+ return ( 'html' ) ;
+}
+
+#------------------------------------------------------
+#
+# Sectioning
+#
+#------------------------------------------------------
+
+=pod
+
+=item * section()
+
+Replies a section
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the new section.
+
+=item * content (string)
+
+is the content of the new section
+
+=item * root (string)
+
+is the root directory for the generated documentation.
+
+=back
+
+=cut
+sub section($$$) : method {
+ my $self = shift ;
+ my $title = $_[0] || confess( 'you must specify the title' ) ;
+ my $content = $_[1] || '' ;
+ my $rootdir = $_[2] || confess( 'you must specify the root directory' ) ;
+ return $self->par( join( '',
+ "<table BORDER=\"0\" WIDTH=\"100%\" ",
+ "CELLPADDING=\"1\" CELLSPACING=\"0\">\n",
+ "<tr>\n",
+ "<td BGCOLOR=\"#EEEEFF\">\n",
+ $title,
+ "</td>",
+ "</tr>\n",
+ "</table><br>\n",
+ $content ) ) ;
+}
+
+#------------------------------------------------------
+#
+# Right Frames
+#
+#------------------------------------------------------
+
+
+=pod
+
+=item * frame_subpart()
+
+Replies a subpart of a frame
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the part.
+
+=item * text (array)
+
+is the content of the frame.
+
+=item * rootdir (string)
+
+is the path to the root directory.
+
+=back
+
+=cut
+sub frame_subpart($$$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $content = "<P>" ;
+ if ( $title ) {
+ $content .= "<FONT size=\"+1\">$title</FONT><BR>\n" ;
+ }
+ if ( isarray( $_[1] ) ) {
+ foreach my $line (@{$_[1]}) {
+ $content .= $line."<BR>\n" ;
+ }
+ }
+ return $content."</P>\n" ;
+}
+
+=pod
+
+=item * frame_window()
+
+Replies a frame
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the frame (could be empty).
+
+=item * text (string)
+
+is the content of the frame.
+
+=item * prefix (optional string)
+
+is a string which is put before the title
+
+=back
+
+=cut
+sub frame_window($$) : method {
+ my $self = shift ;
+ my $title = $_[0] || '' ;
+ my $text = $_[1] || '' ;
+ return join( '',
+ ( $_[2] ? $self->par($_[2]) : '' ),
+ ($title ? "<FONT size=\"+1\"><B>$title</B></FONT>":''),
+ "<TABLE BORDER=\"0\" WIDTH=\"100%\">\n<TR>\n",
+ "<TD NOWRAP>",
+ $text,
+ "</TD></TR></TABLE><BR>\n" ) ;
+}
+
+#------------------------------------------------------
+#
+# Navigation
+#
+#------------------------------------------------------
+
+=pod
+
+=item * get_navigation_bar()
+
+Replies the navigation bar.
+Takes 3 args:
+
+=over
+
+=item * url (string)
+
+is the url of the generated page.
+
+=item * params (hash ref)
+
+is a set of parameters used to generate the bar.
+
+=item * root (string)
+
+is the root directory for the generated documentation.
+
+=back
+
+=cut
+sub get_navigation_bar($$$) : method {
+ my $self = shift ;
+ my $thispage = $_[0] || confess( 'the url must be provided' ) ;
+ my $rootdir = $_[2] || confess( "the rootdir must be supplied" ) ;
+ confess( 'params is not an associative aray' ) unless (ishash($_[1])) ;
+
+ my $overview = "<b>".$self->{'LANG'}->get('I18N_LANG_OVERVIEW')."</b>" ;
+ my $tree = "<b>".$self->{'LANG'}->get('I18N_LANG_TREE')."</b>" ;
+ my $index = "" ;
+ my $newbuttons = '';
+
+ my $prev = html_uc( $self->{'LANG'}->get('I18N_LANG_PREV') ) ;
+ my $next = html_uc( $self->{'LANG'}->get('I18N_LANG_NEXT') ) ;
+
+ if ( ! $_[1]{'overview'} ) {
+ $overview = $self->ext_wt_href('overview-summary',$overview,$rootdir) ;
+ }
+ if ( ! $_[1]{'tree'} ) {
+ $tree = $self->ext_wt_href('overview-tree',$tree,$rootdir) ;
+ }
+ if ( $_[1]{'index'} ) {
+ $index = $self->href( htmlcatfile( $rootdir,
+ $self->filename('index',0) ),
+ "<b>".$self->{'LANG'}->get('I18N_LANG_INDEX')."</b>",
+ $self->browserframe('index') ) ;
+ if ($index) {
+ $index = "<td BGCOLOR=\"#EEEEFF\">&nbsp;$index&nbsp;</td>\n";
+ }
+ }
+ if ( $_[1]{'previous'} ) {
+ $prev = $self->href($_[1]{'previous'},$prev) ;
+ }
+ if ( $_[1]{'next'} ) {
+ $next = $self->href($_[1]{'next'},$next) ;
+ }
+
+ if ( $_[1]{'notree'} ) {
+ $tree = "" ;
+ }
+ else {
+ $tree = "<td BGCOLOR=\"#EEEEFF\">&nbsp;$tree&nbsp;</td>\n" ;
+ }
+
+ # new buttons
+ if ( ( $_[1]{'userdef'} ) &&
+ ( ! isemptyarray($_[1]->{'userdef'}) ) ) {
+ foreach my $button (@{$_[1]->{'userdef'}}) {
+ if ( ($button->{'url'}) && ($button->{'label'}) ) {
+ my $str = $self->href($button->{'url'},
+ $self->{'LANG'}->get($button->{'label'})) ;
+ $newbuttons .= "<td BGCOLOR=\"#EEEEFF\">&nbsp;<B>$str</B>&nbsp;</td>\n" ;
+ }
+ }
+ }
+
+ my $content = join( '',
+ "<table BORDER=\"0\" WIDTH=\"100%\" ",
+ "CELLPADDING=\"1\" CELLSPACING=\"0\">\n",
+ "<tr>\n",
+ "<td COLSPAN=2 BGCOLOR=\"#EEEEFF\">\n",
+ # First row
+ "<table BORDER=\"0\" CELLPADDING=\"0\" ",
+ "CELLSPACING=\"3\">\n",
+ "<tr ALIGN=\"center\" VALIGN=\"top\">\n",
+ "<td BGCOLOR=\"#EEEEFF\">&nbsp;$overview&nbsp;</td>\n",
+ $tree,
+ $newbuttons,
+ $index,
+ "</tr>\n</table>\n",
+ "</td>\n",
+ # Name of the doc
+ "<td ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><em><b>",
+ $self->{'TITLE'},
+ "</b></em></td>\n</tr>\n",
+ # Second row
+ "<tr>\n",
+ "<td BGCOLOR=\"white\"><font SIZE=\"-2\">",
+ "$prev&nbsp;&nbsp;$next",
+ "</font></td>\n",
+ "<td BGCOLOR=\"white\"><font SIZE=\"-2\">",
+ $self->ext_href('main_index',"<b>".
+ html_uc( $self->{'LANG'}->get('I18N_LANG_FRAMES') ).
+ "</b>",$rootdir),
+ "&nbsp;&nbsp;",
+ $self->href($thispage,"<b>".
+ html_uc( $self->{'LANG'}->get('I18N_LANG_NO_FRAME') ).
+ "</b>",
+ $self->browserframe('main_index')),
+ "&nbsp;</font></td>\n",
+ "</tr>\n",
+ "</table>\n"
+ ) ;
+}
+
+#------------------------------------------------------
+#
+# Tabulars
+#
+#------------------------------------------------------
+
+=pod
+
+=item * build_onecolumn_array()
+
+Replies an one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_onecolumn_array($$) : method {
+ my $self = shift ;
+ my $content = join( '',
+ "<DIV><TABLE BORDER=\"1\" ",
+ "CELLPADDING=\"3\" CELLSPACING=\"0\" ",
+ "WIDTH=\"100%\">\n",
+ "<TR BGCOLOR=\"#CCCCFF\">\n",
+ "<TD COLSPAN=2><FONT SIZE=\"+2\"><B>",
+ $_[0] || '',
+ "</B></FONT></TD>\n",
+ "</TR>\n" ) ;
+ confess( 'cells is not an array' ) unless (isarray($_[1])) ;
+ foreach my $case (@{$_[1]}) {
+ $content .= join( '',
+ "<TR BGCOLOR=\"white\">",
+ "<TD WIDTH=\"20%\" ALIGN=\"left\" VALIGN=\"top\">",
+ $case,
+ "</TD>",
+ "</TR>\n" ) ;
+ }
+ $content .= "</TABLE><BR></DIV>\n" ;
+ return $content ;
+}
+
+=pod
+
+=item * build_small_array()
+
+Replies an small one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_small_array($$) : method {
+ my $self = shift ;
+ my $content = join( '',
+ "<P><TABLE BORDER=\"1\" CELLPADDING=\"3\" ",
+ "CELLSPACING=\"0\" WIDTH=\"100%\">\n",
+ "<TR BGCOLOR=\"#EEEEFF\">\n",
+ "<TD><B>",
+ $_[0] || '',
+ "</B></TD>\n",
+ "</TR>\n" ) ;
+ confess( 'cells is not an array' ) unless (isarray($_[1])) ;
+ foreach my $case (@{$_[1]}) {
+ $content .= join( '',
+ "<TR BGCOLOR=\"white\">",
+ "<TD ALIGN=\"left\" VALIGN=\"top\">",
+ $case,
+ "</TD></TR>\n" ) ;
+ }
+ $content .= "</TABLE></P>\n" ;
+ return $content ;
+}
+
+=pod
+
+=item * build_tiny_array()
+
+Replies an small one-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_tiny_array($$) : method {
+ my $self = shift ;
+ my $content = join( '',
+ "<P><TABLE BORDER=\"1\" CELLPADDING=\"3\" ",
+ "CELLSPACING=\"0\" WIDTH=\"100%\">\n",
+ "<TR BGCOLOR=\"#EEEEEFF\">\n",
+ "<TD><FONT SIZE=\"-1\"><B>",
+ $_[0] || '',
+ "</B></FONT></TD>\n",
+ "</TR>\n" ) ;
+ confess( 'cells is not an array' ) unless (isarray($_[1])) ;
+ foreach my $case (@{$_[1]}) {
+ $content .= join( '',
+ "<TR BGCOLOR=\"white\">",
+ "<TD ALIGN=\"left\" VALIGN=\"top\">",
+ "<FONT SIZE=\"-1\">",
+ $case,
+ "</FONT>",
+ "</TD></TR>\n" ) ;
+ }
+ $content .= "</TABLE></P>\n" ;
+ return $content ;
+}
+
+=pod
+
+=item * build_twocolumn_array()
+
+Replies an two-column array.
+Takes 2 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=back
+
+=cut
+sub build_twocolumn_array($$) : method {
+ my $self = shift ;
+ my $content = join( '',
+ "<P></P><TABLE BORDER=\"1\" ",
+ "CELLPADDING=\"3\" CELLSPACING=\"0\" ",
+ "WIDTH=\"100%\">\n",
+ "<TR BGCOLOR=\"#CCCCFF\">\n",
+ "<TD COLSPAN=2><FONT SIZE=\"+2\"><B>",
+ $_[0] || '',
+ "</B></FONT></TD>\n",
+ "</TR>\n" ) ;
+ confess( 'cells is not an array' ) unless (isarray($_[1])) ;
+ foreach my $cellule (@{$_[1]}) {
+ my $name = $cellule->{name} ;
+ my $explanation = $cellule->{explanation} || '' ;
+ if ( $name ) {
+ if ( ! $explanation ) {
+ $explanation = "&nbsp;" ;
+ }
+ $content = join( '',
+ $content,
+ "<TR BGCOLOR=\"white\">",
+ "<TD WIDTH=\"20%\" ALIGN=\"left\" VALIGN=\"top\">",
+ $name,
+ "</TD><TD>",
+ $explanation,
+ "</TD></TR>\n" ) ;
+ }
+ }
+ $content .= "</TABLE>\n" ;
+ return $content ;
+}
+
+=pod
+
+=item * build_threecolumn_array()
+
+Replies an two-column array.
+Takes 3 args:
+
+=over
+
+=item * title (string)
+
+is the title of the array
+
+=item * cells (array ref)
+
+is the content of the returned cells.
+
+=item * anchor (string)
+
+is the name of the anchor.
+
+=back
+
+=cut
+sub build_threecolumn_array($$$) : method {
+ my $self = shift ;
+ my $content = join( '',
+ "<P>",
+ ( $_[2] ? "<A NAME=\"$_[2]\"></A>" : '' ),
+ "<TABLE BORDER=\"1\" ",
+ "CELLPADDING=\"3\" CELLSPACING=\"0\" ",
+ "WIDTH=\"100%\">\n",
+ "<TR BGCOLOR=\"#CCCCFF\">\n",
+ "<TD COLSPAN=2><FONT SIZE=\"+2\"><B>",
+ $_[0] || '' ,
+ "</B></FONT></TD>\n",
+ "</TR>\n" ) ;
+ confess( 'cells is not an array' ) unless (isarray($_[1])) ;
+ foreach my $cellule (@{$_[1]}) {
+ my $name = ${%{$cellule}}{name} ;
+ my $explanation = ${%{$cellule}}{explanation} || '' ;
+ my $type = ${%{$cellule}}{type} ;
+ if ( $name ) {
+ if ( ! $explanation ) {
+ $explanation = "&nbsp;" ;
+ }
+ $content = join( '',
+ $content,
+ "<TR BGCOLOR=\"white\"><TD WIDTH=\"1%\" ",
+ "VALIGN=\"top\"><FONT SIZE=\"-1\"><CODE>",
+ $type,
+ "</CODE></FONT></TD>",
+ "<TD ALIGN=\"left\" VALIGN=\"top\"><CODE>",
+ $name,
+ "</CODE><BR>\n",
+ $explanation,
+ "</TD></TR>\n" ) ;
+ }
+ }
+ $content .= "</TABLE></P>\n" ;
+ return $content ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Writer.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Writer.pm
new file mode 100644
index 0000000000..f6ace330ba
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/Writer.pm
@@ -0,0 +1,211 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::Writer - An output stream writer
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::Writer is a Perl module, which permits to
+abstract the output streams used by bib2html.
+
+=head1 SYNOPSYS
+
+Bib2HTML::Generator::Writer->new( ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::Writer is a Perl module, which permits to
+abstract the output streams used by bib2html.
+
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Writer.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::Writer;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of abstract generator
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = {} ;
+ return $self;
+}
+
+=pod
+
+=item * openstream($)
+
+Open the output stream.
+Takes 1 param:
+
+=over
+
+=item * filename (string)
+
+is the name of the output file.
+
+=back
+
+=cut
+sub openstream($) {
+ my $self = shift;
+ my $filename = shift || confess( 'you must supply the root directory' ) ;
+ return 1;
+}
+
+=pod
+
+=item * out($)
+
+Put a string into the output stream.
+Takes 1 param:
+
+=over
+
+=item * str (string)
+
+is the string to output.
+
+=back
+
+=cut
+sub out($) {
+ my $self = shift;
+ my $str = shift || '';
+ return 1;
+}
+
+=pod
+
+=item * closestream()
+
+Close the currently opened stream.
+
+=cut
+sub closestream() {
+ my $self = shift;
+ return 1;
+}
+
+=pod
+
+=item * create_output_directory()
+
+Create the output directory if required.
+Replies the output filename (directory).
+Takes n params:
+
+=over
+
+=item * output (string)
+
+is the output directory to create
+
+=pod
+
+=item * create_output_directory()
+
+Create the output directory if required.
+Replies the output filename (directory).
+Takes n params:
+
+=over
+
+=item * output (string)
+
+is the output directory to create.
+
+=item * exceptions (list of strings)
+
+is the list of the file in the existing output directory
+to not remove.
+
+=back
+
+=cut
+sub create_output_directory($@) {
+ my $self = shift;
+ my $output = shift;
+ return $output;
+}
+
+=pod
+
+=item * is_file_creation_allowed()
+
+Replies if this writer allows to create files.
+
+=cut
+sub is_file_creation_allowed() {
+ my $self = shift;
+ return undef;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/XMLGen.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/XMLGen.pm
new file mode 100644
index 0000000000..300a8fedb5
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/XMLGen.pm
@@ -0,0 +1,1364 @@
+# Copyright (C) 2004-07 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Generator::XMLGen - A basic XML generator
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Generator::XMLGen ;
+
+my $gen = Bib2HTML::Generator::XMLGen->new( content, output, info, titles,
+ lang, theme, params ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Generator::XMLGen is a Perl module, which permits to
+generate XML pages for the BibTeX database.
+The generated XML file is compliant with the DTD from
+http://bibtexml.sf.net/
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a generator script, say something like this:
+
+ use Bib2HTML::Generator::XMLGen;
+
+ my $gen = Bib2HTML::Generator::XMLGen->new( { }, "./bib",
+ { 'BIB2HTML_VERSION' => "0.1",
+ },
+ { 'SHORT' => "This is the title",
+ 'LONG' => "This is the title",
+ },
+ "English",
+ "Simple", ""
+ ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * content (hash)
+
+see AbstractGenerator help.
+
+=item * output (string)
+
+see AbstractGenerator help.
+
+=item * bib2html_data (hash)
+
+see AbstractGenerator help.
+
+=item * titles (hash)
+
+see AbstractGenerator help.
+
+=item * lang (string)
+
+see AbstractGenerator help.
+
+=item * theme (string)
+
+is the name of the theme to use
+
+=item * show_bibtex (boolean)
+
+indicates if this parser must generate a verbatim of the BibTeX code
+
+=item * params (optional array)
+
+is the set of parameters passed to the generator.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in HTMLGen.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Generator::XMLGen;
+
+@ISA = ('Bib2HTML::Generator::AbstractGenerator');
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Carp ;
+use File::Spec ;
+use File::Basename ;
+
+use Bib2HTML::Generator::AbstractGenerator;
+use Bib2HTML::General::Misc;
+use Bib2HTML::General::Error;
+use Bib2HTML::General::HTML;
+use Bib2HTML::General::Encode;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of this generator
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$$$$$;$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+
+ my @langs = ();
+ if (isarray($_[4])) {
+ foreach my $l (@{$_[4]}) {
+ if ($l !~ /_[a-zA-Z0-9]+Gen$/) {
+ push @langs, $l."_XMLGen";
+ }
+ push @langs, $l;
+ }
+ }
+ else {
+ @langs = ( $_[4] );
+ if ($_[4] !~ /_[a-zA-Z0-9]+Gen$/) {
+ unshift @langs, $_[4]."_XMLGen";
+ }
+ }
+
+ my $self = $class->SUPER::new($_[0], #content
+ $_[1], #output
+ $_[2], #bib2html info
+ $_[3], #titles
+ \@langs, #lang
+ $_[6], #show bibtex
+ $_[7], #params
+ ) ;
+ bless( $self, $class );
+
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Generation parameters
+#
+#------------------------------------------------------
+
+=pod
+
+=item * save_generator_parameter()
+
+Replies if the specified generator parameter was supported.
+This function was called each time a generator parameter was
+given to this generator. By default, simply update the
+given parameter value (second parameter).
+You could do some stuff before
+saving (splitting...). Replies false is the parameter was
+not recognized. Don't forget to call inherited functions.
+Takes 2 args:
+
+=over
+
+=item * param_name (string)
+
+is the name of the parameter.
+
+=item * param_value (byref string)
+
+is the value of the parameter.
+
+=back
+
+=cut
+sub save_generator_parameter($$) {
+ my $self = shift ;
+ if ( ( $_[0] eq 'xml-encoding' ) ) {
+ # will be saved by PARENT::new
+ return 1 ;
+ }
+ else {
+ return $self->SUPER::save_generator_parameter($_[0],$_[1]) ;
+ }
+}
+
+=pod
+
+=item * display_supported_generator_params()
+
+Display the list of supported generator parameters.
+
+=cut
+sub display_supported_generator_params() {
+ my $self = shift ;
+ $self->SUPER::display_supported_generator_params() ;
+
+ $self->show_supported_param('xml-encoding',
+ 'String, the character encoding used in the HTML pages '.
+ '("UTF8", "ISO-8859-1"...).' );
+}
+
+#------------------------------------------------------
+#
+# Generation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * pre_processing()
+
+Pre_processing.
+
+=cut
+sub pre_processing() : method {
+ my $self = shift ;
+
+ # Set the HTML encoding
+ if (!$self->{'GENERATOR_PARAMS'}{'xml-encoding'}) {
+ $self->{'GENERATOR_PARAMS'}{'xml-encoding'} = get_default_encoding();
+ }
+ set_default_encoding($self->{'GENERATOR_PARAMS'}{'xml-encoding'});
+
+ # Call inherited generation method
+ $self->SUPER::pre_processing() ;
+}
+
+=pod
+
+=item * do_processing()
+
+Main processing.
+
+=cut
+sub do_processing() : method {
+ my $self = shift ;
+
+ # Call inherited generation method
+ $self->SUPER::do_processing() ;
+
+ # Generates each part of the document
+ my $t = '' ;
+
+ # Generates the content for each entries
+ $self->create_XMLENTRIES($t) ;
+
+ # Generates the complete data file
+ $self->create_XML_file($t) ;
+
+ # Generates the header and the footer
+ $self->create_XMLHEADER($t) ;
+ $self->create_XMLFOOTER($t) ;
+
+ # Create7 file file
+ $self->create_FILE($t) ;
+}
+
+=pod
+
+=item * create_the_xml_entry()
+
+Generates and replies the XML string for the specified entry
+Takes 1 arg:
+
+=over
+
+=item * key (string)
+
+is the key of the bibtex entry.
+
+=back
+
+=cut
+sub create_the_xml_entry($) : method {
+ my $self = shift ;
+ my $key = shift ;
+
+ # Compute entry constants
+ my $type = $self->{'CONTENT'}{'entries'}{"$key"}{'type'} ;
+ my $entry = '' ;
+
+ # Calls the content building function
+ my $fct = "create_XMLENTRY_$type" ;
+ if ( my $funcref = $self->can( $fct ) ) {
+ $self->$funcref( $key,
+ $self->{'CONTENT'}{'entries'}{"$key"},
+ $entry ) ;
+ }
+ else {
+ Bib2HTML::General::Error::warm("I don't know how to generate a '\@".$type.
+ "' for the entry '$key'. Assume '\@misc'",
+ extract_file_from_location( $self->{'CONTENT'}{'entries'}{"$key"}{'location'} ),
+ extract_line_from_location( $self->{'CONTENT'}{'entries'}{"$key"}{'location'} ) ) ;
+ $self->create_XMLENTRY_misc( $key,
+ $self->{'CONTENT'}{'entries'}{"$key"},
+ $entry ) ;
+ }
+
+ # Create the entry's XML string
+ $entry = $self->build_xmltag("bibtex:$type",$entry) ;
+ $entry = $self->build_xmltag("bibtex:entry",$entry,
+ "id=\"$key\"") ;
+ $_[0] .= $entry ;
+}
+
+=pod
+
+=item * create_the_standalone_xml_entry()
+
+Generates and replies the standalone XML string for the specified entry
+Takes 1 arg:
+
+=over
+
+=item * key (string)
+
+is the key of the bibtex entry.
+
+=back
+
+=cut
+sub create_the_standalone_xml_entry($) : method {
+ my $self = shift ;
+
+ my $content = $self->create_the_xml_entry($_[0]) ;
+ $self->create_XML_file($content) ;
+ $self->create_XMLHEADER($content) ;
+ return $content ;
+}
+
+=pod
+
+=item * create_XMLENTRIES()
+
+Generates the XML pages for each entry
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content to fill
+
+=back
+
+=cut
+sub create_XMLENTRIES($) : method {
+ my $self = shift ;
+ my @entries = $self->get_all_entries_ayt() ;
+ my $i = $#entries ;
+ while ( $i >= 0 ) {
+ # Compute entry constants
+ my $type = $self->{'CONTENT'}{'entries'}{$entries[$i]}{'type'} ;
+ my $entry = '' ;
+
+ # Calls the content building function
+ my $fct = "create_XMLENTRY_$type" ;
+ if ( my $funcref = $self->can( $fct ) ) {
+ $self->$funcref( $entries[$i],
+ $self->{'CONTENT'}{'entries'}{$entries[$i]},
+ $entry ) ;
+ }
+ else {
+ Bib2HTML::General::Error::warm("I don't know how to generate a '\@".$type.
+ "' for the entry '".$entries[$i]."'. Assume '\@misc'",
+ extract_file_from_location( $self->{'CONTENT'}{'entries'}{$entries[$i]}{'location'} ),
+ extract_line_from_location( $self->{'CONTENT'}{'entries'}{$entries[$i]}{'location'} ) ) ;
+ $self->create_XMLENTRY_misc( $entries[$i],
+ $self->{'CONTENT'}{'entries'}{$entries[$i]},
+ $entry ) ;
+ }
+
+ # Create the entry's XML string
+ $entry = $self->build_xmltag("bibtex:$type",$entry) ;
+ $entry = $self->build_xmltag("bibtex:entry",$entry,
+ "id=\"".$entries[$i]."\"") ;
+ $_[0] .= $entry ;
+
+ $i -- ;
+ }
+}
+
+=pod
+
+=item * create_XMLHEADER
+
+Replies the header of the XML file.
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content to fill
+
+=back
+
+=cut
+sub create_XMLHEADER($) : method {
+ my $self = shift ;
+ my $encoding = $self->genparam('xml-encoding') || "ISO-8859-1";
+ $_[0] = join( '',
+ "<?xml version=\"1.0\" encoding=\"",
+ $encoding,
+ "\"?>\n",
+ "<!DOCTYPE bibtex:file PUBLIC \"-//BibTeXML//DTD XML for BibTeX v1.0//EN\" \"bibteXML-ext.dtd\" >\n",
+ $_[0]);
+}
+
+=pod
+
+=item * create_XMLFOOTER
+
+Replies the header of the XML file.
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content to fill
+
+=back
+
+=cut
+sub create_XMLFOOTER($) : method {
+ my $self = shift ;
+ $_[0] = join( '',
+ $_[0],
+ "<!-- File generated with bib2html ",
+ $self->{'BIB2HTML'}{'VERSION'},
+ " the ",
+ "".localtime(),
+ "\n Copyright (c) ",
+ $self->{'BIB2HTML'}{'AUTHOR'},
+ " (",
+ $self->{'BIB2HTML'}{'AUTHOR_EMAIL'},
+ ") -->\n");
+}
+
+=pod
+
+=item * create_XML_file
+
+Create <bibtex:file>
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content to fill
+
+=back
+
+=cut
+sub create_XML_file($) : method {
+ my $self = shift ;
+ $_[0] = $self->build_xmltag('bibtex:file',$_[0],
+ "xmlns:bibtex=\"http://bibtexml.sf.net/\"") ;
+}
+
+=pod
+
+=item * create_FILE
+
+Creates the XML file.
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content of the XML file.
+
+=back
+
+=cut
+sub create_FILE($) : method {
+ my $self = shift ;
+ Bib2HTML::General::Verbose::two( "Writing ".$self->{'TARGET'}."..." ) ;
+
+ my $writer = $self->get_stream_writer();
+
+ $writer->openstream($self->{'TARGET'});
+ $writer->out($_[0]||'') ;
+ $writer->closestream() ;
+}
+
+=pod
+
+=item * create_XMLENTRY_REQUIREDFIELD()
+
+Generates a required XML field.
+Takes 4 args:
+
+=over
+
+=item * name (string)
+
+is the name of the field.
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_REQUIREDFIELD($$$$) : method {
+ my $self = shift ;
+ my $name = shift ;
+ my $entrykey = shift ;
+ my $data = shift ;
+
+ my $content = '' ;
+ if ( exists $data->{'fields'}{"$name"} ) {
+ $content = $data->{'fields'}{"$name"} || '' ;
+ }
+ $content = strip_html_tags($content); #get_html_entities() ;
+ $content =~ s/\s+/ /g;
+ $_[0] .= $self->build_xmltag("bibtex:$name",$content) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_OPTIONALFIELD()
+
+Generates a optional XML field.
+Takes 4 args:
+
+=over
+
+=item * name (string)
+
+is the name of the field.
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_OPTIONALFIELD($$$$) : method {
+ my $self = shift ;
+ my $name = shift ;
+ my $entrykey = shift ;
+ my $data = shift ;
+
+ if ( exists $data->{'fields'}{"$name"} ) {
+ my $content = $data->{'fields'}{"$name"} || '' ;
+ $content = strip_html_tags($content); #get_html_entities(strip_html_tags($content)) ;
+ $content =~ s/\s+/ /g;
+ $_[0] .= $self->build_xmltag("bibtex:$name",$content) ;
+ }
+}
+
+=pod
+
+=item * create_XMLENTRY_NAMEFIELD()
+
+Generates a optional names' XML field.
+Takes 4 args:
+
+=over
+
+=item * name (string)
+
+is the name of the field.
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_NAMEFIELD($$$$) : method {
+ my $self = shift ;
+ my $name = shift ;
+ my $entrykey = shift ;
+ my $data = shift ;
+
+ if ( exists $data->{'fields'}{"$name"} ) {
+ my @authors = $self->get_all_authors($data->{'fields'}{"$name"} || '') ;
+ my $content = '' ;
+ foreach my $author (@authors) {
+ my $aut = '' ;
+ if (!$author->{'et al'}) {
+ if ($author->{'first'}) {
+ if ($author->{'first'} =~ /^[a-zA-Z]+\.(?:[a-zA-Z]+\.)*$/) {
+ $aut .= $self->build_xmltag('bibtex:initials',
+ strip_html_tags($author->{'first'}));
+ #get_html_entities(strip_html_tags($author->{'first'}))) ;
+ }
+ else {
+ $aut .= $self->build_xmltag('bibtex:first',
+ strip_html_tags($author->{'first'}));
+ # get_html_entities(strip_html_tags($author->{'first'}))) ;
+ }
+ }
+ if ($author->{'last'}) {
+ $aut .= $self->build_xmltag('bibtex:last',
+ strip_html_tags($author->{'last'}));
+ # get_html_entities(strip_html_tags($author->{'last'}))) ;
+ }
+ if ($author->{'von'}) {
+ $aut .= $self->build_xmltag('bibtex:prelast',
+ strip_html_tags($author->{'first'}));
+ # get_html_entities(strip_html_tags($author->{'von'}))) ;
+ }
+ if ($author->{'jr'}) {
+ $aut .= $self->build_xmltag('bibtex:lineage',
+ strip_html_tags($author->{'first'}));
+ # get_html_entities(strip_html_tags($author->{'jr'}))) ;
+ }
+ }
+ $content .= $self->build_xmltag("bibtex:people",$aut) ;
+ }
+ if ($content) {
+ $_[0] .= $self->build_xmltag("bibtex:$name",$content) ;
+ }
+ }
+}
+
+=pod
+
+=item * create_XMLENTRY_KEYWORDSFIELD()
+
+Generates a optional keywords' XML field.
+Takes 4 args:
+
+=over
+
+=item * name (string)
+
+is the name of the field.
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_KEYWORDSFIELD($$$$) : method {
+ my $self = shift ;
+ my $name = shift ;
+ my $entrykey = shift ;
+ my $data = shift ;
+
+ if ( exists $data->{'fields'}{"$name"} ) {
+ my $content = '' ;
+ my @words ;
+ if ($data->{'fields'}{"$name"} =~ /;,:/) {
+ @words = split(/\s*[;,:]\s*/,$data->{'fields'}{"$name"}) ;
+ }
+ else {
+ @words = split(/\s+/,$data->{'fields'}{"$name"}) ;
+ }
+ foreach my $word (@words) {
+ $content .= $self->build_xmltag('bibtex:keyword',
+ strip_html_tags($word));
+ #get_html_entities(strip_html_tags($word))) ;
+ }
+ if ($content) {
+ $_[0] .= $self->build_xmltag("bibtex:$name",$content) ;
+ }
+ }
+}
+
+=pod
+
+=item * create_XMLENTRY_DEFAULTFIELDS()
+
+Generates the default XML fields.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_DEFAULTFIELDS($$$) : method {
+ my $self = shift ;
+
+ $self->create_XMLENTRY_REQUIREDFIELD('title',@_) ;
+
+ $self->create_XMLENTRY_NAMEFIELD('author',@_) ;
+ $self->create_XMLENTRY_NAMEFIELD('editor',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('month',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('note',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('abstract',@_) ;
+ $self->create_XMLENTRY_KEYWORDSFIELD('keywords',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('isbn',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('issn',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('lccn',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('url',@_) ;
+
+ if ( exists $_[1]{'fields'}{'annote'} ) {
+ $self->create_XMLENTRY_OPTIONALFIELD('annote',@_) ;
+ }
+ elsif ( exists $_[1]{'fields'}{'comments'} ) {
+ $self->create_XMLENTRY_OPTIONALFIELD('comments',@_) ;
+ }
+}
+
+#------------------------------------------------------
+#
+# Generation of entries API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * create_XMLENTRY_article()
+
+Generates the XML entry for an article.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_article($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_REQUIREDFIELD('journal',@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('volume',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('number',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('pages',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_book()
+
+Generates the XML entry for a book.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_book($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_REQUIREDFIELD('publisher',@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('series',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('volume',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('number',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('edition',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_booklet()
+
+Generates the XML entry for a book's part.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_booklet($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('howpublished',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_inbook()
+
+Generates the XML entry for a book's part.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_inbook($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('howpublished',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_incollection()
+
+Generates the XML entry for a collection's article.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_incollection($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_inproceedings(@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_inproceedings()
+
+Generates the XML entry for an article in a conference's proceedings.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_inproceedings($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_REQUIREDFIELD('booktitle',@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('series',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('editor',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('volume',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('number',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('pages',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('organization',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('publisher',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('type',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_manual()
+
+Generates the XML entry for a manual.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_manual($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('edition',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('organization',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_masterthesis()
+
+Generates the XML entry for a master's thesis.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_masterthesis($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_phdthesis(@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_mastersthesis()
+
+Generates the XML entry for a master's thesis.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_mastersthesis($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_phdthesis(@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_phdthesis()
+
+Generates the XML entry for a PHD thesis.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_phdthesis($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_REQUIREDFIELD('school',@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('type',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_proceedings()
+
+Generates the XML entry for a conference's proceedings.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_proceedings($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('series',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('volume',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('number',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('organization',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('publisher',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_techreport()
+
+Generates the XML entry for a technical report.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_techreport($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_REQUIREDFIELD('institution',@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('number',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('address',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('type',@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_unpublished()
+
+Generates the XML entry for an unpublished document.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_unpublished($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+}
+
+=pod
+
+=item * create_XMLENTRY_misc()
+
+Generates the XML entry for a miscellaneous document.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * data (hash)
+
+is the data for the entry.
+
+=item * content (ref string)
+
+is the content to update.
+
+=back
+
+=cut
+sub create_XMLENTRY_misc($$$) : method {
+ my $self = shift ;
+ $self->create_XMLENTRY_DEFAULTFIELDS(@_) ;
+
+ $self->create_XMLENTRY_OPTIONALFIELD('howpublished',@_) ;
+ $self->create_XMLENTRY_OPTIONALFIELD('year',@_) ;
+}
+
+#------------------------------------------------------
+#
+# Uitility API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * indent
+
+indent the specified string.
+Takes 1 arg:
+
+=over
+
+=item * content (string)
+
+is the content of the XML file.
+
+=back
+
+=cut
+sub indent($) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my @lines = split(/\n/,($_[0]||'')) ;
+ @lines = map { " $_" } @lines ;
+ $text = join("\n",@lines) ;
+ if ( $text !~ /\n$/ ) {
+ $text .= "\n" ;
+ }
+ return $text ;
+}
+
+=pod
+
+=item * build_xmllevel
+
+replies an XML tag built from the parameters.
+Takes 3 args:
+
+=over
+
+=item * name (string)
+
+is the name of the tag.
+
+=item * content (string)
+
+is the content of the tag.
+
+=item * params (optional string)
+
+is the list of parameters for the tags.
+
+=back
+
+=cut
+sub build_xmltag($$;$) : method {
+ my $self = shift ;
+ my $name = $_[0] || confess('you must supply a tag name') ;
+ my $content = $_[1] || '' ;
+ my $params = $_[2] || '' ;
+ if ($content) {
+ my $begin = "<$name".($params?" $params":"").">" ;
+ my $end = "</$name>\n" ;
+ if (($content =~ /\n/)||(length("$begin$content$end")>=40)) {
+ return join( '',
+ "$begin\n",
+ $self->indent($content),
+ "$end" );
+ }
+ else {
+ $content =~ s/^\s+// ;
+ $content =~ s/\s+$// ;
+ return join( '',
+ "$begin",
+ $content,
+ "$end" );
+ }
+ }
+ else {
+ return "<$name".($params?" $params":"")." />" ;
+ }
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 2004-07 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML-ext.dtd b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML-ext.dtd
new file mode 100644
index 0000000000..6d27b24388
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML-ext.dtd
@@ -0,0 +1,161 @@
+<!--
+ - File: $Id: bibteXML-ext.dtd, 2003.06.26 13:52:00 vbg Exp $
+ -
+ - This DTD expresses XML markup similar to the BibTeX language
+ - specified for LaTeX, or actually its content model.
+ - For documentation on BibTeX, see
+ - http://www.ctan.org/tex-archive/biblio/bibtex/distribs/doc/
+ -
+ - Suggested invocation:
+ -
+ - <?xml version="1.0" encoding="UTF-8"?>
+ - <!DOCTYPE bibtex:file PUBLIC
+ - "-//BibTeXML//DTD XML for BibTeX (extended) v1.0//EN"
+ - "bibteXML-ext.dtd" >
+ - <bibtex:file xmlns:bibtex="http://bibtexml.sf.net/">
+ - ...
+ - </bibtex:file>
+ -
+ - Available from http://bibtexml.sf.net/
+ -
+ - This code originally developed by
+ - Vidar Bronken Gundersen
+ - Zeger W. Hendrikse
+ -
+ - This program is free software; you can redistribute it and/or
+ - modify it under the terms of the GNU General Public License.
+ - See http://www.gnu.org/copyleft/gpl.html
+ -
+-->
+
+
+<!-- popular user fields -->
+
+<!ENTITY % user.fields
+ "( bibtex:abstract?, bibtex:affiliation?,
+ bibtex:contents?, bibtex:copyright?,
+ (bibtex:isbn | bibtex:issn)?, bibtex:doi?,
+ bibtex:keywords?, bibtex:language?, bibtex:lccn?,
+ bibtex:location?, bibtex:mrnumber?, bibtex:price?,
+ bibtex:size?, bibtex:url?, bibtex:category? )">
+
+<!ENTITY % BibTeXML.common.standard.fields
+ ", bibtex:key?, bibtex:crossref?, %user.fields;">
+
+
+<!-- ..................................................................... -->
+<!-- Other popular fields
+ -
+ - BibTeX is extremely popular, and many people have used it to store
+ - information. Here is a list of some of the more common fields:
+ -
+ - [affiliation] The authors affiliation.
+ - [abstract] An abstract of the work.
+ - [contents] A Table of Contents
+ - [copyright] Copyright information.
+ - [ISBN] The International Standard Book Number.
+ - [ISSN] The International Standard Serial Number.
+ - Used to identify a journal.
+ - [keywords] Key words used for searching or possibly for annotation.
+ - [language] The language the document is in.
+ - [location] A location associated with the entry,
+ - such as the city in which a conference took place.
+ - [LCCN] The Library of Congress Call Number.
+ - I've also seen this as lib-congress.
+ - [mrnumber] The Mathematical Reviews number.
+ - [price] The price of the document.
+ - [size] The physical dimensions of a work.
+ - [URL] The WWW Universal Resource Locator that points to the item being
+ - referenced. This often is used for technical reports to point to the
+ - ftp site where the postscript source of the report is located.
+ -
+ - When using BibTeX with LaTeX you need
+ - BibTeX style files to print these data.
+ -
+ - Ref: www.ecst.csuchico.edu/~jacobsd/bib/formats/bibtex.html
+-->
+
+<!ELEMENT bibtex:abstract (#PCDATA) >
+<!ELEMENT bibtex:affiliation (#PCDATA) >
+<!ELEMENT bibtex:contents (#PCDATA) >
+<!ELEMENT bibtex:copyright (#PCDATA) >
+<!ELEMENT bibtex:isbn (#PCDATA) >
+<!ELEMENT bibtex:issn (#PCDATA) >
+<!ELEMENT bibtex:language (#PCDATA) >
+<!ELEMENT bibtex:lccn (#PCDATA) >
+<!ELEMENT bibtex:location (#PCDATA) >
+<!ELEMENT bibtex:mrnumber (#PCDATA) >
+<!ELEMENT bibtex:price (#PCDATA) >
+<!ELEMENT bibtex:size (#PCDATA) >
+<!ELEMENT bibtex:url (#PCDATA) >
+
+
+<!-- User requested fields
+ - [category] Category of this bibitem
+ - [DOI] The Digital Object Identifier (www.doi.org)
+ - used to redirect to articles, a key like 10.1000/203
+-->
+
+<!ELEMENT bibtex:category (#PCDATA) >
+<!ELEMENT bibtex:doi (#PCDATA) >
+
+
+<!-- ..................................................................... -->
+<!-- Alternative syntax for compound fields
+ - for author, editor, keywords and title fields.
+ - Backwards compatible syntax.
+-->
+
+<!ENTITY % BibTeXML.author.element "IGNORE">
+<!ENTITY % BibTeXML.editor.element "IGNORE">
+
+<!ENTITY % author.qname "(bibtex:author | bibtex:authorlist)">
+<!ENTITY % editor.qname "(bibtex:editor | bibtex:editorlist)">
+
+<!ELEMENT bibtex:authorlist (bibtex:person+) >
+<!ELEMENT bibtex:editorlist (bibtex:person+) >
+<!ELEMENT bibtex:author (#PCDATA) >
+<!ELEMENT bibtex:editor (#PCDATA) >
+
+<!ELEMENT bibtex:person ( ( bibtex:initials |
+ (bibtex:first, bibtex:middle?)),
+ bibtex:prelast?, bibtex:last,
+ bibtex:lineage?)>
+
+<!-- first, middle and last name should be obvious
+ - preLast is for names like Thomas *de* Burghes,
+ - lineage is used for "Jr" in names like "James T. Kirk, Jr."
+ -->
+<!ATTLIST bibtex:person email CDATA #IMPLIED
+ url CDATA #IMPLIED
+>
+<!ELEMENT bibtex:first (#PCDATA) >
+<!ELEMENT bibtex:initials (#PCDATA) >
+<!ELEMENT bibtex:last (#PCDATA) >
+<!ELEMENT bibtex:middle (#PCDATA) >
+<!ELEMENT bibtex:prelast (#PCDATA) >
+<!ELEMENT bibtex:lineage (#PCDATA) >
+
+
+<!ENTITY % BibTeXML.title.element "IGNORE">
+<!ENTITY % title.qname "(bibtex:title | bibtex:titlelist)">
+<!ELEMENT bibtex:titlelist (bibtex:title, bibtex:subtitle?)>
+<!ELEMENT bibtex:subtitle (#PCDATA) >
+<!ELEMENT bibtex:title (#PCDATA) >
+
+<!ENTITY % BibTeXML.keywords.element "IGNORE">
+<!ENTITY % keywords.qname "bibtex:keywords">
+<!ELEMENT bibtex:keywords (bibtex:keyword+) >
+<!ELEMENT bibtex:keyword (#PCDATA) >
+
+
+<!-- ..................................................................... -->
+<!-- reuse the strict BibTeXML DTD -->
+<!ENTITY % BibTeXML-strict PUBLIC
+ "-//BibTeXML//DTD XML for BibTeX v1.0//EN"
+ "bibteXML.dtd">
+%BibTeXML-strict;
+
+
+<!-- ..................................................................... -->
+<!-- End of bibtex dtd -->
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML.dtd b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML.dtd
new file mode 100644
index 0000000000..ebc4524bd0
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/bibteXML.dtd
@@ -0,0 +1,816 @@
+<!--
+ - File: $Id: bibteXML.dtd, 2003.01.18 21:46:00 vbg Exp $
+ -
+ - This DTD expresses XML markup similar to the BibTeX language
+ - specified for LaTeX, or actually its content model.
+ - For documentation on BibTeX, see
+ - http://www.ctan.org/tex-archive/biblio/bibtex/distribs/doc/
+ -
+ - Suggested invocation:
+ -
+ - <?xml version="1.0" encoding="UTF-8"?>
+ - <!DOCTYPE bibtex:file PUBLIC
+ - "-//BibTeXML//DTD XML for BibTeX v1.0//EN"
+ - "bibteXML.dtd" >
+ - <bibtex:file xmlns:bibtex="http://bibtexml.sf.net/">
+ - ...
+ - </bibtex:file>
+ -
+ - Available from http://bibtexml.sf.net/
+ -
+ - This code originally developed by
+ - Vidar Bronken Gundersen
+ - Zeger W. Hendrikse
+ - Marco Kuhlmann
+ -
+ - This program is free software; you can redistribute it and/or
+ - modify it under the terms of the GNU General Public License.
+ - See http://www.gnu.org/copyleft/gpl.html
+ -
+-->
+
+<!NOTATION BibTeX PUBLIC "-//Oren Patashnik//NOTATION BibTeX Manuals//EN">
+
+<!-- Qualified Names module .............................................. -->
+
+<!-- Qualified Names
+ -
+ - This module is contained in two parts, labeled Section 'A' and 'B':
+ -
+ - Section A declares parameter entities to support namespace-
+ - qualified names, namespace declarations, and name prefixing.
+ -
+ - Section B declares parameter entities used to provide
+ - namespace-qualified names for all element types.
+ -
+ - This module is derived from the XHTML Qualified Names Template module.
+ -
+-->
+
+<!-- Section A: XML Namespace Framework :::::::::::::::::::: -->
+
+<!ENTITY % NS.prefixed "INCLUDE" >
+<!ENTITY % BibTeXML.prefixed "%NS.prefixed;" >
+
+
+<!ENTITY % BibTeXML.xmlns "http://bibtexml.sf.net/" >
+<!ENTITY % BibTeXML.prefix "bibtex" >
+<![%BibTeXML.prefixed;[
+<!ENTITY % BibTeXML.xmlns.extra.attrib "" >
+]]>
+<!ENTITY % BibTeXML.xmlns.extra.attrib
+ "" >
+
+<![%BibTeXML.prefixed;[
+<!ENTITY % BibTeXML.pfx "%BibTeXML.prefix;:" >
+<!ENTITY % BibTeXML.xmlns.attrib
+ "xmlns:%BibTeXML.prefix; CDATA #FIXED '%BibTeXML.xmlns;'
+ %BibTeXML.xmlns.extra.attrib;"
+>
+]]>
+<!ENTITY % BibTeXML.pfx "" >
+<!ENTITY % BibTeXML.xmlns.attrib
+ "xmlns CDATA #FIXED '%BibTeXML.xmlns;'
+ %BibTeXML.xmlns.extra.attrib;"
+>
+
+<![%NS.prefixed;[
+<!ENTITY % XHTML.xmlns.extra.attrib
+ "%BibTeXML.xmlns.attrib;" >
+]]>
+<!ENTITY % XHTML.xmlns.extra.attrib
+ "%BibTeXML.xmlns.attrib;"
+>
+
+<!-- Section B: Qualified Names ::::::::::::::::::::::::::::: -->
+
+<!-- 9. This section declares parameter entities used to provide
+ - namespace-qualified names for all element types.
+-->
+
+<!ENTITY % file.qname "%BibTeXML.pfx;file" >
+<!ENTITY % entry.qname "%BibTeXML.pfx;entry" >
+
+<!ENTITY % article.qname "%BibTeXML.pfx;article" >
+<!ENTITY % book.qname "%BibTeXML.pfx;book" >
+<!ENTITY % booklet.qname "%BibTeXML.pfx;booklet" >
+<!ENTITY % manual.qname "%BibTeXML.pfx;manual" >
+<!ENTITY % techreport.qname "%BibTeXML.pfx;techreport" >
+<!ENTITY % mastersthesis.qname "%BibTeXML.pfx;mastersthesis" >
+<!ENTITY % phdthesis.qname "%BibTeXML.pfx;phdthesis" >
+<!ENTITY % inbook.qname "%BibTeXML.pfx;inbook" >
+<!ENTITY % incollection.qname "%BibTeXML.pfx;incollection" >
+<!ENTITY % proceedings.qname "%BibTeXML.pfx;proceedings" >
+<!ENTITY % inproceedings.qname "%BibTeXML.pfx;inproceedings" >
+<!ENTITY % conference.qname "%BibTeXML.pfx;conference" >
+<!ENTITY % unpublished.qname "%BibTeXML.pfx;unpublished" >
+<!ENTITY % misc.qname "%BibTeXML.pfx;misc" >
+
+<!ENTITY % address.qname "%BibTeXML.pfx;address" >
+<!ENTITY % author.qname "%BibTeXML.pfx;author" >
+<!ENTITY % booktitle.qname "%BibTeXML.pfx;booktitle" >
+<!ENTITY % chapter.qname "%BibTeXML.pfx;chapter" >
+<!ENTITY % edition.qname "%BibTeXML.pfx;edition" >
+<!ENTITY % editor.qname "%BibTeXML.pfx;editor" >
+<!ENTITY % howpublished.qname "%BibTeXML.pfx;howpublished" >
+<!ENTITY % institution.qname "%BibTeXML.pfx;institution" >
+<!ENTITY % journal.qname "%BibTeXML.pfx;journal" >
+<!ENTITY % month.qname "%BibTeXML.pfx;month" >
+<!ENTITY % note.qname "%BibTeXML.pfx;note" >
+<!ENTITY % number.qname "%BibTeXML.pfx;number" >
+<!ENTITY % organization.qname "%BibTeXML.pfx;organization" >
+<!ENTITY % pages.qname "%BibTeXML.pfx;pages" >
+<!ENTITY % publisher.qname "%BibTeXML.pfx;publisher" >
+<!ENTITY % school.qname "%BibTeXML.pfx;school" >
+<!ENTITY % series.qname "%BibTeXML.pfx;series" >
+<!ENTITY % title.qname "%BibTeXML.pfx;title" >
+<!ENTITY % type.qname "%BibTeXML.pfx;type" >
+<!ENTITY % volume.qname "%BibTeXML.pfx;volume" >
+<!ENTITY % year.qname "%BibTeXML.pfx;year" >
+
+<!ENTITY % key.qname "%BibTeXML.pfx;key" >
+<!ENTITY % crossref.qname "%BibTeXML.pfx;crossref" >
+<!ENTITY % annote.qname "%BibTeXML.pfx;annote" >
+
+
+<!-- ignores subsequent instantiation of this module when
+ - used as external subset rather than module fragment.
+ - NOTE: Do not modify this parameter entity, otherwise
+ - a recursive parsing situation may result.
+-->
+<!ENTITY % BibTeXML-qname.module "IGNORE" >
+
+
+<!-- if %NS.prefixed; is INCLUDE, include all NS attributes,
+ otherwise just those associated with MathML
+-->
+<![%NS.prefixed;[
+ <!ENTITY % BibTeXML.NamespaceDecl.attrib
+ "%BibTeXML.xmlns.attrib;"
+>
+]]>
+<!ENTITY % BibTeXML.NamespaceDecl.attrib
+ "%BibTeXML.xmlns.attrib;"
+>
+
+
+<!-- ..................................................................... -->
+<!-- Main structure -->
+
+<!-- %entry.qname; may contain one of the bibliographic types. -->
+
+<!ENTITY % BibTeXML.standard.entries.class
+ "%article.qname; | %book.qname; | %booklet.qname; |
+ %manual.qname; | %techreport.qname; |
+ %mastersthesis.qname; | %phdthesis.qname; |
+ %inbook.qname; | %incollection.qname; |
+ %proceedings.qname; | %inproceedings.qname; | %conference.qname; |
+ %unpublished.qname; | %misc.qname; ">
+
+<!ENTITY % BibTeXML.additional.entries.class "">
+
+<!ENTITY % BibTeXML.entries.class
+ "%BibTeXML.standard.entries.class;
+ %BibTeXML.additional.entries.class;">
+
+<!ENTITY % BibTeXML.entry.module "INCLUDE">
+<![%BibTeXML.entry.module;[
+<!ENTITY % BibTeXML.entry.element "INCLUDE">
+<![%BibTeXML.entry.element;[
+<!ELEMENT %entry.qname; (%BibTeXML.entries.class;)>
+]]>
+<!ENTITY % BibTeXML.entry.attlist "INCLUDE">
+<![%BibTeXML.entry.attlist;[
+<!ATTLIST %entry.qname;
+ id ID #REQUIRED >
+]]>
+]]>
+
+
+<!-- %file.qname; is the document top element with a namespace indicator. -->
+
+<!ENTITY % BibTeXML.file.module "INCLUDE">
+<![%BibTeXML.file.module;[
+<!ENTITY % BibTeXML.file.element "INCLUDE">
+<![%BibTeXML.file.element;[
+<!ELEMENT %file.qname; (%entry.qname;)* >
+]]>
+<!ENTITY % BibTeXML.file.attlist "INCLUDE">
+<![%BibTeXML.file.attlist;[
+<!ATTLIST %file.qname;
+ %BibTeXML.NamespaceDecl.attrib; >
+]]>
+]]>
+
+
+<!-- ..................................................................... -->
+<!-- Parameter entities -->
+
+<!-- these are additional elements often used, but not included in the
+ standard BibTeX distribution, these must be added to the
+ bibliography styles, otherwise these fields will be omitted by
+ the formatter -->
+
+<!ENTITY % BibTeXML.common.standard.fields
+ ", %key.qname;?, %crossref.qname;?" >
+
+<!ENTITY % BibTeXML.additional.fields "">
+
+
+<!-- ..................................................................... -->
+<!-- Entries in the BibTeX database -->
+
+<!-- [article] An article from a journal or magazine.
+ - Required fields: author, title, journal, year.
+ - Optional fields: volume, number, pages, month, note. -->
+
+<!ENTITY % BibTeXML.article.module "INCLUDE">
+<![%BibTeXML.article.module;[
+<!ENTITY % BibTeXML.article.standard.fields
+ "%author.qname;, %title.qname;, %journal.qname;,
+ %year.qname;, %volume.qname;?, %number.qname;?,
+ %pages.qname;?, %month.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.article.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.article.fields
+ "%BibTeXML.article.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.article.additional.fields;">
+<!ENTITY % BibTeXML.article.element "INCLUDE">
+<![%BibTeXML.article.element;[
+<!ELEMENT %article.qname; (%BibTeXML.article.fields;)?>
+]]>
+]]>
+
+
+<!-- [book] A book with an explicit publisher.
+ - Required fields: author or editor, title, publisher, year.
+ - Optional fields: volume or number, series, address,
+ - edition, month, note. -->
+
+<!ENTITY % BibTeXML.book.module "INCLUDE">
+<![%BibTeXML.book.module;[
+<!ENTITY % BibTeXML.book.standard.fields
+ "(%author.qname; | %editor.qname;), %title.qname;, %publisher.qname;,
+ %year.qname;, (%volume.qname; | %number.qname;)?, %series.qname;?,
+ %address.qname;?, %edition.qname;?, %month.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.book.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.book.fields
+ "%BibTeXML.book.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.book.additional.fields;">
+<!ENTITY % BibTeXML.book.element "INCLUDE">
+<![%BibTeXML.book.element;[
+<!ELEMENT %book.qname; (%BibTeXML.book.fields;)>
+]]>
+]]>
+
+
+<!-- [booklet] A work that is printed and bound, but without a named
+ - publisher or sponsoring institution
+ - Required field: title.
+ - Optional fields: author, howpublished, address, month, year, note. -->
+
+<!ENTITY % BibTeXML.booklet.module "INCLUDE">
+<![%BibTeXML.booklet.module;[
+<!ENTITY % BibTeXML.booklet.standard.fields
+ "%author.qname;?, %title.qname;, %howpublished.qname;?,
+ %address.qname;?, %month.qname;?, %year.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.booklet.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.booklet.fields
+ "%BibTeXML.booklet.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.booklet.additional.fields;">
+<!ENTITY % BibTeXML.booklet.element "INCLUDE">
+<![%BibTeXML.booklet.element;[
+<!ELEMENT %booklet.qname; (%BibTeXML.booklet.fields;)>
+]]>
+]]>
+
+
+<!-- [inbook] A part of a book, which may be a chapter (or section or
+ - whatever) and/or a range of pages.
+ - Required fields: author or editor, title, chapter and/or pages,
+ - publisher, year.
+ - Optional fields: volume or number, series, type, address,
+ - edition, month, note. -->
+
+<!ENTITY % BibTeXML.inbook.module "INCLUDE">
+<![%BibTeXML.inbook.module;[
+<!ENTITY % BibTeXML.inbook.standard.fields
+ "(%author.qname; | %editor.qname;), %title.qname;,
+ ((%chapter.qname;, %pages.qname;?) | %pages.qname;),
+ %publisher.qname;, %year.qname;,
+ (%volume.qname; | %number.qname;)?, %series.qname;?,
+ %type.qname;?, %address.qname;?, %edition.qname;?,
+ %month.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.inbook.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.inbook.fields
+ "%BibTeXML.inbook.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.inbook.additional.fields;">
+<!ENTITY % BibTeXML.inbook.element "INCLUDE">
+<![%BibTeXML.inbook.element;[
+<!ELEMENT %inbook.qname; (%BibTeXML.inbook.fields;)>
+]]>
+]]>
+
+<!--
+ - > I want to express that the elements a and/or b are legal that is
+ - > one of them or both must be present in the document instance
+ - > (see the element content for BibTeX entry `InBook').
+ - in content model: ((a , b?) | b) if order matters
+ - ((a , b?) | (b , a?)) otherwise
+-->
+
+
+<!-- [incollection] A part of a book having its own title.
+ - Required fields: author, title, booktitle, publisher, year.
+ - Optional fields: editor, volume or number, series, type,
+ - chapter, pages, address, edition, month, note. -->
+
+<!ENTITY % BibTeXML.incollection.module "INCLUDE">
+<![%BibTeXML.incollection.module;[
+<!ENTITY % BibTeXML.incollection.standard.fields
+ "%author.qname;, %title.qname;, %booktitle.qname;,
+ %publisher.qname;, %year.qname;, %editor.qname;?,
+ (%volume.qname; | %number.qname;)?, %series.qname;?,
+ %type.qname;?, %chapter.qname;?, %pages.qname;?, %address.qname;?,
+ %edition.qname;?, %month.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.incollection.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.incollection.fields
+ "%BibTeXML.incollection.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.incollection.additional.fields;">
+<!ENTITY % BibTeXML.incollection.element "INCLUDE">
+<![%BibTeXML.incollection.element;[
+<!ELEMENT %incollection.qname; (%BibTeXML.incollection.fields;)>
+]]>
+]]>
+
+
+<!-- [inproceedings] An article in a conference proceedings.
+ - Required fields: author, title, booktitle, year.
+ - Optional fields: editor, volume or number, series, pages,
+ - address, month, organization, publisher, note. -->
+
+<!ENTITY % BibTeXML.inproceedings.common.fields
+ "(%author.qname;, %title.qname;, %booktitle.qname;, %year.qname;,
+ %editor.qname;?, (%volume.qname; | %number.qname;)?,
+ %series.qname;?, %pages.qname;?, %address.qname;?,
+ %month.qname;?, %organization.qname;?, %publisher.qname;?,
+ %note.qname;?)">
+
+<!ENTITY % BibTeXML.inproceedings.module "INCLUDE">
+<![%BibTeXML.inproceedings.module;[
+<!ENTITY % BibTeXML.inproceedings.standard.fields
+ "%BibTeXML.inproceedings.common.fields;">
+<!ENTITY % BibTeXML.inproceedings.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.inproceedings.fields
+ "%BibTeXML.inproceedings.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.inproceedings.additional.fields;">
+<!ENTITY % BibTeXML.inproceedings.element "INCLUDE">
+<![%BibTeXML.inproceedings.element;[
+<!ELEMENT %inproceedings.qname; (%BibTeXML.inproceedings.fields;)>
+]]>
+]]>
+
+
+<!-- [conference] The same as INPROCEEDINGS,
+ - included for Scribe compatibility. -->
+
+<!ENTITY % BibTeXML.conference.module "INCLUDE">
+<![%BibTeXML.conference.module;[
+<!ENTITY % BibTeXML.conference.standard.fields
+ "%BibTeXML.inproceedings.common.fields;">
+<!ENTITY % BibTeXML.conference.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.conference.fields
+ "%BibTeXML.conference.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.conference.additional.fields;">
+<!ENTITY % BibTeXML.conference.element "INCLUDE">
+<![%BibTeXML.conference.element;[
+<!ELEMENT %conference.qname; (%BibTeXML.conference.fields;)>
+]]>
+]]>
+
+
+<!-- [manual] Technical documentation
+ - Required field: title.
+ - Optional fields: author, organization, address,
+ - edition, month, year, note. -->
+
+<!ENTITY % BibTeXML.manual.module "INCLUDE">
+<![%BibTeXML.manual.module;[
+<!ENTITY % BibTeXML.manual.standard.fields
+ "%author.qname;?, %title.qname;, %organization.qname;?,
+ %address.qname;?, %edition.qname;?, %month.qname;?, %year.qname;?,
+ %note.qname;?">
+<!ENTITY % BibTeXML.manual.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.manual.fields
+ "%BibTeXML.manual.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.manual.additional.fields;">
+<!ENTITY % BibTeXML.manual.element "INCLUDE">
+<![%BibTeXML.manual.element;[
+<!ELEMENT %manual.qname; (%BibTeXML.manual.fields;)>
+]]>
+]]>
+
+
+<!-- [mastersthesis] A Master's thesis.
+ - Required fields: author, title, school, year.
+ - Optional fields: type, address, month, note. -->
+
+<!ENTITY % BibTeXML.thesis.common.fields
+ "(%author.qname;, %title.qname;,
+ %school.qname;, %year.qname;, %type.qname;?,
+ %address.qname;?, %month.qname;?, %note.qname;?)">
+
+<!ENTITY % BibTeXML.mastersthesis.module "INCLUDE">
+<![%BibTeXML.mastersthesis.module;[
+<!ENTITY % BibTeXML.mastersthesis.standard.fields
+ "%BibTeXML.thesis.common.fields;">
+<!ENTITY % BibTeXML.mastersthesis.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.mastersthesis.fields
+ "%BibTeXML.mastersthesis.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.mastersthesis.additional.fields;">
+<!ENTITY % BibTeXML.mastersthesis.element "INCLUDE">
+<![%BibTeXML.mastersthesis.element;[
+<!ELEMENT %mastersthesis.qname; (%BibTeXML.mastersthesis.fields;)>
+]]>
+]]>
+
+
+<!-- [phdthesis] A PhD thesis.
+ - Required fields: author, title, school, year.
+ - Optional fields: type, address, month, note. -->
+
+<!ENTITY % BibTeXML.phdthesis.module "INCLUDE">
+<![%BibTeXML.phdthesis.module;[
+<!ENTITY % BibTeXML.phdthesis.standard.fields
+ "%BibTeXML.thesis.common.fields;">
+<!ENTITY % BibTeXML.phdthesis.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.phdthesis.fields
+ "%BibTeXML.phdthesis.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.phdthesis.additional.fields;">
+<!ENTITY % BibTeXML.phdthesis.element "INCLUDE">
+<![%BibTeXML.phdthesis.element;[
+<!ELEMENT %phdthesis.qname; (%BibTeXML.phdthesis.fields;)>
+]]>
+]]>
+
+
+<!-- [misc] Use this type when nothing else fits.
+ - Required fields: none.
+ - Optional fields: author, title, howpublished, month, year, note. -->
+
+<!ENTITY % BibTeXML.misc.module "INCLUDE">
+<![%BibTeXML.misc.module;[
+<!ENTITY % BibTeXML.misc.standard.fields
+ "%author.qname;?, %title.qname;?, %howpublished.qname;?,
+ %month.qname;?, %year.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.misc.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.misc.fields
+ "%BibTeXML.misc.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.misc.additional.fields;">
+<!ENTITY % BibTeXML.misc.element "INCLUDE">
+<![%BibTeXML.misc.element;[
+<!ELEMENT %misc.qname; (%BibTeXML.misc.fields;)>
+]]>
+]]>
+
+
+<!-- [proceedings] The proceedings of a conference.
+ - Required fields: title, year.
+ - Optional fields: editor, volume or number, series,
+ - address, month, organization, publisher, note. -->
+
+<!ENTITY % BibTeXML.proceedings.module "INCLUDE">
+<![%BibTeXML.proceedings.module;[
+<!ENTITY % BibTeXML.proceedings.standard.fields
+ "%editor.qname;?, %title.qname;, %year.qname;,
+ (%volume.qname; | %number.qname;)?, %series.qname;?,
+ %address.qname;?, %month.qname;?, %organization.qname;?,
+ %publisher.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.proceedings.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.proceedings.fields
+ "%BibTeXML.proceedings.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.proceedings.additional.fields;">
+<!ENTITY % BibTeXML.proceedings.element "INCLUDE">
+<![%BibTeXML.proceedings.element;[
+<!ELEMENT %proceedings.qname; (%BibTeXML.proceedings.fields;)>
+]]>
+]]>
+
+
+<!-- [techreport] A report published by a school or other institution,
+ - usually numbered within a series.
+ - Required fields: author, title, institution, year.
+ - Optional fields: type, number, address, month, note. -->
+
+<!ENTITY % BibTeXML.techreport.module "INCLUDE">
+<![%BibTeXML.techreport.module;[
+<!ENTITY % BibTeXML.techreport.standard.fields
+ "%author.qname;, %title.qname;, %institution.qname;,
+ %year.qname;, %type.qname;?, %number.qname;?,
+ %address.qname;?, %month.qname;?, %note.qname;?">
+<!ENTITY % BibTeXML.techreport.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.techreport.fields
+ "%BibTeXML.techreport.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.techreport.additional.fields;">
+<!ENTITY % BibTeXML.techreport.element "INCLUDE">
+<![%BibTeXML.techreport.element;[
+<!ELEMENT %techreport.qname; (%BibTeXML.techreport.fields;)>
+]]>
+]]>
+
+
+<!-- [unpublished] A document having an author and title, but not
+ - formally published.
+ - Required fields: author, title, note.
+ - Optional fields: month, year. -->
+
+<!ENTITY % BibTeXML.unpublished.module "INCLUDE">
+<![%BibTeXML.unpublished.module;[
+<!ENTITY % BibTeXML.unpublished.standard.fields
+ "%author.qname;, %title.qname;, %note.qname;,
+ %month.qname;?, %year.qname;?">
+<!ENTITY % BibTeXML.unpublished.additional.fields
+ "%BibTeXML.additional.fields;">
+<!ENTITY % BibTeXML.unpublished.fields
+ "%BibTeXML.unpublished.standard.fields;
+ %BibTeXML.common.standard.fields;
+ %BibTeXML.unpublished.additional.fields;">
+<!ENTITY % BibTeXML.unpublished.element "INCLUDE">
+<![%BibTeXML.unpublished.element;[
+<!ELEMENT %unpublished.qname; (%BibTeXML.unpublished.fields;)>
+]]>
+]]>
+
+
+<!-- ..................................................................... -->
+<!-- Fields from the standard bibliography styles -->
+
+<!--
+ - Below is a description of all fields recognized by the standard
+ - bibliography styles. An entry can also contain other fields, which
+ - are ignored by those styles.
+ -
+ - [address] Usually the address of the publisher or other type of
+ - institution For major publishing houses, van~Leunen recommends
+ - omitting the information entirely. For small publishers, on the other
+ - hand, you can help the reader by giving the complete address.
+ -
+ - [annote] An annotation It is not used by the standard bibliography
+ - styles, but may be used by others that produce an annotated
+ - bibliography.
+ -
+ - [author] The name(s) of the author(s), in the format described in the
+ - LaTeX book.
+ -
+ - [booktitle] Title of a book, part of which is being cited. See the
+ - LaTeX book for how to type titles. For book entries, use the title
+ - field instead.
+ -
+ - [chapter] A chapter (or section or whatever) number.
+ -
+ - [crossref] The database key of the entry being cross referenced.
+ -
+ - [edition] The edition of a book-for example, ``Second''. This
+ - should be an ordinal, and should have the first letter capitalized, as
+ - shown here; the standard styles convert to lower case when necessary.
+ -
+ - [editor] Name(s) of editor(s), typed as indicated in the LaTeX book.
+ - If there is also an author field, then the editor field gives the
+ - editor of the book or collection in which the reference appears.
+ -
+ - [howpublished] How something strange has been published. The first
+ - word should be capitalized.
+ -
+ - [institution] The sponsoring institution of a technical report.
+ -
+ - [journal] A journal name. Abbreviations are provided for many
+ - journals; see the Local Guide.
+ -
+ - [key] Used for alphabetizing, cross referencing, and creating a label
+ - when the ``author'' information (described in Section [ref: ] is
+ - missing. This field should not be confused with the key that appears
+ - in the \cite command and at the beginning of the database entry.
+ -
+ - [month] The month in which the work was published or, for an
+ - unpublished work, in which it was written You should use the
+ - standard three-letter abbreviation, as described in Appendix B.1.3 of
+ - the LaTeX book.
+ -
+ - [note] Any additional information that can help the reader. The first
+ - word should be capitalized.
+ -
+ - [number] The number of a journal, magazine, technical report, or of a
+ - work in a series. An issue of a journal or magazine is usually
+ - identified by its volume and number; the organization that issues a
+ - technical report usually gives it a number; and sometimes books are
+ - given numbers in a named series.
+ -
+ - [organization] The organization that sponsors a conference or that
+ - publishes a manual.
+ -
+ - [pages] One or more page numbers or range of numbers, such as 42-111
+ - or 7,41,73-97 or 43+ (the `+' in this last example indicates pages
+ - following that don't form a simple range). To make it easier to
+ - maintain Scribe-compatible databases, the standard styles convert a
+ - single dash (as in 7-33) to the double dash used in TeX to denote
+ - number ranges (as in 7-33).
+ -
+ - [publisher] The publisher's name.
+ -
+ - [school] The name of the school where a thesis was written
+ -
+ - [series] The name of a series or set of books. When citing an entire
+ - book, the the title field gives its title and an optional series field
+ - gives the name of a series or multi-volume set in which the book is
+ - published.
+ -
+ - [title] The work's title, typed as explained in the LaTeX book.
+ -
+ - [type] The type of a technical report-for example, ``Research Note''.
+ -
+ - [volume] The volume of a journal or multivolume book.
+ -
+ - [year] The year of publication or, for an unpublished work, the year
+ - it was written. Generally it should consist of four numerals, such as
+ - 1984, although the standard styles can handle any year whose last four
+ - nonpunctuation characters are numerals, such as `(about 1984)'.
+-->
+
+
+<!ENTITY % BibTeXML.address.element "INCLUDE">
+<![%BibTeXML.address.element;[
+<!ELEMENT %address.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.author.element "INCLUDE">
+<![%BibTeXML.author.element;[
+<!ELEMENT %author.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.booktitle.element "INCLUDE">
+<![%BibTeXML.booktitle.element;[
+<!ELEMENT %booktitle.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.chapter.element "INCLUDE">
+<![%BibTeXML.chapter.element;[
+<!ELEMENT %chapter.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.edition.element "INCLUDE">
+<![%BibTeXML.edition.element;[
+<!ELEMENT %edition.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.editor.element "INCLUDE">
+<![%BibTeXML.editor.element;[
+<!ELEMENT %editor.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.howpublished.element "INCLUDE">
+<![%BibTeXML.howpublished.element;[
+<!ELEMENT %howpublished.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.institution.element "INCLUDE">
+<![%BibTeXML.institution.element;[
+<!ELEMENT %institution.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.journal.element "INCLUDE">
+<![%BibTeXML.journal.element;[
+<!ELEMENT %journal.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.month.element "INCLUDE">
+<![%BibTeXML.month.element;[
+<!ELEMENT %month.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.note.element "INCLUDE">
+<![%BibTeXML.note.element;[
+<!ELEMENT %note.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.number.element "INCLUDE">
+<![%BibTeXML.number.element;[
+<!ELEMENT %number.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.organization.element "INCLUDE">
+<![%BibTeXML.organization.element;[
+<!ELEMENT %organization.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.pages.element "INCLUDE">
+<![%BibTeXML.pages.element;[
+<!ELEMENT %pages.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.publisher.element "INCLUDE">
+<![%BibTeXML.publisher.element;[
+<!ELEMENT %publisher.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.school.element "INCLUDE">
+<![%BibTeXML.school.element;[
+<!ELEMENT %school.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.series.element "INCLUDE">
+<![%BibTeXML.series.element;[
+<!ELEMENT %series.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.title.element "INCLUDE">
+<![%BibTeXML.title.element;[
+<!ELEMENT %title.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.type.element "INCLUDE">
+<![%BibTeXML.type.element;[
+<!ELEMENT %type.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.volume.element "INCLUDE">
+<![%BibTeXML.volume.element;[
+<!ELEMENT %volume.qname; (#PCDATA)>
+]]>
+
+<!ENTITY % BibTeXML.year.element "INCLUDE">
+<![%BibTeXML.year.element;[
+<!ELEMENT %year.qname; (#PCDATA)>
+]]>
+
+<!--
+ - In addition to the fields listed above, each entry type also has
+ - an optional key field, used in some styles for alphabetizing, or
+ - for forming a \bibitem label. You should include a key field for
+ - any entry whose ``author'' information is missing;
+-->
+
+<!ENTITY % BibTeXML.key.element "INCLUDE">
+<![%BibTeXML.key.element;[
+<!ELEMENT %key.qname; (#PCDATA)>
+]]>
+
+<!--
+ - BibTEX has a new cross-referencing feature, explained by an example.
+ - @INPROCEEDINGS(no-gnats,
+ - crossref = "gg-proceedings",
+ - @PROCEEDINGS(gg-proceedings,
+-->
+
+<!ENTITY % BibTeXML.crossref.element "INCLUDE">
+<![%BibTeXML.crossref.element;[
+<!ELEMENT %crossref.qname; (#PCDATA)>
+]]>
+
+<!--
+ - Annotation is not used by the standard bibliography styles,
+ - if you prefer otherwise, incude it in BibTeXML.common.standard.fields
+-->
+
+<!ENTITY % BibTeXML.annote.element "INCLUDE">
+<![%BibTeXML.annote.element;[
+<!ELEMENT %annote.qname; (#PCDATA)>
+]]>
+
+
+<!-- ..................................................................... -->
+<!-- Predefined/reserved character entities -->
+
+<!ENTITY amp "&#38;#38;">
+<!ENTITY lt "&#38;#60;">
+<!ENTITY gt "&#62;">
+<!ENTITY apos "&#39;">
+<!ENTITY quot "&#34;">
+
+
+<!-- ..................................................................... -->
+<!-- End of bibtex dtd -->
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/drive.png b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/drive.png
new file mode 100644
index 0000000000..ad10ee3e6b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/drive.png
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/loupe.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/loupe.gif
new file mode 100644
index 0000000000..e8b70f72d8
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/loupe.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-css.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-css.gif
new file mode 100644
index 0000000000..9b2f596e01
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-css.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-html401.gif b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-html401.gif
new file mode 100644
index 0000000000..1270561e17
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Generator/valid-html401.gif
Binary files differ
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/JabRef/JabRef.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/JabRef/JabRef.pm
new file mode 100644
index 0000000000..4d8697f23b
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/JabRef/JabRef.pm
@@ -0,0 +1,209 @@
+# Copyright (C) 2007 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::JabRef::JabRef - A translator to support JabRef format.
+
+=head1 DESCRIPTION
+
+Bib2HTML::JabRef::JabRef is a Perl module, which permits to
+translate bibTeX data according to the JabRef format.
+
+=head1 SYNOPSYS
+
+my $j = Bib2HTML::JabRef::JabRef->new() ;
+$j->parser(content);
+
+=cut
+
+package Bib2HTML::JabRef::JabRef;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of JabRef Translator
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $self = {} ;
+ bless($self,$class);
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Translation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * parse($)
+
+Translate the specified content which must be a reference
+to an hashtable given by a parser.
+
+=cut
+sub parse($) : method {
+ my $self = shift ;
+
+ $self->parseComments(@{$_[0]->{'comments'}});
+
+ if (($self->{'variables'}{'groupsversion'} !~ /^\s*([0-9]+)\s*;\s*$/)||
+ (int($1) < 3)) {
+ Bib2HTML::General::Error::syserr( "the JabRef translator does not support groups' version below 3.0" ) ;
+ }
+
+ # Treat the groups
+ if ($self->{'variables'}{'groupstree'}) {
+ my %categoryAssignation = $self->assignCategories($self->{'variables'}{'groupstree'});
+ $self->createCategories(\%categoryAssignation,$_[0]->{'entries'});
+ }
+}
+
+#------------------------------------------------------
+#
+# Tool API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * createCategories(\%$)
+
+Add the categories to each bibtex entries.
+
+=cut
+sub createCategories(\%$) {
+ my $self = shift;
+ foreach my $key (keys(%{$_[0]})) {
+ if (exists $_[1]->{"$key"}) {
+ my $newcategories = join(':',@{$_[0]->{"$key"}});
+ if ($_[1]->{"$key"}{'fields'}{'domains'}) {
+ $newcategories .= ":".$_[1]->{"$key"}{'fields'}{'domains'};
+ }
+ $_[1]->{"$key"}{'fields'}{'domains'} = "$newcategories";
+ }
+ }
+}
+
+=pod
+
+=item * assignCategories($)
+
+Parse the JabRef group list and replies the assignations
+for each bibtex entry.
+
+=cut
+sub assignCategories($) {
+ my $self = shift;
+ my $jabrefgroups = "$_[0]";
+ my %assignments = ();
+ my @categories = ();
+
+ while (($jabrefgroups)&&
+ ($jabrefgroups =~ /^\s*([0-9]+)\s+([^:]*):(.*?)(?<!\\);\s*(.*)$/s)) {
+ my $order = "$1";
+ my $content = "$3";
+ $jabrefgroups = "$4";
+
+ if (lc("$2") eq "explicitgroup") {
+ $content =~ s/[\n\r]+//g; # remove carriage returns because they are not significant
+
+ my @elements = split(/\\;/, "$content");
+ my $name = shift @elements;
+ shift @elements; # eat the number
+
+ splice(@categories,($order-1));
+ $categories[$order-1] = "$name";
+
+ foreach my $key (@elements) {
+ if (!$assignments{"$key"}) {
+ $assignments{"$key"} = [];
+ }
+ push @{$assignments{"$key"}}, join('/',@categories);
+ }
+ }
+ }
+
+ return %assignments;
+}
+
+=pod
+
+=item * parseComments(@)
+
+Parse the given comments to detect JabRef tokens.
+
+=cut
+sub parseComments(@) : method {
+ my $self = shift ;
+
+ foreach my $comment (@_) {
+ if ($comment =~ /^\s*jabref\-meta:\s*(.+?)\s*\:\s*(.*?)\s*$/is) {
+ $self->{'variables'}{lc("$1")} = "$2";
+ }
+ }
+
+}
+
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 2007 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Main.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Main.pm
new file mode 100644
index 0000000000..a9d2864132
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Main.pm
@@ -0,0 +1,433 @@
+# Copyright (C) 2002-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+package Bib2HTML::Main;
+
+@ISA = ('Exporter');
+@EXPORT = qw( &launchBib2HTML ) ;
+@EXPORT_OK = qw();
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+
+use Getopt::Long ;
+use Pod::Usage ;
+use File::Basename ;
+use File::Spec ;
+use File::Path ;
+
+use Bib2HTML::Release ;
+use Bib2HTML::General::Verbose ;
+use Bib2HTML::General::Error ;
+use Bib2HTML::General::Misc ;
+use Bib2HTML::Parser::Parser ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of bib2html
+my $VERSION = Bib2HTML::Release::getVersionNumber() ;
+# Date of this release of bib2html
+my $VERSION_DATE = Bib2HTML::Release::getVersionDate() ;
+# URL from which the users can submit a bug
+my $SUBMIT_BUG_URL = Bib2HTML::Release::getBugReportURL() ;
+# Email of the author of bib2html
+my $AUTHOR = Bib2HTML::Release::getAuthorName() ;
+# Email of the author of bib2html
+my $AUTHOR_EMAIL = Bib2HTML::Release::getAuthorEmail() ;
+# Page of bib2html
+my $URL = Bib2HTML::Release::getMainURL() ;
+# Contributors to Bib2HTML
+my %CONTRIBUTORS = Bib2HTML::Release::getContributors() ;
+
+# Default Generator
+my $DEFAULT_GENERATOR = 'HTML' ;
+# Default Language
+my $DEFAULT_LANGUAGE = 'English' ;
+# Default Theme
+my $DEFAULT_THEME = 'Simple' ;
+
+#------------------------------------------------------
+#
+# Functions
+#
+#------------------------------------------------------
+
+sub check_output($$) {
+ my $output = shift ;
+ my $force = shift ;
+ if ( ! $output ) {
+ $output = File::Spec->catdir( ".", "bib2html" ) ;
+ }
+ if ( ( -e "$output" ) && ( ! $force ) ) {
+ Bib2HTML::General::Error::syserr( "The output '$output".
+ "' already exists. Use the -f option to force the overwrite\n" ) ;
+ }
+ return "$output" ;
+}
+
+sub show_usage($$$) {
+ my $exitval = shift;
+ my $PERLSCRIPTDIR = shift;
+ my $PERLSCRIPTNAME = shift;
+
+ my $basename = "$PERLSCRIPTNAME";
+ $basename =~ s/\.[^.]*$//;
+
+ my $sharedir = "/usr/share";
+
+ my @searchdirs = (
+ File::Spec->catdir("$PERLSCRIPTDIR",'pod'),
+ File::Spec->catdir("$PERLSCRIPTDIR",'man'),
+ File::Spec->catdir("$PERLSCRIPTDIR",File::Spec->updir(),'pod'),
+ File::Spec->catdir("$PERLSCRIPTDIR",File::Spec->updir(),'man'),
+ File::Spec->catdir("$sharedir",'doc',"$basename"),
+ File::Spec->catdir("$sharedir",'doc',"$basename"),
+ File::Spec->catdir("$sharedir",'doc',"$basename",'pod'),
+ File::Spec->catdir("$sharedir",'doc',"$basename",'man'),
+ );
+
+ my @langs = ();
+
+ if (($ENV{'LANG'})&&($ENV{'LANG'} =~ /^([^_.\-]+)/)) {
+ push @langs, "$1";
+ }
+
+ push @langs, 'en';
+
+ foreach my $lang (@langs) {
+ foreach my $dir (@searchdirs) {
+ my $pod = File::Spec->catdir("$dir","${basename}_${lang}.pod");
+ if ( -r "$pod" ) {
+ print "$pod\n";
+ pod2usage(-exitval => $exitval, -input => "$pod");
+ exit $exitval;
+ }
+ }
+ }
+
+ die("unable to find the documentation file for $basename\n");
+}
+
+sub show_manual($$$) {
+ my $exitval = shift;
+ my $PERLSCRIPTDIR = shift;
+ my $PERLSCRIPTNAME = shift;
+
+ my $basename = "$PERLSCRIPTNAME";
+ $basename =~ s/\.[^.]*$//;
+
+ my $sharedir = "/usr/share";
+
+ my @searchdirs = (
+ File::Spec->catdir("$PERLSCRIPTDIR",'pod'),
+ File::Spec->catdir("$PERLSCRIPTDIR",'man'),
+ File::Spec->catdir("$PERLSCRIPTDIR",File::Spec->updir(),'pod'),
+ File::Spec->catdir("$PERLSCRIPTDIR",File::Spec->updir(),'man'),
+ File::Spec->catdir("$sharedir",'doc',"$basename"),
+ File::Spec->catdir("$sharedir",'doc',"$basename"),
+ File::Spec->catdir("$sharedir",'doc',"$basename",'pod'),
+ File::Spec->catdir("$sharedir",'doc',"$basename",'man'),
+ );
+
+ my @langs = ();
+
+ if (($ENV{'LANG'})&&($ENV{'LANG'} =~ /^([^_.\-]+)/)) {
+ push @langs, "$1";
+ }
+
+ push @langs, 'en';
+
+ foreach my $lang (@langs) {
+ foreach my $dir (@searchdirs) {
+ my $pod = File::Spec->catdir("$dir","${basename}_${lang}.pod");
+ if ( -r "$pod" ) {
+ print "$pod\n";
+ use Pod::Perldoc;
+ @ARGV = ( "$pod" );
+ Pod::Perldoc->run();
+ exit $exitval;
+ }
+ }
+ }
+
+ die("unable to find the documentation file for $basename\n");
+}
+
+#------------------------------------------------------
+#
+# Main Program
+#
+#------------------------------------------------------
+
+sub launchBib2HTML($$) {
+
+ my $PERLSCRIPTDIR = shift;
+ my $PERLSCRIPTNAME = shift;
+
+ # Command line options
+ my %options = () ;
+
+ # Read the command line
+ $options{warnings} = 1 ;
+ $options{genphpdoc} = 1 ;
+ $options{generator} = "$DEFAULT_GENERATOR" ;
+ $options{lang} = "$DEFAULT_LANGUAGE" ;
+ $options{theme} = "$DEFAULT_THEME" ;
+ $options{genparams} = {} ;
+ $options{'show-bibtex'} = 1 ;
+ Getopt::Long::Configure("bundling") ;
+ if ( ! GetOptions( "b|bibtex!" => \$options{'show-bibtex'},
+ "checknames" => \$options{'check-names'},
+ "cvs" => sub {
+ @{$options{'protected_files'}} = ()
+ unless ( exists $options{'protected_files'} ) ;
+ push @{$options{'protected_files'}}, ".cvs", "CVSROOT", "CVS" ;
+ },
+ "doctitle=s" => \$options{'title'},
+ "f|force" => \$options{'force'},
+ "generator|g=s" => \$options{'generator'},
+ 'generatorparam|d:s%' => sub {
+ my $name = lc($_[1]) ;
+ @{$options{'genparams'}{"$name"}} = ()
+ unless ( exists $options{'genparams'}{"$name"} ) ;
+ push @{$options{'genparams'}{"$name"}}, $_[2] ;
+ },
+ "generatorparams!" => \$options{'genparamlist'},
+ "genlist" => \$options{'genlist'},
+ "h|?" => \$options{'help'},
+ "help|man|manual" => \$options{'manual'},
+ "jabref!" => \$options{'jabref'},
+ "lang=s" => \$options{'lang'},
+ "langlist" => \$options{'langlist'},
+ "o|output=s" => sub {
+ $options{'output'} = $_[1];
+ delete $options{'stdout'};
+ },
+ "p|preamble=s" => \$options{'tex-preamble'},
+ "protect=s" => sub {
+ my $regex = lc($_[1]) ;
+ @{$options{'protected_files'}} = ()
+ unless ( exists $options{'protected_files'} ) ;
+ push @{$options{'protected_files'}}, $regex ;
+ },
+ "q" => \$options{'quiet'},
+ "sortw!" => \$options{'sort-warnings'},
+ "stdout" => sub {
+ delete $options{'output'};
+ $options{'stdout'} = 1;
+ },
+ "svn" => sub {
+ @{$options{'protected_files'}} = ()
+ unless ( exists $options{'protected_files'} ) ;
+ push @{$options{'protected_files'}}, ".svn", "svn" ;
+ },
+ "texcmd" => \$options{'tex-commands'},
+ "theme=s" => \$options{'theme'},
+ "themelist" => \$options{'themelist'},
+ "v+" => \$options{'verbose'},
+ "version" => \$options{'version'},
+ "warning!" => \$options{'warnings'},
+ "windowtitle=s" => \$options{'wintitle'},
+ ) ) {
+ show_usage(2,"$PERLSCRIPTDIR","$PERLSCRIPTNAME") ;
+ }
+
+ # Generator class
+ if ( $options{'generator'} !~ /::/ ) {
+ $options{'generator'} = "Bib2HTML::Generator::".$options{'generator'}."Gen" ;
+ }
+ eval "require ".$options{'generator'}.";" ;
+ if ( $@ ) {
+ Bib2HTML::General::Error::syserr( "Unable to find the generator class: ".$options{'generator'}."\n$@\n" ) ;
+ }
+
+ # Show the version number
+ if ( $options{version} ) {
+
+ my $final_copyright = 1998;
+ if ($VERSION_DATE =~ /^([0-9]+)\/[0-9]+\/[0-9]+$/) {
+ if ($1<=98) {
+ $final_copyright = 2000 + $1;
+ }
+ elsif ($1==99) {
+ $final_copyright = 1999;
+ }
+ else {
+ $final_copyright = $1;
+ }
+ }
+
+ if ($final_copyright!=1998) {
+ $final_copyright = "1998-$final_copyright";
+ }
+
+ print "bib2html $VERSION, $VERSION_DATE\n" ;
+ print "Copyright (c) $final_copyright, $AUTHOR <$AUTHOR_EMAIL>, under GPL\n" ;
+ print "Contributors:\n" ;
+ while ( my ($email,$name) = each(%CONTRIBUTORS) ) {
+ print " $name <$email>\n" ;
+ }
+ exit 1 ;
+ }
+
+ # Show the list of generators
+ if ( $options{genlist} ) {
+ use Bib2HTML::Generator::AbstractGenerator ;
+ Bib2HTML::Generator::AbstractGenerator::display_supported_generators($PERLSCRIPTDIR,
+ "$DEFAULT_GENERATOR") ;
+ exit 1 ;
+ }
+
+ # Show the list of languages
+ if ( $options{langlist} ) {
+ use Bib2HTML::Generator::AbstractGenerator ;
+ Bib2HTML::Generator::AbstractGenerator::display_supported_languages($PERLSCRIPTDIR,
+ "$DEFAULT_LANGUAGE") ;
+ exit 1 ;
+ }
+
+ # Show the list of themes
+ if ( $options{themelist} ) {
+ use Bib2HTML::Generator::AbstractGenerator ;
+ Bib2HTML::Generator::AbstractGenerator::display_supported_themes($PERLSCRIPTDIR,
+ "$DEFAULT_THEME") ;
+ exit 1 ;
+ }
+
+ # Show the list of themes
+ if ( $options{'tex-commands'} ) {
+ use Bib2HTML::Translator::TeX ;
+ Bib2HTML::Translator::TeX::display_supported_commands($PERLSCRIPTDIR) ;
+ exit 1 ;
+ }
+
+ # Show the list of generator params
+ if ( $options{'genparamlist'} ) {
+ ($options{'generator'})->display_supported_generator_params() ;
+ exit 1 ;
+ }
+
+ # Show the help screens
+ if ( $options{manual} ) {
+ show_manual(1,"$PERLSCRIPTDIR","$PERLSCRIPTNAME") ;
+ }
+ if ( $options{help} || ( $#ARGV < 0 ) ) {
+ show_usage(1,"$PERLSCRIPTDIR","$PERLSCRIPTNAME") ;
+ }
+
+ # Force the output to stdout
+ if ( $options{'stdout'} ) {
+ my $name = "stdout" ;
+ $options{'genparams'}{"stdout"} = [1];
+ }
+
+ #
+ # Sets the default values of options
+ #
+ # Titles:
+
+ # Verbosing:
+ if ( $options{quiet} ) {
+ $options{verbose} = -1 ;
+ }
+ Bib2HTML::General::Verbose::setlevel( $options{verbose} ) ;
+
+ # Error messages:
+ if ( $options{'warnings'} ) {
+ Bib2HTML::General::Error::unsetwarningaserror() ;
+ }
+ else {
+ Bib2HTML::General::Error::setwarningaserror() ;
+ }
+ if ( $options{'sort-warnings'} ) {
+ Bib2HTML::General::Error::setsortwarnings() ;
+ }
+ else {
+ Bib2HTML::General::Error::unsetsortwarnings() ;
+ }
+
+ #
+ # Create the output directory
+ #
+ unless ($options{'stdout'}) {
+ $options{'output'} = check_output($options{'output'},$options{'force'});
+ }
+
+ # Read the BibTeX files
+ my $parser = new Bib2HTML::Parser::Parser($options{'show-bibtex'}) ;
+ if ( $options{'tex-preamble'} ) {
+ $parser->read_preambles( $options{'tex-preamble'} ) ;
+ }
+ $parser->parse( \@ARGV ) ;
+
+ # Check if the names of the authors are similars
+ if ( $options{'check-names'} ) {
+ eval "require Bib2HTML::Checker::Names;" ;
+ if ( $@ ) {
+ Bib2HTML::General::Error::syserr( "Unable to find the generator class: Bib2HTML::Checker::Names\n$@\n" ) ;
+ }
+ my $check = new Bib2HTML::Checker::Names() ;
+ $check->check($parser->content()) ;
+ }
+
+ # Translate the entries according to the JabRef tool
+ if ($options{'jabref'}) {
+ use Bib2HTML::JabRef::JabRef;
+
+ my $jabref = new Bib2HTML::JabRef::JabRef();
+
+ $jabref->parse($parser->content());
+ }
+
+ # Create the generator
+ #
+ Bib2HTML::Generator::LangManager::set_default_lang("$DEFAULT_LANGUAGE");
+ my $generator = ($options{'generator'})->new( $parser->content(),
+ $options{'output'},
+ { 'VERSION' => $VERSION,
+ 'BUG_URL' => $SUBMIT_BUG_URL,
+ 'URL' => $URL,
+ 'AUTHOR_EMAIL' => $AUTHOR_EMAIL,
+ 'AUTHOR' => $AUTHOR,
+ 'PERLSCRIPTDIR' => $PERLSCRIPTDIR,
+ },
+ { 'SHORT' => $options{'wintitle'},
+ 'LONG' => $options{'title'},
+ },
+ $options{'lang'},
+ $options{'theme'},
+ $options{'show-bibtex'},
+ $options{'genparams'} ) ;
+ if ($options{'protected_files'}) {
+ $generator->set_unremovable_files(@{$options{'protected_files'}});
+ }
+
+ # Generates the HMTL pages
+ #
+ $generator->generate() ;
+
+ # Display the quantity of warnings
+ Bib2HTML::General::Error::printwarningcount() ;
+
+ exit 0 ;
+}
+
+1;
+__END__
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/BibScanner.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/BibScanner.pm
new file mode 100644
index 0000000000..d984818c78
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/BibScanner.pm
@@ -0,0 +1,817 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Parser::BibScanner - A scanner for extracted bibtex entries
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Parser::BibScanner ;
+
+my $scan = Bib2HTML::Parser::BibScanner->new() ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Parser::BibScanner is a Perl module, which scannes
+a source file to recognize the bibtex entries
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a scanner, say something like this:
+
+ use Bib2HTML::Parser::BibScanner;
+
+ my $scan = Bib2HTML::Parser::BibScanner->new() ;
+
+...or something similar.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in BibScanner.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Parser::BibScanner;
+
+@ISA = ('Bib2HTML::Parser::Scanner');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+use File::Basename ;
+
+use Bib2HTML::Parser::Scanner ;
+use Bib2HTML::General::Misc ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the scanner
+my $VERSION = "2.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new() : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ }
+ else {
+ if ( $_[0] ) {
+ if ( ! $_[1] ) {
+ Bib2HTML::General::Error::syserr( "You must supply the initial state to the ".
+ "BibScanner constructor" ) ;
+ }
+ if ( ! $_[2] ) {
+ Bib2HTML::General::Error::syserr( "You must supply the final states to the ".
+ "BibScanner constructor" ) ;
+ }
+ $self = $class->SUPER::new( $_[0], $_[1], $_[2] ) ;
+ }
+ else {
+ $self = $class->SUPER::new(
+ { 'main' => [ { state => 'line_comment',
+ pattern => '\\%',
+ merge => 1,
+ splitmerging => 1,
+ },
+ { state => 'block_comment',
+ pattern => '\\@COMMENT\\s*\\{\\s*',
+ caseinsensitive => 1,
+ },
+ { state => 'line_comment',
+ pattern => '\\@COMMENT\b\\s*',
+ merge => 1,
+ splitmerging => 1,
+ caseinsensitive => 1,
+ },
+ { state => 'constant',
+ pattern => '\\@STRING\\s*\\{\\s*',
+ caseinsensitive => 1,
+ },
+ { state => 'preamble',
+ pattern => '\\@PREAMBLE\\s*',
+ caseinsensitive => 1,
+ },
+ { state => 'entry',
+ pattern => '@',
+ merge => 1,
+ },
+ { state => 'main',
+ pattern => '[^@%]+',
+ },
+ ],
+ # Eats the comment
+ 'line_comment' => [ { state => 'main',
+ pattern => "\n",
+ },
+ { state => 'line_comment',
+ pattern => "[^\n]+",
+ merge => 1,
+ },
+ ],
+ 'block_comment' => [ { state => 'main',
+ pattern => "\\}",
+ splitmerging => 1,
+ merge => 1,
+ },
+ { state => 'block_comment',
+ pattern => "[^\\}]+",
+ merge => 1,
+ },
+ ],
+ # Matches @something
+ 'entry' => [ { state => 'entry_type',
+ pattern => '[a-zA-Z]+',
+ },
+ ],
+ 'entry_type' => [ { state => 'entry_key',
+ pattern => "\\{\\s*",
+ },
+ { state => 'entry_type',
+ pattern => "\\s+",
+ },
+ ],
+ 'entry_key' => [ { state => 'entry_fields',
+ pattern => '[^,\s]+',
+ },
+ { state => 'entry_key',
+ pattern => '\\s+',
+ },
+ ],
+ 'entry_fields' => [ { state => 'entry_fields',
+ pattern => ',\\s*',
+ },
+ { state => 'entry_fields',
+ pattern => '\\s+',
+ },
+ { state => 'entry_fieldname',
+ pattern => '[a-zA-Z0-9.:_\\-]+',
+ },
+ { state => 'main',
+ pattern => '\\s*\\}',
+ },
+ ],
+ 'entry_fieldname' => [ { state => 'string',
+ pattern => '\\s*=\\s*',
+ },
+ { state => 'main',
+ pattern => '\\}',
+ },
+ { state => 'entry_fieldname',
+ pattern => '\\s+',
+ },
+ { state => 'entry_fields',
+ pattern => '.',
+ },
+ ],
+ # Matches @STRING
+ 'constant' => [ { state => 'main',
+ pattern => '\\}',
+ },
+ { state => 'constant_name',
+ pattern => '[a-zA-Z0-9.:]+',
+ },
+ { state => 'constant',
+ pattern => '\\s+',
+ },
+ ],
+ 'constant_name' => [ { state => 'string',
+ pattern => '=\\s*',
+ },
+ { state => 'main',
+ pattern => '\\}',
+ },
+ { state => 'constant_name',
+ pattern => '\\s+',
+ },
+ ],
+ # Matches @PREAMBLE
+ 'preamble' => [ { state => 'braced_string',
+ pattern => '\\{',
+ merge => 1,
+ splitmerging => 1,
+ },
+ { state => 'preamble',
+ pattern => '\\s+',
+ },
+ ],
+ 'preamble_end' => [ { state => 'main',
+ pattern => '.',
+ },
+ ],
+ # Matches a string
+ 'string' => [ { state => 'string',
+ pattern => '\\s+',
+ },
+ { state => 'braced_string',
+ pattern => '{',
+ merge => 1,
+ splitmerging => 1,
+ },
+ { state => 'quoted_string',
+ pattern => '\"',
+ merge => 1,
+ splitmerging => 1,
+ },
+ { state => 'keyword_string',
+ pattern => '[^\\s"{},;#]+',
+ }
+ ],
+ 'keyword_string' => [],
+ # Matches a braced string
+ 'braced_string' => [ { state => 'close_braced_string',
+ pattern => '}',
+ },
+ { state => 'open_braced_string',
+ pattern => '{',
+ },
+ { state => 'braced_string',
+ pattern => '\\\\.',
+ merge => 1,
+ },
+ { state => 'braced_string',
+ pattern => '[^{}\\\\]+',
+ merge => 1,
+ }
+ ],
+ 'close_braced_string' => [],
+ 'open_braced_string' => [],
+ # Matches a quoted string
+ 'quoted_string' => [ { state => 'quote_quoted_string',
+ pattern => '\"',
+ },
+ { state => 'quoted_string',
+ pattern => '\\\\.',
+ merge => 1,
+ },
+ { state => 'quoted_string',
+ pattern => '[^\"\\\\]+',
+ merge => 1,
+ }
+ ],
+ 'quote_quoted_string' => [],
+ # Concatenation operator
+ 'concatenation_operator' => [ { state => 'string',
+ pattern => '\\s*\\#\\s*',
+ },
+ { state=> 'concatenation_operator',
+ pattern => '[^#]',
+ },
+ ],
+ },
+ 'main',
+ [ 'main', 'line_comment' ]
+ ) ;
+ }
+ # Initializes the class attributes
+ $self->clearentries() ;
+ }
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Callback functions
+#
+#------------------------------------------------------
+
+sub transition_callback_concatenation_operator_concatenation_operator($) {
+ my $self = shift ;
+ $self->ungetpattern( $_[0] ) ;
+ $self->pop_state() ;
+}
+
+sub transition_callback_concatenation_operator_string($) {
+ my $self = shift ;
+ $self->translate_to_contatenatedstring() ;
+}
+
+sub transition_callback_string_keyword_string($) {
+ my $self = shift ;
+ $self->setstring($_[0],1) ;
+ $self->pop_state() ;
+}
+
+sub transition_callback_braced_string_close_braced_string($) {
+ my $self = shift ;
+ $self->setstring($_[0]) ;
+ if ( $self->{'BUFFER'}{'BRACE_COUNT'} > 0 ) {
+ $self->{'BUFFER'}{'BRACE_COUNT'} -- ;
+ $self->set_state('braced_string');
+ }
+ else {
+ $self->pop_state() ;
+ }
+}
+
+sub transition_callback_braced_string_open_braced_string($) {
+ my $self = shift ;
+ $self->{'BUFFER'}{'BRACE_COUNT'} ++ ;
+ $self->setstring($_[0]) ;
+ $self->set_state('braced_string');
+}
+
+sub transition_callback_string_braced_string($) {
+ my $self = shift ;
+ $self->{'BUFFER'}{'BRACE_COUNT'} = 0 ;
+}
+
+sub transition_callback_quoted_string_quote_quoted_string($) {
+ my $self = shift ;
+ $self->setstring($_[0]) ;
+ $self->pop_state('braced_string') ;
+}
+
+sub state_callback_string($$) {
+ my $self = shift ;
+ if ( ( $_[1] !~ /string/ ) &&
+ ( $_[1] ne 'concatenation_operator' ) ) {
+ $self->clearstring() ;
+ $self->push_state($_[1]) ;
+ }
+ $self->push_state('concatenation_operator') ;
+}
+
+sub transition_callback_entry_fields_main($) {
+ my $self = shift ;
+ $self->addentry( $self->{'BUFFER'}{'currententry'}{'key'},
+ $self->{'BUFFER'}{'currententry'}{'type'},
+ $self->{'BUFFER'}{'currententry'}{'fields'},
+ $self->{'BUFFER'}{'currententry'}{'lineno'} ) ;
+ delete( $self->{'BUFFER'}{'currententry'} ) ;
+}
+
+sub transition_callback_entry_fieldname_main($) {
+ my $self = shift ;
+ my $field = $self->{'BUFFER'}{'currentfield'} ;
+ $self->{'BUFFER'}{'currententry'}{'fields'}{$field} = $self->clearstring() ;
+ $self->transition_callback_entry_fields_main(undef) ;
+}
+
+sub transition_callback_entry_fieldname_entry_fields($) {
+ my $self = shift ;
+ my $field = $self->{'BUFFER'}{'currentfield'} ;
+ $self->{'BUFFER'}{'currententry'}{'fields'}{$field} = $self->clearstring() ;
+}
+
+sub transition_callback_entry_fields_entry_fieldname($) {
+ my $self = shift ;
+ $self->{'BUFFER'}{'currentfield'} = $_[0] || '' ;
+}
+
+sub transition_callback_entry_key_entry_fields($) {
+ my $self = shift ;
+ $self->{'BUFFER'}{'currententry'}{'key'} = $_[0] || '' ;
+}
+
+sub transition_callback_entry_entry_type($) {
+ my $self = shift ;
+ my $type = $_[0] || '' ;
+ $type =~ s/^\s*\@// ;
+ $self->{'BUFFER'}{'currententry'} = { 'type' => lc($type),
+ 'lineno' => $self->{'LINENO'},
+ } ;
+}
+
+sub transition_callback_preamble_braced_string($) {
+ my $self = shift ;
+ $self->{'BUFFER'}{'BRACE_COUNT'} = 0 ;
+ $self->push_state('preamble_end');
+}
+
+sub transition_callback_preamble_end_main($) {
+ my $self = shift ;
+ $self->addpreamble( $self->clearstring(), $self->{'LINENO'} ) ;
+ $self->ungetpattern($_[0]);
+}
+
+sub transition_callback_constant_constant_name($) {
+ my $self = shift ;
+ $self->{'BUFFER'}{'constant'}{'name'} = $_[0] || '' ;
+ $self->{'BUFFER'}{'constant'}{'lineno'} = $self->{'LINENO'} ;
+}
+
+sub transition_callback_constant_name_main($) {
+ my $self = shift ;
+ $self->addconstant( $self->{'BUFFER'}{'constant'}{'name'},
+ $self->clearstring(),
+ $self->{'BUFFER'}{'constant'}{'lineno'} ) ;
+}
+
+sub transition_callback_block_comment_main($) {
+ my $self = shift ;
+ $self->addcomment("$_[0]");
+}
+
+#------------------------------------------------------
+#
+# Scanning API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * scanentries()
+
+Replies an array that contains the bibtex
+parts readed from the source file.
+Takes 1 arg:
+
+=over
+
+=item * filename (string)
+
+is the name of the file from which the bibtex parts must
+be extracted.
+
+=back
+
+=cut
+sub scanentries($) : method {
+ my $self = shift ;
+ my $filename = $_[0] || confess( 'you must supply the filename' ) ;
+ $self->clearentries() ;
+ $self->clearstring() ;
+
+ if ( ! $self->scan( $filename ) ) {
+ Bib2HTML::General::Error::err( "Unexpected end of file (state: ".$self->{'SM_CURRENT_STATE'}.")",
+ $filename,
+ $self->{'LINENO'} ) ;
+ }
+
+ Bib2HTML::General::Verbose::three( join( '',
+ "\t",
+ hashcount($self->{'BIBSCANNER_ENTRIES'}{'entries'}),
+ " entr",
+ (hashcount($self->{'BIBSCANNER_ENTRIES'}{'entries'})>1)?"ies":"y" ) ) ;
+
+ return $self->getentries() ;
+}
+
+#------------------------------------------------------
+#
+# Block functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * clearentries()
+
+Destroyes all recognized blocks.
+
+=cut
+sub clearentries() {
+ my $self = shift ;
+ $self->{'BIBSCANNER_ENTRIES'} = { 'constants' => {},
+ 'comments' => [],
+ 'preambles' => [],
+ 'entries' => {},
+ } ;
+}
+
+=pod
+
+=item * getentries()
+
+Replies the readed entries
+
+=cut
+sub getentries() {
+ my $self = shift ;
+ return $self->{'BIBSCANNER_ENTRIES'} ;
+}
+
+=pod
+
+=item * addconstant()
+
+Adds a constant inside the readed data.
+Takes 3 args:
+
+=over
+
+=item * name (string)
+
+is the name of the constant
+
+=item * value (string)
+
+is the value of the constant
+
+=item * lineno (integer)
+
+is the line number where the constant starts
+
+=back
+
+=cut
+sub addconstant($$$) {
+ my $self = shift ;
+ my $name = $_[0] || '' ;
+ my $lineno = $_[2] || 0 ;
+ my $lcname = lc( $name ) ;
+ if ( ! $lcname ) {
+ Bib2HTML::General::Error::warm( "I expected a string name. Ignore this constant definition.",
+ $self->{'FILENAME'},
+ $self->{'LINENO'} ) ;
+ }
+ elsif ( exists $self->{'BIBSCANNER_ENTRIES'}{'constants'}{$lcname} ) {
+ Bib2HTML::General::Error::warm( "the \@STRING '".$name."' was already ".
+ "defined. Ignored the last instance.",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ else {
+ $self->{'BIBSCANNER_ENTRIES'}{'constants'}{$lcname}{'text'} = $_[1] ;
+ $self->{'BIBSCANNER_ENTRIES'}{'constants'}{$lcname}{'location'} = $self->{'FILENAME'}.":".$lineno ;
+ }
+}
+
+=pod
+
+=item * addcomment()
+
+Adds a comment inside the readed data.
+Takes 3 args:
+
+=over
+
+=item * value (string)
+
+is the value of the comment
+
+=back
+
+=cut
+sub addcomment($) {
+ my $self = shift ;
+ my $value = $_[0] || '' ;
+ push @{$self->{'BIBSCANNER_ENTRIES'}{'comments'}}, "$value";
+}
+
+=pod
+
+=item * addpreamble()
+
+Adds a preamble inside the readed data.
+Takes 1 args:
+
+=over
+
+=item * content (string)
+
+is the content of the preamble
+
+=item * lineno (integer)
+
+is the line number where the preamble starts
+
+=back
+
+=cut
+sub addpreamble($$) {
+ my $self = shift ;
+ my $lineno = $_[1] || 0 ;
+ if ( $_[0] ) {
+ push @{$self->{'BIBSCANNER_ENTRIES'}{'preambles'}}, { 'tex' => $_[0],
+ 'location' => $self->{'FILENAME'}.":".$lineno,
+ } ;
+ }
+}
+
+=pod
+
+=item * addentry()
+
+Adds an entry inside the readed data.
+Takes 3 args:
+
+=over
+
+=item * key (string)
+
+is the bibtex key
+
+=item * type (string)
+
+is the bibtex type of the entry
+
+=item * fields (hash)
+
+is the list of the field for this entry
+
+=item * lineno (integer)
+
+is the line number where the entry starts
+
+=back
+
+=cut
+sub addentry($$$$) {
+ my $self = shift ;
+ my $key = $_[0] || confess( 'you must supply the entry key' ) ;
+ my $type = $_[1] || confess( 'you must supply the entry type' ) ;
+ my $fields = $_[2] || { } ;
+ my $lineno = $_[3] || 0 ;
+ $fields = { } unless ishash( $fields ) ;
+
+ if ($key !~ /^[a-zA-Z0-9.:_\-=\+]+$/) {
+ Bib2HTML::General::Error::warm( "the entry '".$key."' does not respect the ".
+ "official entry key guidelines from ".
+ "the BibTeX specifications.",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+
+ if ( exists $self->{'BIBSCANNER_ENTRIES'}{'entries'}{$key} ) {
+ Bib2HTML::General::Error::warm( "the entry '".$key."' was already ".
+ "defined. Ignored the last instance.",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ else {
+ $self->{'BIBSCANNER_ENTRIES'}{'entries'}{$key}{'type'} = lc($type) ;
+ $self->{'BIBSCANNER_ENTRIES'}{'entries'}{$key}{'location'} = $self->{'FILENAME'}.":".$lineno ;
+ $self->{'BIBSCANNER_ENTRIES'}{'entries'}{$key}{'dirname'} = dirname($self->{'FILENAME'}) ;
+ while ( my ($k, $value) = each (%{$fields}) ) {
+ # Patched by: Martin P.J. ZINSER <zinser@zinser.no-ip.info>
+ # lc was added to support multi-case field names
+ $self->{'BIBSCANNER_ENTRIES'}{'entries'}{$key}{'fields'}{lc($k)} = $value ;
+ }
+ }
+}
+
+#------------------------------------------------------
+#
+# String functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * clearstring()
+
+Clear the string, and replies the old value.
+
+=cut
+sub clearstring() {
+ my $self = shift ;
+ my $str = $self->getstring() ;
+ delete( $self->{'BUFFER'}{'string'} ) ;
+ return $str ;
+}
+
+=pod
+
+=item * getstring()
+
+Replies the current string.
+
+=cut
+sub getstring() {
+ my $self = shift ;
+ if ( isarray( $self->{'BUFFER'}{'string'} ) ) {
+ for(my $i=0; $i<=$#{$self->{'BUFFER'}{'string'}}; $i++) {
+ $self->{'BUFFER'}{'string'}[$i] = $self->cleanstring($self->{'BUFFER'}{'string'}[$i]) ;
+ }
+ return $self->{'BUFFER'}{'string'} ;
+ }
+ else {
+ return $self->cleanstring($self->{'BUFFER'}{'string'}) ;
+ }
+}
+
+=pod
+
+=item * cleanstring()
+
+Removes string delimiters.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is the string to remove.
+
+=over
+
+=cut
+sub cleanstring($) {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ $text =~ s/[ \t]*[\n\r][ \t]*/ /gm ;
+ if ( $text =~ /^\".*\"$/ ) {
+ $text =~ s/^\"/{/ ;
+ $text =~ s/\"$/}/ ;
+ }
+ return $text ;
+}
+
+=pod
+
+=item * setstring()
+
+Sets the string.
+
+=cut
+sub setstring($;$) {
+ my $self = shift ;
+ my $iskeyword = $_[1] || 0 ;
+ my $str = $_[0] || '' ;
+ if ( isarray( $self->{'BUFFER'}{'string'} ) ) {
+ my $last = $#{$self->{'BUFFER'}{'string'}} ;
+ if ( $self->{'BUFFER'}{'string'}[$last] ) {
+ $self->{'BUFFER'}{'string'}[$last] .= $str ;
+ }
+ else {
+ $self->{'BUFFER'}{'string'}[$last] = $str ;
+ }
+ }
+ elsif ( $self->{'BUFFER'}{'string'} ) {
+ $self->{'BUFFER'}{'string'} .= $str ;
+ }
+ else {
+ $self->{'BUFFER'}{'string'} = $str ;
+ }
+}
+
+=pod
+
+=item * translate_to_contatenatedstring()
+
+Sets the string as a concatened string if
+it was not already set as.
+Adds an empty element to this contatened
+string.
+A concatened string is used to split the
+different components of the string in order
+to extract the potential string constant to
+replace.
+
+=cut
+sub translate_to_contatenatedstring() {
+ my $self = shift ;
+ force_add_value_entry($self->{'BUFFER'}, 'string', '' ) ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Parser.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Parser.pm
new file mode 100644
index 0000000000..25a146e1ed
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Parser.pm
@@ -0,0 +1,477 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Parser::Parser - A parser for BibTeX files.
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Parser::Parser ;
+
+my $gen = Bib2HTML::Parser::Parser->new() ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Parser::Parser is a Perl module, which parses
+a source file to recognize the BibTeX tokens.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To create a parser, say something like this:
+
+ use Bib2HTML::Parser::Parser;
+
+ my $parser = Bib2HTML::Parser::Parser->new() ;
+
+...or something similar.
+The constructor could take 1 arg:
+
+=over
+
+=item * show_bibtex (boolean)
+
+indicates if the BibTeX code will be generated inside
+a verbatim area. This flag permits to this parser
+to store (or not) the initial value of each field.
+Caution about the memory space.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Parser.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Parser::Parser;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+use File::Basename ;
+use File::Spec ;
+
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::Error ;
+use Bib2HTML::General::Verbose ;
+
+use Bib2HTML::Parser::BibScanner ;
+
+use Bib2HTML::Translator::TeX ;
+use Bib2HTML::Translator::BibTeXEntry ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the parser
+my $VERSION = "2.1" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new(;$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ bless( $self, $class );
+ }
+ else {
+ $self = { 'CONTENT' => {},
+ 'FILE_PREAMBLES' => '',
+ 'SHOW_BIBTEX' => $_[0],
+ } ;
+ bless( $self, $class );
+ $self->clearcontent() ;
+ }
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Getter/setter functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * content()
+
+Replies the content of the documentation
+read by the parser.
+
+=cut
+sub content() : method {
+ my $self = shift ;
+ return $self->{'CONTENT'} ;
+}
+
+=pod
+
+=item * clearcontent()
+
+Destoys the readed content and sets it
+to the empty.
+
+=cut
+sub clearcontent() : method {
+ my $self = shift ;
+ $self->{'CONTENT'} = { } ;
+}
+
+#------------------------------------------------------
+#
+# Main parsing functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * parse()
+
+Parses the files.
+Takes 1 arg:
+
+=over
+
+=item * file_list (array ref)
+
+is an array that contains the names of the files and the
+directories from which the parser must read the bibtex entries.
+
+=back
+
+=cut
+sub parse(\@) : method {
+ my $self = shift ;
+ $self->clearcontent() ;
+ # Evaluate the TeX expressions
+ if ( ( $self->{'FILE_PREAMBLES'} ) &&
+ ( exists( $self->{'FILE_PREAMBLES'}{'tex'} ) ) &&
+ ( $self->{'FILE_PREAMBLES'}{'tex'} ) ) {
+ Bib2HTML::General::Verbose::two( "Evaluate the user's LaTeX definitions...\n" ) ;
+ my $trans = Bib2HTML::Translator::TeX->new( $self->{'FILE_PREAMBLES'}{'filename'} ) ;
+ $trans->translate( $self->{'FILE_PREAMBLES'}{'tex'},
+ $self->{'CONTENT'}{'entries'} ) ;
+ }
+ # Evaluate each file
+ if ( isarray( $_[0] ) ) {
+ foreach my $file (@{$_[0]}) {
+ $self->readfile( $file ) ;
+ }
+ }
+ else {
+ die("END1");
+ $self->readfile( $_[0] ) ;
+ }
+ # Save the TeX entries
+ if ( $self->{'SHOW_BIBTEX'} ) {
+ $self->save_bibtex_entries() ;
+ }
+ # Evalute TeX expressions
+ $self->tex_translation() ;
+ # Expand the crossref fields
+ $self->expand_crossref() ;
+
+ return $self->content() ;
+}
+
+=pod
+
+=item * readfile()
+
+Reads the content of a file.
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+is the name of the file to read.
+
+=back
+
+=cut
+sub readfile($) : method {
+ my $self = shift ;
+ my $filename = $_[0] || confess( 'you must supply the filename' ) ;
+
+ # Read the file content
+ Bib2HTML::General::Verbose::two( "Read $filename..." ) ;
+ my $scanner = new Bib2HTML::Parser::BibScanner() ;
+ if ($self->{'CONTENT'}) {
+ my $content = $scanner->scanentries($filename) ;
+ # Merge the constants
+ if ($content->{'constants'}) {
+ foreach my $constant (keys %{$content->{'constants'}}) {
+ if (exists $self->{'CONTENT'}{'constants'}{"$constant"}) {
+ Bib2HTML::General::Error::warm( "multiple definition for the constant '".
+ $constant."'",
+ $filename,
+ extract_line_from_location($content->{'constants'}{"$constant"}{'location'})) ;
+ }
+ $self->{'CONTENT'}{'constants'}{"$constant"} = $content->{'constants'}{"$constant"} ;
+ }
+ }
+ # Merge the preambles
+ if ($content->{'preambles'}) {
+ push @{$self->{'CONTENT'}{'preambles'}}, @{$content->{'preambles'}} ;
+ }
+ # Merge the comments
+ if ($content->{'comments'}) {
+ push @{$self->{'CONTENT'}{'comments'}}, @{$content->{'comments'}} ;
+ }
+ # Merge the red content to the previous content
+ if ($content->{'entries'}) {
+ foreach my $entry (keys %{$content->{'entries'}}) {
+ if (exists $self->{'CONTENT'}{'entries'}{"$entry"}) {
+ Bib2HTML::General::Error::warm( "multiple definition for the entry '".
+ $entry."'",
+ $filename,
+ extract_line_from_location($content->{'entriess'}{"$entry"}{'location'})) ;
+ }
+ $self->{'CONTENT'}{'entries'}{"$entry"} = $content->{'entries'}{"$entry"} ;
+ }
+ }
+ }
+ else {
+ $self->{'CONTENT'} = $scanner->scanentries($filename) ;
+ }
+}
+
+=pod
+
+=item * read_preambles()
+
+Read some LaTeX commands from a file.
+There commands are defined previously
+any command from the BibTeX files.
+Takes 1 arg:
+
+=over
+
+=item * file (string)
+
+=back
+
+=cut
+sub read_preambles($) : method {
+ my $self = shift ;
+ $self->{'FILE_PREAMBLES'} = '' ;
+ if ( $_[0] ) {
+ Bib2HTML::General::Verbose::two( "Reading the user's LaTeX definitions...\n" ) ;
+ if ( ( -f $_[0] ) &&
+ ( -r $_[0] ) ) {
+ my $tex = '' ;
+ local *FILE_PREAMBLE ;
+ open( *FILE_PREAMBLE, "< $_[0]" )
+ or Bib2HTML::General::Error::syserr( "$_[0]: $!" ) ;
+ while ( my $line = <FILE_PREAMBLE> ) {
+ $tex .= $line ;
+ }
+ close( *FILE_PREAMBLE ) ;
+ $tex =~ s/^[ \t\n\r]+// ;
+ $tex =~ s/[ \t\n\r]+$// ;
+ if ( $tex ) {
+ $self->{'FILE_PREAMBLES'} = {} ;
+ $self->{'FILE_PREAMBLES'}{'tex'} = $tex ;
+ $self->{'FILE_PREAMBLES'}{'filename'} = $_[0] ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::syserr( "unable to find or read the preamble file '$_[0]'" ) ;
+ }
+ }
+}
+
+=pod
+
+=item * expand_crossref()
+
+Expands crossref fields.
+
+=cut
+sub expand_crossref() : method {
+ my $self = shift ;
+
+ Bib2HTML::General::Verbose::two( "Expand crossref fields...\n" ) ;
+
+ foreach my $entry (keys %{$self->{'CONTENT'}{'entries'}}) {
+
+ if ( exists $self->{'CONTENT'}{'entries'}{"$entry"}{'fields'}{'crossref'} ) {
+
+ my $parent = $self->{'CONTENT'}{'entries'}{"$entry"}{'fields'}{'crossref'} ;
+ if ( exists $self->{'CONTENT'}{'entries'}{"$parent"} ) {
+
+ foreach my $field (keys %{$self->{'CONTENT'}{'entries'}{"$parent"}{'fields'}}) {
+ if ( ! exists $self->{'CONTENT'}{'entries'}{"$entry"}{'fields'}{"$field"} ) {
+ $self->{'CONTENT'}{'entries'}{"$entry"}{'fields'}{"$field"} =
+ $self->{'CONTENT'}{'entries'}{"$parent"}{'fields'}{"$field"} ;
+ }
+ }
+
+ }
+ else {
+ my $filename = extract_file_from_location( $self->{'CONTENT'}{'entries'}{"$entry"}{'location'} ) ;
+ my $lineno = extract_line_from_location( $self->{'CONTENT'}{'entries'}{"$entry"}{'location'} ) ;
+ Bib2HTML::General::Error::warm( "unable to find the entry '$parent' required for ".
+ "the crossref from '$entry'",
+ $filename, $lineno ) ;
+ }
+
+ }
+ }
+
+}
+
+=pod
+
+=item * tex_translation()
+
+Translates TeX expressions
+
+=cut
+sub tex_translation() : method {
+ my $self = shift ;
+
+ # Evaluate @preamble
+ Bib2HTML::General::Verbose::two( "Evaluate TeX expressions for the preambles...\n" ) ;
+
+ foreach my $preamble (@{$self->{'CONTENT'}{'preambles'}}) {
+ if ( $preamble->{'tex'} ) {
+ my $trans = Bib2HTML::Translator::TeX->new( extract_file_from_location( $preamble->{'location'} ) ) ;
+ $trans->translate( $preamble->{'tex'},
+ $self->{'CONTENT'}{'entries'},
+ extract_line_from_location( $preamble->{'location'} ) ) ;
+ }
+ }
+
+ # Evaluate @string
+ Bib2HTML::General::Verbose::two( "Evaluate TeX expressions for the constants...\n" ) ;
+ my $be = new Bib2HTML::Translator::BibTeXEntry() ;
+ foreach my $const (keys %{$self->{'CONTENT'}{'constants'}}) {
+ $self->{'CONTENT'}{'constants'}{$const}{'text'} = $be->expand_bibtex_vars($self->{'CONTENT'}{'constants'}{$const}{'text'},
+ $self->{'CONTENT'}{'constants'}) ;
+ }
+
+ # Evaluate @preamble
+ Bib2HTML::General::Verbose::two( "Evaluate TeX expressions for the preambles...\n" ) ;
+
+ # Evaluate entries' fields
+ foreach my $entry (keys %{$self->{'CONTENT'}{'entries'}}) {
+
+ Bib2HTML::General::Verbose::two( "Evaluate TeX expressions for '$entry'...\n" ) ;
+ my $filename = extract_file_from_location( $self->{'CONTENT'}{'entries'}{$entry}{'location'} ) ;
+ my $lineno = extract_line_from_location( $self->{'CONTENT'}{'entries'}{$entry}{'location'} ) ;
+ my $trans = Bib2HTML::Translator::TeX->new( $filename ) ;
+
+ foreach my $field (keys %{$self->{'CONTENT'}{'entries'}{$entry}{'fields'}}) {
+
+ if ( ! bibtex_ignore_field_parsing( $field ) ) {
+
+ # Translate the TeX code of this field into HTML source code
+ Bib2HTML::General::Verbose::three( "\ttreat field '$field'" ) ;
+
+ my $text = $be->expand_bibtex_vars($self->{'CONTENT'}{'entries'}{$entry}{'fields'}{$field},
+ $self->{'CONTENT'}{'constants'} ) ;
+
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{$field} = $trans->translate( $text,
+ $self->{'CONTENT'}{'entries'},
+ $lineno ) ;
+
+ }
+ else {
+
+ # Do not translate the TeX code of this field into HTML source code
+ # Simply remove the
+ if ( $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{$field} =~ /^{(.*)}$/) {
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{$field} = "$1" ;
+ }
+
+ }
+ }
+
+ }
+
+}
+
+=pod
+
+=item * save_bibtex_entries()
+
+Saves the original text for the BibTeX entries
+
+=cut
+sub save_bibtex_entries() : method {
+ my $self = shift ;
+
+ Bib2HTML::General::Verbose::two( "Save the BibTeX original values for futher verbatim...\n" ) ;
+
+ # Evaluate entries' fields
+ foreach my $entry (keys %{$self->{'CONTENT'}{'entries'}}) {
+
+ foreach my $field (keys %{$self->{'CONTENT'}{'entries'}{$entry}{'fields'}}) {
+
+ $self->{'CONTENT'}{'entries'}{$entry}{'original-fields'}{$field} =
+ $self->{'CONTENT'}{'entries'}{$entry}{'fields'}{$field} ;
+
+ }
+
+ }
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Scanner.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Scanner.pm
new file mode 100644
index 0000000000..bd02275638
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/Scanner.pm
@@ -0,0 +1,490 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Parser::Scanner - An abstract scanner for extracted bibtex entries
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Parser::Scanner ;
+
+my $scan = Bib2HTML::Parser::StateMachine->new(
+ transitions,
+ initial_state,
+ final_states
+ ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Parser::Scanner is a Perl module, which is a
+state machine which reads a input stream. This is an
+abstract scanner, i.e. it is not specific to a language
+such as PHP, HTML...
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a scanner, say something like this:
+
+ use Bib2HTML::Parser::Scanner;
+
+ my $sm = Bib2HTML::Parser::Scanner->new(
+ { '0' => [ { callback => 'myfunc',
+ pattern => 'a+',
+ state => '1',
+ },
+ { state => '0' },
+ ],
+ '1' => { state => '0',
+ },
+ },
+ '0',
+ [ '1' ]
+ ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * transitions (hash ref)
+
+describes the states of this machine. It must be an
+associative array in which the keys are the name of
+each states, and the associated values describe the
+states with an array of transitions or with only
+one transition. A transition is defined as an
+associative array in which the following keys are
+recognized:
+
+=over
+
+=item * state (string)
+
+is the name of the state on which the machine must be
+after this transition. B<This value is required.>
+
+=item * pattern (string)
+
+is a regular expression that describe the selection
+condition needed to do this translation. B<This
+value is optional>. But, only once transition
+is able to not defined the pattern. This special
+transition is the default (if no other transition
+could be selected).
+
+=item * callback (string)
+
+is the name (not the reference) to a function that
+must be called each time this transition was selected.
+B<This value is optional>.
+
+=item * merge (boolean)
+
+if true and the state does not changed, the recognized
+token will be merged to the previous token.
+B<This value is optional>.
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Scanner.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Parser::Scanner;
+
+@ISA = ('Bib2HTML::Parser::StateMachine');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+use File::Basename ;
+
+use Bib2HTML::Parser::StateMachine ;
+use Bib2HTML::General::Misc ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the scanner
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ }
+ else {
+ $self = $class->SUPER::new( $_[0], $_[1], $_[2] ) ;
+ $self->{'LINENO'} = 0 ;
+ $self->{'STATE_STACK'} = [] ;
+ }
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Scanning functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * scan()
+
+Reads a input stream. Replies if the state machine is
+in a final state.
+Takes 1 arg:
+
+=over
+
+=item * filename (string)
+
+is the name of the file from which the tokens must
+be extracted.
+
+=back
+
+=cut
+sub scan($) : method {
+ my $self = shift ;
+ my $filename = $_[0] || confess( 'you must supply the filename' ) ;
+ local *SOURCEFILE ;
+ open( SOURCEFILE, "< $filename" )
+ or Bib2HTML::General::Error::syserr( "unable to open $filename: $!" ) ;
+
+ # Initialize the state machine
+ $self->{'LINENO'} = 0 ;
+ $self->{'FILENAME'} = $filename ;
+
+ $self->resetstatemachine() ;
+
+ while ( my $line = <SOURCEFILE> ) {
+ # Read a line
+ $self->{'LINENO'} ++ ;
+ # Translate the red line
+ # This translation is dependent of
+ # the scanner which inherited from this Scanner.
+ $line = $self->translate_current_line( $line ) ;
+ if ( $line !~ /^(\n|\r|\s)$/ ) {
+ while ( $line ) {
+ # Clear the buffer which store the unget
+ # tokens
+ $self->{'UNGET_BUFFER'} = '' ;
+ # Try to recognize the next token
+ # according to the translation table
+ $line = $self->changestatefrom( $line ) ;
+ # In case some call to ungetpattern
+ # was made, merges the unget string
+ # to the start of the current red
+ # line
+ if ( $self->{'UNGET_BUFFER'} ) {
+ $line = $self->{'UNGET_BUFFER'} . $line ;
+ }
+ }
+ }
+ }
+ $self->changestateforEOF() ;
+
+ Bib2HTML::General::Verbose::three( join( '',
+ "\t",
+ $self->{'LINENO'},
+ " line",
+ ($self->{'LINENO'}>1)?"s":"",
+ "\n" ) ) ;
+
+ close( SOURCEFILE )
+ or Bib2HTML::General::Error::syserr( "unable to close $filename: $!" ) ;
+
+ return $self->isfinalstate() ;
+}
+
+=pod
+
+=item * ungetpattern()
+
+Pushes the specified string into the current red string.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is the text that must be put inside the current stream.
+
+=back
+
+=cut
+sub ungetpattern($) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ $self->{'UNGET_BUFFER'} = $text . $self->{'UNGET_BUFFER'} ;
+ Bib2HTML::General::Verbose::verb( join( '',
+ "\t\tUNGET = '",
+ tohumanreadable($text),
+ "'" ),
+ 4 ) ;
+}
+
+=pod
+
+=item * translate_current_line()
+
+Replies the translation of the current line which was readed from
+the current input file.
+Takes 1 arg:
+
+=over
+
+=item * line (string)
+
+is the line to translate.
+
+=back
+
+=cut
+sub translate_current_line($) : method {
+ my $self = shift ;
+ return ($_[0] || '') ;
+}
+
+=pod
+
+=item * push_switch_state()
+
+Pushes the current state on the state stack and switch to the specified state.
+Takes 1 arg:
+
+=over
+
+=item * state (string)
+
+is the name of the new state to reach.
+
+=back
+
+=cut
+sub push_switch_state($) : method {
+ my $self = shift ;
+ my $state = $_[0] || confess( 'you must supply a state' ) ;
+ if ( exists $self->{'SM_STATES'}{$state} ) {
+ if ( Bib2HTML::General::Verbose::currentlevel() >= 4 ) {
+ my $verbstr = join( '',
+ "\t\ttoken = '",
+ tohumanreadable($self->{'SM_PREVIOUS_TOKEN'}),
+ "'" ) ;
+ $verbstr .= ", PUSH('".$self->{'SM_CURRENT_STATE'}."') -> '".$state."'" ;
+ Bib2HTML::General::Verbose::verb( "$verbstr.", 4 ) ;
+ }
+ push @{$self->{'STATE_STACK'}}, $self->{'SM_CURRENT_STATE'} ;
+ $self->{'SM_CURRENT_STATE'} = $state ;
+ }
+ else {
+ Bib2HTML::General::Error::syserr( "Unable to switch to the unexisting state '$state'" ) ;
+ }
+}
+
+=pod
+
+=item * push_state()
+
+Pushes the current state on the state stack. Does not switch to another state.
+Takes 1 arg:
+
+=over
+
+=item * state (string)
+
+is the name of the state to push.
+
+=back
+
+=cut
+sub push_state($) : method {
+ my $self = shift ;
+ my $state = $_[0] || confess( 'you must supply the state' ) ;
+ if ( exists $self->{'SM_STATES'}{$state} ) {
+ if ( Bib2HTML::General::Verbose::currentlevel() >= 4 ) {
+ my $verbstr = join( '',
+ "\t\ttoken = '",
+ tohumanreadable($self->{'SM_PREVIOUS_TOKEN'}),
+ "'" ) ;
+ $verbstr .= ", PUSH('".$self->{'SM_CURRENT_STATE'}."')" ;
+ Bib2HTML::General::Verbose::verb( "$verbstr.", 4 ) ;
+ }
+ push @{$self->{'STATE_STACK'}}, $state ;
+ }
+ else {
+ confess( "Unable to push the unexisting state '$state'" ) ;
+ }
+}
+
+=pod
+
+=item * pop_state()
+
+Pops a state from the state stack and set as the new current state.
+
+=cut
+sub pop_state() : method {
+ my $self = shift ;
+ if ( isemptyarray( $self->{'STATE_STACK'} ) ) {
+ confess( "Unable to pop a state from an empty state stack" ) ;
+ }
+ else {
+ my $state = pop @{$self->{'STATE_STACK'}} ;
+ if ( Bib2HTML::General::Verbose::currentlevel() >= 4 ) {
+ my $verbstr = join( '',
+ "\t\ttoken = '",
+ tohumanreadable($self->{'SM_PREVIOUS_TOKEN'}),
+ "'" ) ;
+ $verbstr .= ", POP('".$self->{'SM_CURRENT_STATE'}."') -> '$state'" ;
+ Bib2HTML::General::Verbose::verb( "$verbstr.", 4 ) ;
+ }
+ $self->{'SM_CURRENT_STATE'} = $state ;
+ }
+}
+
+=pod
+
+=item * set_state()
+
+Sets the current state, and replies the old state.
+Takes 1 arg:
+
+=over
+
+=item * state (string)
+
+is the name of the new state.
+
+=back
+
+=cut
+sub set_state($) : method {
+ my $self = shift ;
+ my $state = $_[0] || confess( 'you must supply the state' ) ;
+ my $old = $self->{'SM_CURRENT_STATE'} ;
+ $self->{'SM_CURRENT_STATE'} = $state ;
+ return $old ;
+}
+
+=pod
+
+=item * get_state()
+
+Replies the current state machine.
+
+=cut
+sub get_state() : method {
+ my $self = shift ;
+ return $self->{'SM_CURRENT_STATE'} ;
+}
+
+=pod
+
+=item * get_stackstate()
+
+Replies the current state machine on the top of the stack.
+
+=cut
+sub get_stackstate() : method {
+ my $self = shift ;
+ return $self->{'STATE_STACK'}->[$#{$self->{'STATE_STACK'}}] ;
+}
+
+=pod
+
+=item * get_statestack()
+
+Replies the whole state stack.
+
+=cut
+sub get_statestack() : method {
+ my $self = shift ;
+ return @{$self->{'STATE_STACK'}} ;
+}
+
+=pod
+
+=item * backend_error_function()
+
+Called each time no rule match the current buffer.
+
+=over
+
+=item * msg (string)
+
+is the error message.
+
+=back
+
+=cut
+sub backend_error_function($) : method {
+ my $self = shift ;
+ confess( 'you must supply the error message' ) unless $_[0] ;
+ Bib2HTML::General::Error::err( $_[0],
+ $self->{'FILENAME'},
+ $self->{'LINENO'} ) ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/StateMachine.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/StateMachine.pm
new file mode 100644
index 0000000000..d3b090c3a6
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Parser/StateMachine.pm
@@ -0,0 +1,643 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Parser::StateMachine - A state machine
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Parser::StateMachine ;
+
+my $sm = Bib2HTML::Parser::StateMachine->new(
+ transitions,
+ initial_state,
+ final_states
+ ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Parser::StateMachine is a Perl module, which
+implementes a state machine.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To start a scanner, say something like this:
+
+ use Bib2HTML::Parser::StateMachine;
+
+ my $sm = Bib2HTML::Parser::StateMachine->new(
+ { '0' => [ { callback => 'myfunc',
+ pattern => 'a+',
+ state => '1',
+ },
+ { state => '0' },
+ ],
+ '1' => { state => '0',
+ },
+ },
+ '0',
+ [ '1' ]
+ ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * transitions (hash ref)
+
+describes the states of this machine. It must be an
+associative array in which the keys are the name of
+each states, and the associated values describe the
+states with an array of transitions or with only
+one transition. A transition is defined as an
+associative array in which the following keys are
+recognized:
+
+=over
+
+=item * state (string)
+
+is the name of the state on which the machine must <be
+after this transition. B<This value is required.>
+
+=item * pattern (string)
+
+is a regular expression that describe the selection
+condition needed to do this translation. B<This
+value is optional>. But, only once transition
+is able to not defined the pattern. This special
+transition is the default (if no other transition
+could be selected). If the pattern was equal to
+the string "$EOF", it matchs the end of the stream
+(see changestateforEOF()).
+
+=item * callback (string)
+
+is the name (not the reference) to a function that
+must be called each time this transition was selected.
+B<This value is optional>.
+
+=item * merge (boolean)
+
+if true, the recognized
+token will be merged to the next token.
+B<This value is optional>.
+
+=item * splitmerging (boolean)
+
+if true, the previously saved tokens
+are passed to the callbacks functions.
+If I<merge> was also true, the current
+token is not merging.
+B<This value is optional>.
+
+=back
+
+=item * initial_state (string)
+
+is the name of the initial state of the machine.
+This state must be defined inside the previous parameter.
+
+=item * final_states (array ref)
+
+is an array that lists all the final states recognized
+by this machine. This array is used by isfinalstate()
+to determine is this machine is inside a stable final
+state.
+
+=back
+
+=head2 State change
+
+To change the state of the machine, say something like this:
+
+ $scan->changestatefrom( "the string" ) ;
+
+...where "the string" is a string which permits to select
+the next state.
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in StateMachine.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Parser::StateMachine;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+use File::Basename ;
+
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::Verbose ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the scanner
+my $VERSION = "1.0" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($$$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ }
+ else {
+ $self = { } ;
+ # Sets the description of this machine
+ $self->{'SM_STATES'} = { 'SM_PREVIOUS_TOKEN' => "",
+ } ;
+ foreach my $state ( keys %{$_[0]} ) {
+ my $list ;
+ # Gets the list of the transitions
+ if ( isarray( $_[0]{$state} ) ) {
+ $list = $_[0]{$state} ;
+ }
+ else {
+ $list = [ $_[0]{$state} ] ;
+ }
+ # Checks the transitions
+ my $default = 0 ;
+ foreach my $trans ( @{$list} ) {
+ # Search for the target state
+ if ( ( exists $trans->{'state'} ) &&
+ ( "s".$trans->{'state'} eq "s" ) ) {
+ confess( "A transition of the state '$state' ".
+ "must have a target state." ) ;
+ }
+ if ( ! exists $_[0]{$trans->{'state'}} ) {
+ confess( "The transition state '".
+ $trans->{'state'}.
+ "' from '$state' was not found." ) ;
+ }
+ # Search for the default transition
+ if ( ! $trans->{'pattern'} ) {
+ if ( $default ) {
+ confess( "More than once default transition ".
+ "for the transition '$state'." ) ;
+ }
+ $default = 1 ;
+ $trans->{'pattern'} = '.' ;
+ }
+ elsif ( ! is_valid_regex( $trans->{'pattern'} ) ) {
+ confess( "The regular expression '".
+ $trans->{'pattern'}.
+ "' is not well-formed." ) ;
+ }
+ }
+ # Copies the state
+ @{$self->{'SM_STATES'}{$state}} = @{$list} ;
+ }
+
+ # Sets the initial state
+ if ( exists $self->{'SM_STATES'}{$_[1]} ) {
+ $self->{'SM_INITIAL_STATE'} = $_[1] ;
+ $self->{'SM_CURRENT_STATE'} = $_[1] ;
+ }
+ else {
+ confess( "The initial state '$_[1]' is not defined." ) ;
+ }
+
+ # Sets the final states
+ $self->{'SM_FINAL_STATES'} = [] ;
+ foreach my $state ( @{$_[2]} ) {
+ if ( exists $self->{'SM_STATES'}{$state} ) {
+ push( @{$self->{'SM_FINAL_STATES'}}, $state ) ;
+ }
+ else {
+ confess( "The final state '$state' is not defined." ) ;
+ }
+ }
+ if ( isemptyarray( $self->{'SM_FINAL_STATES'} ) ) {
+ confess( "No final state defined." ) ;
+ }
+ }
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Getters / Setters
+#
+#------------------------------------------------------
+
+=pod
+
+=item * getcurrentstate()
+
+Replies the name of the current state of this
+machine.
+
+=cut
+sub getcurrentstate() : method {
+ my $self = shift ;
+ return $self->{'SM_CURRENT_STATE'} ;
+}
+
+=pod
+
+=item * isfinalstate()
+
+Replies the machine is inside a final state.
+
+=cut
+sub isfinalstate() : method {
+ my $self = shift ;
+ return strinarray( $self->{'SM_CURRENT_STATE'},
+ $self->{'SM_FINAL_STATES'} ) ;
+}
+
+=pod
+
+=item * resetstatemachine()
+
+Forces the state of this machine to the initial
+state.
+
+=cut
+sub resetstatemachine() : method {
+ my $self = shift ;
+ $self->{'SM_CURRENT_STATE'} = $self->{'SM_INITIAL_STATE'} ;
+ $self->{'SM_PREVIOUS_TOKEN'} = "" ;
+}
+
+#------------------------------------------------------
+#
+# State changement functions
+#
+#------------------------------------------------------
+
+=pod
+
+=item * changestatefrom()
+
+This method permits to select the new state according to
+the specified string and to the current state.
+The state transitions are defined when initializing.
+This method calls the callback function specified
+to the constructor, or (if not exists) calls the
+class methods transition_callback_XXX_YYY() and
+state_callback_YYY(), where XXX is the name of
+the old state, and YYY is the name of the new state.
+
+This method replies the rest of the specified
+parameter that is not eaten.
+
+Takes 1 arg:
+
+=over
+
+=item * token (string)
+
+is eaten to determine the new state.
+
+=back
+
+=item * transition_callback_XXX_YYY()
+
+This method is called each time a transition
+from the state XXX to the state YYY was
+encountered.
+Takes 1 arg:
+
+=over
+
+=item * token (string)
+
+is the last recognized token.
+
+=back
+
+=item * state_callback_YYY()
+
+This method is called each time the machine
+arrived inside a state (except for the
+initial state).
+Takes 1 arg:
+
+=over
+
+=item * token (string)
+
+is the last recognized token.
+
+=back
+
+=cut
+sub changestatefrom($) : method {
+ my $self = shift ;
+ my $input = $_[0] || '' ;
+
+ # Searches the max token matching
+ my $trans = $self->_searchtransition( $input, 0 ) ;
+
+ # Treats the translation matching
+ if ( ! isemptyhash( $trans ) ) {
+ my ($token,$rest) ;
+ if ( $trans->{'caseinsensitive'} ) {
+ $input =~ /^($trans->{'pattern'})(.*)$/si ;
+ ($token,$rest) = ($1,$2) ;
+ }
+ else {
+ $input =~ /^($trans->{'pattern'})(.*)$/s ;
+ ($token,$rest) = ($1,$2) ;
+ }
+
+ my $oldstate = $self->{'SM_CURRENT_STATE'} ;
+ $self->{'SM_CURRENT_STATE'} = $trans->{'state'} ;
+ $input = $rest ;
+
+ my $for_event = undef ;
+ if ( ( $trans->{'merge'} ) &&
+ ( $trans->{'splitmerging'} ) ) {
+ # Generates an transition event
+ # and merges the current token
+ $for_event = $self->{'SM_PREVIOUS_TOKEN'} ;
+ $self->{'SM_PREVIOUS_TOKEN'} = $token ;
+ }
+ elsif ( ( $trans->{'merge'} ) &&
+ ( ! $trans->{'splitmerging'} ) ) {
+ # Merges the current token
+ $self->{'SM_PREVIOUS_TOKEN'} .= $token ;
+ }
+ else {
+ # Does not merged the current token
+ $for_event = $self->{'SM_PREVIOUS_TOKEN'} . $token ;
+ $self->{'SM_PREVIOUS_TOKEN'} = "" ;
+ }
+
+ if ( defined $for_event ) {
+ $self->_callback( $for_event,
+ $oldstate,
+ $trans ) ;
+ }
+ }
+ elsif ( $self->can('backend_error_function') ) {
+ $self->backend_error_function( "Syntax error: unexpected character sequence \"".
+ tohumanreadable("$input").
+ "\"\n(unable to find a transition from ".
+ "the state '".
+ $self->{'SM_CURRENT_STATE'}.
+ "')." ) ;
+ exit(1) ;
+ }
+ else {
+ confess( "Syntax error: unexpected character sequence \"".
+ tohumanreadable("$input").
+ "\"\n(unable to find a transition from ".
+ "the state '".
+ $self->{'SM_CURRENT_STATE'}.
+ "')." ) ;
+ }
+ return $input ;
+}
+
+=pod
+
+=item * changestateforEOF()
+
+This method permits to select the new state according to
+an EOF and to the current state.
+The state transitions are defined when initializing.
+This method calls the class method
+EOF_callback_function() (only if no transition with
+the pattern '$EOF' was found from the current state).
+
+=item * EOF_callback_function()
+
+The methid is called each time the EOF was encountered
+and a transition with pattern '$EOF' is not found from
+the current state.
+
+=over
+
+=item * token (string)
+
+is the token which is not already eaten by the machine.
+
+=back
+
+=cut
+sub changestateforEOF() : method {
+ my $self = shift ;
+
+ # Calls the callback functions
+ # if a token was not treated
+
+ my $trans = $self->_searchtransition( "", 1 ) ;
+ if ( ! isemptyhash( $trans ) ) {
+ my $oldstate = $self->{'SM_CURRENT_STATE'} ;
+ $self->{'SM_CURRENT_STATE'} = $trans->{'state'} ;
+ $self->_callback( $self->{'SM_PREVIOUS_CONTENT'},
+ $oldstate,
+ $trans ) ;
+ }
+ else {
+ if ( Bib2HTML::General::Verbose::currentlevel() >= 4 ) {
+ my $verbstr = join( '',
+ "\t\ttoken = '",
+ tohumanreadable($self->{'SM_PREVIOUS_TOKEN'}),
+ "'" ) ;
+ $verbstr .= ", when EOF in '".$self->{'SM_CURRENT_STATE'}."'" ;
+ Bib2HTML::General::Verbose::verb( "$verbstr.", 4 ) ;
+ }
+ my $reffunc = $self->can( "EOF_callback_function" ) ;
+ if ( $reffunc ) {
+ $self->$reffunc( $self->{'SM_PREVIOUS_TOKEN'} ) ;
+ }
+ }
+}
+
+=pod
+
+=item * _callback()
+
+Calls the callback functions.
+Takes 3 args:
+
+=over
+
+=item * token (string)
+
+is the token to pass to the callback functions.
+
+=item * old_state (string)
+
+is the name of the state before the transition
+(the name of the state after the transition is
+stored inside $self->{'SM_CURRENT_STATE'}).
+
+=item * transition (hash ref)
+
+is the transition choosen.
+
+=back
+
+=cut
+sub _callback($$$) : method {
+ my $self = shift ;
+ my $token = $_[0] || '' ;
+ my $oldstate = $_[1] || confess( 'you must supply the old state' ) ;
+ if ( Bib2HTML::General::Verbose::currentlevel() >= 4 ) {
+ my $verbstr = join( '',
+ "\t\ttoken = '",
+ tohumanreadable($token),
+ "'" ) ;
+ if ( $self->{'SM_CURRENT_STATE'} eq $oldstate ) {
+ $verbstr .= ", in state '".tohumanreadable($oldstate)."'" ;
+ }
+ else {
+ $verbstr .= join( '',
+ ", transition: '",
+ tohumanreadable($oldstate),
+ "' -> '",
+ tohumanreadable($self->{'SM_CURRENT_STATE'}),
+ "'" ) ;
+ }
+ Bib2HTML::General::Verbose::verb( "$verbstr.", 4 ) ;
+ }
+
+ if ( ishash( $_[2] ) ) {
+ if ( ( exists $_[2]->{'callback'} ) &&
+ ( my $func = $self->can($_[2]->{'callback'}) ) ) {
+ $self->$func( $token, $oldstate ) ;
+ }
+ else {
+ my $reffunc = $self->can( "transition_callback_".
+ $oldstate."_".
+ $self->{'SM_CURRENT_STATE'} ) ;
+ if ( $reffunc ) {
+ $self->$reffunc( $token ) ;
+ }
+ $reffunc = $self->can( "state_callback_".
+ $self->{'SM_CURRENT_STATE'} ) ;
+ if ( $reffunc ) {
+ $self->$reffunc( $token, $oldstate ) ;
+ }
+ }
+ }
+}
+
+=pod
+
+=item * _searchtransition()
+
+Search a valid transition
+Takes 2 args:
+
+=over
+
+=item * input (string)
+
+is the content of the string to scan.
+
+=item * eof (boolean)
+
+is true if an EOF was encountered. In this
+case, the I<input> will be ignored.
+
+=back
+
+=cut
+sub _searchtransition($$) : method {
+ my $self = shift ;
+ my $input = $_[0] || '' ;
+ my $eof = $_[1] || 0 ;
+ # Searches the max token matching
+ my $maxlength = 0 ;
+ my $trans = {} ;
+ my $recognizedtoken = "" ;
+ foreach my $t (@{$self->{'SM_STATES'}{$self->{'SM_CURRENT_STATE'}}}) {
+ if ( ( ( $eof ) &&
+ ( $input eq '$EOF' ) ) ||
+ ( ( $t->{'caseinsensitive'} ) &&
+ ( $input =~ /^($t->{'pattern'})/si ) ) ||
+ ( ( ! $t->{'caseinsensitive'} ) &&
+ ( $input =~ /^($t->{'pattern'})/s ) ) ) {
+ my $token = $1 ;
+ if ( length($token) > $maxlength ) {
+ $maxlength = length($token) ;
+ $trans = $t ;
+ $recognizedtoken = $token ;
+ }
+ }
+ }
+ if ( ( $recognizedtoken ) && ( Bib2HTML::General::Verbose::currentlevel() >= 5 ) ) {
+ Bib2HTML::General::Verbose::verb( join( '',
+ "\t\tnext transition:\n\t\t\tfrom: ",
+ $self->{'SM_CURRENT_STATE'},
+ "\n\t\t\tto: ",
+ $trans->{'state'},
+ "\n\t\t\tpattern: /",
+ $trans->{'pattern'},
+ "/\n\t\t\ttoken: '",
+ $recognizedtoken,
+ "'\n"),
+ 5 ) ;
+ }
+ return $trans ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland <galland@arakhne.org>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Release.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Release.pm
new file mode 100644
index 0000000000..0c69e78772
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Release.pm
@@ -0,0 +1,89 @@
+# Copyright (C) 2002-09 Stephane Galland <galland@arakhne.org>
+# Copyright (C) 2011 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+package Bib2HTML::Release;
+@ISA = ('Exporter');
+@EXPORT = qw( &getVersionNumber &getVersionDate &getBugReportURL
+ &getAuthorName &getAuthorEmail &getMainURL
+ &getContributors ) ;
+@EXPORT_OK = qw();
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+my $VERSION = "6.7" ;
+
+#------------------------------------------------------
+#
+# DEFINITIONS
+#
+#------------------------------------------------------
+
+my $BIB2HTML_VERSION = $VERSION ;
+my $BIB2HTML_DATE = '2011/07/31' ;
+my $BIB2HTML_BUG_URL = 'mailto:bugreport@arakhne.org' ;
+my $BIB2HTML_AUTHOR = 'Stephane GALLAND' ;
+my $BIB2HTML_AUTHOR_EMAIL = 'galland@arakhne.org' ;
+my $BIB2HTML_URL = 'http://www.arakhne.org/bib2ml/' ;
+my %BIB2HTML_CONTRIBS = ( 'zinser@zinser.no-ip.info' => "Martin P.J. ZINSER",
+ 'preining@logic.at' => "Norbert PREINING",
+ 'sebastian.rodriguez@utbm.fr' => "Sebastian RODRIGUEZ",
+ 'michail@mpi-sb.mpg.de' => "Dimitris MICHAIL",
+ 'joao.lourenco@di.fct.unl.pt' => "Joao LOURENCO",
+ 'paolini@di.unito.it' => "Luca PAOLINI",
+ 'cri@linux.it' => "Cristian RIGAMONTI",
+ 'loew@mathematik.tu-darmstadt.de' => "Tobias LOEW",
+ 'loew@mathematik.tu-darmstadt.de' => "Tobias LOEW",
+ 'gasper.jaklic@fmf.uni-lj.si' => "Gasper JAKLIC",
+ 'olivier.hugues@gmail.com' => "Olivier HUGUES",
+ ) ;
+
+#------------------------------------------------------
+#
+# Functions
+#
+#------------------------------------------------------
+
+sub getVersionNumber() {
+ return $BIB2HTML_VERSION ;
+}
+
+sub getVersionDate() {
+ return $BIB2HTML_DATE ;
+}
+
+sub getBugReportURL() {
+ return $BIB2HTML_BUG_URL ;
+}
+
+sub getAuthorName() {
+ return $BIB2HTML_AUTHOR ;
+}
+
+sub getAuthorEmail() {
+ return $BIB2HTML_AUTHOR_EMAIL ;
+}
+
+sub getMainURL() {
+ return $BIB2HTML_URL ;
+}
+
+sub getContributors() {
+ return %BIB2HTML_CONTRIBS ;
+}
+
+1;
+__END__
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXEntry.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXEntry.pm
new file mode 100644
index 0000000000..03711b69fa
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXEntry.pm
@@ -0,0 +1,498 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Translator::BibTeXEntry - An BibTeX entry manager
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Translator::BibTeXEntry ;
+
+my $gen = Bib2HTML::Translator::BibTeXEntry->new() ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Translator::BibTeXEntry is a Perl module, which parses
+the names according to the BibTeX format and build a BibTeX
+bibliographical reference.
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To create a parser, say something like this:
+
+ use Bib2HTML::Translator::BibTeXEntry;
+
+ my $parser = Bib2HTML::Translator::BibTeXEntry->new() ;
+
+...or something similar.
+
+=cut
+
+package Bib2HTML::Translator::BibTeXEntry;
+
+@ISA = ('Exporter');
+@EXPORT = qw(bibtex_ignore_field_parsing);
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::HTML ;
+use Bib2HTML::Translator::BibTeXName ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the parser
+my $VERSION = "3.1" ;
+
+# List of ignore field for the parsing
+my @IGNORE_PARSING_FOR_FIELDS = ( 'localfile', 'url', 'pdf',
+ ) ;
+
+# List of ignore field for the parsing
+my @IGNORE_ENTRY_EXPORT_FOR_FIELDS = ( 'localfile', 'url', 'pdf',
+ 'domain', 'nddomain', 'rddomain',
+ 'abstract', 'keywords',
+ ) ;
+
+# Citation label database
+my %CITATION_LABEL_DATABASE = () ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ }
+ else {
+ $self = { } ;
+ }
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Citation
+#
+#------------------------------------------------------
+
+=pod
+
+=item * citation_label()
+
+Replies the citation label of the specified entry.
+Takes 1 arg:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * entry (hash)
+
+is the entry for which creates an entry.
+
+=back
+
+=cut
+sub citation_label($$) : method {
+ my $self = shift ;
+ my $key = $_[0] || confess( 'you must supply the key' ) ;
+ my $entry = $_[1] || confess( 'you must supply the entry data' ) ;
+ if ( ( ! exists $CITATION_LABEL_DATABASE{$key} ) ||
+ ( ! $CITATION_LABEL_DATABASE{$key} ) ) {
+ my $bibtex = new Bib2HTML::Translator::BibTeXName() ;
+ my @authors ;
+ if ( $entry->{'fields'}{'author'} ) {
+ @authors = $bibtex->splitnames( $entry->{'fields'}{'author'} ) ;
+ }
+ else {
+ @authors = $bibtex->splitnames( $entry->{'fields'}{'editor'} ) ;
+ }
+ my $label ;
+ if ( @authors ) {
+ my $count = 0 ;
+ foreach my $author ( @authors ) {
+ if ( $author->{'last'} ) {
+ if ($count<3) {
+ $label .= html_uc( html_substr( $author->{'last'}, 0, 1 ) ) ;
+ }
+ $count ++ ;
+ }
+ }
+ if ( $count <= 1 ) {
+ $label = html_ucfirst(html_lc(html_substr($authors[0]->{'last'}, 0, 3))) ;
+ }
+ else {
+ $label .= "+" ;
+ }
+ if ( $entry->{'fields'}{'year'} ) {
+ $label .= substr($entry->{'fields'}{'year'},-2) ;
+ }
+ }
+ else {
+ $label = 'unk' ;
+ if ( $entry->{'fields'}{'year'} ) {
+ $label .= substr($entry->{'fields'}{'year'},-2) ;
+ }
+ }
+ my $count = 0 ;
+ my $lbl = $label ;
+ while ( valueinhash( $lbl, \%CITATION_LABEL_DATABASE ) ) {
+ $count ++ ;
+ $lbl = $label . integer2alphabetic( $count ) ;
+ }
+ $CITATION_LABEL_DATABASE{$key} = $lbl ;
+ }
+ return $CITATION_LABEL_DATABASE{$key} ;
+}
+
+=pod
+
+=item * save_citation_label()
+
+Replies the citation label of the specified entry.
+Takes 1 arg:
+
+=over
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * entry (hash)
+
+is the entry for which creates an entry.
+
+=back
+
+=cut
+sub save_citation_label($$) : method {
+ my $self = shift ;
+ my $key = $_[0] || confess( 'you must supply the key' ) ;
+ if ( ( $_[1] ) &&
+ ( ! $CITATION_LABEL_DATABASE{$key} ) ) {
+ $CITATION_LABEL_DATABASE{$key} = $_[1] ;
+ }
+}
+
+=pod
+
+=item * bibtex_ignore_field_parsing()
+
+Replies if the specified field could be parsed
+Takes 1 arg:
+
+=over
+
+=item * field (string)
+
+is the name of the field.
+
+=back
+
+=cut
+sub bibtex_ignore_field_parsing($) {
+ my $field = $_[0] || confess( 'you must supply the field name' ) ;
+ return ( strinarray($field,\@IGNORE_PARSING_FOR_FIELDS) ) ;
+}
+
+=pod
+
+=item * bibtex_ignore_field_in_export()
+
+Replies if the specified field must be ignored during export
+Takes 1 arg:
+
+=over
+
+=item * field (string)
+
+is the name of the field.
+
+=back
+
+=cut
+sub bibtex_ignore_field_in_export($) {
+ my $field = $_[0] || confess( 'you must supply the field name' ) ;
+ return (( $field =~ /^opt/i) ||
+ ( strinarray($field,\@IGNORE_ENTRY_EXPORT_FOR_FIELDS) )) ;
+}
+
+=pod
+
+=item * bibtex_build_entry()
+
+Replies a string which corresponds to the BibTeX source
+code for the specified parameters.
+Takes 4 args:
+
+=over
+
+=item * type (string)
+
+is the type of the entry.
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * fields (hash)
+
+is the list of fields.
+
+=item * constants (hash)
+
+is the list of constants.
+
+=back
+
+=cut
+sub bibtex_build_entry($$\%\%) {
+ my $self = shift ;
+ return '' unless ($_[0]&&$_[1]) ;
+ my $code = join('',
+ "@",
+ $_[0],
+ "{",
+ $_[1],
+ ",\n" ) ;
+ while ( my ($field,$value) = each(%{$_[2]}) ) {
+ if ( $field ) {
+ $code .= " $field = " ;
+ if ( isarray($value) ) {
+ $code .= "{".$self->expand_bibtex_vars($value,$_[3])."}" ;
+ }
+ else {
+ $code .= "$value" ;
+ }
+ $code .= ",\n" ;
+ }
+ }
+ $code .= "}" ;
+ return $code ;
+}
+
+=pod
+
+=item * bibtex_build_entry_html()
+
+Replies an HTML string which corresponds to the BibTeX source
+code for the specified parameters.
+Takes 5 args:
+
+=over
+
+=item * type (string)
+
+is the type of the entry.
+
+=item * key (string)
+
+is the key of the entry.
+
+=item * fields (hash)
+
+is the list of fields.
+
+=item * constants (hash)
+
+is the list of constants.
+
+=item * page_width (integer)
+
+is the size of the page. It is used to split the
+lines (default value is 80).
+
+=back
+
+=cut
+sub bibtex_build_entry_html($$\%\%$) {
+ my $self = shift ;
+ return '' unless ($_[0]&&$_[1]) ;
+ my $page_width = ((($_[4])&&($_[4]>0))?$_[4]:80) ;
+ my $code = join('',
+ "@",
+ $_[0],
+ "{",
+ $_[1],
+ ",\n" ) ;
+ while ( my ($field,$value) = each(%{$_[2]}) ) {
+ if (($field)&&(!bibtex_ignore_field_in_export($field))) {
+ my $fldval = " $field = " ;
+ my $indent = length("$fldval") ;
+ if ( isarray($value) ) {
+ $fldval .= "{".$self->expand_bibtex_vars($value,$_[3])."}" ;
+ $indent ++ ;
+ }
+ else {
+ $fldval .= "$value" ;
+ $indent ++ if ( $value =~ /^\{.*\}$/ ) ;
+ }
+ $fldval .= "," ;
+ if (bibtex_ignore_field_parsing("$field")) {
+ $code .= "$fldval" ;
+ }
+ else {
+ $code .= splittocolumn("$fldval",$page_width,$indent, 2) ;
+ }
+ $code .= "\n" ;
+ }
+ }
+ $code .= "}" ;
+ return $code ;
+}
+
+=pod
+
+=item * expand_bibtex_vars()
+
+Does the TeX preprocessing which permits to
+replace the constants (@STRING) by there values.
+The parameter could be a sting or an array in
+case the BibTeX merging operator was used to
+build the value.
+Takes 2 args:
+
+=over
+
+=item * tex (string or array)
+
+is the tex expression to evaluate
+
+=item * constants (hash)
+
+is the list of constants.
+
+=back
+
+=cut
+sub expand_bibtex_vars($\%) {
+ my $self = shift ;
+ if ( $_[0] ) {
+
+ if ( isarray($_[0]) ) {
+
+ # Treats the case of the BibTeX merging operator
+ my @text = () ;
+ foreach my $elt (@{$_[0]}) {
+ push @text, $self->expand_bibtex_vars($elt,$_[1]) ;
+ }
+ return join( '', @text) ;
+
+ }
+ else {
+
+ # Treat "standard" definition
+ return $self->__expand_bibtex_vars($_[0],$_[1]) ;
+
+ }
+
+ }
+ return '' ;
+}
+
+=pod
+
+=item * __expand_bibtex_vars()
+
+Does the TeX preprocessing which permits to
+replace the constants (@STRING) by there values.
+Takes 2 args:
+
+=over
+
+=item * tex (string)
+
+is the tex expression to evaluate
+
+=item * constants (hash)
+
+is the list of constants.
+
+=back
+
+=cut
+sub __expand_bibtex_vars($) : method {
+ my $self = shift ;
+
+ my $tex = $_[0] || confess( 'you must supply a TeX expression' ) ;
+
+ return $1 if ( $tex =~ /^{(.*)}$/ ) ;
+
+ my $lctex = lc($tex) ;
+ trim $lctex ;
+
+ return $tex
+ unless ( exists $_[1]->{$lctex} ) ;
+
+ my $lcval = lc($_[1]->{$lctex}{'text'}) ;
+ trim $lcval ;
+
+ if ( $lcval eq $lctex ) {
+ return $_[1]->{$lctex}{'text'} ;
+ }
+ else {
+ return $self->expand_bibtex_vars($_[1]->{$lctex}{'text'},$_[1]) ;
+ }
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXName.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXName.pm
new file mode 100644
index 0000000000..0a36f5b133
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/BibTeXName.pm
@@ -0,0 +1,931 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Translator::BibTeXName - An parser for BibTeX names
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Translator::BibTeXName ;
+
+my $gen = Bib2HTML::Translator::BibTeXName->new() ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Translator::BibTeXName is a Perl module, which parses
+the names according to the BibTeX format
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To create a parser, say something like this:
+
+ use Bib2HTML::Translator::BibTeXName;
+
+ my $parser = Bib2HTML::Translator::BibTeXName->new() ;
+
+...or something similar.
+
+=cut
+
+package Bib2HTML::Translator::BibTeXName;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::HTML ;
+use Bib2HTML::General::Error ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the parser
+my $VERSION = "2.2" ;
+
+# The string for the junior part of a name
+my @JUNIOR_PARTS = ( 'junior', 'jr.', 'jr', 'senior', 'sen.', 'sen',
+ 'esq.', 'esq', 'phd.', 'phd' ) ;
+
+# This is the label generated for the "et al."
+my $ETAL_STRING = "<i>et&nbsp;al.</i>" ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ }
+ else {
+ $self = { } ;
+ }
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Getters
+#
+#------------------------------------------------------
+
+=pod
+
+=item * countnames()
+
+Replies the quantity of names inside the specified string
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is the text to parse.
+
+=back
+
+=cut
+sub countnames($) : method {
+ my $self = shift ;
+ my @names = $self->splitnames($_[0]||'') ;
+ return int(@names) ;
+}
+
+=pod
+
+=item * samenames()
+
+Replies if the two names are the same.
+Takes 2 args:
+
+=over
+
+=item * name1 (hash)
+
+=item * name2 (hash)
+
+=back
+
+=cut
+sub samenames($$) : method {
+ my $self = shift ;
+ if ( $_[0]->{'et al'} || $_[0]->{'et al'} ) {
+ return 0 ;
+ }
+ my $n1 = $self->formatname($_[0],'l,i.') ;
+ my $n2 = $self->formatname($_[1],'l,i.') ;
+ $n1 =~ s/[ \t\n\r]+//g ;
+ $n2 =~ s/[ \t\n\r]+//g ;
+ return ( lc($n1) eq lc($n2) ) ;
+}
+
+=pod
+
+=item * isauthorin()
+
+Replies if the first parameter is a author which
+appears inside the second parameter.
+
+Takes 2 args:
+
+=over
+
+=item * author (hash)
+
+=item * authors (string)
+
+=back
+
+=cut
+sub isauthorin($$) : method {
+ my $self = shift ;
+ if ( $_[0]->{'et al'} || (!$_[1]) ) {
+ return 0 ;
+ }
+ my @names = $self->splitnames($_[1]) ;
+ foreach my $author (@names) {
+ if ( $self->samenames($_[0],$author) ) {
+ return 1 ;
+ }
+ }
+ return 0 ;
+}
+
+#------------------------------------------------------
+#
+# Formating API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * formatname()
+
+Replies a well-formated name
+Takes 2 args:
+
+=over
+
+=item * name (hash)
+
+is the components of the name to format
+
+=item * format (string)
+
+is the format of the name (composed by v l L f f. i i. j)
+
+=back
+
+=cut
+sub formatname($$) : method {
+ my $self = shift ;
+ confess( 'you must supply a name' ) unless (($_[0])&&(ishash($_[0]))) ;
+ confess( 'you must supply a valid format string' ) unless $_[1] ;
+
+ if ( $_[0]->{'et al'} ) {
+ return $ETAL_STRING ;
+ }
+ my @blocks = $self->_extract_blocks( $_[1] ) ;
+
+ my $name = '' ;
+ foreach my $part (@blocks) {
+ my $txt;
+ my $isa = isarray( $part );
+ if ( $isa ) {
+ $txt = join('',@{$part});
+ }
+ else {
+ $txt = $part;
+ }
+ if ($txt) {
+ $name .= $self->_formatname_scan_pattern($txt,$_[0],$isa) ;
+ }
+ }
+ return $name ;
+}
+
+# $_[0]: patterns
+# $_[1]: hash of the name's components
+# $_[2]: 1 if all the given patterns must be found
+sub _formatname_scan_pattern($$$) {
+ my $self = shift ;
+ confess( 'you must supply a name' ) unless (($_[1])&&(ishash($_[1]))) ;
+ my $pattern = $_[0] || '' ;
+ my $result = '' ;
+ my $foundall = 1 ;
+
+ while ( $pattern =~ /^([^a-zA-Z.]*)([a-zA-Z.]+)(.*)$/ ) {
+ ($result, my $str, $pattern) = ($result.$1, $2, $3) ;
+ if ( $str eq 'l' ) {
+ $foundall = ( $foundall && $_[1]->{'last'} ) ;
+ $result .= html_ucwords( $_[1]->{'last'} ) ;
+ }
+ elsif ( $str eq 'L' ) {
+ $foundall = ( $foundall && $_[1]->{'last'} ) ;
+ $result .= html_ucwords( $_[1]->{'last'} ) ;
+ }
+ elsif ( $str eq 'f' ) {
+ $foundall = ( $foundall && $_[1]->{'first'} ) ;
+ $result .= html_ucwords( $_[1]->{'first'} ) ;
+ }
+ elsif ( $str eq 'f.' ) {
+ $foundall = ( $foundall && $_[1]->{'first'} ) ;
+ $result .= html_ucwords( html_getinitiales( $_[1]->{'first'} ) ) ;
+ }
+ elsif ( $str eq 'i' ) {
+ my $ff = html_ucwords( $_[1]->{'first'} ) ;
+ if ($ff =~ /^[ \t\n\r]*([^ \t\n\r]+)/) {
+ $ff = $1 ;
+ }
+ else {
+ $ff = '' ;
+ }
+ $foundall = ( $foundall && $ff ) ;
+ $result .= $ff ;
+ }
+ elsif ( $str eq 'i.' ) {
+ my $ff = html_ucwords( html_getinitiales( $_[1]->{'first'} ) ) ;
+ if ($ff =~ /^[ \t\n\r]*([^ \t\n\r]+)/) {
+ $ff = $1 ;
+ }
+ else {
+ $ff = '' ;
+ }
+ $foundall = ( $foundall && $ff ) ;
+ $result .= $ff ;
+ }
+ elsif ( $str eq 'v' ) {
+ $foundall = ( $foundall && $_[1]->{'von'} ) ;
+ $result .= $_[1]->{'von'} ;
+ }
+ elsif ( $str eq 'j' ) {
+ $foundall = ( $foundall && $_[1]->{'jr'} ) ;
+ $result .= $_[1]->{'jr'} ;
+ }
+ else {
+ $result .= $str ;
+ }
+ }
+ if ( $pattern ) {
+ $result .= $pattern ;
+ }
+
+ if ( ( ! $_[2] ) || ( $foundall ) ) {
+ return $result ;
+ }
+ else {
+ return '' ;
+ }
+}
+
+=pod
+
+=item * formatnames()
+
+Replies well-formated names
+Takes 4 args:
+
+=over
+
+=item * names (hash)
+
+is the components of the name to format
+
+=item * formatname (string)
+
+is the format of one name (composed by the letters [vlfj.{}]+)
+
+=item * formatnames (string)
+
+is the format which permits to merge the names (composed by the letters [n{}]+)
+
+=item * count (optional integer)
+
+is the maximum number of names which must be put inside the result.
+
+=back
+
+=cut
+sub formatnames($$$) : method {
+ my $self = shift ;
+ return $self->formatnames_withurl($_[0], $_[1], $_[2], undef, $_[3], $_[4]) ;
+}
+
+=pod
+
+=item * formatnames_withurl()
+
+Replies well-formated names
+with a link to their list-of-papers page.
+Takes 4 args:
+
+=over
+
+=item * names (hash)
+
+is the components of the name to format
+
+=item * formatname (string)
+
+is the format of one name (composed by the letters [vlfj.{}]+)
+
+=item * formatnames (string)
+
+is the format which permits to merge the names (composed by the letters [n{}]+)
+
+=item * backend_object (AbstractGenertor object)
+
+is the pointer to the object to call for creating the URL.
+The called methid is: formatnames_url_backend.
+
+=item * count (optional integer)
+
+is the maximum number of names which must be put inside the result.
+
+=item * rootdir (optional string)
+
+=back
+
+=cut
+sub formatnames_withurl($$$$;$$) : method {
+ my $self = shift ;
+ return '' unless $_[0] ;
+ confess( 'you must supply a valid format string for a name' ) unless $_[1] ;
+ confess( 'you must supply a valid format string for all names' ) unless $_[2] ;
+ my $backend = $_[3] || undef ;
+ my $max = (($_[4])&&($_[4]>=-1)) ? $_[4] : 1 ;
+ my $rootdir = $_[5] || '' ;
+ my @authors = $self->splitnames( $_[0] ) ;
+
+ if ( $max <= 0 ) {
+ $max = int(@authors) ;
+ }
+
+ my @blocks = $self->_extract_blocks( $_[2] ) ;
+ my ($sep1,$sep2) = (join('',@{$blocks[1]}),
+ join('',@{$blocks[3]})) ;
+
+ my ($i,$names) = (0,'') ;
+ while ( ( $i <= $#authors ) && ( $i < $max ) ) {
+ my $name ;
+ if ( $authors[$i]{'et al'} ) {
+ $name = " ".$ETAL_STRING ;
+ }
+ else {
+ $name = $self->formatname( $authors[$i], $_[1] ) ;
+ # Add the url
+ if ($backend) {
+ $name = $backend->formatnames_url_backend($authors[$i], $name, $rootdir) ;
+ }
+ if ( $names ) {
+ $names .= ( $i == $#authors ) ? $sep1 : $sep2 ;
+ }
+ }
+ $names .= $name ;
+ $i ++ ;
+ }
+ if ( int(@authors) > $max ) {
+ $names .= " ".$ETAL_STRING ;
+ }
+ return $names ;
+}
+
+#------------------------------------------------------
+#
+# Extracting API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * splitnames()
+
+Splits the specified string into names.
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is the text to split
+
+=back
+
+=cut
+sub splitnames($) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my @names = () ;
+
+ # Support no-standard notation "et al"
+ if ( $text =~ /\s*et[ \t\r\n~]+al\.?\s*/g ) {
+ my $original = $text ;
+ $text =~ s/\s*et[ \t\r\n~]+al\.?\s*/ and others /g ;
+ $text =~ s/^\s+//m ;
+ $text =~ s/\s+$//m ;
+ Bib2HTML::General::Error::syswarm( "the string \"".$original."\" does not respect the BibTeX standard for author's names. ".
+ "Assume \"".$text."\"." ) ;
+ }
+
+ # Scan the authors to extract the brace blocks
+ my @blocks = $self->_extract_blocks($text) ;
+
+ # Split the top level blocks
+ for(my $i=0; $i<=$#blocks; $i++) {
+ if ( ! isarray( $blocks[$i] ) ) {
+ my @parts ;
+ if ( $blocks[$i] =~ /^\s*and\s*$/i ) {
+ @parts = ( '', '' ) ;
+ }
+ else {
+ @parts = split /(?<=\s)and(?=\s)/i, " ".$blocks[$i]." " ;
+ }
+ if ( ! isemptyarray( \@names ) ) {
+ $names[$#names] .= $parts[0] ;
+ for(my $j=1; $j<=$#parts; $j++) {
+ push @names, $parts[$j] ;
+ }
+ }
+ else {
+ for(my $j=0; $j<=$#parts; $j++) {
+ my $p = $parts[$j] ;
+ $p =~ s/^\s+//gm ;
+ $p =~ s/\s+$//gm ;
+ if ( $p ) {
+ push @names, $p ;
+ }
+ }
+ }
+ }
+ else {
+ if ( ! isemptyarray( \@names ) ) {
+ $names[$#names] .= join( '', @{$blocks[$i]} ) ;
+ }
+ else {
+ push @names, join( '', @{$blocks[$i]} ) ;
+ }
+ }
+ }
+
+ # Parse the names to extract the components
+ my @newnames = () ;
+ for(my $i=0; $i<=$#names; $i++) {
+ my $r = $self->scan_name($names[$i]) ;
+
+ if ( isarray( $r ) ) {
+ foreach my $n (@{$r}) {
+ push @newnames, $n ;
+ }
+ }
+ else {
+ push @newnames, $r ;
+ }
+ }
+
+ return @newnames ;
+}
+
+=pod
+
+=item * scan_name()
+
+Scans a single name to extract there components.
+The recognized formats are :
+First [von] Last [jr]
+[von] Last, First [jr]
+[von] Last, jr, First
+
+Takes 1 arg:
+
+=over
+
+=item * name (string)
+
+is the name to scan
+
+=back
+
+=cut
+sub scan_name($) : method {
+ my $self = shift ;
+ my $name = $_[0] || '' ;
+ my ($first,$von,$last,$jr) = ('','','','') ;
+ if ( $name =~ /^\s*others?\s*$/i ) {
+ #
+ # et al.
+ #
+ return { 'first' => $first,
+ 'von' => $von,
+ 'last' => $last,
+ 'jr' => $jr,
+ 'et al' => 1,
+ } ;
+ }
+ elsif ( $name =~ /^([^,]*),([^,]*),(.*)$/ ) {
+ my ($p1,$p2,$p3) = ($1,$2,$3) ;
+ if ( $self->_is_junior( $p2 ) ) {
+ #
+ # [von] Last, jr, First
+ #
+ ($von,$last,$jr,$first) = $self->_scanname_vl_j_f( $p1,$p2,$p3 ) ;
+ }
+ else {
+ #
+ # name, name, ...
+ #
+ Bib2HTML::General::Error::syswarm( "BibTeX author's names are expressed with a quiet ambigous syntax: ".$name.". Assume ',' as names' separator." ) ;
+ my $subnames = [] ;
+ foreach my $subname ( split(/\s*,\s*/, $name ) ) {
+ ($von,$last,$jr,$first) = $self->_scanname_fvlj( $subname ) ;
+ $first =~ s/^\s+// ;
+ $first =~ s/\s+$// ;
+ $last =~ s/^\s+// ;
+ $last =~ s/\s+$// ;
+ $von =~ s/^\s+// ;
+ $von =~ s/\s+$// ;
+ $jr =~ s/^\s+// ;
+ $jr =~ s/\s+$// ;
+ push @{$subnames}, { 'first' => html_ucfirst($first),
+ 'von' => lc($von),
+ 'last' => html_ucfirst($last),
+ 'jr' => $jr,
+ 'et al' => 0,
+ } ;
+ }
+ return $subnames ;
+ }
+ }
+ elsif ( $name =~ /^([^,]*),(.*)$/ ) {
+ my ($p1,$p2) = ($1,$2) ;
+ if ( $self->_is_junior( $p2 ) ) {
+ #
+ # First [von] Last, jr
+ #
+ ($von,$last,$jr,$first) = $self->_scanname_fvl_j( $p1,$p2 );
+ }
+ else {
+ #
+ # [von] Last, First [jr]
+ #
+ ($von,$last,$jr,$first) = $self->_scanname_vl_fj( $p1,$p2 ) ;
+ }
+
+ }
+ elsif ( $name !~ /,/ ) {
+ #
+ # First [von] Last [jr]
+ #
+ ($von,$last,$jr,$first) = $self->_scanname_fvlj( $name ) ;
+ }
+ else {
+ Bib2HTML::General::syserr( "unable to recognize a pattern for the bibTeX name: $name" ) ;
+ }
+ $first =~ s/^\s+// ;
+ $first =~ s/\s+$// ;
+ $last =~ s/^\s+// ;
+ $last =~ s/\s+$// ;
+ $von =~ s/^\s+// ;
+ $von =~ s/\s+$// ;
+ $jr =~ s/^\s+// ;
+ $jr =~ s/\s+$// ;
+ return { 'first' => html_ucfirst($first),
+ 'von' => lc($von),
+ 'last' => html_ucfirst($last),
+ 'jr' => $jr,
+ 'et al' => 0,
+ } ;
+}
+
+=pod
+
+=item * _scanname_fvlj()
+
+Name pattern: [von] Last, First [jr]
+
+=cut
+sub _scanname_vl_fj($$) {
+ my $self = shift ;
+ my ($p1,$p2)=($_[0],$_[1]) ;
+ $p1 =~ s/^\s+//mg ;
+ $p1 =~ s/\s+$//mg ;
+ $p2 =~ s/^\s+//mg ;
+ $p2 =~ s/\s+$//mg ;
+ my ($von,$last,$jr,$first)=('','','','') ;
+ $first = $p2 ;
+ if ( $p2 =~ /^(.*)\s+([a-zA-Z.]+)$/ ) {
+ my ($p3,$p4)=($1,$2) ;
+ $p3 =~ s/^\s+//mg ;
+ $p3 =~ s/\s+$//mg ;
+ $p4 =~ s/^\s+//mg ;
+ $p4 =~ s/\s+$//mg ;
+ if ( $self->_is_junior($p4) ) {
+ $first = $p3 ;
+ $jr = $p4 ;
+ }
+ }
+ ($von,$last) = $self->_get_first_majword( $p1 ) ;
+ return ($von,$last,$jr,$first) ;
+}
+
+=pod
+
+=item * _scanname_fvl_j()
+
+Name pattern: First [von] Last, jr
+
+=cut
+sub _scanname_fvl_j($$) {
+ my $self = shift ;
+ my ($name,$jr) = ($_[0],$_[1]) ;
+ $name =~ s/^\s+//mg ;
+ $name =~ s/\s+$//mg ;
+ $jr =~ s/^\s+//mg ;
+ $jr =~ s/\s+$//mg ;
+ my ($von,$last,undef,$first)=$self->_scanname_fvlj($name) ;
+ return ($von,$last,$jr,$first) ;
+}
+
+=pod
+
+=item * _scanname_fvlj()
+
+Name pattern: First [von] Last [jr]
+
+=cut
+sub _scanname_fvlj($) {
+ my $self = shift ;
+ my $name = $_[0] ;
+ $name =~ s/^\s+//mg ;
+ $name =~ s/\s+$//mg ;
+ my ($von,$last,$jr,$first)=('','','','') ;
+ ($first,my $reste) = $self->_get_majwords($name) ;
+ # If the reste variable is empty (ie no von found)
+ # It means that the last upercase word must
+ # be the lastname
+ if ( ! $reste ) {
+ if ( $name =~ /^(.*?)\s+([^\s]+)\s*$/ ) {
+ ($first,$reste) = ($1,$2) ;
+ }
+ else {
+ ($first,$reste) = ('',$name) ;
+ }
+ }
+ $first =~ s/^\s+//mg ;
+ $first =~ s/\s+$//mg ;
+ $reste =~ s/^\s+//mg ;
+ $reste =~ s/\s+$//mg ;
+ ($von,$reste) = $self->_get_first_majword($reste) ;
+ $von =~ s/^\s+//mg ;
+ $von =~ s/\s+$//mg ;
+ $reste =~ s/^\s+//mg ;
+ $reste =~ s/\s+$//mg ;
+ if ( ( $reste =~ /^(.*)\s+([a-zA-Z.]+)$/ ) &&
+ ( $self->_is_junior($2) ) ) {
+ ($last,$jr) = ($1,$2) ;
+ }
+ else {
+ $last = $reste ;
+ }
+ return ($von,$last,$jr,$first) ;
+}
+
+=pod
+
+=item * _scanname_vl_j_f()
+
+Name pattern: [von] Last, jr, First
+
+=cut
+sub _scanname_vl_j_f($$$) {
+ my $self = shift ;
+ my ($p1,$p2,$p3) = ($_[0],$_[1],$_[2]) ;
+ $p1 =~ s/^\s+//mg ;
+ $p1 =~ s/\s+$//mg ;
+ $p2 =~ s/^\s+//mg ;
+ $p2 =~ s/\s+$//mg ;
+ $p3 =~ s/^\s+//mg ;
+ $p3 =~ s/\s+$//mg ;
+ my ($von,$last,$jr,$first)=('','',$p2,$p3) ;
+ ($von,$last) = $self->_get_first_majword( $p1 ) ;
+ return ($von,$last,$jr,$first) ;
+}
+
+=pod
+
+=item * _get_majwords()
+
+Replies all the maj words from the begining.
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub _get_majwords($) {
+ my $self = shift ;
+ return ('','') unless $_[0] ;
+ my @words = split(/\s+/, $_[0]) ;
+ my ($maj,$after) = ('','') ;
+ my $inmaj = 1 ;
+ foreach my $word (@words) {
+ if ( $word !~ /^&?[A-Z].*$/ ) {
+ $inmaj = 0 ;
+ }
+ if ( $inmaj ) {
+ $maj .= ($maj?' ':'').$word ;
+ }
+ else {
+ $after .= ($after?' ':'').$word ;
+ }
+ }
+ return ($maj,$after) ;
+}
+
+=pod
+
+=item * _get_first_majword()
+
+Replies the string that begins from the first word
+with first majuscule letter.
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub _get_first_majword($) {
+ my $self = shift ;
+ return ('','') unless $_[0] ;
+ my @words = split(/\s+/, $_[0] ) ;
+ my ($before,$after) = ('','') ;
+ my $found = 0 ;
+ foreach my $word (@words) {
+ if ( $word =~ /^&?[A-Z].*$/ ) {
+ $found = 1 ;
+ }
+ if ( $found ) {
+ $after .= ($after?' ':'').$word ;
+ }
+ else {
+ $before .= ($before?' ':'').$word ;
+ }
+ }
+ if ( ! $after ) {
+ return ('',$before) ;
+ }
+ else {
+ return ($before,$after) ;
+ }
+}
+
+=pod
+
+=item * _is_junior()
+
+Replies if the parameter is a string that corresponds
+to the junior part of a BibTeX name.
+
+=over
+
+=item * text (string)
+
+=back
+
+=cut
+sub _is_junior($) {
+ my $self = shift ;
+ my $jr = $_[0] ;
+ if ( $jr ) {
+ $jr =~ s/^\s+//mg ;
+ $jr =~ s/\s+$//mg ;
+ return ( ( strinarray( lc($jr), \@JUNIOR_PARTS ) ) ||
+ ( isnumber($jr) ) ) ;
+ }
+ else {
+ return $jr ;
+ }
+}
+
+=pod
+
+=item * _extract_blocks()
+
+Extracts the blocks from the specified string
+Takes 1 arg:
+
+=over
+
+=item * text (string)
+
+is the text to parse.
+
+=back
+
+=cut
+sub _extract_blocks($) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my @blocks = () ;
+ my $currentblock = "" ;
+ my $count = 0 ;
+ while ( $text =~ /^(.*?)((?:\\\{)|(?:\\\})|\{|\})(.*)$/ ) {
+ (my $before, my $sep, $text) = ($1,$2,$3) ;
+ $currentblock .= $before ;
+ if ( ( $sep eq '\\{' ) || ( $sep eq '\\}' ) ) {
+ $currentblock .= $sep ;
+ }
+ elsif ( $sep eq '{' ) {
+ if ( $count > 0 ) {
+ $currentblock .= $sep ;
+ }
+ else {
+ push @blocks, $currentblock ;
+ $currentblock = '' ;
+ }
+ $count ++ ;
+ }
+ elsif ( $sep eq '}' ) {
+ $count -- unless ($count <= 0) ;
+ if ( $count > 0 ) {
+ $currentblock .= $sep ;
+ }
+ else {
+ push @blocks, [ $currentblock ] ;
+ $currentblock = '' ;
+ }
+ }
+ else {
+ confess( "Invalid block: $sep\n" ) ;
+ }
+ }
+ if ( $text ) {
+ $currentblock .= $text ;
+ }
+ if ( $currentblock ) {
+ push @blocks, $currentblock ;
+ }
+ return @blocks ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/TeX.pm b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/TeX.pm
new file mode 100644
index 0000000000..31bf65068e
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/Bib2HTML/Translator/TeX.pm
@@ -0,0 +1,2603 @@
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+=pod
+
+=head1 NAME
+
+Bib2HTML::Translator::TeX - A translator from TeX to HTML
+
+=head1 SYNOPSYS
+
+use Bib2HTML::Translator::BibTeX ;
+
+my $gen = Bib2HTML::Translator::TeX->new( filename ) ;
+
+=head1 DESCRIPTION
+
+Bib2HTML::Translator::TeX is a Perl module, which translate a
+TeX string into an HTML string
+
+=head1 GETTING STARTED
+
+=head2 Initialization
+
+To create a parser, say something like this:
+
+ use Bib2HTML::Translator::TeX;
+
+ my $parser = Bib2HTML::Translator::TeX->new( 'toto.bib', '<math>', '</math>' ) ;
+
+...or something similar. Acceptable parameters to the constructor are:
+
+=over
+
+=item * filename (string)
+
+is the filename under parsing.
+
+=item * start_math (optional string)
+
+is the HTML balise which permits to start the math mode
+
+=item * stop_math (optional string)
+
+is the HTML balise which permits to stop the math mode
+
+=back
+
+=head1 METHOD DESCRIPTIONS
+
+This section contains only the methods in Parser.pm itself.
+
+=over
+
+=cut
+
+package Bib2HTML::Translator::TeX;
+
+@ISA = ('Exporter');
+@EXPORT = qw();
+@EXPORT_OK = qw( &addtrans_char &gettrans_char
+ &addtrans_cmd_noparam &addtrans_cmd
+ &addtrans_cmd_func &gettrans_cmd
+ &display_supported_commands );
+
+use strict;
+use vars qw(@ISA @EXPORT @EXPORT_OK $VERSION);
+use Exporter;
+use Carp ;
+
+use Bib2HTML::General::Misc ;
+use Bib2HTML::General::HTML ;
+use Bib2HTML::General::Error ;
+use Bib2HTML::General::Verbose ;
+use Bib2HTML::Translator::BibTeXEntry ;
+
+#------------------------------------------------------
+#
+# Global vars
+#
+#------------------------------------------------------
+
+# Version number of the parser
+my $VERSION = "3.0" ;
+
+###############################################################
+# This is the list of characters which will be automatically
+# and directly translatable into a HTML entity
+#
+my %TEX_HTML_CHAR_TRANS = ( '~' => '&nbsp;', #unsecable space
+ '£' => '&pound;', #pound sign
+ '¤' => '&curren;', #currency sign
+ '|' => '&brvbar', #broken bar = broken vertical bar
+ '§' => '&sect;', #section sign
+ '°' => '&deg;', #degree sign
+ '²' => '&sup2;', #superscript two = superscript digit two = squared
+ 'µ' => '&micro;', #micro sign
+ 'À' => '&Agrave;', #latin capital letter A with grave = latin capital letter A grave
+ 'Á' => '&Aacute;', #latin capital letter A with acute
+ 'Â' => '&Acirc;', #latin capital letter A with circumflex
+ 'Ã' => '&Atilde;', #latin capital letter A with tilde
+ 'Ä' => '&Auml;', #latin capital letter A with diaeresis
+ 'Å' => '&Aring;', #latin capital letter A with ring above = latin capital letter A ring
+ 'Æ' => '&AElig;', #latin capital letter AE = latin capital ligature AE
+ 'Ç' => '&Ccedil;', #latin capital letter C with cedilla
+ 'È' => '&Egrave;', #latin capital letter E with grave
+ 'É' => '&Eacute;', #latin capital letter E with acute
+ 'Ê' => '&Ecirc;', #latin capital letter E with circumflex
+ 'Ë' => '&Euml;', #latin capital letter E with diaeresis
+ 'Ì' => '&Igrave;', #latin capital letter I with grave
+ 'Í' => '&Iacute;', #latin capital letter I with acute
+ 'Î' => '&Icirc;', #latin capital letter I with circumflex
+ 'Ï' => '&Iuml;', #latin capital letter I with diaeresis
+ 'Ñ' => '&Ntilde;', #latin capital letter N with tilde
+ 'Ò' => '&Ograve;', #latin capital letter O with grave
+ 'Ó' => '&Oacute;', #latin capital letter O with acute
+ 'Ô' => '&Ocirc;', #latin capital letter O with circumflex
+ 'Õ' => '&Otilde;', #latin capital letter O with tilde
+ 'Ö' => '&Ouml;', #latin capital letter O with diaeresis
+ 'Ø' => '&Oslash;', #latin capital letter O with stroke = latin capital letter O slash
+ 'Ù' => '&Ugrave;', #latin capital letter U with grave
+ 'Ú' => '&Uacute;', #latin capital letter U with acute
+ 'Û' => '&Ucirc;', #latin capital letter U with circumflex
+ 'Ü' => '&Uuml;', #latin capital letter U with diaeresis
+ 'Ý' => '&Yacute;', #latin capital letter Y with acute
+ 'à' => '&agrave;', #latin small letter a with grave = latin small letter a grave
+ 'á' => '&aacute;', #latin small letter a with acute
+ 'â' => '&acirc;', #latin small letter a with circumflex
+ 'ã' => '&atilde;', #latin small letter a with tilde
+ 'ä' => '&auml;', #latin small letter a with diaeresis
+ 'å' => '&aring;', #latin small letter a with ring above = latin small letter a ring
+ 'æ' => '&aelig;', #latin small letter ae = latin small ligature ae
+ 'ç' => '&ccedil;', #latin small letter c with cedilla
+ 'è' => '&egrave;', #latin small letter e with grave
+ 'é' => '&eacute;', #latin small letter e with acute
+ 'ê' => '&ecirc;', #latin small letter e with circumflex
+ 'ë' => '&euml;', #latin small letter e with diaeresis
+ 'ì' => '&igrave;', #latin small letter i with grave
+ 'í' => '&iacute;', #latin small letter i with acute
+ 'î' => '&icirc;', #latin small letter i with circumflex
+ 'ï' => '&iuml;', #latin small letter i with diaeresis
+ 'ñ' => '&ntilde;', #latin small letter n with tilde
+ 'ò' => '&ograve;', #latin small letter o with grave
+ 'ó' => '&oacute;', #latin small letter o with acute
+ 'ô' => '&ocirc;', #latin small letter o with circumflex
+ 'õ' => '&otilde;', #latin small letter o with tilde
+ 'ö' => '&ouml;', #latin small letter o with diaeresis
+ 'ø' => '&oslash;', #latin small letter o with stroke = latin small letter o slash
+ 'ù' => '&ugrave;', #latin small letter u with grave
+ 'ú' => '&uacute;', #latin small letter u with acute
+ 'û' => '&ucirc;', #latin small letter u with circumflex
+ 'ü' => '&uuml;', #latin small letter u with diaeresis
+ 'ý' => '&yacute;', #latin small letter y with acute
+ 'ÿ' => '&yuml;', #latin small letter y with diaeresis
+ '"' => '&quot;', #quotation mark = APL quote
+ '^' => '&circ;', #modifier letter circumflex accent
+ '<' => '&lt;', #less-than sign
+ '>' => '&gt;', #greater-than sign
+ ) ;
+
+###############################################################
+# This is the list of text-mode commands.
+# The commands must respect one of the following formats:
+# 1) 'TeXCmdName' => "HTML code"
+# permits to translate the LaTeX command \TeXCmdName
+# into the specified "HTML code".
+# 2) 'TeXCmdName' => { 'params' => params
+# 'html' => "HTML code"
+# }
+# replaces the command \TeXCmdName by the specified
+# "HTML code". This last could contains a parameter
+# number (eg, #1 for the first, #2 for the second,
+# etc.) which will be replaced by the value
+# passed to the LaTeX command. The params specifies
+# the parameter prototype of the LaTeX command. It
+# must contains one (or more) of:
+# {} for a needed parameter
+# [d] for an optional parameter. d
+# is the default value given to this parameter
+# if it was not provided inside the LaTeX code
+# \\ for a LaTeX command name
+# ! indicates that the following sign ({} or[])
+# must not be interpreted by the LaTeX
+# translator. It must be used for verbatim
+# output
+# - to read the text until the end of the current
+# LaTeX context
+# 3) 'TeXCmdName' => { 'params' => params
+# 'latex' => "LaTeX code"
+# }
+# replaces the command \TeXCmdName by the specified
+# "LaTeX code". This last could contains a parameter
+# number (eg, #1 for the first, #2 for the second,
+# etc.) which will be replaced by the value
+# passed to the LaTeX command. The params specifies
+# the parameter prototype of the LaTeX command. It
+# must contains one (or more) of the macros defined
+# in the point 2).
+# 4) 'TeXCmdName' => { 'params' => params
+# 'func' => "callback_function_name"
+# }
+# replaces the command \TeXCmdName by the result of
+# the specified callback function. This callback
+# function must take, at least, 1 parameters:
+# the current line number. The parameters of the
+# LaTeX command will be passed to this callback
+# function after this line number.
+# Example: for \newcommand{\cmdname}[4][default]{code #2}
+# we implements the callback function:
+# sub texcommand_newcommand {
+# my $lineno = shift || 0 ;
+# my ($cmdname,$nb_params) =
+# ( $_[0], $_[1] || 0 ) ;
+# my ($default,$code) =
+# ($_[2] || '', $_[3] || '') ;
+# ...
+# return '' ;
+# }
+# The params specifies the parameter prototype of
+# the LaTeX command. It must contains one (or more)
+# of the macros defined in the point 2).
+# 5) 'TeXCmdName' => { 'params' => params
+# 'texfunc' => "callback_function_name"
+# }
+# replaces the command \TeXCmdName by the result of
+# the specified callback function. The callback
+# must assume that its result was some LaTeX expression
+# which will be evaluated (this is the major difference
+# between a 'func' and a 'texfunc', VERY IMPORTANT point).
+# The callback function works same as for 'func' (point 4).
+#
+my %TEX_HTML_COMMANDS = (
+
+ ' ' => ' ',
+ '_' => '_', # underline sign
+ '-' => '', # hyphenation sign
+ '$' => '\$',
+ ',' => '&nbsp;',
+ ';' => '&nbsp;',
+ '%' => '%',
+ '}' => '}',
+ '{' => '{',
+ '&' => '&amp;',
+ '\\' => '<br>',
+ '&' => '&amp;', #ampersand
+ # Patch by Norbert Preining added the 2003/03/17
+ '#' => '#',
+ '\'' => { 'params' => '{}',
+ 'func' => 'texcommand_acute',
+ },
+ '`' => { 'params' => '{}',
+ 'func' => 'texcommand_grave',
+ },
+ '~' => { 'params' => '{}',
+ 'func' => 'texcommand_tilde',
+ },
+ '"' => { 'params' => '{}',
+ 'func' => 'texcommand_uml',
+ },
+ '^' => { 'params' => '{}',
+ 'func' => 'texcommand_circ',
+ },
+ '=' => { 'params' => '{}', # One parameter
+ 'func' => 'texcommand_bar',
+ },
+ 'AA' => '&Aring;',
+ 'aa' => '&aring;',
+ 'AE' => '&AElig;', #latin small letter ae = latin small ligature ae
+ 'ae' => '&aelig;', #latin small letter ae = latin small ligature ae
+ 'begin' => { 'params' => '!{}', # Start environment
+ 'texfunc' => 'texcommand_beginenv',
+ },
+ 'backslash' => '\\',
+ 'beginblock' => '', # Ignored
+ 'bf' => { 'params' => '-', # Bold font
+ 'func' => 'texcommand_font_bold',
+ },
+ 'bfseries' => { 'params' => '-', # Bold font
+ 'func' => 'texcommand_font_bold',
+ },
+ 'BibtoHTML' => 'B<small>IB</small>2HTML', # Bib2HTML logo
+ 'bibtohtml' => 'B<small>IB</small>2HTML', # Bib2HTML logo
+ 'BibTeX' => 'B<small>IB</small>T<small>E</small>X', # BibTeX logo
+ 'c' => { 'params' => '{}',
+ 'func' => 'texcommand_cedil',
+ },
+ 'cdot' => '&middot;', #middle dot = Georgian comma = Greek middle dot
+ 'cite' => { 'params' => '[]{}',
+ 'func' => 'texcommand_cite',
+ },
+ 'def' => { 'params' => '\\{}',
+ 'func' => 'texcommand_def',
+ },
+ 'degree' => '&deg;', #degree sign
+ 'dg' => '&eth;', #latin small letter eth
+ 'DH' => '&ETH;', #latin capital letter ETH
+ 'div' => '&divide;', #division sign
+ 'edef' => { 'params' => '\\{}',
+ 'func' => 'texcommand_edef',
+ },
+ 'Emph' => { 'params' => '{}',
+ 'html' => '<strong>#1</strong>',
+ },
+ 'em' => { 'params' => '-', # Emphasis
+ 'html' => "<em>#1</em>",
+ },
+ 'emph' => { 'params' => '{}', # Emphasis
+ 'html' => '<em>#1</em>',
+ },
+ 'end' => { 'params' => '!{}', # End environment
+ 'texfunc' => 'texcommand_endenv',
+ },
+ 'enditemize' => '</UL>',
+ 'ensuremath' => { 'params' => '{}',
+ 'func' => 'texcommand_ensuremath',
+ },
+ 'footnotesize' => { 'params' => '-',
+ 'html' => "<font size=\"-2\">#1</font>",
+ },
+ 'gdef' => { 'params' => '\\{}',
+ 'func' => 'texcommand_def',
+ },
+ 'global' => '', # ignored
+ 'guillemotleft' => '&laquo;', #left-pointing double angle quotation mark
+ 'guillemotright' => '&raquo;', #right-pointing double angle quotation mark = right pointing guillemet
+ 'Huge' => { 'params' => '-',
+ 'html' => "<font size=\"+5\">#1</font>",
+ },
+ 'html' => { 'params' => '!{}', # verbatim HTML code
+ 'html' => '#1',
+ },
+ 'huge' => { 'params' => '-',
+ 'html' => "<font size=\"+4\">#1</font>",
+ },
+ 'i' => 'i',
+ 'it' => { 'params' => '-', # Italic font
+ 'func' => 'texcommand_font_italic',
+ },
+ 'item' => '<LI>',
+ 'itshape' => { 'params' => '-', # Italic font
+ 'func' => 'texcommand_font_italic',
+ },
+ # Patch by Norbert Preining added the 2003/03/17
+ 'L' => 'L', # L bar
+ 'LARGE' => { 'params' => '-',
+ 'html' => "<font size=\"+3\">#1</font>",
+ },
+ 'Large' => { 'params' => '-',
+ 'html' => "<font size=\"+2\">#1</font>",
+ },
+ 'LaTeX' => 'L<sup><small>A</small></sup>T<small>E</small>X', # LaTeX logo
+ 'large' => { 'params' => '-',
+ 'html' => "<font size=\"+1\">#1</font>",
+ },
+ 'latex' => { 'params' => '{}', # Ignore the LaTeX commands
+ 'html' => '',
+ },
+ 'lnot' => '&not;', #not sign
+ 'mdseries' => { 'params' => '-', # Unbold Font
+ 'func' => 'texcommand_font_medium',
+ },
+ 'newcommand' => { 'params' => '{}[][]{}',
+ 'func' => 'texcommand_newcommand',
+ },
+ 'normalfont' => { 'params' => '-',
+ 'func' => 'texcommand_font_normal',
+ },
+ 'normalsize' => { 'params' => '-',
+ 'html' => "<font size=\"+0\">#1</font>",
+ },
+ 'O' => '&Oslash;',
+ 'o' => '&oslash;',
+ 'OE' => '&OElig;', #latin capital ligature OE
+ 'oe' => '&oelig;', #latin small ligature oe
+ 'P' => '&para;', #pilcrow sign = paragraph sign
+ 'pm' => '&plusmn;', #plus-minus sign = plus-or-minus sign
+ 'pounds' => '&pounds;', #pound sign
+ 'renewcommand' => { 'params' => '{}[][]{}',
+ 'func' => 'texcommand_newcommand',
+ },
+ 'rm' => { 'params' => '-', # Roman font
+ 'func' => "texcommand_font_roman",
+ },
+ 'rmfamily' => { 'params' => '-', # Roman font
+ 'func' => "texcommand_font_roman",
+ },
+ 'S' => '&sect;', #section sign
+ 'sc' => { 'params' => '-', # Small-caps font
+ 'func' => "texcommand_font_smallcap",
+ },
+ 'scriptsize' => { 'params' => '-',
+ 'html' => "<font size=\"-3\">#1</font>",
+ },
+ 'scshape' => { 'params' => '-', # Small-caps font
+ 'func' => "texcommand_font_smallcap",
+ },
+ 'sf' => { 'params' => '-', # Sans Serif font
+ 'func' => "texcommand_font_serif",
+ },
+ 'sffamily' => { 'params' => '-', # Sans Serif font
+ 'func' => "texcommand_font_serif",
+ },
+ 'sl' => { 'params' => '-', # Slanted font
+ 'func' => "texcommand_font_slanted",
+ },
+ 'slshape' => { 'params' => '-', # Slanted font
+ 'func' => "texcommand_font_slanted",
+ },
+ 'small' => { 'params' => '-',
+ 'html' => "<font size=\"-1\">#1</font>",
+ },
+ 'ss' => '&szlig;', #latin small letter sharp s = ess-zed
+ 'startblock' => '', # Ignored
+ 'startitemize' => '<UL>',
+ 'string' => { 'params' => '{}',
+ 'html' => "#1",
+ },
+ 'TeX' => 'T<small>E</small>X', # TeX logo
+ 'text' => { 'params' => '{}',
+ 'func' => 'texcommand_ensuretext',
+ },
+ 'textasciicircum' => '&circ;', # circumflex accent sign
+ 'textasciitilde' => '~', # tilde sign
+ 'textbackslash' => '\\',
+ 'textbf' => { 'params' => '{}', # Bold font
+ 'func' => 'texcommand_font_bold',
+ },
+ 'textbrokenbar' => '&brvbar;', #broken bar = broken vertical bar
+ 'textcent' => '&cent;', #cent sign
+ 'textcopyright' => '&copy;', #copyright sign
+ 'textcurrency' => '&curren;', #currency sign
+ 'textexcladown' => '&iexcl;', #inverted exclamation mark, U+00A1 ISOnum
+ 'textit' => { 'params' => '{}', # Italic Font
+ 'func' => 'texcommand_font_italic',
+ },
+ 'textmd' => { 'params' => '{}', # Unbold Font
+ 'func' => 'texcommand_font_medium',
+ },
+ 'textnormal' => { 'params' => '{}',
+ 'func' => 'texcommand_font_normal',
+ },
+ 'textonehalf' => '&frac12;', #vulgar fraction one half = fraction one half
+ 'textonequarter' => '&frac14;', #vulgar fraction one quarter = fraction one quarter
+ 'textordfeminine' => '&ordf;', #feminine ordinal indicator
+ 'textordmasculine' => '&ordm;', #masculine ordinal indicator
+ 'textquestiondown' => '&iquest;', #inverted question mark = turned question mark
+ 'textregistered' => '&reg;', #registered sign = registered trade mark sign
+ 'textrm' => { 'params' => '{}', # Roman Font
+ 'func' => 'texcommand_font_roman',
+ },
+ 'textsc' => { 'params' => '{}', # Small-caps Font
+ 'func' => 'texcommand_font_smallcap',
+ },
+ 'textsf' => { 'params' => '{}', # Sans Serif Font
+ 'func' => 'texcommand_font_serif',
+ },
+ 'textsl' => { 'params' => '{}', # Slanted Font
+ 'func' => 'texcommand_font_slanted',
+ },
+ 'textthreequarters' => '&frac34;', #vulgar fraction three quarters = fraction three quarters
+ 'texttt' => { 'params' => '{}',
+ 'func' => 'texcommand_font_typewriter',
+ },
+ 'textup' => { 'params' => '{}', # Up right font
+ 'func' => 'texcommand_font_upright',
+ },
+ 'textyen' => '&yen;', #yen sign = yuan sign
+ 'times' => '&times;', #multiplication sign
+ 'tiny' => { 'params' => '-',
+ 'html' => "<font size=\"-4\">#1</font>",
+ },
+ 'TH' => '&THORN;', #latin capital letter THORN
+ 'th' => '&thorn;', #latin small letter thorn
+ 'tt' => { 'params' => '-', # Typewriter font
+ 'func' => "texcommand_font_typewriter",
+ },
+ 'ttfamily' => { 'params' => '-', # Type writer font
+ 'func' => 'texcommand_font_typewriter',
+ },
+ 'u' => { 'params' => '{}', # added by Tobia
+ 'func' => 'texcommand_ucircle',
+ },
+ 'uline' => { 'params' => '{}', # Underline font
+ 'html' => "<u>#1</u>",
+ },
+ 'upshape' => { 'params' => '{}', # Up right font
+ 'func' => 'texcommand_font_upright',
+ },
+ 'url' => { 'params' => '{}', # URL hyperlink
+ 'html' => "<a=\"#1\">#1</a>",
+ },
+ 'v' => { 'params' => '{}',
+ 'func' => 'texcommand_caron',
+ },
+ 'xdef' => { 'params' => '\\{}',
+ 'func' => 'texcommand_edef',
+ },
+
+ ) ;
+
+###############################################################
+# This is the list of math-mode commands.
+# The commands must respect one of the following formats:
+# 1) 'TeXCmdName' => "HTML code"
+# permits to translate the LaTeX command \TeXCmdName
+# into the specified "HTML code".
+# 2) 'TeXCmdName' => { 'params' => params
+# 'html' => "HTML code"
+# }
+# replaces the command \TeXCmdName by the specified
+# "HTML code". This last could contains a parameter
+# number (eg, #1 for the first, #2 for the second,
+# etc.) which will be replaced by the value
+# passed to the LaTeX command. The params specifies
+# the parameter prototype of the LaTeX command. It
+# must contains one (or more) of:
+# {} for a needed parameter
+# [d] for an optional parameter. d
+# is the default value given to this parameter
+# if it was not provided inside the LaTeX code
+# \\ for a LaTeX command name
+# ! indicates that the following sign ({} or[])
+# must not be interpreted by the LaTeX
+# translator. It must be used for verbatim
+# output
+# - to read the text until the end of the current
+# LaTeX context
+# 3) 'TeXCmdName' => { 'params' => params
+# 'latex' => "LaTeX code"
+# }
+# replaces the command \TeXCmdName by the specified
+# "LaTeX code". This last could contains a parameter
+# number (eg, #1 for the first, #2 for the second,
+# etc.) which will be replaced by the value
+# passed to the LaTeX command. The params specifies
+# the parameter prototype of the LaTeX command. It
+# must contains one (or more) of the macros defined
+# in the point 2).
+# 3) 'TeXCmdName' => { 'params' => params
+# 'func' => "callback_function_name"
+# }
+# replaces the command \TeXCmdName by the result of
+# the specified callback function. This callback
+# function must take, at least, 1 parameters:
+# the current line number. The parameters of the
+# LaTeX command will be passed to this callback
+# function after this line number.
+# Example: for \newcommand{\cmdname}[4][default]{code #2}
+# we implements the callback function:
+# sub texcommand_newcommand {
+# my $lineno = shift || 0 ;
+# my ($cmdname,$nb_params) =
+# ( $_[0], $_[1] || 0 ) ;
+# my ($default,$code) =
+# ($_[2] || '', $_[3] || '') ;
+# ...
+# return '' ;
+# }
+# The params specifies the parameter prototype of
+# the LaTeX command. It must contains one (or more)
+# of the macros defined in the point 2).
+# 4) 'TeXCmdName' => { 'params' => params
+# 'texfunc' => "callback_function_name"
+# }
+# replaces the command \TeXCmdName by the result of
+# the specified callback function. The callback
+# must assume that its result was some LaTeX expression
+# which will be evaluated (this is the major difference
+# between a 'func' and a 'texfunc', VERY IMPORTANT point).
+# The callback function works same as for 'func' (point 3).
+#
+my %MATH_TEX_HTML_COMMANDS = (
+
+ '}' => '}',
+ '{' => '{',
+ '&' => '&amp;',
+ '_' => { 'params' => "{}",
+ 'html' => "<sub>#1</sub>",
+ 'special' => 1,
+ },
+ '^' => { 'params' => "{}",
+ 'html' => "<sup class=\"exponent\">#1</sup>",
+ 'special' => 1,
+ },
+
+ 'mathmicro' => '&micro;', #micro sign
+ 'maththreesuperior' => '&sup3;', #superscript three = superscript digit three = cubed
+ 'mathtwosuperior' => '&sup2;', #superscript two = superscript digit two = squared
+
+ # MATH-ML commands
+ 'alpha' => "&alpha;",
+ 'angle' => "&ang;",
+ 'approx' => "&asymp;",
+ 'ast' => "&lowast;",
+ 'beta' => "&beta;",
+ 'bot' => "&perp;",
+ 'bullet' => "&bull;",
+ 'cap' => "&cap;",
+ 'cdots' => "&hellip;",
+ 'chi' => "&chi;",
+ 'clubsuit' => "&clubs;",
+ 'cong' => "&cong;",
+ 'cup' => "&cup;",
+ 'dagger' => "&dagger;",
+ 'ddagger' => "&Dagger;",
+ 'delta' => "&delta;",
+ 'Delta' => "&Delta;",
+ 'diamondsuit' => "&loz;",
+ 'div' => "&divide;",
+ 'downarrow' => "&darr;",
+ 'Downarrow' => "&dArr;",
+ 'emptyset' => "&empty;",
+ 'epsilon' => "&epsilon;",
+ 'Epsilon' => "&Epsilon;",
+ 'equiv' => "&equiv;",
+ 'eta' => "&eta;",
+ 'exists' => "&exist;",
+ 'forall' => "&forall;",
+ 'gamma' => "&gamma;",
+ 'Gamma' => "&Gamma;",
+ 'geq' => "&ge;",
+ 'heartsuit' => "&hearts;",
+ 'Im' => "&image;",
+ 'in' => "&isin;",
+ 'infty' => "&infin;",
+ 'infinity' => "&infin;",
+ 'int' => "&int;",
+ 'iota' => "&iota;",
+ 'kappa' => "&kappa;",
+ 'lambda' => "&lambda;",
+ 'Lambda' => "&Lambda;",
+ 'langle' => "&lang;",
+ 'lceil' => "&lceil;",
+ 'ldots' => "&hellip;",
+ 'leftarrow' => "&larr;",
+ 'Leftarrow' => "&lArr;",
+ 'leftrightarrow' => "&harr;",
+ 'Leftrightarrow' => "&hArr;",
+ 'leq' => "&le;",
+ 'lfloor' => "&lfloor;",
+ 'mathbb' => { 'params' => '{}', # Math Set characters
+ 'func' => 'texcommand_font_mathset',
+ },
+ 'mathbf' => { 'params' => '{}', # Bold font
+ 'func' => 'texcommand_font_bold',
+ },
+ 'mathit' => { 'params' => '{}', # Italic Font
+ 'func' => 'texcommand_font_italic',
+ },
+ 'mathrm' => { 'params' => '{}', # Roman Font
+ 'func' => 'texcommand_font_roman',
+ },
+ 'mathsf' => { 'params' => '{}', # Sans Serif Font
+ 'func' => 'texcommand_font_serif',
+ },
+ 'mathtt' => { 'params' => '{}',
+ 'func' => 'texcommand_font_typewriter',
+ },
+ 'mathnormal' => { 'params' => '{}',
+ 'func' => 'texcommand_font_normal',
+ },
+ 'mu' => "&mu;",
+ 'nabla' => "&nabla;",
+ 'neg' => "&not;",
+ 'neq' => "&ne;",
+ 'ni' => "&ni;",
+ 'not\in' => "&notin;",
+ 'not\subset' => "&nsub;",
+ 'nu' => "&nu;",
+ 'omega' => "&omega;",
+ 'Omega' => "&Omega;",
+ 'ominus' => "&ominus;",
+ 'oplus' => "&oplus;",
+ 'oslash' => "&oslash;",
+ 'Oslash' => "&Oslash;",
+ 'otimes' => "&otimes;",
+ 'partial' => "&part;",
+ 'phi' => "&phi;",
+ 'Phi' => "&Phi;",
+ 'pi' => "&pi;",
+ 'Pi' => "&Pi;",
+ 'pm' => "&plusmn;",
+ 'prime' => "&prime;",
+ 'prod' => "&prod;",
+ 'propto' => "&prop;",
+ 'psi' => "&psi;",
+ 'Psi' => "&Psi;",
+ 'rangle' => "&rang;",
+ 'rceil' => "&rceil;",
+ 'Re' => "&real;",
+ 'rfloor' => "&rfloor;",
+ 'rho' => "&rho;",
+ 'rightarrow' => "&rarr;",
+ 'Rightarrow' => "&rArr;",
+ 'sigma' => "&sigma;",
+ 'Sigma' => "&Sigma;",
+ 'sim' => "&sim;",
+ 'spadesuit' => "&spades;",
+ 'sqrt' => "&radic;",
+ 'subseteq' => "&sube;",
+ 'subset' => "&sub;",
+ 'sum' => "&sum;",
+ 'supseteq' => "&supe;",
+ 'supset' => "&sup;",
+ 'surd' => "&radic;",
+ 'tau' => "&tau;",
+ 'theta' => "&theta;",
+ 'Theta' => "&Theta;",
+ 'times' => "&times;",
+ 'to' => "&rarr;",
+ 'uparrow' => "&uarr;",
+ 'Uparrow' => "&uArr;",
+ 'upsilon' => "&upsilon;",
+ 'Upsilon' => "&Upsilon;",
+ 'varpi' => "&piv;",
+ 'vee' => "&or;",
+ 'wedge' => "&and;",
+ 'wp' => "&weierp;",
+ 'xi' => "&xi;",
+ 'Xi' => "&Xi;",
+ 'zeta' => "&zeta;",
+
+ ) ;
+
+#------------------------------------------------------
+#
+# Constructor
+#
+#------------------------------------------------------
+
+sub new($;$$) : method {
+ my $proto = shift;
+ my $class = ref($proto) || $proto;
+ my $parent = ref($proto) && $proto ;
+
+ my $self ;
+ if ( $parent ) {
+ %{$self} = %{$parent} ;
+ }
+ else {
+ $self = { 'FILENAME' => $_[0] || '',
+ 'DATABASE' => undef,
+ 'MATH_MODE' => 0,
+ 'MATH_MODE_START' => $_[2] || "<math>",
+ 'MATH_MODE_STOP' => $_[3] || "</math>",
+ 'FONTS' => { 'ALLS' => [],
+ 'SERIES' => [],
+ 'FAMILIES' => [],
+ 'SHAPES' => [],
+ },
+ 'ENVIRONMENTS' => [],
+ } ;
+ }
+ bless( $self, $class );
+ return $self;
+}
+
+#------------------------------------------------------
+#
+# Translation API
+#
+#------------------------------------------------------
+
+=pod
+
+=item * translate()
+
+Translate the specified string from a TeX string to
+an HTML string
+Takes 3 args:
+
+=over
+
+=item * text (string)
+
+is the text to translate
+
+=item * database (hash)
+
+is the complee database content.
+
+=item * lineno (optional integer)
+
+is the line number where the text can be found
+
+=back
+
+=cut
+sub translate($$;$) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my $lineno = $_[2] || 0 ;
+ my $html = '' ;
+
+ if ( $_[1] ) {
+ $self->{'DATABASE'} = $_[1] ;
+ }
+
+ # Search the first separator
+ my ($eaten,$sep,$tex) = $self->eat_to_separator($text) ;
+
+ while ($sep) {
+
+ # Translate the already eaten string
+ $eaten = $self->translate_chars( $eaten, $lineno ) ;
+
+ if ( ( $sep eq '{' ) || ( $sep eq '}' ) ) {
+ # Ignore braces
+ }
+ elsif ( $sep eq '\\' ) {
+ (my $eaten2,$tex) = $self->translate_cmd($tex, $lineno, '\\') ;
+ $eaten .= $eaten2 ;
+ }
+ elsif ( $sep eq '$' ) {
+ # Math mode
+ if ( ! $self->is_math_mode() ) {
+ $eaten .= $self->start_math_mode(1) ;
+ }
+ elsif ( $self->is_inline_math_mode() ) {
+ $eaten .= $self->stop_math_mode() ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "you try to close with a '\$' a mathematical mode opened with '\\['",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ }
+ elsif ( ( $sep eq '_' ) ||
+ ( $sep eq '^' ) ) {
+ # Special math mode commands
+ (my $eaten2,$tex) = $self->translate_cmd($sep.$tex, $lineno ) ;
+ $eaten .= $eaten2 ;
+ }
+ else { # Unknow separator, treat as text
+ $eaten .= $self->translate_chars( $sep, $lineno ) ;
+ }
+
+ # Translate the text before the separator
+ $html .= $eaten ;
+
+ # Search the next separator
+ ($eaten,$sep,$tex) = $self->eat_to_separator($tex) ;
+ }
+
+ if ( $eaten ) {
+ $html .= $self->translate_chars( $eaten, $lineno ) ;
+ }
+
+ # Remove multiple white spaces
+ $html =~ s/ +/ /g ;
+
+ return $html ;
+}
+
+=pod
+
+=item * eat_to_separator()
+
+Eats the specified text until the first separator.
+Takes 2 args:
+
+=over
+
+=item * text (string)
+
+is the text to eat
+
+=item * seps (optional string)
+
+is the list of additional separators
+
+=back
+
+=cut
+sub eat_to_separator($;$) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my $separators = $_[1] || '' ;
+ my ($before,$sep,$after) ;
+
+ $separators .= "_^{}\$\\\\" ;
+
+ if ( $text =~ /^(.*?)([$separators])(.*)$/ ) {
+ ($before,$sep,$after) = ($1,$2,$3) ;
+ }
+ else {
+ $before = $text ;
+ $sep = $after = '' ;
+ }
+ return ($before,$sep,$after) ;
+}
+
+=pod
+
+=item * translate_chars()
+
+Translate the chars inside the specified string.
+Takes 2 args:
+
+=over
+
+=item * text (string)
+
+is the text to translate
+
+=item * lineno (integer)
+
+=back
+
+=cut
+sub translate_chars($$) : method {
+ my $self = shift ;
+ my $html = $_[0] || '' ;
+ my $lineno = $_[1] || 0 ;
+ my @parts = split( /\&/, $html ) ;
+ for(my $i=0; $i<@parts; $i++) {
+ # Translate from the trans table
+ while ( my ($char,$hstr) = each( %TEX_HTML_CHAR_TRANS ) ) {
+ if ( $i > 0 ) {
+ Bib2HTML::General::Error::warm( "you type a '\&'. It could be a LaTeX syntax error. Assume '\\&'.",
+ $self->{'FILENAME'}, $lineno ) ;
+ }
+ $parts[$i] =~ s/\Q$char\E/$hstr/g ;
+ }
+ }
+ $html = join( '&amp;', @parts ) ;
+ return get_restricted_html_entities( $html ) ;
+}
+
+=pod
+
+=item * translate_cmd()
+
+Translate a TeX command.
+Takes 3 args:
+
+=over
+
+=item * text (string)
+
+is the text, which follows the backslash, to scan
+
+=item * lineno (integer)
+
+=item * prefix (optional string)
+
+is a prefix merged to the command name. Use carefully.
+
+=back
+
+=cut
+sub translate_cmd($$;$) : method {
+ my $self = shift ;
+ my ($eaten,$tex,$lineno) = ('',
+ $_[0] || '',
+ $_[1] || 0 ) ;
+ my $cmd_prefix = $_[2] || '' ;
+
+ # Gets the command name
+ if ( $tex =~ /^\[(.*)/ ) { # Starts multi-line math mode
+ $tex = $1 ;
+ if ( ! $self->is_math_mode() ) {
+ $eaten .= $self->start_math_mode(2) ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "you try to open twice a mathematical mode with '".$cmd_prefix."['",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ }
+ elsif ( $tex =~ /^\](.*)/ ) { # Stop multi-line math mode
+ $tex = $1 ;
+ if ( $self->is_multiline_math_mode() ) {
+ $eaten .= $self->stop_math_mode() ;
+ }
+ elsif ( $self->is_math_mode() ) {
+ Bib2HTML::General::Error::warm( "you try to close with a '".$cmd_prefix."[' a mathematical mode opened with '\$'",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "you try to close with '".$cmd_prefix."]' a mathematical mode which was not opened",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ }
+ elsif ( $tex =~ /^((?:[a-zA-Z]+)|.)(.*)/ ) { # default LaTeX command
+ (my $cmdname,$tex) = ($1,$2) ;
+ if ( $cmdname ) {
+ my $trans = $self->search_cmd_trans( $cmdname, $lineno, ($cmd_prefix ne "\\") ) ;
+ if ( defined( $trans ) ) {
+ # Seach the command inside the translation table
+ ($eaten,$tex) = $self->run_cmd( $cmd_prefix.$cmdname, $trans, $tex, $lineno ) ;
+ }
+ elsif ( $self->is_math_mode() ) {
+ Bib2HTML::General::Error::warm( "unrecognized TeX command in mathematical mode: ".
+ $cmd_prefix.$cmdname,
+ $self->{'FILENAME'},
+ $lineno ) ;
+ $eaten = "<font color=\"gray\">[$cmdname]</font>" ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "unrecognized TeX command: ".
+ $cmd_prefix.$cmdname,
+ $self->{'FILENAME'},
+ $lineno ) ;
+ $eaten = "<font color=\"gray\">[$cmdname]</font>" ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::warm( "invalid syntax for the TeX command: ".
+ $cmd_prefix.$_[0],
+ $self->{'FILENAME'},
+ $lineno ) ;
+ $eaten = $cmd_prefix ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::warm( "invalid syntax for the TeX command: ".
+ $cmd_prefix.$_[0],
+ $self->{'FILENAME'},
+ $lineno ) ;
+ $eaten = $cmd_prefix ;
+ }
+
+ return ($eaten,$tex) ;
+}
+
+=pod
+
+=item * search_cmd_trans()
+
+Replies the translation entry that corresponds to
+the specified TeX command.
+Takes 3 args:
+
+=over
+
+=item * name (string)
+
+is the name of the TeX command to search.
+
+=item * lineno (integer)
+
+=item * special (optional boolean)
+
+indicates if the searched command has a special purpose
+(example: _ in math mode)
+
+=back
+
+=cut
+sub search_cmd_trans($$;$) : method {
+ my $self = shift ;
+ my $lineno = $_[1] || 0 ;
+ my $special = $_[2] ;
+ my ($math, $text) ;
+ my ($found_math,$found_text) = (0,0) ;
+ if ( ( $_[0] ) &&
+ ( exists $MATH_TEX_HTML_COMMANDS{$_[0]} ) ) {
+ $found_math = ( ( ( !$special ) &&
+ ( ( ! ishash( $MATH_TEX_HTML_COMMANDS{$_[0]} ) ) ||
+ ( ! exists $MATH_TEX_HTML_COMMANDS{$_[0]}{'special'} ) ||
+ ( ! $MATH_TEX_HTML_COMMANDS{$_[0]}{'special'} ) ) ) ||
+ ( ( $special ) &&
+ ( ishash( $MATH_TEX_HTML_COMMANDS{$_[0]} ) ) &&
+ ( exists $MATH_TEX_HTML_COMMANDS{$_[0]}{'special'} ) &&
+ ( $MATH_TEX_HTML_COMMANDS{$_[0]}{'special'} ) ) ) ;
+ $math = $MATH_TEX_HTML_COMMANDS{$_[0]}
+ if ( $found_math ) ;
+ }
+ if ( ( $_[0] ) &&
+ ( exists $TEX_HTML_COMMANDS{$_[0]} ) ) {
+ $found_text = ( ( ( !$special ) &&
+ ( ( ! ishash( $TEX_HTML_COMMANDS{$_[0]} ) ) ||
+ ( ! exists $TEX_HTML_COMMANDS{$_[0]}{'special'} ) ||
+ ( ! $TEX_HTML_COMMANDS{$_[0]}{'special'} ) ) ) ||
+ ( ( $special ) &&
+ ( ishash( $TEX_HTML_COMMANDS{$_[0]} ) ) &&
+ ( exists $TEX_HTML_COMMANDS{$_[0]}{'special'} ) &&
+ ( $TEX_HTML_COMMANDS{$_[0]}{'special'} ) ) ) ;
+ $text = $TEX_HTML_COMMANDS{$_[0]}
+ if ( $found_text ) ;
+ }
+
+ if ( $found_math || $found_text ) {
+ if ( $self->is_math_mode() ) {
+ if ( ! $found_math ) {
+ Bib2HTML::General::Error::warm( "the command ".
+ ( $special ? '' : '\\' ).
+ $_[0].
+ " was not defined for math-mode, assumes to use the text-mode version instead",
+ $self->{'FILENAME'}, $lineno ) ;
+ return $text ;
+ }
+ else {
+ return $math ;
+ }
+ }
+ elsif ( ! $found_text ) {
+ Bib2HTML::General::Error::warm( "the command ".
+ ( $special ? '' : '\\' ).
+ $_[0].
+ " was not defined for text-mode, assumes to use the math-mode version instead",
+ $self->{'FILENAME'}, $lineno ) ;
+ return $math ;
+ }
+ else {
+ return $text ;
+ }
+ }
+ return undef ;
+}
+
+=pod
+
+=item * run_cmd()
+
+Eaten the specified tex according to the specified command.
+Takes 4 args:
+
+=over
+
+=item * name (string)
+
+is the name of the TeX command.
+
+=item * trans (mixed)
+
+is the translation for the command.
+
+=item * text (string)
+
+is the text from which some data must be extracted to
+treat the command.
+
+=item * lineno(integer)
+
+is le line number where the text starts
+
+=back
+
+=cut
+sub run_cmd($$$$) : method {
+ my $self = shift ;
+ my ($eaten,$cmdname,$tex,$lineno) = ('',
+ $_[0] || confess( 'you must supply the TeX command name'),
+ $_[2] || '',
+ $_[3] || 0 ) ;
+ if ( ( ishash( $_[1] ) ) &&
+ ( exists $_[1]->{'params'} ) ) {
+ # This command has params
+ ($tex,my @params) = $self->eat_cmd_parameters( $_[1]->{'params'}, $tex, $lineno ) ;
+ # Apply the command
+ if ( exists $_[1]->{'html'} ) {
+ # Replace by the HTML translation
+ $eaten = $_[1]->{'html'} ;
+ for(my $i=1; $i<=@params; $i++) {
+ if ( $eaten =~ /\#$i/ ) {
+ my $p = ($params[$i-1])->{'text'} ;
+ if ( ($params[$i-1])->{'eval'} ) {
+ $p = $self->translate( $p, undef, $lineno ) ;
+ }
+ $eaten =~ s/\#$i/$p/g ;
+ }
+ }
+ }
+ elsif ( exists $_[1]->{'latex'} ) {
+ # Replace by the LaTeX commands
+ my $cmd = $_[1]->{'latex'} ;
+ for(my $i=1; $i<=@params; $i++) {
+ if ( $cmd =~ /\#$i/ ) {
+ my $p = ($params[$i-1])->{'text'} ;
+ if ( ($params[$i-1])->{'eval'} ) {
+ $p = $self->translate( $p, undef, $lineno ) ;
+ }
+ $cmd =~ s/\#$i/$p/g ;
+ }
+ }
+ $tex = $cmd.$tex ;
+ }
+ elsif ( exists $_[1]->{'func'} ) {
+ # Replace by the string replied by the callback function
+ my $reffunc = $self->can($_[1]->{'func'}) ;
+ if ( $reffunc ) {
+ $eaten = $self->$reffunc( $lineno, @params ) ;
+ }
+ elsif ( issub( $_[1]->{'func'} ) ) {
+ $eaten = $_[1]->{'func'}( $lineno, @params ) ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "unable to find the callback function 'sub ".
+ $_[1]->{'func'}.
+ "{}' for the TeX command $cmdname",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ }
+ elsif ( exists $_[1]->{'texfunc'} ) {
+ # Replace by the string replied by the callback function
+ my $reffunc = $self->can($_[1]->{'texfunc'}) ;
+ if ( $reffunc ) {
+ my $result = $self->$reffunc( $lineno, @params ) ;
+ $tex = $result . $tex ;
+ }
+ elsif ( issub( $_[1]->{'texfunc'} ) ) {
+ my $result = $_[1]->{'texfunc'}( $lineno, @params ) ;
+ $tex = $result . $tex ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "unable to find the callback function 'sub ".
+ $_[1]->{'func'}.
+ "{}' for the TeX command $cmdname",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ }
+ }
+ }
+ else {
+ # No param, put the HTML string inside the output stream
+ $eaten = $_[1] ;
+ }
+ return ($eaten,$tex) ;
+}
+
+=pod
+
+=item * eat_cmd_parameters()
+
+Eaten the specified command parameters.
+Takes 3 args:
+
+=over
+
+=item * params (string)
+
+is the description of the parameters to eat.
+
+=item * text (string)
+
+is the text from which some data must be extracted.
+
+=item * lineno (integer)
+
+=back
+
+=cut
+sub eat_cmd_parameters($$$) : method {
+ my $self = shift ;
+ my $p_params = $_[0] || '' ;
+ my $tex = $_[1] || '' ;
+ my $lineno = $_[2] || 0 ;
+ my @params = () ;
+ while ( $p_params =~ /((?:\!?\{\})|(?:\!?\[[^\]]*\])|-|\\)/g ) {
+ my $p = $1 ;
+ # Eats no significant white spaces
+ $tex =~ s/^ +// ;
+ if ( $p =~ /^(\!?)\{\}/ ) { # Eates a needed parameter
+ my $optional = $1 || '' ;
+ my $prem = substr($tex,0,1) ;
+ $tex = substr($tex,1) ;
+ if ( $prem eq '{' ) {
+ (my $context,$tex) = $self->eat_context( $tex, '\\}' ) ;
+ push @params, { 'eval' => ($optional ne '!'),
+ 'text' => $context,
+ } ;
+ }
+ elsif ( $prem eq '\\' ) {
+ (my $eaten,$tex) = $self->translate_cmd($tex, $lineno, '\\') ;
+ push @params, { 'eval' => 0,
+ 'text' => $eaten,
+ } ;
+ }
+ else {
+ push @params, { 'eval' => ($optional ne '!'),
+ 'text' => $prem,
+ } ;
+ }
+ }
+ elsif( $p =~ /^(\!?)\[([^\]]*)\]/ ) { # Eates an optional parameter
+ my ($optional,$default_val) = ( $1 || '', $2 || '' ) ;
+ my $prem = substr($tex,0,1) ;
+ if ( $prem eq '[' ) {
+ (my $context,$tex) = $self->eat_context( substr($tex,1), '\\]' ) ;
+ push @params, { 'eval' => ($optional ne '!'),
+ 'text' => $context,
+ } ;
+ }
+ else {
+ push @params, { 'eval' => ($optional ne '!'),
+ 'text' => $default_val,
+ } ;
+ }
+ }
+ elsif( $p eq '\\' ) { # Eates a TeX command name
+ if ( $tex =~ /^\\((?:[a-zA-Z]+|.))(.*)$/ ) {
+ $tex = $2 ;
+ push @params, { 'eval' => 1,
+ 'text' => $1,
+ } ;
+ }
+ else {
+ Bib2HTML::General::Error::warm( "expected a TeX command name: ".$tex,
+ $self->{'FILENAME'},
+ $lineno ) ;
+ push @params, { 'eval' => 1,
+ 'text' => '',
+ } ;
+ }
+ }
+ elsif ( $p eq '-' ) { # Eates until the end of the current context
+ (my $context,$tex) = $self->eat_context( $tex, '\\}' ) ;
+ push @params, { 'eval' => 1,
+ 'text' => $context,
+ } ;
+ }
+ else {
+ confess( "unable to recognize the following argument specification: $p" ) ;
+ }
+ }
+ return ($tex,@params) ;
+}
+
+=pod
+
+=item * eat_context()
+
+Eaten the current context.
+Takes 2 args:
+
+=over
+
+=item * text (string)
+
+is the text from which some data must be extracted.
+
+=item * end (string)
+
+is the ending separator
+
+=back
+
+=cut
+sub eat_context($$) : method {
+ my $self = shift ;
+ my $text = $_[0] || '' ;
+ my $enddelim = $_[1] || confess( 'you must supply the closing delimiter' ) ;
+ my $context = '' ;
+ my $contextlevel = 0 ;
+
+ # Search the first separator
+ my ($eaten,$sep,$tex) = $self->eat_to_separator($text,$enddelim) ;
+
+ while ($sep) {
+
+ if ( $sep eq '{' ) { # open a context
+ $contextlevel ++ ;
+ $eaten .= $sep ;
+ }
+ elsif ( $sep eq '}' ) { # close a context
+ if ( $contextlevel <= 0 ) {
+ return ($context.$eaten,$tex) ;
+ }
+ $eaten .= $sep ;
+ $contextlevel -- ;
+ }
+ elsif ( $sep eq '\\' ) {
+ $tex =~ /^([a-zA-Z]+|.)(.*)$/ ;
+ $eaten .= "\\$1";
+ $tex = $2 ;
+ }
+ elsif ( ( $contextlevel <= 0 ) &&
+ ( $sep =~ /$enddelim/ ) ) { # The closing delemiter was found
+ return ($context.$eaten,$tex) ;
+ }
+ else { # Unknow separator, treat as text
+ $eaten .= $sep ;
+ }
+
+ # Translate the text before the separator
+ $context .= $eaten ;
+
+ # Search the next separator
+ ($eaten,$sep,$tex) = $self->eat_to_separator($tex,$enddelim) ;
+ }
+
+ return ($context.$eaten,$tex) ;
+}
+
+#------------------------------------------------------
+#
+# Translation table updates
+#
+#------------------------------------------------------
+
+=pod
+
+=item * start_math_mode()
+
+Starts the mathematical mode.
+Takes 1 arg:
+
+=over
+
+=item * mode (integer)
+
+is the math mode to start (1: inline, 2: multi-line)
+
+=back
+
+=cut
+sub start_math_mode($) {
+ my $self = shift ;
+ if ( $self->is_math_mode() ) {
+ return '' ;
+ }
+ else {
+ $self->{'MATH_MODE'} = ( $_[0] % 3 ) ;
+ my $tag = '' ;
+ if ( $self->{'MATH_MODE'} == 2 ) {
+ $tag .= "<blockquote>" ;
+ }
+ return $tag.$self->{'MATH_MODE_START'} ;
+ }
+}
+
+=pod
+
+=item * stop_math_mode()
+
+Stops the mathematical mode.
+
+=cut
+sub stop_math_mode() {
+ my $self = shift ;
+ if ( $self->is_math_mode() ) {
+ my $tag = $self->{'MATH_MODE_STOP'} ;
+ if ( $self->{'MATH_MODE'} == 2 ) {
+ $tag .= "</blockquote>" ;
+ }
+ $self->{'MATH_MODE'} = 0 ;
+ return $tag ;
+ }
+ else {
+ return '' ;
+ }
+}
+
+=pod
+
+=item * is_math_mode()
+
+Replies if inside a mathematical mode.
+
+=cut
+sub is_math_mode() {
+ my $self = shift ;
+ return ( $self->{'MATH_MODE'} != 0 ) ;
+}
+
+=pod
+
+=item * is_inline_math_mode()
+
+Replies if inside a inlined mathematical mode.
+
+=cut
+sub is_inline_math_mode() {
+ my $self = shift ;
+ return ( $self->{'MATH_MODE'} == 1 ) ;
+}
+
+=pod
+
+=item * is_multiline_math_mode()
+
+Replies if inside a multi-lined mathematical mode.
+
+=cut
+sub is_multiline_math_mode() {
+ my $self = shift ;
+ return ( $self->{'MATH_MODE'} == 2 ) ;
+}
+
+#------------------------------------------------------
+#
+# Information
+#
+#------------------------------------------------------
+
+=pod
+
+=item * display_supported_commands()
+
+Display the list of supported LaTeX commands.
+Takes 1 arg:
+
+=over
+
+=item * perldir (string)
+
+is the path to the directory where the Perl packages
+are stored.
+
+=back
+
+=cut
+sub display_supported_commands($) {
+ my $path = $_[0] || confess( 'you must specify the pm path' ) ;
+ my (@c1,@c2) = ((),()) ;
+ foreach my $cmd ( keys %TEX_HTML_COMMANDS ) {
+ my $prefix = '' ;
+ if ( ( !ishash( $TEX_HTML_COMMANDS{$cmd} ) ) ||
+ ( ! exists $TEX_HTML_COMMANDS{$cmd}{'special'} ) ||
+ ( ! $TEX_HTML_COMMANDS{$cmd}{'special'} ) ) {
+ $prefix = "\\" ;
+ }
+ if ( $cmd =~ /^[a-zA-Z0-9]/ ) {
+ push @c2, $prefix.$cmd ;
+ }
+ else {
+ push @c1, $prefix.$cmd ;
+ }
+ }
+ foreach my $cmd ( keys %MATH_TEX_HTML_COMMANDS ) {
+ if ( ! exists $TEX_HTML_COMMANDS{$cmd} ) {
+ my $prefix = '' ;
+ if ( ( !ishash( $TEX_HTML_COMMANDS{$cmd} ) ) ||
+ ( ! exists $TEX_HTML_COMMANDS{$cmd}{'special'} ) ||
+ ( ! $TEX_HTML_COMMANDS{$cmd}{'special'} ) ) {
+ $prefix = "\\" ;
+ }
+ if ( $cmd =~ /^[a-zA-Z0-9]/ ) {
+ push @c2, $prefix.$cmd ;
+ }
+ else {
+ push @c1, $prefix.$cmd ;
+ }
+ }
+ }
+ foreach my $cmd ( sort @c1 ) {
+ print "$cmd\n" ;
+ }
+ foreach my $cmd ( sort @c2 ) {
+ print "$cmd\n" ;
+ }
+}
+
+#------------------------------------------------------
+#
+# Translation table updates
+#
+#------------------------------------------------------
+
+=pod
+
+=item * addtrans_char()
+
+Static method which permits to add a translation entry
+for a character.
+Takes 2 args:
+
+=over
+
+=item * char (string)
+
+is the character to translate
+
+=item * html (string)
+
+is the HTML translation of the character.
+
+=back
+
+=cut
+sub addtrans_char($$) {
+ confess( 'you must supply the character to translate' ) unless $_[0] ;
+ Bib2HTML::General::Verbose::three( "\tadd the HTML translation for '".$_[0]."'" ) ;
+ $TEX_HTML_CHAR_TRANS{$_[0]} = ( $_[1] || '' ) ;
+}
+
+=pod
+
+=item * gettrans_char()
+
+Static method which replies the translation table from a character to HTML string.
+
+=cut
+sub gettrans_char() {
+ return \%TEX_HTML_CHAR_TRANS ;
+}
+
+=pod
+
+=item * addtrans_cmd_noparam()
+
+Static method which permits to add a translation entry
+for a TeX command. The new TeX command does not have any
+parameter.
+Takes 3 args:
+
+=over
+
+=item * cmd (string)
+
+is the name od the TeX command
+
+=item * html (string)
+
+is the HTML translation of the character.
+
+=item * tex_content (optional boolean)
+
+indicates if the content contains LaTeX code (if true)
+or HTML code (if false - default).
+
+=back
+
+=cut
+sub addtrans_cmd_noparam($$;$) {
+ confess( 'you must supply the character to translate' ) unless $_[0] ;
+ Bib2HTML::General::Verbose::three( "\tadd the TeX translation for {\\".$_[0]."}" ) ;
+ if ( $_[2] ) {
+ $TEX_HTML_COMMANDS{$_[0]} = { 'params' => '',
+ 'latex' => ( $_[1] || '' ),
+ } ;
+ }
+ else {
+ $TEX_HTML_COMMANDS{$_[0]} = ( $_[1] || '' ) ;
+ }
+}
+
+=pod
+
+=item * addtrans_cmd_html()
+
+Static method which permits to add a translation entry
+for a TeX command. The new TeX command has parameters, but
+it can be directly translated as HTML code.
+Takes 4 args:
+
+=over
+
+=item * cmd (string)
+
+is the name od the TeX command
+
+=item * params (string)
+
+is the description of the parameters:
+
+=over
+
+=item {} for a parameter
+
+=item [val] for an optional parameter where val is the default value
+
+=item \ for a TeX command name
+
+=item ! will avoid the LaTeX interpretation of the following sign ({} or [])
+
+=item - for all the text until the end of the current context
+
+=back
+
+=item * html (string)
+
+is the HTML translation of the character. #n means the n-th parameter,
+where n is an integer greater or equal to 1.
+
+=item * tex_content (optional boolean)
+
+indicates if the content contains LaTeX code (if true)
+or HTML code (if false - default).
+
+=back
+
+=cut
+sub addtrans_cmd_html($$$;$) {
+ confess( 'you must supply the TeX command name' ) unless $_[0] ;
+ my $params = $_[1] || confess( 'you must supply the parameter description' ) ;
+ my $html = $_[2] || '' ;
+ if ( ( $params eq '-' ) ||
+ ( $params =~ /(?:(?:\{\})|(?:\[[^\]]*\])|\\)+/ ) ) {
+ Bib2HTML::General::Verbose::three( "\tadd the TeX translation for \\".$_[0].$params ) ;
+ if ( $_[3] ) {
+ %{$TEX_HTML_COMMANDS{$_[0]}} = ( 'params' => $params,
+ 'latex' => $html,
+ ) ;
+ }
+ else {
+ %{$TEX_HTML_COMMANDS{$_[0]}} = ( 'params' => $params,
+ 'html' => $html,
+ ) ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::syserr( "invalid syntax for the parameters of the ".
+ "TeX command '".$_[0]."': ".$params ) ;
+ }
+}
+
+=pod
+
+=item * addtrans_cmd_func()
+
+Static method which permits to add a translation entry
+for a TeX command. The new TeX command has parameters, but
+a callback function must be called to treat this command.
+Takes 3 args:
+
+=over
+
+=item * cmd (string)
+
+is the name od the TeX command
+
+=item * params (string)
+
+is the description of the parameters:
+
+=over
+
+=item {} for a parameter
+
+=item [val] for an optional parameter where val is the default value
+
+=item \ for a TeX command name
+
+=item ! will avoid the LaTeX interpretation of the following sign ({} or [])
+
+=item - for all the text until the end of the current context
+
+=back
+
+=item * func (string)
+
+is the name of the method to call.
+
+=back
+
+=cut
+sub addtrans_cmd_func($$$) {
+ confess( 'you must supply the TeX command name' ) unless $_[0] ;
+ my $params = $_[1] || confess( 'you must supply the parameter description' ) ;
+ my $func = $_[2] || confess( 'you must supply the callback function' ) ;
+ if ( ( $params eq '-' ) ||
+ ( $params =~ /(?:(?:\{\})|(?:\[[^\]]*\])|\\)+/ ) ) {
+ Bib2HTML::General::Verbose::three( "\tadd the TeX translation for \\".$_[0].$params ) ;
+ %{$TEX_HTML_COMMANDS{$_[0]}} = ( 'params' => $params,
+ 'func' => $func,
+ ) ;
+ }
+ else {
+ Bib2HTML::General::Error::syserr( "invalid syntax for the parameters of the ".
+ "TeX command '".$_[0]."': ".$params ) ;
+ }
+}
+
+=pod
+
+=item * gettrans_cmd()
+
+Replies the translation table from a TeX command to HTML string.
+
+=cut
+sub gettrans_cmd() {
+ return \%TEX_HTML_COMMANDS ;
+}
+
+=pod
+
+=item * __texcommand_map_to()
+
+Makes the specified mapping of a TeX command.
+Takes at least 4 args:
+
+=over
+
+=item * map (hash)
+
+is the mapping associative array
+
+=item * default (string)
+
+is the default value return if the mapping was unavailable
+
+=item * lineno (integer)
+
+=item * params (array)
+
+is the list of parameters
+
+=back
+
+=cut
+sub __texcommand_map_to($$$) {
+ my $self = shift ;
+ my $lineno = $_[2] || 0 ;
+ if ( ( $_[3] ) &&
+ ( $_[3]->{'text'} ) ) {
+ if ( $_[0]->{$_[3]->{'text'}} ) {
+ return "&".$_[0]->{$_[3]->{'text'}}.";" ;
+ }
+ else {
+ # Patch by Norbert Preining added the 2003/03/17
+ Bib2HTML::General::Error::warm( "An accentuation command was found, but the corresponding character '".
+ $_[3]->{'text'}.
+ "' is not supported. Assume '".
+ $_[1].$_[3]->{'text'}."'.",
+ $self->{'FILENAME'}, $lineno ) ;
+ }
+ }
+ else {
+ Bib2HTML::General::Error::warm( "no command name after a slash. Assume '".$_[1].$_[3]->{'text'}."'.",
+ $self->{'FILENAME'}, $lineno ) ;
+ }
+ # Patch by Norbert Preining added the 2003/03/17
+ return "$_[1]$_[3]->{'text'}";
+}
+
+=pod
+
+=item * __texcommand_font_series()
+
+Apply the specified font series (Medium or Bold).
+Takes at least 4 args:
+
+=over
+
+=item * start_balise (hash)
+
+is the HTML balise used to start this style
+
+=item * end_balise (hash)
+
+is the HTML balise used to end this style
+
+=item * fontset (string)
+
+is the name of the font set to manage (eg, SERIES, SHAPES...)
+
+=item * lineno (integer)
+
+=item * params (array)
+
+is the list of parameters
+
+=back
+
+=cut
+sub __texcommand_font_style($$$$;@) {
+ my $self = shift ;
+ my $lineno = $_[2] || 0 ;
+ my ($begin,$end) = ( $_[0] || '', $_[1] || '' ) ;
+ my ($set,$text) = ( $_[2] || '', '' ) ;
+
+ confess( "You must supply a valid fontset name (from ".
+ join( ', ', keys %{$self->{'FONTS'}} ).
+ ")." ) unless ( exists $self->{'FONTS'}{$set} ) ;
+
+ my $last = ( int(@{$self->{'FONTS'}{$set}}) > 0 ) ?
+ $self->{'FONTS'}{$set}->[$#{$self->{'FONTS'}{$set}}] : '' ;
+
+ my $elt = { 'begin' => $begin,
+ 'end' => $end,
+ } ;
+ push @{$self->{'FONTS'}{$set}}, $elt ;
+ push @{$self->{'FONTS'}{'ALLS'}}, $elt ;
+
+ if ( ( ! $last ) ||
+ ( ! ishash( $last ) ) ||
+ ( $last->{'begin'} ne $begin ) ) {
+ $text .= ( ( $last && ( ishash($last) ) ) ? $last->{'end'} : '' ).$begin ;
+ }
+
+ if ( ( $_[4] ) && ( ishash( $_[4] ) ) ) {
+ if ( $_[4]->{'eval'} ) {
+ $text .= $self->translate( $_[4]->{'text'}, undef, $lineno ) ;
+ }
+ else {
+ $text .= $_[4] ;
+ }
+ }
+
+ if ( ( ! $last ) ||
+ ( ! ishash( $last ) ) ||
+ ( $last->{'begin'} ne $begin ) ) {
+ $text .= $end.( ( $last && ( ishash($last) ) ) ? $last->{'begin'} : '' ) ;
+ }
+
+ pop @{$self->{'FONTS'}{'ALLS'}} ;
+ pop @{$self->{'FONTS'}{$set}} ;
+
+ if ( $begin || $end ) {
+ $text =~ s/\Q$begin$end\E//g ;
+ $text =~ s/\Q$end$begin\E//g ;
+ }
+
+ return $text ;
+}
+
+#------------------------------------------------------
+#
+# TeX command callbacks
+#
+#------------------------------------------------------
+
+=pod
+
+=item * texcommand_font_medium()
+
+Treats \textmd or \mdseries
+
+=cut
+sub texcommand_font_medium {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '',
+ '',
+ 'SERIES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_mathset()
+
+Treats \mathbb
+
+=cut
+sub texcommand_font_mathset {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '<i>',
+ '</i>',
+ 'SERIES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_bold()
+
+Treats \bf or \textbf
+
+=cut
+sub texcommand_font_bold {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '<b>',
+ '</b>',
+ 'SERIES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_roman()
+
+Treats \rm or \textrm
+
+=cut
+sub texcommand_font_roman {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '',
+ '',
+ 'FAMILIES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_serif()
+
+Treats \sf or \textsf
+
+=cut
+sub texcommand_font_serif {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '<font face="Sans Serif">',
+ '<!-- /fontSF --></font>',
+ 'FAMILIES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_typewriter()
+
+Treats \tt or \texttt
+
+=cut
+sub texcommand_font_typewriter {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '<tt>',
+ '</tt>',
+ 'FAMILIES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_upright()
+
+Treats \upshape or \textup
+
+=cut
+sub texcommand_font_upright {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '',
+ '',
+ 'SHAPES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_italic()
+
+Treats \it or \textit
+
+=cut
+sub texcommand_font_italic {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '<i>',
+ '</i>',
+ 'SHAPES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_slanted()
+
+Treats \sl or \textsl
+
+=cut
+sub texcommand_font_slanted {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_font_style( '<i><tt>',
+ '</tt></i>',
+ 'SHAPES',
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_font_smallcap()
+
+Treats \sc or \textsc
+
+=cut
+sub texcommand_font_smallcap {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ my $text = $self->__texcommand_font_style( '<!-- SMALL CAPS -->',
+ '<!-- /SMALL CAPS -->',
+ 'SHAPES',
+ $lineno, @_ ) ;
+ my $r = '' ;
+ while ( ( $text ) &&
+ ( $text =~ /^(.*?)<!-- SMALL CAPS -->(.*?)<!-- \/SMALL CAPS -->(.*)$/ ) ) {
+ (my $prev, my $sc, $text) = ($1,$2,$3) ;
+ $r .= $prev . html_sc( $sc ) ;
+ }
+ if ( $text ) {
+ $r .= $text ;
+ }
+ return $r ;
+}
+
+=pod
+
+=item * texcommand_font_normal()
+
+Treats \textnormal or \normalfont
+
+=cut
+sub texcommand_font_normal {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ my ($begin,$end)=('','');
+ foreach my $envs ( @{$self->{'FONTS'}{'ALLS'}} ) {
+ if ( $envs ) {
+ $begin .= $envs->{'begin'} ;
+ $end = $envs->{'end'} . $end ;
+ }
+ }
+ return $end.($_[0]->{'text'}||'').$begin ;
+}
+
+=pod
+
+=item * texcommand_cedil()
+
+Treats \c{}
+
+=cut
+sub texcommand_cedil {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'C' => 'Ccedil',
+ 'c' => 'ccedil',
+ 'S' => '#x015e',
+ 's' => '#x015f',
+ 'T' => '#x0162',
+ 't' => '#x0163',
+ },
+ "&cedil;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_ucircle()
+
+Treats \u{}
+
+=cut
+sub texcommand_ucircle { # added by Tobia
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'A' => '#x0102',
+ 'a' => '#x0103',
+ },
+ "&#x0306;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_acute()
+
+Treats \'{}
+
+=cut
+sub texcommand_acute {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'A' => 'Aacute',
+ 'E' => 'Eacute',
+ 'I' => 'Iacute',
+ 'O' => 'Oacute',
+ 'U' => 'Uacute',
+ 'Y' => 'Yacute',
+ 'a' => 'aacute',
+ 'e' => 'eacute',
+ 'i' => 'iacute',
+ 'o' => 'oacute',
+ 'u' => 'uacute',
+ 'y' => 'yacute',
+ '\\i' => 'iacute',
+ #Patched by Gasper Jaklic <gasper.jaklic@fmf.uni-lj.si>
+ 'C' => '#262',
+ 'c' => '#263',
+ },
+ "&acute;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_grave()
+
+Treats \'{}
+
+=cut
+sub texcommand_grave {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'A' => 'Agrave',
+ 'E' => 'Egrave',
+ 'I' => 'Igrave',
+ 'O' => 'Ograve',
+ 'U' => 'Ugrave',
+ 'a' => 'agrave',
+ 'e' => 'egrave',
+ 'i' => 'igrave',
+ 'o' => 'ograve',
+ 'u' => 'ugrave',
+ '\\i' => 'igrave',
+ },
+ "&grave;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_tilde()
+
+Treats \~{}
+
+=cut
+sub texcommand_tilde {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'A' => 'Atilde',
+ 'N' => 'Ntilde',
+ 'O' => 'Otilde',
+ 'a' => 'atilde',
+ 'n' => 'ntilde',
+ 'o' => 'otilde',
+ },
+ "&tilde;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_uml()
+
+Treats \"{}
+
+=cut
+sub texcommand_uml {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'A' => 'Auml',
+ 'E' => 'Euml',
+ 'I' => 'Iuml',
+ 'O' => 'Ouml',
+ 'U' => 'Uuml',
+ 'Y' => 'Yuml',
+ 'a' => 'auml',
+ 'e' => 'euml',
+ 'i' => 'iuml',
+ 'o' => 'ouml',
+ 'u' => 'uuml',
+ 'y' => 'yuml',
+ '\\i' => 'iuml',
+ },
+ "&uml;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_circ()
+
+Treats \^{}
+
+=cut
+sub texcommand_circ {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'A' => 'Acirc',
+ 'E' => 'Ecirc',
+ 'I' => 'Icirc',
+ 'O' => 'Ocirc',
+ 'U' => 'Ucirc',
+ 'a' => 'acirc',
+ 'e' => 'ecirc',
+ 'i' => 'icirc',
+ 'o' => 'ocirc',
+ 'u' => 'ucirc',
+ '\\i' => 'icirc',
+ },
+ "&circ;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_caron()
+
+Treats \v{}
+
+=cut
+sub texcommand_caron {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return $self->__texcommand_map_to( { 'S' => 'Scaron',
+ 's' => 'scaron',
+ #Patched by Luca Paolini <paolini@di.unito.it>
+ #Patched by Gasper Jaklic <gasper.jaklic@fmf.uni-lj.si>
+ 'C' => '#268',
+ 'c' => '#269',
+ 'D' => '#270',
+ 'd' => '#271',
+ 'E' => '#282',
+ 'e' => '#283',
+ 'L' => '#317',
+ 'l' => '#318',
+ 'N' => '#327',
+ 'n' => '#328',
+ 'R' => '#344',
+ 'r' => '#345',
+ 'T' => '#356',
+ 't' => '#357',
+ 'Z' => '#381',
+ 'z' => '#382',
+ },
+ "",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_bar()
+
+Treats \={}
+
+=cut
+sub texcommand_bar {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ return "&macr;" unless $_[0] ;
+ return $self->__texcommand_map_to( { },
+ "&macr;",
+ $lineno, @_ ) ;
+}
+
+=pod
+
+=item * texcommand_def()
+
+Treats \def and \gdef
+
+=cut
+sub texcommand_def {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ Bib2HTML::General::Error::warm( "command name expected after a \\def or a \\gdef",
+ $self->{'FILENAME'},
+ $lineno )
+ unless $_[0]->{'text'} ;
+ # The command definition is never evaluated
+ my $trans_txt = $_[1]->{'text'} ;
+ addtrans_cmd_noparam( $_[0]->{'text'}, $trans_txt, 1 ) ;
+ return '' ;
+}
+
+=pod
+
+=item * texcommand_edef()
+
+Treats \edef and \xdef
+
+=cut
+sub texcommand_edef {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ Bib2HTML::General::Error::warm( "command name expected after a \\edef or a \\xdef",
+ $self->{'FILENAME'},
+ $lineno )
+ unless $_[0]->{'text'} ;
+ # The command definition is always evaluated
+ my $trans_txt = $self->translate( $_[1]->{'text'} || '', undef, $lineno ) ;
+ addtrans_cmd_noparam( $_[0]->{'text'}, $trans_txt, 0 ) ;
+ return '' ;
+}
+
+=pod
+
+=item * texcommand_newcommand()
+
+Treats \newcommand and \renewcommand
+
+=cut
+sub texcommand_newcommand {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ # Check for command name
+ my $name = $_[0]->{'text'} || '' ;
+ $name =~ s/^\\// ;
+ if ( ! $name ) {
+ Bib2HTML::General::Error::warm( "command name expected after a \\def",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ return '' ;
+ }
+ # Builds the parameter definition
+ my $params = "" ;
+ if ( ( $_[1]->{'text'} ) && ( $_[1]->{'text'} > 0 ) ) {
+ my $count = $_[1]->{'text'} ;
+ if ( $_[2]->{'text'} ) {
+ $count -- ;
+ $params .= '['.$_[2]->{'text'}.']' ;
+ }
+ while ( $count > 0 ) {
+ $count -- ;
+ $params .= '{}' ;
+ }
+ }
+
+ # The command definition is never evaluated
+ my $trans = $_[3]->{'text'} || '' ;
+
+ # Adds the command definition
+ if ( $params ) {
+ addtrans_cmd_html( $name, $params, $trans, 1 ) ;
+ }
+ else {
+ addtrans_cmd_noparam( $name, $trans, 1 ) ;
+ }
+ return '' ;
+}
+
+=pod
+
+=item * texcommand_ensuremath()
+
+Treats \ensuremath
+
+=cut
+sub texcommand_ensuremath {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ my $trans = '' ;
+ my $math = $self->is_math_mode() ;
+
+ $trans = $self->start_math_mode(1) unless ( $math ) ;
+
+ if ( $_[0]->{'eval'} ) {
+ $trans .= $self->translate( $_[0]->{'text'} || '', undef, $lineno ) ;
+ }
+ else {
+ $trans .= $_[0]->{'text'} || '' ;
+ }
+
+ $trans .= $self->stop_math_mode() unless ( $math ) ;
+
+ return $trans ;
+}
+
+=pod
+
+=item * texcommand_ensuretext()
+
+Treats \text
+
+=cut
+sub texcommand_ensuretext {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ my $trans = '' ;
+ my $math ;
+ if ( $self->is_inline_math_mode() ) {
+ $math = 1 ;
+ }
+ elsif ( $self->is_multiline_math_mode() ) {
+ $math = 2 ;
+ }
+ else {
+ $math = 0 ;
+ }
+
+ $trans = $self->stop_math_mode() if ( $math ) ;
+
+ if ( $_[0]->{'eval'} ) {
+ $trans .= $self->translate( $_[0]->{'text'} || '', undef, $lineno ) ;
+ }
+ else {
+ $trans .= $_[0]->{'text'} || '' ;
+ }
+
+ $trans .= $self->start_math_mode( $math ) if ( $math ) ;
+
+ return $trans ;
+}
+
+=pod
+
+=item * texcommand_cite()
+
+Treats \cite
+
+=cut
+sub texcommand_cite {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ my $key = $_[1]->{'text'} || '' ;
+ my $label = $_[0]->{'text'} || '' ;
+ my $cite = $label || '?' ;
+ if ( ($key) &&
+ ( ishash($self->{'DATABASE'}) ) &&
+ ( ! isemptyhash( $self->{'DATABASE'} ) ) &&
+ ( exists $self->{'DATABASE'}{$key} ) ) {
+ $cite = "<BIB2HTML action=CITE key=\"$key\"" ;
+ if ( $label ) {
+ my $bibtex = new Bib2HTML::Translator::BibTeXEntry() ;
+ $bibtex->save_citation_label( $key, $label ) ;
+ $cite .= " label=\"".addslashes( $label )."\"" ;
+ }
+ $cite .= ">". ( $label || '?' ) . "</BIB2HTML>" ;
+ }
+ return "[".$cite."]" ;
+}
+
+=pod
+
+=item * texcommand_beginenv()
+
+Treats \begin
+
+=cut
+sub texcommand_beginenv {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ my $env = $_[0]->{'text'} || '' ;
+
+ if ( ! $env ) {
+ Bib2HTML::General::Error::warm( "environment name not found for a command \\begin",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ return '' ;
+ }
+
+ # register the environment opening here to
+ # prevent error during the closing
+ push @{$self->{'ENVIRONMENTS'}}, $env ;
+
+ return "\\start$env" ;
+}
+
+=pod
+
+=item * texcommand_endenv()
+
+Treats \end
+
+=cut
+sub texcommand_endenv {
+ my $self = shift ;
+ my $lineno = shift || 0 ;
+ my $env = $_[0]->{'text'} || '' ;
+
+ if ( ! $env ) {
+ Bib2HTML::General::Error::warm( "environment name not found for a command \\end",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ return '' ;
+ }
+
+ # Pop the environment contex
+ # and warm if the closed environment
+ # does not match the opened
+ if ( isemptyarray($self->{'ENVIRONMENTS'}) ) {
+ Bib2HTML::General::Error::warm( "found \\end{$env} without \\begin{$env}",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ return '' ;
+ }
+
+ my $opened = $self->{'ENVIRONMENTS'}->[$#{$self->{'ENVIRONMENTS'}}] ;
+ if ( ( !$opened ) ||
+ ( $opened ne $env ) ) {
+ Bib2HTML::General::Error::warm( "found \\end{$env} instead of \\end{$opened}",
+ $self->{'FILENAME'},
+ $lineno ) ;
+ return '' ;
+ }
+
+ pop @{$self->{'ENVIRONMENTS'}} ;
+
+ return "\\end$env" ;
+}
+
+1;
+__END__
+
+=back
+
+=head1 COPYRIGHT
+
+(c) Copyright 1998-09 Stéphane Galland E<lt>galland@arakhne.orgE<gt>, under GPL.
+
+=head1 AUTHORS
+
+=over
+
+=item *
+
+Conceived and initially developed by Stéphane Galland E<lt>galland@arakhne.orgE<gt>.
+Some TeX commands are added by Dimitris Michail E<lt>michail@mpi-sb.mpg.deE<gt>
+and Tobias Loew E<lt>loew@mathematik.tu-darmstadt.deE<gt>
+
+=back
+
+=head1 SEE ALSO
+
+bib2html.pl
diff --git a/biblio/bibtex/utils/bib2ml/src/bib2html.php b/biblio/bibtex/utils/bib2ml/src/bib2html.php
new file mode 100755
index 0000000000..841a79fda9
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/bib2html.php
@@ -0,0 +1,41 @@
+<?php
+
+/* bib2html script to generate an HTML document for BibTeX database
+ * Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; see the file COPYING. If not, write to
+ * the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 02111-1307, USA.
+ */
+
+$BIBFILE = '/path/to/my/bibtex/file';
+
+$ARGUMENTS = array(
+ 'bib2html',
+ '--stdout',
+ '-q',
+ "$BIBFILE",
+ );
+
+$cmd = "";
+foreach($ARGUMENTS as $arg) {
+ if ($cmd) {
+ $cmd .= '.';
+ }
+ $cmd .= escapeshellarg("$arg");
+}
+
+exec("$cmd");
+
+?>
diff --git a/biblio/bibtex/utils/bib2ml/src/bib2html.pl b/biblio/bibtex/utils/bib2ml/src/bib2html.pl
new file mode 100755
index 0000000000..4d867a7654
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/bib2html.pl
@@ -0,0 +1,55 @@
+#!/usr/bin/perl -w
+
+# bib2html script to generate an HTML document for BibTeX database
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+use strict ;
+use File::Basename ;
+use File::Spec ;
+
+#------------------------------------------------------
+#
+# Initialization code
+#
+#------------------------------------------------------
+my $PERLSCRIPTDIR ;
+my $PERLSCRIPTNAME ;
+BEGIN{
+ # Where is this script?
+ $PERLSCRIPTDIR = "$0";
+ my $scriptdir = dirname( $PERLSCRIPTDIR );
+ while ( -e $PERLSCRIPTDIR && -l $PERLSCRIPTDIR ) {
+ $PERLSCRIPTDIR = readlink($PERLSCRIPTDIR);
+ if ( substr( $PERLSCRIPTDIR, 0, 1 ) eq '.' ) {
+ $PERLSCRIPTDIR = File::Spec->catfile( $scriptdir, "$PERLSCRIPTDIR" ) ;
+ }
+ $scriptdir = dirname( $PERLSCRIPTDIR );
+ }
+ $PERLSCRIPTNAME = basename( $PERLSCRIPTDIR ) ;
+ $PERLSCRIPTDIR = dirname( $PERLSCRIPTDIR ) ;
+ $PERLSCRIPTDIR = File::Spec->rel2abs( "$PERLSCRIPTDIR" );
+ # Push the path where the script is to retreive the arakhne.org packages
+ push(@INC,"$PERLSCRIPTDIR");
+
+}
+
+use Bib2HTML::Main;
+
+launchBib2HTML("$PERLSCRIPTDIR","$PERLSCRIPTNAME");
+
+__END__
diff --git a/biblio/bibtex/utils/bib2ml/src/bib2sql.pl b/biblio/bibtex/utils/bib2ml/src/bib2sql.pl
new file mode 100755
index 0000000000..d358d7e878
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/bib2sql.pl
@@ -0,0 +1,57 @@
+#!/usr/bin/perl -w
+
+# bib2sql script to generate a SQL document for BibTeX database
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+use strict ;
+use File::Basename ;
+use File::Spec ;
+
+#------------------------------------------------------
+#
+# Initialization code
+#
+#------------------------------------------------------
+my $PERLSCRIPTDIR ;
+my $PERLSCRIPTNAME ;
+BEGIN{
+ # Where is this script?
+ $PERLSCRIPTDIR = "$0";
+ my $scriptdir = dirname( $PERLSCRIPTDIR );
+ while ( -e $PERLSCRIPTDIR && -l $PERLSCRIPTDIR ) {
+ $PERLSCRIPTDIR = readlink($PERLSCRIPTDIR);
+ if ( substr( $PERLSCRIPTDIR, 0, 1 ) eq '.' ) {
+ $PERLSCRIPTDIR = File::Spec->catfile( $scriptdir, "$PERLSCRIPTDIR" ) ;
+ }
+ $scriptdir = dirname( $PERLSCRIPTDIR );
+ }
+ $PERLSCRIPTNAME = basename( $PERLSCRIPTDIR ) ;
+ $PERLSCRIPTDIR = dirname( $PERLSCRIPTDIR ) ;
+ $PERLSCRIPTDIR = File::Spec->rel2abs( "$PERLSCRIPTDIR" );
+ # Push the path where the script is to retreive the arakhne.org packages
+ push(@INC,"$PERLSCRIPTDIR");
+
+}
+
+use Bib2HTML::Main;
+
+push @ARGV, "-g", "SQL";
+
+launchBib2HTML("$PERLSCRIPTDIR","$PERLSCRIPTNAME");
+
+__END__
diff --git a/biblio/bibtex/utils/bib2ml/src/bib2xml.pl b/biblio/bibtex/utils/bib2ml/src/bib2xml.pl
new file mode 100755
index 0000000000..c37b41a83a
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/src/bib2xml.pl
@@ -0,0 +1,57 @@
+#!/usr/bin/perl -w
+
+# bib2xml script to generate a XML document for BibTeX database
+# Copyright (C) 1998-09 Stephane Galland <galland@arakhne.org>
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; see the file COPYING. If not, write to
+# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA 02111-1307, USA.
+
+use strict ;
+use File::Basename ;
+use File::Spec ;
+
+#------------------------------------------------------
+#
+# Initialization code
+#
+#------------------------------------------------------
+my $PERLSCRIPTDIR ;
+my $PERLSCRIPTNAME ;
+BEGIN{
+ # Where is this script?
+ $PERLSCRIPTDIR = "$0";
+ my $scriptdir = dirname( $PERLSCRIPTDIR );
+ while ( -e $PERLSCRIPTDIR && -l $PERLSCRIPTDIR ) {
+ $PERLSCRIPTDIR = readlink($PERLSCRIPTDIR);
+ if ( substr( $PERLSCRIPTDIR, 0, 1 ) eq '.' ) {
+ $PERLSCRIPTDIR = File::Spec->catfile( $scriptdir, "$PERLSCRIPTDIR" ) ;
+ }
+ $scriptdir = dirname( $PERLSCRIPTDIR );
+ }
+ $PERLSCRIPTNAME = basename( $PERLSCRIPTDIR ) ;
+ $PERLSCRIPTDIR = dirname( $PERLSCRIPTDIR ) ;
+ $PERLSCRIPTDIR = File::Spec->rel2abs( "$PERLSCRIPTDIR" );
+ # Push the path where the script is to retreive the arakhne.org packages
+ push(@INC,"$PERLSCRIPTDIR");
+
+}
+
+use Bib2HTML::Main;
+
+push @ARGV, "-g", "XML";
+
+launchBib2HTML("$PERLSCRIPTDIR","$PERLSCRIPTNAME");
+
+__END__
diff --git a/biblio/bibtex/utils/bib2ml/test.bib b/biblio/bibtex/utils/bib2ml/test.bib
new file mode 100644
index 0000000000..2ecb457a85
--- /dev/null
+++ b/biblio/bibtex/utils/bib2ml/test.bib
@@ -0,0 +1,5 @@
+@ARTICLE{ test
+ author = { Galland, Stéphane },
+ title = {My Test},
+ year = 2009,
+}