]> git.lyx.org Git - features.git/blobdiff - src/tex2lyx/text.cpp
Merge branch 'master' of git.lyx.org:lyx
[features.git] / src / tex2lyx / text.cpp
index 2bf2c5aef4422e00497ce45345af83bb664f640f..46cc347db75d8429a47028fedad1ed4e22da659a 100644 (file)
@@ -285,6 +285,18 @@ char const * const known_phrases[] = {"LyX", "TeX", "LaTeXe", "LaTeX", 0};
 char const * const known_coded_phrases[] = {"LyX", "TeX", "LaTeX2e", "LaTeX", 0};
 int const known_phrase_lengths[] = {3, 5, 7, 0};
 
+/// known TIPA combining diacritical marks
+char const * const known_tipa_marks[] = {"textsubwedge", "textsubumlaut",
+"textsubtilde", "textseagull", "textsubbridge", "textinvsubbridge",
+"textsubsquare", "textsubrhalfring", "textsublhalfring", "textsubplus",
+"textovercross", "textsubarch", "textsuperimposetilde", "textraising",
+"textlowering", "textadvancing", "textretracting", "textdoublegrave",
+"texthighrise", "textlowrise", "textrisefall", "textsyllabic",
+"textsubring", 0};
+
+/// TIPA tones that need special handling
+char const * const known_tones[] = {"15", "51", "45", "12", "454", 0};
+
 // string to store the float type to be able to determine the type of subfloats
 string float_type = "";
 
@@ -1413,6 +1425,17 @@ void parse_environment(Parser & p, ostream & os, bool outer,
                p.skip_spaces();
        }
 
+       else if (name == "IPA") {
+               eat_whitespace(p, os, parent_context, false);
+               parent_context.check_layout(os);
+               begin_inset(os, "IPA\n");
+               parse_text_in_inset(p, os, FLAG_END, outer, parent_context);
+               end_inset(os);
+               p.skip_spaces();
+               preamble.registerAutomaticallyLoadedPackage("tipa");
+               preamble.registerAutomaticallyLoadedPackage("tipx");
+       }
+
        else if (name == "CJK") {
                // the scheme is \begin{CJK}{encoding}{mapping}text\end{CJK}
                // It is impossible to decide if a CJK environment was in its own paragraph or within
@@ -1457,6 +1480,8 @@ void parse_environment(Parser & p, ostream & os, bool outer,
                                        output_ert_inset(os, "\\", parent_context);
                                else if (*it == '$')
                                        output_ert_inset(os, "$", parent_context);
+                               else if (*it == '\n' && it + 1 != et && s.begin() + 1 != it)
+                                       os << "\n ";
                                else
                                        os << *it;
                        }
@@ -1675,7 +1700,14 @@ void parse_environment(Parser & p, ostream & os, bool outer,
                begin_inset(os, "Flex ");
                os << to_utf8(newinsetlayout->name()) << '\n'
                   << "status collapsed\n";
-               parse_text_in_inset(p, os, FLAG_END, false, parent_context, newinsetlayout);
+               if (newinsetlayout->isPassThru()) {
+                       string const arg = p.verbatimEnvironment(name);
+                       Context context(true, parent_context.textclass, 
+                                       &parent_context.textclass.plainLayout(),
+                                       parent_context.layout);
+                       output_ert(os, arg, parent_context);
+               } else
+                       parse_text_in_inset(p, os, FLAG_END, false, parent_context, newinsetlayout);
                end_inset(os);
        }
 
@@ -3208,6 +3240,83 @@ void parse_text(Parser & p, ostream & os, unsigned flags, bool outer,
                        }
                }
 
+               else if (t.cs() == "textipa") {
+                       context.check_layout(os);
+                       begin_inset(os, "IPA\n");
+                       parse_text_in_inset(p, os, FLAG_ITEM, outer, context);
+                       end_inset(os);
+                       preamble.registerAutomaticallyLoadedPackage("tipa");
+                       preamble.registerAutomaticallyLoadedPackage("tipx");
+               }
+
+               else if (t.cs() == "texttoptiebar" || t.cs() == "textbottomtiebar") {
+                       context.check_layout(os);
+                       begin_inset(os, "IPADeco " + t.cs().substr(4) + "\n");
+                       os << "status open\n";
+                       parse_text_in_inset(p, os, FLAG_ITEM, outer, context);
+                       end_inset(os);
+                       p.skip_spaces();
+               }
+
+               // the TIPA Combining diacritical marks
+               else if (is_known(t.cs(), known_tipa_marks) || t.cs() == "textvertline") {
+                       preamble.registerAutomaticallyLoadedPackage("tipa");
+                       preamble.registerAutomaticallyLoadedPackage("tipx");
+                       context.check_layout(os);
+                       if (t.cs() == "textvertline") {
+                               os << "|";
+                               skip_braces(p);
+                               continue;
+                       }
+                       // try to see whether the string is in unicodesymbols
+                       bool termination;
+                       docstring rem;
+                       string content = trimSpaceAndEol(p.verbatim_item());
+                       string command = t.asInput() + "{" + content + "}";
+                       set<string> req;
+                       docstring s = encodings.fromLaTeXCommand(from_utf8(command),
+                               Encodings::TEXT_CMD | Encodings::MATH_CMD,
+                               termination, rem, &req);
+                       if (!s.empty()) {
+                               if (!rem.empty())
+                                       cerr << "When parsing " << command
+                                            << ", result is " << to_utf8(s)
+                                            << "+" << to_utf8(rem) << endl;
+                               os << content << to_utf8(s);
+                       } else
+                               // we did not find a non-ert version
+                               output_ert_inset(os, command, context);
+               }
+
+               else if (t.cs() == "tone" ) {
+                       context.check_layout(os);
+                       // register the tone package
+                       preamble.registerAutomaticallyLoadedPackage("tone");
+                       string content = trimSpaceAndEol(p.verbatim_item());
+                       string command = t.asInput() + "{" + content + "}";
+                       // some tones can be detected by unicodesymbols, some need special code
+                       if (is_known(content, known_tones)) {
+                               os << "\\IPAChar " << command << "\n";
+                               continue;
+                       }
+                       // try to see whether the string is in unicodesymbols
+                       bool termination;
+                       docstring rem;
+                       set<string> req;
+                       docstring s = encodings.fromLaTeXCommand(from_utf8(command),
+                               Encodings::TEXT_CMD | Encodings::MATH_CMD,
+                               termination, rem, &req);
+                       if (!s.empty()) {
+                               if (!rem.empty())
+                                       cerr << "When parsing " << command
+                                            << ", result is " << to_utf8(s)
+                                                << "+" << to_utf8(rem) << endl;
+                               os << to_utf8(s);
+                       } else
+                               // we did not find a non-ert version
+                               output_ert_inset(os, command, context);
+               }
+
                else if (t.cs() == "phantom" || t.cs() == "hphantom" ||
                             t.cs() == "vphantom") {
                        context.check_layout(os);
@@ -3516,10 +3625,23 @@ void parse_text(Parser & p, ostream & os, unsigned flags, bool outer,
                        end_inset(os);
                }
 
-               else if (t.cs() == "printindex") {
+               else if (t.cs() == "printindex" || t.cs() == "printsubindex") {
                        context.check_layout(os);
-                       begin_command_inset(os, "index_print", "printindex");
-                       os << "type \"idx\"\n";
+                       string commandname = t.cs();
+                       bool star = false;
+                       if (p.next_token().asInput() == "*") {
+                               commandname += "*";
+                               star = true;
+                               p.get_token();
+                       }
+                       begin_command_inset(os, "index_print", commandname);
+                       string const indexname = p.getArg('[', ']');
+                       if (!star) {
+                               if (indexname.empty())
+                                       os << "type \"idx\"\n";
+                               else
+                                       os << "type \"" << indexname << "\"\n";
+                       }
                        end_inset(os);
                        skip_spaces_braces(p);
                        preamble.registerAutomaticallyLoadedPackage("makeidx");
@@ -3980,6 +4102,10 @@ void parse_text(Parser & p, ostream & os, unsigned flags, bool outer,
                                                continue;
                                } else if (t2.cs() == "bibliography")
                                        output = false;
+                               else if (t2.cs() == "phantomsection") {
+                                       output = false;
+                                       continue;
+                               }
                                else if (t2.cs() == "addcontentsline") {
                                        // get the 3 arguments of \addcontentsline
                                        p.getArg('{', '}');
@@ -3999,6 +4125,13 @@ void parse_text(Parser & p, ostream & os, unsigned flags, bool outer,
                        }
                }
 
+               else if (t.cs() == "phantomsection") {
+                       // we only support this if it occurs between
+                       // \bibliographystyle and \bibliography
+                       if (bibliographystyle.empty())
+                               output_ert_inset(os, "\\phantomsection", context);
+               }
+
                else if (t.cs() == "addcontentsline") {
                        context.check_layout(os);
                        // get the 3 arguments of \addcontentsline
@@ -4036,6 +4169,9 @@ void parse_text(Parser & p, ostream & os, unsigned flags, bool outer,
                                        BibOpts = bibliographystyle;
                                else
                                        BibOpts = BibOpts + ',' + bibliographystyle;
+                               // clear it because each bibtex entry has its style
+                               // and we need an empty string to handle \phantomsection
+                               bibliographystyle.clear();
                        }
                        os << "options " << '"' << BibOpts << '"' << "\n";
                        end_inset(os);
@@ -4344,7 +4480,20 @@ void parse_text(Parser & p, ostream & os, unsigned flags, bool outer,
                        begin_inset(os, "Flex ");
                        os << to_utf8(newinsetlayout->name()) << '\n'
                           << "status collapsed\n";
-                       parse_text_in_inset(p, os, FLAG_ITEM, false, context, newinsetlayout);
+                       if (newinsetlayout->isPassThru()) {
+                               // set catcodes to verbatim early, just in case.
+                               p.setCatcodes(VERBATIM_CATCODES);
+                               string delim = p.get_token().asInput();
+                               if (delim != "{")
+                                       cerr << "Warning: bad delimiter for command " << t.asInput() << endl;
+                               string const arg = p.verbatimStuff("}");
+                               Context newcontext(true, context.textclass);
+                               if (newinsetlayout->forcePlainLayout())
+                                       newcontext.layout = &context.textclass.plainLayout();
+                               output_ert(os, arg, newcontext);
+                       } else
+                               
+                               parse_text_in_inset(p, os, FLAG_ITEM, false, context, newinsetlayout);
                        end_inset(os);
                }
 
@@ -4462,7 +4611,72 @@ void parse_text(Parser & p, ostream & os, unsigned flags, bool outer,
                        bool termination;
                        docstring rem;
                        set<string> req;
-                       docstring s = encodings.fromLaTeXCommand(from_utf8(t.asInput()),
+                       string name = t.asInput();
+                       // handle some TIPA special characters
+                       if (name == "\\textglobfall") {
+                               name = "End";
+                               skip_braces(p);
+                       }
+                       if (name == "\\textdoublevertline") {
+                               name = "\\textbardbl";
+                               skip_braces(p);
+                       }
+                       if (name == "\\!" ) {
+                               if (p.next_token().asInput() == "b") {
+                                       p.get_token();  // eat 'b'
+                                       name = "\\texthtb";
+                                       skip_braces(p);
+                               }
+                               if (p.next_token().asInput() == "d") {
+                                       p.get_token();
+                                       name = "\\texthtd";
+                                       skip_braces(p);
+                               }
+                               if (p.next_token().asInput() == "g") {
+                                       p.get_token();
+                                       name = "\\texthtg";
+                                       skip_braces(p);
+                               }
+                               if (p.next_token().asInput() == "G") {
+                                       p.get_token();
+                                       name = "\\texthtscg";
+                                       skip_braces(p);
+                               }
+                               if (p.next_token().asInput() == "j") {
+                                       p.get_token();
+                                       name = "\\texthtbardotlessj";
+                                       skip_braces(p);
+                               }
+                               if (p.next_token().asInput() == "o") {
+                                       p.get_token();
+                                       name = "\\textbullseye";
+                                       skip_braces(p);
+                               }
+                       }
+                       if (name == "\\*" ) {
+                               if (p.next_token().asInput() == "k") {
+                                       p.get_token();
+                                       name = "\\textturnk";
+                                       skip_braces(p);
+                               }
+                               if (p.next_token().asInput() == "r") {
+                                       p.get_token();  // eat 'b'
+                                       name = "\\textturnr";
+                                       skip_braces(p);
+                               }                               
+                               if (p.next_token().asInput() == "t") {
+                                       p.get_token();
+                                       name = "\\textturnt";
+                                       skip_braces(p);
+                               }
+                               if (p.next_token().asInput() == "w") {
+                                       p.get_token();
+                                       name = "\\textturnw";
+                                       skip_braces(p);
+                               }                               
+                       }
+                       // now get the character from unicodesymbols
+                       docstring s = encodings.fromLaTeXCommand(from_utf8(name),
                                        Encodings::TEXT_CMD, termination, rem, &req);
                        if (!s.empty()) {
                                if (!rem.empty())