]> git.lyx.org Git - lyx.git/blobdiff - src/Font.cpp
adjust
[lyx.git] / src / Font.cpp
index bf71d73c4c89e5fb3184d9659f79efcaa538e1f0..f4e9bd053bf35362bf2064901361f10cb47d41e9 100644 (file)
 
 #include "BufferParams.h" // stateText
 #include "debug.h"
+#include "Encoding.h"
 #include "gettext.h"
 #include "Language.h"
 #include "Color.h"
 #include "Lexer.h"
 #include "LyXRC.h"
+#include "output_latex.h"
+#include "OutputParams.h"
 
+#include "support/convert.h"
 #include "support/lstrings.h"
 
-
-namespace lyx {
-
-using support::ascii_lowercase;
-using support::bformat;
-using support::rtrim;
-using support::subst;
-
 using std::endl;
 using std::string;
 using std::ostream;
+using std::ostringstream;
+using std::istringstream;
+using std::pair;
 
 #ifndef CXX_GLOBAL_CSTD
 using std::strlen;
 #endif
 
+
+namespace lyx {
+
+using support::ascii_lowercase;
+using support::bformat;
+using support::rtrim;
+using support::subst;
+
 //
 // Names for the GUI
 //
@@ -163,37 +170,37 @@ bool operator==(Font::FontBits const & lhs,
 
 
 Font::Font()
-       : bits(sane), lang(default_language)
+       : bits(sane), lang(default_language), open_encoding_(false)
 {}
 
 
 Font::Font(Font::FONT_INIT1)
-       : bits(inherit), lang(default_language)
+       : bits(inherit), lang(default_language), open_encoding_(false)
 {}
 
 
 Font::Font(Font::FONT_INIT2)
-       : bits(ignore), lang(ignore_language)
+       : bits(ignore), lang(ignore_language), open_encoding_(false)
 {}
 
 
 Font::Font(Font::FONT_INIT3)
-       : bits(sane), lang(default_language)
+       : bits(sane), lang(default_language), open_encoding_(false)
 {}
 
 
 Font::Font(Font::FONT_INIT1, Language const * l)
-       : bits(inherit), lang(l)
+       : bits(inherit), lang(l), open_encoding_(false)
 {}
 
 
 Font::Font(Font::FONT_INIT2, Language const * l)
-       : bits(ignore), lang(l)
+       : bits(ignore), lang(l), open_encoding_(false)
 {}
 
 
 Font::Font(Font::FONT_INIT3, Language const * l)
-       : bits(sane), lang(l)
+       : bits(sane), lang(l), open_encoding_(false)
 {}
 
 
@@ -507,21 +514,21 @@ docstring const Font::stateText(BufferParams * params) const
                os << lcolor.getGUIName(color()) << ", ";
        if (emph() != INHERIT)
                os << bformat(_("Emphasis %1$s, "),
-                             _(GUIMiscNames[emph()]));
+                             _(GUIMiscNames[emph()]));
        if (underbar() != INHERIT)
                os << bformat(_("Underline %1$s, "),
-                             _(GUIMiscNames[underbar()]));
+                             _(GUIMiscNames[underbar()]));
        if (noun() != INHERIT)
                os << bformat(_("Noun %1$s, "),
-                             _(GUIMiscNames[noun()]));
+                             _(GUIMiscNames[noun()]));
        if (bits == inherit)
                os << _("Default") << ", ";
        if (!params || (language() != params->language))
                os << bformat(_("Language: %1$s, "),
-                             _(language()->display()));
+                             _(language()->display()));
        if (number() != OFF)
                os << bformat(_("  Number %1$s"),
-                             _(GUIMiscNames[number()]));
+                             _(GUIMiscNames[number()]));
        return rtrim(os.str(), ", ");
 }
 
@@ -671,7 +678,7 @@ Font & Font::lyxRead(Lexer & lex)
                        } else if (ttok == "noun") {
                                setNoun(ON);
                        } else {
-                               lex.printError("Illegal misc type `$$Tokenยด");
+                               lex.printError("Illegal misc type `$$Token'");
                        }
                } else if (tok == "color") {
                        lex.next();
@@ -736,15 +743,32 @@ void Font::lyxWriteChanges(Font const & orgfont,
 
 /// Writes the head of the LaTeX needed to impose this font
 // Returns number of chars written.
-int Font::latexWriteStartChanges(odocstream & os, Font const & base,
-                                    Font const & prev) const
+int Font::latexWriteStartChanges(odocstream & os, BufferParams const & bparams,
+                                   OutputParams const & runparams,
+                                   Font const & base,
+                                   Font const & prev) const
 {
        bool env = false;
 
        int count = 0;
        if (language()->babel() != base.language()->babel() &&
            language() != prev.language()) {
-               if (isRightToLeft() != prev.isRightToLeft()) {
+               if (language()->lang() == "farsi") {
+                       os << "\\textFR{";
+                       count += 8;
+               } else if (!isRightToLeft() &&
+                           base.language()->lang() == "farsi") {
+                       os << "\\textLR{";
+                       count += 8;
+               } else if (language()->lang() == "arabic_arabi") {
+                       os << "\\textAR{";
+                       count += 8;
+               } else if (!isRightToLeft() &&
+                               base.language()->lang() == "arabic_arabi") {
+                       os << "\\textLR{";
+                       count += 8;
+               // currently the remaining RTL languages are arabic_arabtex and hebrew
+               } else if (isRightToLeft() != prev.isRightToLeft()) {
                        if (isRightToLeft()) {
                                os << "\\R{";
                                count += 3;
@@ -752,17 +776,37 @@ int Font::latexWriteStartChanges(odocstream & os, Font const & base,
                                os << "\\L{";
                                count += 3;
                        }
-               } else {
+               } else if (!language()->babel().empty()) {
                        string const tmp =
                                subst(lyxrc.language_command_local,
                                      "$$lang", language()->babel());
                        os << from_ascii(tmp);
                        count += tmp.length();
+               } else {
+                       os << '{';
+                       count += 1;
                }
        }
 
-       if (number() == ON && prev.number() != ON &&
-           language()->lang() == "hebrew") {
+       if (language()->encoding()->package() == Encoding::CJK) {
+               pair<bool, int> const c = switchEncoding(os, bparams,
+                               runparams.moving_arg, *(runparams.encoding),
+                               *(language()->encoding()));
+               if (c.first) {
+                       open_encoding_ = true;
+                       count += c.second;
+                       runparams.encoding = language()->encoding();
+               }
+       }
+
+       // When the current language is Hebrew, Arabic, or Farsi
+       // the numbers are written Left-to-Right. ArabTeX package
+       // reorders the number automatically but the packages used
+       // for Hebrew and Farsi (Arabi) do not.
+       if (number() == ON && prev.number() != ON
+               && (language()->lang() == "hebrew"
+                       || language()->lang() == "farsi" 
+                       || language()->lang() == "arabic_arabi")) {
                os << "{\\beginL ";
                count += 9;
        }
@@ -832,8 +876,11 @@ int Font::latexWriteStartChanges(odocstream & os, Font const & base,
 /// Writes ending block of LaTeX needed to close use of this font
 // Returns number of chars written
 // This one corresponds to latexWriteStartChanges(). (Asger)
-int Font::latexWriteEndChanges(odocstream & os, Font const & base,
-                                  Font const & next) const
+int Font::latexWriteEndChanges(odocstream & os, BufferParams const & bparams,
+                                 OutputParams const & runparams,
+                                 Font const & base,
+                                 Font const & next,
+                                 bool const & closeLanguage) const
 {
        int count = 0;
        bool env = false;
@@ -887,13 +934,33 @@ int Font::latexWriteEndChanges(odocstream & os, Font const & base,
                }
        }
 
-       if (number() == ON && next.number() != ON &&
-           language()->lang() == "hebrew") {
+       // When the current language is Hebrew, Arabic, or Farsi
+       // the numbers are written Left-to-Right. ArabTeX package
+       // reorders the number automatically but the packages used
+       // for Hebrew and Farsi (Arabi) do not.
+       if (number() == ON && next.number() != ON
+               && (language()->lang() == "hebrew"
+                       || language()->lang() == "farsi"
+                       || language()->lang() == "arabic_arabi")) {
                os << "\\endL}";
                count += 6;
        }
 
-       if (language() != base.language() && language() != next.language()) {
+       if (open_encoding_) {
+               // We need to close the encoding even if it does not change
+               // to do correct environment nesting
+               Encoding const * const ascii = encodings.getFromLyXName("ascii");
+               pair<bool, int> const c = switchEncoding(os, bparams,
+                               runparams.moving_arg, *(runparams.encoding),
+                               *ascii);
+               BOOST_ASSERT(c.first);
+               count += c.second;
+               runparams.encoding = ascii;
+               open_encoding_ = false;
+       }
+
+       if (closeLanguage &&
+                       language() != base.language() && language() != next.language()) {
                os << '}';
                ++count;
        }
@@ -910,6 +977,99 @@ Color_color Font::realColor() const
 }
 
 
+std::string Font::toString(bool const toggle) const
+{
+       string lang = "ignore";
+       if (language())
+               lang = language()->lang();
+
+       ostringstream os;
+       os << "family " << family() << '\n'
+          << "series " << series() << '\n'
+          << "shape " << shape() << '\n'
+          << "size " << size() << '\n'
+          << "emph " << emph() << '\n'
+          << "underbar " << underbar() << '\n'
+          << "noun " << noun() << '\n'
+          << "number " << number() << '\n'
+          << "color " << color() << '\n'
+          << "language " << lang << '\n'
+          << "toggleall " << convert<string>(toggle);
+       return os.str();
+}
+
+
+bool Font::fromString(string const & data, bool & toggle)
+{
+       istringstream is(data);
+       Lexer lex(0,0);
+       lex.setStream(is);
+
+       int nset = 0;
+       while (lex.isOK()) {
+               string token;
+               if (lex.next())
+                       token = lex.getString();
+
+               if (token.empty() || !lex.next())
+                       break;
+
+               if (token == "family") {
+                       int const next = lex.getInteger();
+                       setFamily(FONT_FAMILY(next));
+
+               } else if (token == "series") {
+                       int const next = lex.getInteger();
+                       setSeries(FONT_SERIES(next));
+
+               } else if (token == "shape") {
+                       int const next = lex.getInteger();
+                       setShape(FONT_SHAPE(next));
+
+               } else if (token == "size") {
+                       int const next = lex.getInteger();
+                       setSize(FONT_SIZE(next));
+
+               } else if (token == "emph" || token == "underbar" ||
+                          token == "noun" || token == "number") {
+
+                       int const next = lex.getInteger();
+                       FONT_MISC_STATE const misc = FONT_MISC_STATE(next);
+
+                       if (token == "emph")
+                         setEmph(misc);
+                       else if (token == "underbar")
+                               setUnderbar(misc);
+                       else if (token == "noun")
+                               setNoun(misc);
+                       else if (token == "number")
+                               setNumber(misc);
+
+               } else if (token == "color") {
+                       int const next = lex.getInteger();
+                       setColor(Color::color(next));
+
+               } else if (token == "language") {
+                       string const next = lex.getString();
+                       if (next == "ignore")
+                               setLanguage(ignore_language);
+                       else
+                               setLanguage(languages.getLanguage(next));
+
+               } else if (token == "toggleall") {
+                       toggle = lex.getBool();
+
+               } else {
+                       // Unrecognised token
+                       break;
+               }
+
+               ++nset;
+       }
+       return (nset > 0);
+}
+
+
 ostream & operator<<(ostream & os, Font::FONT_MISC_STATE fms)
 {
        return os << int(fms);