diff options
| -rw-r--r-- | NEWS | 2 | ||||
| -rw-r--r-- | README.md | 37 | ||||
| -rw-r--r-- | mammoth/conversion.py | 14 | ||||
| -rw-r--r-- | mammoth/document_matchers.py | 7 | ||||
| -rw-r--r-- | mammoth/styles/parser/document_matcher_parser.py | 15 | ||||
| -rw-r--r-- | tests/conversion_tests.py | 31 | ||||
| -rw-r--r-- | tests/styles/parser/document_matcher_parser_tests.py | 12 |
7 files changed, 117 insertions, 1 deletions
@@ -1,6 +1,6 @@ # 1.8.0 -* Support parsing of run highlights. +* Add style mapping for highlights. # 1.7.1 @@ -622,6 +622,43 @@ small-caps Note that this matches text that has had small caps explicitly applied to it. It will not match any text that is small caps because of its paragraph or run style. +#### Highlight + +Match explicitly highlighted text: + +``` +highlight +``` + +Note that this matches text that has had a highlight explicitly applied to it. +It will not match any text that is highlighted because of its paragraph or run style. + +It's also possible to match specific colours. +For instance, to match yellow highlights: + +``` +highlight[color='yellow'] +``` + +The set of colours typically used are: + +* `black` +* `blue` +* `cyan` +* `green` +* `magenta` +* `red` +* `yellow` +* `white` +* `darkBlue` +* `darkCyan` +* `darkGreen` +* `darkMagenta` +* `darkRed` +* `darkYellow` +* `darkGray` +* `lightGray` + #### Ignoring document elements Use `!` to ignore a document element. diff --git a/mammoth/conversion.py b/mammoth/conversion.py index bdc8687..33f61cc 100644 --- a/mammoth/conversion.py +++ b/mammoth/conversion.py @@ -109,6 +109,10 @@ class _DocumentConverter(documents.element_visitor(args=1)): def visit_run(self, run, context): nodes = lambda: self._visit_all(run.children, context) paths = [] + if run.highlight is not None: + style = self._find_style(Highlight(color=run.highlight), "highlight") + if style is not None: + paths.append(style.html_path) if run.is_small_caps: paths.append(self._find_style_for_run_property("small_caps")) if run.is_all_caps: @@ -354,9 +358,19 @@ class _DocumentConverter(documents.element_visitor(args=1)): return "{0}{1}".format(self._id_prefix, suffix) +@cobble.data +class Highlight: + color = cobble.field() + + def _document_matcher_matches(matcher, element, element_type): if matcher.element_type in ["underline", "strikethrough", "all_caps", "small_caps", "bold", "italic", "comment_reference"]: return matcher.element_type == element_type + elif matcher.element_type == "highlight": + return ( + matcher.element_type == element_type and + (matcher.color is None or matcher.color == element.color) + ) elif matcher.element_type == "break": return ( matcher.element_type == element_type and diff --git a/mammoth/document_matchers.py b/mammoth/document_matchers.py index f831b8a..5d07d39 100644 --- a/mammoth/document_matchers.py +++ b/mammoth/document_matchers.py @@ -51,6 +51,13 @@ class small_caps(object): element_type = "small_caps" +def highlight(color=None): + return HighlightMatcher(color=color) + + +HighlightMatcher = collections.namedtuple("HighlightMatcher", ["color"]) +HighlightMatcher.element_type = "highlight" + class comment_reference(object): element_type = "comment_reference" diff --git a/mammoth/styles/parser/document_matcher_parser.py b/mammoth/styles/parser/document_matcher_parser.py index 9891e4b..e0eb4e1 100644 --- a/mammoth/styles/parser/document_matcher_parser.py +++ b/mammoth/styles/parser/document_matcher_parser.py @@ -52,6 +52,9 @@ def parse_document_matcher(tokens): elif tokens.try_skip(TokenType.IDENTIFIER, "small-caps"): return document_matchers.small_caps + elif tokens.try_skip(TokenType.IDENTIFIER, "highlight"): + return _parse_highlight(tokens) + elif tokens.try_skip(TokenType.IDENTIFIER, "comment-reference"): return document_matchers.comment_reference @@ -98,6 +101,18 @@ def _parse_list_type(tokens): raise LineParseError("Unrecognised list type: {0}".format(list_type)) +def _parse_highlight(tokens): + if tokens.try_skip(TokenType.SYMBOL, "["): + tokens.skip(TokenType.IDENTIFIER, "color") + tokens.skip(TokenType.SYMBOL, "=") + color = parse_string(tokens) + tokens.skip(TokenType.SYMBOL, "]"); + else: + color = None + + return document_matchers.highlight(color=color) + + def _parse_break(tokens): tokens.skip(TokenType.SYMBOL, "[") tokens.skip(TokenType.IDENTIFIER, "type") diff --git a/tests/conversion_tests.py b/tests/conversion_tests.py index 8f02048..8e76714 100644 --- a/tests/conversion_tests.py +++ b/tests/conversion_tests.py @@ -242,6 +242,37 @@ def test_small_caps_runs_can_be_mapped_using_style_mapping(): assert_equal("<span>Hello</span>", result.value) +def test_highlighted_runs_are_ignored_by_default(): + result = convert_document_element_to_html( + documents.run(children=[documents.text("Hello")], highlight="yellow"), + ) + assert_equal("Hello", result.value) + + +def test_highlighted_runs_can_be_configured_with_style_mapping_for_all_highlights(): + result = convert_document_element_to_html( + documents.run(children=[documents.text("Hello")], highlight="yellow"), + style_map=[ + _style_mapping("highlight => mark"), + ], + ) + assert_equal("<mark>Hello</mark>", result.value) + + +def test_highlighted_runs_can_be_configured_with_style_mapping_for_specific_highlight_color(): + result = convert_document_element_to_html( + documents.paragraph(children=[ + documents.run(children=[documents.text("Yellow")], highlight="yellow"), + documents.run(children=[documents.text("Red")], highlight="red"), + ]), + style_map=[ + _style_mapping("highlight[color='yellow'] => mark.yellow"), + _style_mapping("highlight => mark"), + ] + ) + assert_equal('<p><mark class="yellow">Yellow</mark><mark>Red</mark></p>', result.value) + + def test_superscript_runs_are_wrapped_in_sup_tags(): result = convert_document_element_to_html( documents.run( diff --git a/tests/styles/parser/document_matcher_parser_tests.py b/tests/styles/parser/document_matcher_parser_tests.py index 1808571..dd613a1 100644 --- a/tests/styles/parser/document_matcher_parser_tests.py +++ b/tests/styles/parser/document_matcher_parser_tests.py @@ -141,6 +141,18 @@ def test_reads_small_caps(): read_document_matcher("small-caps") ) +def test_reads_highlight_without_color(): + assert_equal( + document_matchers.highlight(), + read_document_matcher("highlight") + ) + +def test_reads_highlight_with_color(): + assert_equal( + document_matchers.highlight(color="yellow"), + read_document_matcher("highlight[color='yellow']") + ) + def test_reads_comment_reference(): assert_equal( document_matchers.comment_reference, |
