#include "support/convert.h"
#include "support/debug.h"
#include "support/lstrings.h"
+#include "support/textutils.h"
#include <algorithm>
#include <boost/next_prior.hpp>
CJK
};
+// FIXME THREAD
+// There could easily be a conflict here, with the export process
+// setting this one way, and a View>Source process (possbily for
+// another Buffer) resetting it.
static int open_encoding_ = none;
static int cjk_inherited_ = 0;
Language const * prev_env_language_ = 0;
if (style.isEnvironment()) {
os << "\\begin{" << from_ascii(style.latexname()) << '}';
if (!style.latexargs().empty()) {
- OutputParams rp = runparams;
- rp.local_font = &pit->getFirstFontSettings(bparams);
- latexArgInsets(*pit, os, rp, style.latexargs());
+ OutputParams rp = runparams;
+ rp.local_font = &pit->getFirstFontSettings(bparams);
+ latexArgInsets(paragraphs, pit, os, rp, style.latexargs());
}
if (style.latextype == LATEX_LIST_ENVIRONMENT) {
os << '{'
LYXERR(Debug::LATEX, "TeXEnvironment for paragraph " << par_begin << " done.");
}
-} // namespace anon
-
-void latexArgInsets(Paragraph const & par, otexstream & os,
- OutputParams const & runparams, Layout::LaTeXArgMap const & latexargs, bool item)
+void getArgInsets(otexstream & os, OutputParams const & runparams, Layout::LaTeXArgMap const & latexargs,
+ map<int, lyx::InsetArgument const *> ilist, vector<string> required, string const & prefix)
{
- map<int, InsetArgument const *> ilist;
- vector<string> required;
-
- InsetList::const_iterator it = par.insetList().begin();
- InsetList::const_iterator end = par.insetList().end();
- for (; it != end; ++it) {
- if (it->inset->lyxCode() == ARG_CODE) {
- InsetArgument const * ins =
- static_cast<InsetArgument const *>(it->inset);
- if (ins->name().empty())
- LYXERR0("Error: Unnamed argument inset!");
- else {
- string const name = item ? split(ins->name(), ':') : ins->name();
- unsigned int const nr = convert<unsigned int>(name);
- ilist[nr] = ins;
- Layout::LaTeXArgMap::const_iterator const lit =
- latexargs.find(ins->name());
- if (lit != latexargs.end()) {
- Layout::latexarg const & arg = (*lit).second;
- if (!arg.requires.empty()) {
- vector<string> req = getVectorFromString(arg.requires);
- required.insert(required.end(), req.begin(), req.end());
- }
- }
- }
- }
- }
-
unsigned int const argnr = latexargs.size();
if (argnr == 0)
return;
ldelim = arg.ldelim;
if (!arg.rdelim.empty())
rdelim = arg.rdelim;
- ins->latexArgument(os, runparams, ldelim, rdelim);
+ ins->latexArgument(os, runparams, ldelim, rdelim, arg.presetarg);
inserted = true;
}
}
Layout::LaTeXArgMap::const_iterator lait = latexargs.begin();
Layout::LaTeXArgMap::const_iterator const laend = latexargs.end();
for (; lait != laend; ++lait) {
- string const name = item ? "item:" + convert<string>(i) : convert<string>(i);
+ string const name = prefix + convert<string>(i);
if ((*lait).first == name) {
Layout::latexarg arg = (*lait).second;
+ docstring preset = arg.presetarg;
+ if (!arg.defaultarg.empty()) {
+ if (!preset.empty())
+ preset += ",";
+ preset += arg.defaultarg;
+ }
if (arg.mandatory) {
docstring ldelim = arg.ldelim.empty() ?
from_ascii("{") : arg.ldelim;
docstring rdelim = arg.rdelim.empty() ?
from_ascii("}") : arg.rdelim;
- os << ldelim << rdelim;
+ os << ldelim << preset << rdelim;
+ } else if (!preset.empty()) {
+ docstring ldelim = arg.ldelim.empty() ?
+ from_ascii("[") : arg.ldelim;
+ docstring rdelim = arg.rdelim.empty() ?
+ from_ascii("]") : arg.rdelim;
+ os << ldelim << preset << rdelim;
} else if (find(required.begin(), required.end(),
(*lait).first) != required.end()) {
docstring ldelim = arg.ldelim.empty() ?
}
}
+
+} // namespace anon
+
+
+void latexArgInsets(Paragraph const & par, otexstream & os,
+ OutputParams const & runparams, Layout::LaTeXArgMap const & latexargs, string const & prefix)
+{
+ map<int, InsetArgument const *> ilist;
+ vector<string> required;
+
+ InsetList::const_iterator it = par.insetList().begin();
+ InsetList::const_iterator end = par.insetList().end();
+ for (; it != end; ++it) {
+ if (it->inset->lyxCode() == ARG_CODE) {
+ InsetArgument const * ins =
+ static_cast<InsetArgument const *>(it->inset);
+ if (ins->name().empty())
+ LYXERR0("Error: Unnamed argument inset!");
+ else {
+ string const name = prefix.empty() ? ins->name() : split(ins->name(), ':');
+ unsigned int const nr = convert<unsigned int>(name);
+ ilist[nr] = ins;
+ Layout::LaTeXArgMap::const_iterator const lit =
+ latexargs.find(ins->name());
+ if (lit != latexargs.end()) {
+ Layout::latexarg const & arg = (*lit).second;
+ if (!arg.requires.empty()) {
+ vector<string> req = getVectorFromString(arg.requires);
+ required.insert(required.end(), req.begin(), req.end());
+ }
+ }
+ }
+ }
+ }
+ getArgInsets(os, runparams, latexargs, ilist, required, prefix);
+}
+
+
+void latexArgInsets(ParagraphList const & pars, ParagraphList::const_iterator pit,
+ otexstream & os, OutputParams const & runparams, Layout::LaTeXArgMap const & latexargs,
+ string const & prefix)
+{
+ map<int, InsetArgument const *> ilist;
+ vector<string> required;
+
+ depth_type const current_depth = pit->params().depth();
+ Layout const current_layout = pit->layout();
+
+ // get the first paragraph in sequence with this layout and depth
+ pit_type offset = 0;
+ while (true) {
+ if (boost::prior(pit, offset) == pars.begin())
+ break;
+ ParagraphList::const_iterator priorpit = boost::prior(pit, offset + 1);
+ if (priorpit->layout() == current_layout
+ && priorpit->params().depth() == current_depth)
+ ++offset;
+ else
+ break;
+ }
+
+ ParagraphList::const_iterator spit = boost::prior(pit, offset);
+
+ for (; spit != pars.end(); ++spit) {
+ if (spit->layout() != current_layout || spit->params().depth() < current_depth)
+ break;
+ if (spit->params().depth() > current_depth)
+ continue;
+ InsetList::const_iterator it = spit->insetList().begin();
+ InsetList::const_iterator end = spit->insetList().end();
+ for (; it != end; ++it) {
+ if (it->inset->lyxCode() == ARG_CODE) {
+ InsetArgument const * ins =
+ static_cast<InsetArgument const *>(it->inset);
+ if (ins->name().empty())
+ LYXERR0("Error: Unnamed argument inset!");
+ else {
+ string const name = prefix.empty() ? ins->name() : split(ins->name(), ':');
+ unsigned int const nr = convert<unsigned int>(name);
+ if (ilist.find(nr) == ilist.end())
+ ilist[nr] = ins;
+ Layout::LaTeXArgMap::const_iterator const lit =
+ latexargs.find(ins->name());
+ if (lit != latexargs.end()) {
+ Layout::latexarg const & arg = (*lit).second;
+ if (!arg.requires.empty()) {
+ vector<string> req = getVectorFromString(arg.requires);
+ required.insert(required.end(), req.begin(), req.end());
+ }
+ }
+ }
+ }
+ }
+ }
+ getArgInsets(os, runparams, latexargs, ilist, required, prefix);
+}
+
namespace {
// output the proper paragraph start according to latextype.
break;
case LATEX_ITEM_ENVIRONMENT:
case LATEX_LIST_ENVIRONMENT:
- os << "\\item";
+ os << "\\" + style.itemcommand();
// Item arguments
if (!style.itemargs().empty())
- latexArgInsets(par, os, runparams, style.itemargs(), true);
+ latexArgInsets(par, os, runparams, style.itemargs(), "item:");
os << " ";
break;
case LATEX_BIB_ENVIRONMENT:
string const & everypar,
int start_pos, int end_pos)
{
- BufferParams const & bparams = buf.params();
+ BufferParams const & bparams = runparams_in.is_child
+ ? buf.masterParams() : buf.params();
ParagraphList const & paragraphs = text.paragraphs();
Paragraph const & par = paragraphs.at(pit);
// FIXME This check should not really be needed.
if (style.pass_thru) {
Font const outerfont = text.outerFont(pit);
- runparams.local_font = &par.getFirstFontSettings(bparams);
parStartCommand(par, os, runparams, style);
par.latex(bparams, outerfont, os, runparams, start_pos, end_pos);
os << '\n';
if (!style.parbreak_is_newline) {
os << '\n';
- } else if (nextpar) {
+ } else if (nextpar && !style.isEnvironment()) {
Layout const nextstyle = text.inset().forcePlainLayout()
? bparams.documentClass().plainLayout()
: nextpar->layout();
par.getFontSettings(bparams, i).language()->encoding();
if (encoding->package() != Encoding::CJK
&& runparams.encoding->package() == Encoding::inputenc
- && c < 0x80)
+ && isASCII(c))
continue;
if (par.isInset(i))
break;
}
}
- runparams.local_font = &par.getFirstFontSettings(bparams);
parStartCommand(par, os, runparams, style);
Font const outerfont = text.outerFont(pit);
os << "\\" << from_ascii(font.latexSize()) << " \\par}";
} else if (is_command) {
os << '}';
+ if (!style.postcommandargs().empty())
+ latexArgInsets(par, os, runparams, style.postcommandargs(), "post:");
if (runparams.encoding != prev_encoding) {
runparams.encoding = prev_encoding;
if (!runparams.isFullUnicode())
// not for ArabTeX
&& (par_language->lang() != "arabic_arabtex"
&& outer_language->lang() != "arabic_arabtex")
- // have we opened and \L or \R environment?
+ // have we opened an \L or \R environment?
&& runparams.local_font != 0
&& runparams.local_font->isRightToLeft() != par_language->rightToLeft()
// are we about to close the language?
OutputParams const & runparams,
string const & everypar)
{
+ LASSERT(runparams.par_begin <= runparams.par_end,
+ { os << "% LaTeX Output Error\n"; return; } );
+
BufferParams const & bparams = buf.params();
bool const maintext = text.isMainText();
}
ParagraphList const & paragraphs = text.paragraphs();
- LASSERT(runparams.par_begin <= runparams.par_end, /**/);
if (runparams.par_begin == runparams.par_end) {
// The full doc will be exported but it is easier to just rely on
{
Encoding const & oldEnc = *runparams.encoding;
bool moving_arg = runparams.moving_arg;
- if (!force && ((bparams.inputenc != "auto" && bparams.inputenc != "default")
- || moving_arg))
+ // If we switch from/to CJK, we need to switch anyway, despite custom inputenc
+ bool const from_to_cjk =
+ (oldEnc.package() == Encoding::CJK && newEnc.package() != Encoding::CJK)
+ || (oldEnc.package() != Encoding::CJK && newEnc.package() == Encoding::CJK);
+ if (!force && !from_to_cjk
+ && ((bparams.inputenc != "auto" && bparams.inputenc != "default") || moving_arg))
return make_pair(false, 0);
// Do nothing if the encoding is unchanged.