]> git.lyx.org Git - features.git/blobdiff - lib/lyx2lyx/lyx2lyx_tools.py
lyx2lyx refactoring
[features.git] / lib / lyx2lyx / lyx2lyx_tools.py
index f8d30cd4706d74c27ff6ecc3d8b7c467981de0ca..fd641385b88d176a349830a4f1b743ce3aa1c700 100644 (file)
@@ -83,10 +83,15 @@ insert_document_option(document, option):
 
 remove_document_option(document, option):
   Remove _option_ as a document option.
+
+revert_language(document, lyxname, babelname="", polyglossianame=""):
+  Reverts native language support to ERT
+  If babelname or polyglossianame is empty, it is assumed
+  this language package is not supported for the given language.
 '''
 
-import re
-from parser_tools import find_token, find_end_of_inset, get_containing_layout
+import re, sys
+from parser_tools import find_token, find_end_of_inset, get_containing_layout, get_value, get_bool_value
 from unicode_symbols import unicode_reps
 
 # This will accept either a list of lines or a single line.
@@ -140,24 +145,38 @@ def insert_to_preamble(document, text, index = 0):
 # Created from the reversed list to keep the first of alternative definitions.
 licr_table = dict((ord(ch), cmd) for cmd, ch in unicode_reps[::-1])
 
-def put_cmd_in_ert(cmd):
+def put_cmd_in_ert(cmd, is_open=False, as_paragraph=False):
     """
     Return ERT inset wrapping `cmd` as a list of strings.
 
     `cmd` can be a string or list of lines. Non-ASCII characters are converted
-    to the respective LICR macros if defined in unicodesymbols.
+    to the respective LICR macros if defined in unicodesymbols,
+    `is_open` is a boolean setting the inset status to "open",
+    `as_paragraph` wraps the ERT inset in a Standard paragraph.
     """
-    ret = ["\\begin_inset ERT", "status collapsed", "", "\\begin_layout Plain Layout", ""]
-    # It will be faster to work with a single string internally.
+    
+    status = {False:"collapsed", True:"open"}
+    ert_inset = ["\\begin_inset ERT", "status %s"%status[is_open], "",
+                 "\\begin_layout Plain Layout", "",
+                 # content here ([5:5])
+                 "\\end_layout", "", "\\end_inset"]
+
+    paragraph = ["\\begin_layout Standard", 
+                 # content here ([1:1])
+                 "", "", "\\end_layout", ""]
+    # ensure cmd is an unicode instance and make it "LyX safe".
     if isinstance(cmd, list):
         cmd = u"\n".join(cmd)
-    else:
-        cmd = u"%s" % cmd # ensure it is an unicode instance
+    elif sys.version_info[0] == 2 and isinstance(cmd, str):
+        cmd = cmd.decode('utf8')
     cmd = cmd.translate(licr_table)
     cmd = cmd.replace("\\", "\n\\backslash\n")
-    ret += cmd.splitlines()
-    ret += ["\\end_layout", "", "\\end_inset"]
-    return ret
+    
+    ert_inset[5:5] = cmd.splitlines()
+    if not as_paragraph:
+        return ert_inset
+    paragraph[1:1] = ert_inset
+    return paragraph
 
 
 def get_ert(lines, i, verbatim = False):
@@ -567,7 +586,7 @@ def insert_document_option(document, option):
         return
 
     # add it to the end of the options
-    document.header[options_line] += " ,%s" % option
+    document.header[options_line] += ",%s" % option
 
 
 def remove_document_option(document, option):
@@ -614,3 +633,106 @@ def is_document_option(document, option):
         return False
 
     return True
+
+def revert_language(document, lyxname, babelname="", polyglossianame=""):
+    " Revert native language support "
+
+    # Does the document use polyglossia?
+    use_polyglossia = False
+    if get_bool_value(document.header, "\\use_non_tex_fonts"):
+        i = find_token(document.header, "\\language_package")
+        if i == -1:
+            document.warning("Malformed document! Missing \\language_package")
+        else:
+            pack = get_value(document.header, "\\language_package", i)
+            if pack == "default" or pack == "auto":
+                use_polyglossia = True
+
+    # Do we use this language with polyglossia?
+    with_polyglossia = use_polyglossia and polyglossianame != ""
+    # Do we use this language with babel?
+    with_babel = with_polyglossia == False and babelname != ""
+
+    # Are we dealing with a primary or secondary language?
+    primary = False
+    secondary = False
+
+    orig_doc_language = document.language
+    # Main language first
+    if document.language == lyxname:
+        primary = True
+        document.language = "english"
+        i = find_token(document.header, "\\language %s" % lyxname, 0)
+        if i != -1:
+            document.header[i] = "\\language english"
+        if with_polyglossia:
+            add_to_preamble(document, ["\\AtBeginDocument{\setotherlanguage{%s}}" % polyglossianame])
+            document.body[2 : 2] = put_cmd_in_ert("\\resetdefaultlanguage{%s}"%polyglossianame,
+                                                  is_open=True, as_paragraph=True)
+
+    # Now secondary languages
+    i = 0
+    while True:
+        i = find_token(document.body, '\\lang', i)
+        if i == -1:
+            break
+        if document.body[i].startswith('\\lang %s' % lyxname):
+            secondary = True
+            endlang = get_containing_layout(document.body, i)[2]
+            langswitch = find_token(document.body, '\\lang', i + 1, endlang)
+            as_paragraph = True
+            if langswitch != -1:
+                endlang = langswitch
+                as_paragraph = False
+            if with_polyglossia:
+                add_to_preamble(document, ["\\AtBeginDocument{\setotherlanguage{%s}}" % polyglossianame])
+                document.body[endlang:endlang] = put_cmd_in_ert("\\end{%s}"%polyglossianame,
+                                                                is_open=True,
+                                                                as_paragraph=as_paragraph)
+            elif with_babel:
+                document.body[endlang:endlang] = put_cmd_in_ert("\\end{otherlanguage}",
+                                                                is_open=True,
+                                                                as_paragraph=as_paragraph)
+            del document.body[i]
+            if with_polyglossia:
+                document.body[i:i] = put_cmd_in_ert("\\begin{%s}"%polyglossianame,
+                                                    is_open=True)
+            elif with_babel:
+                document.body[i:i] = put_cmd_in_ert("\\begin{otherlanguage}{%s}" % babelname,
+                                                    is_open=True)
+        elif primary and document.body[i].startswith('\\lang english'):
+            # Since we switched the main language manually, English parts need to be marked
+            endlang = get_containing_layout(document.body, i)[2]
+            langswitch = find_token(document.body, '\\lang', i + 1, endlang)
+            as_paragraph = True
+            if langswitch != -1:
+                endlang = langswitch
+                as_paragraph = False
+            if with_polyglossia:
+                parent = get_containing_layout(document.body, i)
+                document.body[endlang:endlang] = put_cmd_in_ert("\\end{english}",
+                                                                is_open=True,
+                                                                as_paragraph=as_paragraph)
+            elif with_babel:
+                parent = get_containing_layout(document.body, i)
+                document.body[endlang:endlang] = put_cmd_in_ert("\\end{otherlanguage}",
+                                                                is_open=True,
+                                                                as_paragraph=as_paragraph)
+            del document.body[i]
+            if with_polyglossia:
+                document.body[i:i] = put_cmd_in_ert("\\begin{english}",
+                                                    is_open=True)
+            elif with_babel:
+                document.body[i:i] = put_cmd_in_ert("\\begin{otherlanguage}{english}",
+                                                    is_open=True)
+        else:
+            i += 1
+
+    # With babel, we need to add the language options
+    if with_babel and (primary or secondary):
+        insert_document_option(document, babelname)
+        if secondary and document.body[10] != "selectlanguage{%s}" % orig_doc_language:
+            # Since the user options are always placed after the babel options,
+            # we need to reset the main language
+            document.body[2:2] = put_cmd_in_ert("\\selectlanguage{%s}" % orig_doc_language,
+                                                is_open=True, as_paragraph=True)