From e18208b7503bf97518a6a6126f125ec004a916c0 Mon Sep 17 00:00:00 2001 From: Adrian Perez Date: Wed, 30 Nov 2011 22:41:13 +0200 Subject: [PATCH] doctool: Support translation of underlines for sub-pages For files which do not qualify to be included as part of the HTML index it is needed to translate the sectioning when assembling the TeX code for PDF file generation, because in this case the files are included inline and it is needed for them to create subsections instead of top level chapters. Also, the sorting is improved to take only into account the numnbering that precedes the descriptive text in the filenames of .rst sources. This makes sorting the files for inlining in the TeX output work as expected. --- doc/tools/doctool | 70 ++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 63 insertions(+), 7 deletions(-) diff --git a/doc/tools/doctool b/doc/tools/doctool index 166abb664..78b5f0e66 100755 --- a/doc/tools/doctool +++ b/doc/tools/doctool @@ -3,6 +3,7 @@ import sys, shlex, subprocess from optparse import OptionParser, OptionGroup from docutils.writers import latex2e +import re try: import locale @@ -42,6 +43,23 @@ OPT.docinfo.add_option("-i", "--info", dest="docinfo", help="Read project information from FILE") +is_index_filename = re.compile(r'^[0-9]{2}-[a-zA-Z].*').match + + +def str_to_numeric_tuple(s): + r = [] + for item in s.split("-"): + try: + r.append(int(item, 10)) + except ValueError: + # Tried to convert a non-integer, bail out + break + return tuple(r) + +def str_tuple_sort(a, b): + return cmp(str_to_numeric_tuple(a), str_to_numeric_tuple(b)) + + def optparser(*groups): parser.add_option_group(OPT.common) [parser.add_option_group(g) for g in groups] @@ -50,7 +68,12 @@ def optparser(*groups): class DupRefsRemover(object): def __init__(self, out): - self.out = out + if hasattr(out, "write"): + self.out = out.write + elif hasattr(out, "handle_line"): + self.out = out.handle_line + else: + raise ValueError("%r has no write/handle_line" % out) self.ref = dict() def handle_line(self, line): @@ -64,9 +87,35 @@ class DupRefsRemover(object): else: # Add reference and print it out self.ref[r[0]] = r[1] - self.out.write(line) + self.out(line) else: - self.out.write(line) + self.out(line) + + +class UnderlineXlate(object): + _XLATE = { + "#": "=", + "=": "-", + "-": "~", + "~": "^", + } + + def __init__(self, out): + if hasattr(out, "write"): + self.out = out.write + elif hasattr(out, "handle_line"): + self.out = out.handle_line + else: + raise ValueError("%r has no write/handle_line" % out) + + def handle_line(self, line): + sline = line.strip() + if len(sline): + if sline[0] in self._XLATE: + sline = sline.replace(sline[0], self._XLATE[sline[0]]) + self.out(sline) + return + self.out(line) @@ -239,13 +288,17 @@ class DocTool(object): print out = DupRefsRemover(sys.stdout) + out_xlate = UnderlineXlate(out) - for name in sorted(args): + args = list(args) + args.sort(str_tuple_sort) + + for name in args: if not name.endswith(".rst"): continue f = file(name, "rU") - map(out.handle_line, + map(is_index_filename(name) and out.handle_line or out_xlate.handle_line, filter(lambda l: ".. contents::" not in l, f.readlines()) ) @@ -263,9 +316,12 @@ class DocTool(object): f.close() print - for name in sorted(args): + args = list(args) + args.sort(str_tuple_sort) + + for name in args: # Skip non-RST inputs - if not name.endswith(".rst"): + if not name.endswith(".rst") or not is_index_filename(name): continue f = file(name, "rU")