git-svn-id: svn://svn.icms.temple.edu/lammps-ro/trunk@15590 f3b2605a-c512-4ea7-a41b-209d697bcdaa
This commit is contained in:
@ -25,6 +25,7 @@ import re
|
|||||||
import sys
|
import sys
|
||||||
import argparse
|
import argparse
|
||||||
|
|
||||||
|
|
||||||
class Markup(object):
|
class Markup(object):
|
||||||
BOLD_START = "["
|
BOLD_START = "["
|
||||||
BOLD_END = "]"
|
BOLD_END = "]"
|
||||||
@ -77,6 +78,7 @@ class Markup(object):
|
|||||||
text = text.replace('\"%s\"_%s' % (name, link), href, 1)
|
text = text.replace('\"%s\"_%s' % (name, link), href, 1)
|
||||||
return text
|
return text
|
||||||
|
|
||||||
|
|
||||||
class HTMLMarkup(Markup):
|
class HTMLMarkup(Markup):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
super().__init__()
|
super().__init__()
|
||||||
@ -101,6 +103,7 @@ class HTMLMarkup(Markup):
|
|||||||
|
|
||||||
return "<A HREF = \"" + href + "\">" + content + "</A>"
|
return "<A HREF = \"" + href + "\">" + content + "</A>"
|
||||||
|
|
||||||
|
|
||||||
class Formatting(object):
|
class Formatting(object):
|
||||||
UNORDERED_LIST_MODE = "unordered-list"
|
UNORDERED_LIST_MODE = "unordered-list"
|
||||||
ORDERED_LIST_MODE = "ordered-list"
|
ORDERED_LIST_MODE = "ordered-list"
|
||||||
@ -435,6 +438,7 @@ class Formatting(object):
|
|||||||
|
|
||||||
return rows
|
return rows
|
||||||
|
|
||||||
|
|
||||||
class HTMLFormatting(Formatting):
|
class HTMLFormatting(Formatting):
|
||||||
def __init__(self, markup):
|
def __init__(self, markup):
|
||||||
super().__init__(markup)
|
super().__init__(markup)
|
||||||
@ -448,6 +452,7 @@ class HTMLFormatting(Formatting):
|
|||||||
def raw_html(self, content):
|
def raw_html(self, content):
|
||||||
return content
|
return content
|
||||||
|
|
||||||
|
|
||||||
class TxtParser(object):
|
class TxtParser(object):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.markup = HTMLMarkup()
|
self.markup = HTMLMarkup()
|
||||||
@ -630,6 +635,7 @@ class TxtParser(object):
|
|||||||
|
|
||||||
i += 1
|
i += 1
|
||||||
|
|
||||||
|
|
||||||
class Txt2Html(TxtParser):
|
class Txt2Html(TxtParser):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
super().__init__()
|
super().__init__()
|
||||||
@ -641,6 +647,7 @@ class Txt2Html(TxtParser):
|
|||||||
line.startswith(".. END_HTML_ONLY") or \
|
line.startswith(".. END_HTML_ONLY") or \
|
||||||
super().is_paragraph_separator(line)
|
super().is_paragraph_separator(line)
|
||||||
|
|
||||||
|
|
||||||
class TxtConverter:
|
class TxtConverter:
|
||||||
def get_argument_parser(self):
|
def get_argument_parser(self):
|
||||||
return None
|
return None
|
||||||
@ -665,7 +672,15 @@ class TxtConverter:
|
|||||||
print("Converting", filename, "...", file=err)
|
print("Converting", filename, "...", file=err)
|
||||||
content = f.read()
|
content = f.read()
|
||||||
converter = self.create_converter(parsed_args)
|
converter = self.create_converter(parsed_args)
|
||||||
result = converter.convert(content)
|
|
||||||
|
try:
|
||||||
|
result = converter.convert(content)
|
||||||
|
except Exception as e:
|
||||||
|
msg = "###########################################################################\n" \
|
||||||
|
" ERROR: " + e.args[0] + "\n" \
|
||||||
|
"###########################################################################\n"
|
||||||
|
print(msg, file=err)
|
||||||
|
result = msg
|
||||||
|
|
||||||
if write_to_files:
|
if write_to_files:
|
||||||
output_filename = self.get_output_filename(filename)
|
output_filename = self.get_output_filename(filename)
|
||||||
@ -674,6 +689,7 @@ class TxtConverter:
|
|||||||
else:
|
else:
|
||||||
print(result, end='', file=out)
|
print(result, end='', file=out)
|
||||||
|
|
||||||
|
|
||||||
class Txt2HtmlConverter(TxtConverter):
|
class Txt2HtmlConverter(TxtConverter):
|
||||||
def get_argument_parser(self):
|
def get_argument_parser(self):
|
||||||
parser = argparse.ArgumentParser(description='converts a text file with simple formatting & markup into HTML.\n'
|
parser = argparse.ArgumentParser(description='converts a text file with simple formatting & markup into HTML.\n'
|
||||||
|
|||||||
@ -24,6 +24,7 @@ import argparse
|
|||||||
from lammpsdoc import lammps_filters
|
from lammpsdoc import lammps_filters
|
||||||
from lammpsdoc.txt2html import Markup, Formatting, TxtParser, TxtConverter
|
from lammpsdoc.txt2html import Markup, Formatting, TxtParser, TxtConverter
|
||||||
|
|
||||||
|
|
||||||
class RSTMarkup(Markup):
|
class RSTMarkup(Markup):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
super().__init__()
|
super().__init__()
|
||||||
@ -65,6 +66,7 @@ class RSTMarkup(Markup):
|
|||||||
def escape_rst_chars(self, text):
|
def escape_rst_chars(self, text):
|
||||||
text = text.replace('*', '\\*')
|
text = text.replace('*', '\\*')
|
||||||
text = text.replace('^', '\\^')
|
text = text.replace('^', '\\^')
|
||||||
|
text = text.replace('|', '\\|')
|
||||||
text = re.sub(r'([^"])_', r'\1\\_', text)
|
text = re.sub(r'([^"])_', r'\1\\_', text)
|
||||||
return text
|
return text
|
||||||
|
|
||||||
@ -72,6 +74,7 @@ class RSTMarkup(Markup):
|
|||||||
text = text.replace('\\*', '*')
|
text = text.replace('\\*', '*')
|
||||||
text = text.replace('\\^', '^')
|
text = text.replace('\\^', '^')
|
||||||
text = text.replace('\\_', '_')
|
text = text.replace('\\_', '_')
|
||||||
|
text = text.replace('\\|', '|')
|
||||||
return text
|
return text
|
||||||
|
|
||||||
def inline_math(self, text):
|
def inline_math(self, text):
|
||||||
@ -112,13 +115,18 @@ class RSTMarkup(Markup):
|
|||||||
|
|
||||||
return "`%s <%s>`_" % (content, href)
|
return "`%s <%s>`_" % (content, href)
|
||||||
|
|
||||||
|
|
||||||
class RSTFormatting(Formatting):
|
class RSTFormatting(Formatting):
|
||||||
RST_HEADER_TYPES = '#*=-^"'
|
RST_HEADER_TYPES = '#*=-^"'
|
||||||
|
|
||||||
def __init__(self, markup):
|
def __init__(self, markup):
|
||||||
super().__init__(markup)
|
super().__init__(markup)
|
||||||
|
self.indent_level = 0
|
||||||
|
|
||||||
def paragraph(self, content):
|
def paragraph(self, content):
|
||||||
|
if self.indent_level > 0:
|
||||||
|
return '\n' + self.list_indent(content.strip(), self.indent_level)
|
||||||
|
|
||||||
return content.strip() + "\n"
|
return content.strip() + "\n"
|
||||||
|
|
||||||
def center(self, content):
|
def center(self, content):
|
||||||
@ -128,7 +136,9 @@ class RSTFormatting(Formatting):
|
|||||||
return content.strip()
|
return content.strip()
|
||||||
|
|
||||||
def preformat(self, content):
|
def preformat(self, content):
|
||||||
return ".. parsed-literal::\n\n" + self.indent(content.rstrip())
|
if self.indent_level > 0:
|
||||||
|
return self.list_indent("\n.. parsed-literal::\n\n" + self.indent(content.rstrip()), self.indent_level)
|
||||||
|
return "\n.. parsed-literal::\n\n" + self.indent(content.rstrip())
|
||||||
|
|
||||||
def horizontal_rule(self, content):
|
def horizontal_rule(self, content):
|
||||||
return "\n----------\n\n" + content.strip()
|
return "\n----------\n\n" + content.strip()
|
||||||
@ -159,7 +169,7 @@ class RSTFormatting(Formatting):
|
|||||||
|
|
||||||
def header(self, content, level):
|
def header(self, content, level):
|
||||||
header_content = content.strip()
|
header_content = content.strip()
|
||||||
header_content = re.sub(r'[0-9]+\.[0-9]*\s+', '', header_content)
|
header_content = re.sub(r'[0-9]+\.([0-9]*\.?)*\s+', '', header_content)
|
||||||
header_underline = RSTFormatting.RST_HEADER_TYPES[level-1] * len(header_content)
|
header_underline = RSTFormatting.RST_HEADER_TYPES[level-1] * len(header_content)
|
||||||
return header_content + "\n" + header_underline + "\n"
|
return header_content + "\n" + header_underline + "\n"
|
||||||
|
|
||||||
@ -178,14 +188,17 @@ class RSTFormatting(Formatting):
|
|||||||
return self.indent(paragraph.strip())
|
return self.indent(paragraph.strip())
|
||||||
|
|
||||||
def unordered_list_begin(self, paragraph):
|
def unordered_list_begin(self, paragraph):
|
||||||
|
self.indent_level += 1
|
||||||
return paragraph
|
return paragraph
|
||||||
|
|
||||||
def unordered_list_end(self, paragraph):
|
def unordered_list_end(self, paragraph):
|
||||||
|
self.indent_level -= 1
|
||||||
return paragraph.rstrip() + '\n'
|
return paragraph.rstrip() + '\n'
|
||||||
|
|
||||||
def ordered_list_begin(self, paragraph):
|
def ordered_list_begin(self, paragraph):
|
||||||
if paragraph.startswith('* '):
|
if paragraph.startswith('* '):
|
||||||
paragraph = '#. ' + paragraph[2:]
|
paragraph = '#. ' + paragraph[2:]
|
||||||
|
self.indent_level += 1
|
||||||
return paragraph
|
return paragraph
|
||||||
|
|
||||||
def definition_list_begin(self, paragraph):
|
def definition_list_begin(self, paragraph):
|
||||||
@ -195,6 +208,7 @@ class RSTFormatting(Formatting):
|
|||||||
return paragraph
|
return paragraph
|
||||||
|
|
||||||
def ordered_list_end(self, paragraph):
|
def ordered_list_end(self, paragraph):
|
||||||
|
self.indent_level -= 1
|
||||||
return paragraph.rstrip() + '\n'
|
return paragraph.rstrip() + '\n'
|
||||||
|
|
||||||
def ordered_list(self, paragraph):
|
def ordered_list(self, paragraph):
|
||||||
@ -228,6 +242,12 @@ class RSTFormatting(Formatting):
|
|||||||
indented += " %s\n" % line
|
indented += " %s\n" % line
|
||||||
return indented
|
return indented
|
||||||
|
|
||||||
|
def list_indent(self, content, level=1):
|
||||||
|
indented = ""
|
||||||
|
for line in content.splitlines():
|
||||||
|
indented += " " * level + ("%s\n" % line)
|
||||||
|
return indented
|
||||||
|
|
||||||
def get_max_column_widths(self, rows):
|
def get_max_column_widths(self, rows):
|
||||||
num_columns = max([len(row) for row in rows])
|
num_columns = max([len(row) for row in rows])
|
||||||
max_widths = [0] * num_columns
|
max_widths = [0] * num_columns
|
||||||
@ -321,6 +341,7 @@ class RSTFormatting(Formatting):
|
|||||||
|
|
||||||
return text + post
|
return text + post
|
||||||
|
|
||||||
|
|
||||||
class Txt2Rst(TxtParser):
|
class Txt2Rst(TxtParser):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
super().__init__()
|
super().__init__()
|
||||||
@ -354,6 +375,11 @@ class Txt2Rst(TxtParser):
|
|||||||
return commands
|
return commands
|
||||||
return super().order_commands(commands)
|
return super().order_commands(commands)
|
||||||
|
|
||||||
|
def transform_paragraphs(self, content):
|
||||||
|
if self.format.indent_level > 0:
|
||||||
|
raise Exception("unbalanced number of ulb,ule or olb,ole pairs!")
|
||||||
|
return super().transform_paragraphs(content)
|
||||||
|
|
||||||
|
|
||||||
class Txt2RstConverter(TxtConverter):
|
class Txt2RstConverter(TxtConverter):
|
||||||
def get_argument_parser(self):
|
def get_argument_parser(self):
|
||||||
@ -370,6 +396,7 @@ class Txt2RstConverter(TxtConverter):
|
|||||||
filename, ext = os.path.splitext(path)
|
filename, ext = os.path.splitext(path)
|
||||||
return filename + ".rst"
|
return filename + ".rst"
|
||||||
|
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
app = Txt2RstConverter()
|
app = Txt2RstConverter()
|
||||||
app.run()
|
app.run()
|
||||||
|
|||||||
@ -81,6 +81,10 @@ class TestMarkup(unittest.TestCase):
|
|||||||
s = self.markup.convert("[*bold] and {italic*}")
|
s = self.markup.convert("[*bold] and {italic*}")
|
||||||
self.assertEqual("**\*bold** and *italic\**", s)
|
self.assertEqual("**\*bold** and *italic\**", s)
|
||||||
|
|
||||||
|
def test_escape_rst_characters(self):
|
||||||
|
s = self.markup.convert("[|bold|] and {|italic|}")
|
||||||
|
self.assertEqual("**\|bold\|** and *\|italic\|*", s)
|
||||||
|
|
||||||
def test_escape_hat_character(self):
|
def test_escape_hat_character(self):
|
||||||
s = self.markup.convert("x^2")
|
s = self.markup.convert("x^2")
|
||||||
self.assertEqual("x\^2", s)
|
self.assertEqual("x\^2", s)
|
||||||
@ -155,13 +159,13 @@ class TestFormatting(unittest.TestCase):
|
|||||||
|
|
||||||
def test_preformat_formatting(self):
|
def test_preformat_formatting(self):
|
||||||
s = self.txt2rst.convert("Hello :pre\n")
|
s = self.txt2rst.convert("Hello :pre\n")
|
||||||
self.assertEqual(".. parsed-literal::\n\n"
|
self.assertEqual("\n.. parsed-literal::\n\n"
|
||||||
" Hello\n\n", s)
|
" Hello\n\n", s)
|
||||||
|
|
||||||
def test_preformat_formatting_with_indentation(self):
|
def test_preformat_formatting_with_indentation(self):
|
||||||
s = self.txt2rst.convert(" Hello\n"
|
s = self.txt2rst.convert(" Hello\n"
|
||||||
" World :pre\n")
|
" World :pre\n")
|
||||||
self.assertEqual(".. parsed-literal::\n\n"
|
self.assertEqual("\n.. parsed-literal::\n\n"
|
||||||
" Hello\n"
|
" Hello\n"
|
||||||
" World\n\n", s)
|
" World\n\n", s)
|
||||||
|
|
||||||
@ -196,6 +200,16 @@ class TestFormatting(unittest.TestCase):
|
|||||||
self.assertEqual("Level\n"
|
self.assertEqual("Level\n"
|
||||||
"#####\n\n", s)
|
"#####\n\n", s)
|
||||||
|
|
||||||
|
def test_filter_header_numbers_deep(self):
|
||||||
|
s = self.txt2rst.convert("1.1.1.1.1 Level :h1\n")
|
||||||
|
self.assertEqual("Level\n"
|
||||||
|
"#####\n\n", s)
|
||||||
|
|
||||||
|
def test_no_filter_date(self):
|
||||||
|
s = self.txt2rst.convert("9 Sept 2016 version :h1\n")
|
||||||
|
self.assertEqual("9 Sept 2016 version\n"
|
||||||
|
"###################\n\n", s)
|
||||||
|
|
||||||
def test_all_breaks(self):
|
def test_all_breaks(self):
|
||||||
s = self.txt2rst.convert("one\n"
|
s = self.txt2rst.convert("one\n"
|
||||||
"two\n"
|
"two\n"
|
||||||
@ -308,8 +322,6 @@ class TestListFormatting(unittest.TestCase):
|
|||||||
"* third\n"
|
"* third\n"
|
||||||
" paragraph\n\n", s)
|
" paragraph\n\n", s)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def test_definition_list(self):
|
def test_definition_list(self):
|
||||||
s = self.txt2rst.convert("A\n"
|
s = self.txt2rst.convert("A\n"
|
||||||
"first\n"
|
"first\n"
|
||||||
@ -322,6 +334,39 @@ class TestListFormatting(unittest.TestCase):
|
|||||||
" second\n"
|
" second\n"
|
||||||
"\n\n", s)
|
"\n\n", s)
|
||||||
|
|
||||||
|
def test_multi_paragraph_lists(self):
|
||||||
|
s = self.txt2rst.convert("first\n"
|
||||||
|
"paragraph of first bullet :ulb,l\n\n"
|
||||||
|
"second paragraph of first bullet\n\n"
|
||||||
|
"first paragraph of second bullet :l\n\n"
|
||||||
|
":ule\n")
|
||||||
|
self.assertEqual("* first\n"
|
||||||
|
" paragraph of first bullet\n"
|
||||||
|
"\n"
|
||||||
|
" second paragraph of first bullet\n"
|
||||||
|
"\n"
|
||||||
|
"* first paragraph of second bullet\n\n\n", s)
|
||||||
|
|
||||||
|
def test_multi_paragraph_lists_with_listing(self):
|
||||||
|
s = self.txt2rst.convert("first\n"
|
||||||
|
"paragraph of first bullet :ulb,l\n\n"
|
||||||
|
"code1 :pre\n"
|
||||||
|
"or\n"
|
||||||
|
"\n"
|
||||||
|
"first paragraph of second bullet :l\n\n"
|
||||||
|
":ule\n")
|
||||||
|
self.assertEqual("* first\n"
|
||||||
|
" paragraph of first bullet\n"
|
||||||
|
" \n"
|
||||||
|
" .. parsed-literal::\n"
|
||||||
|
" \n"
|
||||||
|
" code1\n"
|
||||||
|
"\n\n"
|
||||||
|
" or\n"
|
||||||
|
"\n"
|
||||||
|
"* first paragraph of second bullet\n\n\n", s)
|
||||||
|
|
||||||
|
|
||||||
class TestSpecialCommands(unittest.TestCase):
|
class TestSpecialCommands(unittest.TestCase):
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
self.txt2rst = txt2rst.Txt2Rst()
|
self.txt2rst = txt2rst.Txt2Rst()
|
||||||
|
|||||||
Reference in New Issue
Block a user