#include "Bullet.h"
#include "Chktex.h"
#include "debug.h"
+#include "encoding.h"
#include "errorlist.h"
#include "exporter.h"
#include "format.h"
#include "funcrequest.h"
#include "gettext.h"
-#include "iterators.h"
+#include "insetiterator.h"
#include "language.h"
#include "LaTeX.h"
#include "LaTeXFeatures.h"
#include "lyxtext.h"
#include "lyxrc.h"
#include "lyxvc.h"
+#include "lyx_main.h"
#include "messages.h"
#include "output.h"
#include "output_docbook.h"
#include "paragraph.h"
#include "paragraph_funcs.h"
#include "ParagraphParameters.h"
-#include "PosIterator.h"
+#include "pariterator.h"
#include "sgml.h"
#include "texrow.h"
#include "undo.h"
#include "insets/insetinclude.h"
#include "insets/insettext.h"
+#include "mathed/math_macrotemplate.h"
+#include "mathed/math_macrotable.h"
+#include "mathed/math_support.h"
+
#include "frontends/Alert.h"
#include "graphics/Previews.h"
#include <boost/bind.hpp>
-#include "support/std_sstream.h"
+#include <utime.h>
#include <iomanip>
#include <stack>
+#include <sstream>
-#include <utime.h>
-
-#ifdef HAVE_LOCALE
-#endif
using lyx::pos_type;
+using lyx::par_type;
using lyx::support::AddName;
-using lyx::support::atoi;
using lyx::support::bformat;
using lyx::support::ChangeExtension;
using lyx::support::cmd_ret;
-using lyx::support::CreateBufferTmpDir;
+using lyx::support::createBufferTmpDir;
using lyx::support::destroyDir;
using lyx::support::FileInfo;
using lyx::support::FileInfo;
-using lyx::support::getExtFromContents;
+using lyx::support::getFormatFromContents;
using lyx::support::IsDirWriteable;
using lyx::support::IsFileWriteable;
using lyx::support::LibFileSearch;
using std::ifstream;
using std::ios;
+using std::map;
using std::ostream;
using std::ostringstream;
using std::ofstream;
namespace {
-const int LYX_FORMAT = 225;
+const int LYX_FORMAT = 237;
} // namespace anon
limited_stack<Undo> undostack;
limited_stack<Undo> redostack;
BufferParams params;
- ParagraphList paragraphs;
LyXVC lyxvc;
string temppath;
- bool nicefile;
TexRow texrow;
- /// need to regenerate .tex ?
+ /// need to regenerate .tex?
DepClean dep_clean;
- /// is save needed
+ /// is save needed?
mutable bool lyx_clean;
- /// is autosave needed
+ /// is autosave needed?
mutable bool bak_clean;
- /// is this a unnamed file (New...)
+ /// is this a unnamed file (New...)?
bool unnamed;
/// buffer is r/o
boost::scoped_ptr<Messages> messages;
- /** set to true only when the file is fully loaded.
+ /** Set to true only when the file is fully loaded.
* Used to prevent the premature generation of previews
* and by the citation inset.
*/
bool file_fully_loaded;
- /// our Text
- LyXText text;
+ /// our LyXText that should be wrapped in an InsetText
+ InsetText inset;
+
+ ///
+ MacroTable macros;
};
Buffer::Impl::Impl(Buffer & parent, string const & file, bool readonly_)
- : nicefile(true),
- lyx_clean(true), bak_clean(true), unnamed(false), read_only(readonly_),
+ : lyx_clean(true), bak_clean(true), unnamed(false), read_only(readonly_),
filename(file), filepath(OnlyPath(file)), file_fully_loaded(false),
- text(0, 0, 0, paragraphs)
+ inset(params)
{
lyxvc.buffer(&parent);
- if (readonly_ || lyxrc.use_tempdir)
- temppath = CreateBufferTmpDir();
+ temppath = createBufferTmpDir();
+ // FIXME: And now do something if temppath == string(), because we
+ // assume from now on that temppath points to a valid temp dir.
+ // See http://www.mail-archive.com/lyx-devel@lists.lyx.org/msg67406.html
}
bformat(_("Could not remove the temporary directory %1$s"), temppath()));
}
- paragraphs().clear();
-
// Remove any previewed LaTeX snippets associated with this buffer.
lyx::graphics::Previews::get().removeLoader(*this);
}
LyXText & Buffer::text() const
{
- return const_cast<LyXText &>(pimpl_->text);
+ return const_cast<LyXText &>(pimpl_->inset.text_);
+}
+
+
+InsetBase & Buffer::inset() const
+{
+ return const_cast<InsetText &>(pimpl_->inset);
}
ParagraphList & Buffer::paragraphs()
{
- return pimpl_->paragraphs;
+ return text().paragraphs();
}
ParagraphList const & Buffer::paragraphs() const
{
- return pimpl_->paragraphs;
+ return text().paragraphs();
}
}
-bool & Buffer::niceFile()
-{
- return pimpl_->nicefile;
-}
-
-
-bool Buffer::niceFile() const
-{
- return pimpl_->nicefile;
-}
-
-
TexRow & Buffer::texrow()
{
return pimpl_->texrow;
if (filename.empty())
return make_pair(Buffer::latexlog, string());
- string path = OnlyPath(filename);
-
- if (lyxrc.use_tempdir || !IsDirWriteable(path))
- path = temppath();
+ string const path = temppath();
string const fname = AddName(path,
OnlyFilename(ChangeExtension(filename,
} // anon
+
int Buffer::readHeader(LyXLex & lex)
{
int unknown_tokens = 0;
+ int line = -1;
+ int begin_header_line = -1;
while (lex.isOK()) {
- lex.nextToken();
+ lex.next();
string const token = lex.getString();
if (token.empty())
if (token == "\\end_header")
break;
+ ++line;
+ if (token == "\\begin_header") {
+ begin_header_line = line;
+ continue;
+ }
+
lyxerr[Debug::PARSER] << "Handling header token: `"
<< token << '\'' << endl;
-
string unknown = params().readToken(lex, token);
if (!unknown.empty()) {
- if (unknown[0] != '\\') {
+ if (unknown[0] != '\\' and token == "\\textclass") {
unknownClass(unknown);
} else {
++unknown_tokens;
}
}
}
+ if (begin_header_line) {
+ string const s = _("\\begin_header is missing");
+ error(ErrorItem(_("Header error"), s, -1, 0, 0));
+ }
return unknown_tokens;
}
-// candidate for move to BufferView
-// (at least some parts in the beginning of the func)
-//
// Uwe C. Schroeder
// changed to be public and have one parameter
-// if par = 0 normal behavior
-// else insert behavior
// Returns false if "\end_document" is not read (Asger)
-bool Buffer::readBody(LyXLex & lex, ParagraphList::iterator pit)
+bool Buffer::readDocument(LyXLex & lex)
{
- Paragraph::depth_type depth = 0;
- bool the_end_read = false;
+ lex.next();
+ string const token = lex.getString();
+ if (token != "\\begin_document") {
+ string const s = _("\\begin_document is missing");
+ error(ErrorItem(_("Header error"), s, -1, 0, 0));
+ }
if (paragraphs().empty()) {
readHeader(lex);
tmpbuf.readHeader(lex);
}
- while (lex.isOK()) {
- lex.nextToken();
- string const token = lex.getString();
-
- if (token.empty())
- continue;
-
- lyxerr[Debug::PARSER] << "Handling token: `"
- << token << '\'' << endl;
-
- if (token == "\\end_document") {
- the_end_read = true;
- continue;
- }
-
- readParagraph(lex, token, paragraphs(), pit, depth);
- }
-
- return the_end_read;
-}
-
-
-int Buffer::readParagraph(LyXLex & lex, string const & token,
- ParagraphList & pars, ParagraphList::iterator & pit,
- lyx::depth_type & depth)
-{
- static Change current_change;
- int unknown = 0;
-
- if (token == "\\begin_layout") {
- lex.pushToken(token);
-
- Paragraph par;
- par.params().depth(depth);
- if (params().tracking_changes)
- par.trackChanges();
- LyXFont f(LyXFont::ALL_INHERIT, params().language);
- par.setFont(0, f);
-
- // insert after
- if (pit != pars.end())
- ++pit;
-
- pit = pars.insert(pit, par);
-
- // FIXME: goddamn InsetTabular makes us pass a Buffer
- // not BufferParams
- ::readParagraph(*this, *pit, lex);
-
- } else if (token == "\\begin_deeper") {
- ++depth;
- } else if (token == "\\end_deeper") {
- if (!depth) {
- lex.printError("\\end_deeper: " "depth is already null");
- } else {
- --depth;
- }
- } else {
- ++unknown;
- }
- return unknown;
+ return text().read(*this, lex);
}
// needed to insert the selection
-void Buffer::insertStringAsLines(ParagraphList::iterator & par, pos_type & pos,
- LyXFont const & fn,string const & str)
+void Buffer::insertStringAsLines(ParagraphList & pars,
+ par_type & par, pos_type & pos,
+ LyXFont const & fn, string const & str)
{
- LyXLayout_ptr const & layout = par->layout();
+ LyXLayout_ptr const & layout = pars[par].layout();
LyXFont font = fn;
- par->checkInsertChar(font);
+ pars[par].checkInsertChar(font);
// insert the string, don't insert doublespace
bool space_inserted = true;
- bool autobreakrows = !par->inInset() ||
- static_cast<InsetText *>(par->inInset())->getAutoBreakRows();
- for(string::const_iterator cit = str.begin();
+ bool autobreakrows = pars[par].autoBreakRows();
+ for (string::const_iterator cit = str.begin();
cit != str.end(); ++cit) {
if (*cit == '\n') {
- if (autobreakrows && (!par->empty() || par->allowEmpty())) {
+ if (autobreakrows && (!pars[par].empty() || pars[par].allowEmpty())) {
breakParagraph(params(), paragraphs(), par, pos,
layout->isEnvironment());
++par;
}
// do not insert consecutive spaces if !free_spacing
} else if ((*cit == ' ' || *cit == '\t') &&
- space_inserted && !par->isFreeSpacing()) {
+ space_inserted && !pars[par].isFreeSpacing()) {
continue;
} else if (*cit == '\t') {
- if (!par->isFreeSpacing()) {
+ if (!pars[par].isFreeSpacing()) {
// tabs are like spaces here
- par->insertChar(pos, ' ', font);
+ pars[par].insertChar(pos, ' ', font);
++pos;
space_inserted = true;
} else {
- const pos_type nb = 8 - pos % 8;
- for (pos_type a = 0; a < nb ; ++a) {
- par->insertChar(pos, ' ', font);
+ const pos_type n = 8 - pos % 8;
+ for (pos_type i = 0; i < n; ++i) {
+ pars[par].insertChar(pos, ' ', font);
++pos;
}
space_inserted = true;
continue;
} else {
// just insert the character
- par->insertChar(pos, *cit, font);
+ pars[par].insertChar(pos, *cit, font);
++pos;
space_inserted = (*cit == ' ');
}
bool Buffer::readFile(string const & filename)
{
// Check if the file is compressed.
- string const format = getExtFromContents(filename);
+ string const format = getFormatFromContents(filename);
if (format == "gzip" || format == "zip" || format == "compress") {
params().compressed = true;
}
- bool ret = readFile(filename, paragraphs().begin());
+ // remove dummy empty par
+ paragraphs().clear();
+ bool ret = readFile(filename, paragraphs().size());
// After we have read a file, we must ensure that the buffer
// language is set and used in the gui.
}
-bool Buffer::readFile(string const & filename, ParagraphList::iterator pit)
+bool Buffer::readFile(string const & filename, par_type pit)
{
LyXLex lex(0, 0);
lex.setFile(filename);
-
return readFile(lex, filename, pit);
}
}
-bool Buffer::readFile(LyXLex & lex, string const & filename,
- ParagraphList::iterator pit)
+bool Buffer::readFile(LyXLex & lex, string const & filename, par_type pit)
{
BOOST_ASSERT(!filename.empty());
return false;
}
- lex.eatLine();
+ lex.next();
string tmp_format = lex.getString();
//lyxerr << "LyX Format: `" << tmp_format << '\'' << endl;
// if present remove ".," from string.
int file_format = strToInt(tmp_format);
//lyxerr << "format: " << file_format << endl;
- if (file_format > LYX_FORMAT) {
- Alert::warning(_("Document format failure"),
- bformat(_("%1$s was created with a newer"
- " version of LyX. This is likely to"
- " cause problems."),
- filename));
- } else if (file_format < LYX_FORMAT) {
+ if (file_format != LYX_FORMAT) {
string const tmpfile = tempName();
+ if (tmpfile.empty()) {
+ Alert::error(_("Conversion failed"),
+ bformat(_("%1$s is from an earlier"
+ " version of LyX, but a temporary"
+ " file for converting it could"
+ " not be created."),
+ filename));
+ return false;
+ }
string command = LibFileSearch("lyx2lyx", "lyx2lyx");
if (command.empty()) {
Alert::error(_("Conversion script not found"),
}
- bool the_end = readBody(lex, pit);
- params().setPaperStuff();
-
- if (!the_end) {
+ if (readDocument(lex)) {
Alert::error(_("Document format failure"),
bformat(_("%1$s ended unexpectedly, which means"
" that it is probably corrupted."),
filename));
}
+
+ //lyxerr << "removing " << MacroTable::localMacros().size()
+ // << " temporary macro entries" << endl;
+ //MacroTable::localMacros().clear();
+ params().setPaperStuff();
+
pimpl_->file_fully_loaded = true;
return true;
}
removeAutosaveFile(fileName());
} else {
// Saving failed, so backup is not backup
- if (lyxrc.make_backup) {
+ if (lyxrc.make_backup)
rename(s, fileName());
- }
return false;
}
return true;
bool Buffer::writeFile(string const & fname) const
{
- if (pimpl_->read_only && (fname == fileName())) {
+ if (pimpl_->read_only && fname == fileName())
return false;
- }
FileInfo finfo(fname);
- if (finfo.exist() && !finfo.writable()) {
+ if (finfo.exist() && !finfo.writable())
return false;
- }
- bool retval;
+ bool retval = false;
if (params().compressed) {
gz::ogzstream ofs(fname.c_str());
-
if (!ofs)
return false;
bool Buffer::do_writeFile(ostream & ofs) const
{
-
#ifdef HAVE_LOCALE
// Use the standard "C" locale for file output.
ofs.imbue(std::locale::classic());
// write out a comment in the top of the file
ofs << "#LyX " << lyx_version
<< " created this file. For more info see http://www.lyx.org/\n"
- << "\\lyxformat " << LYX_FORMAT << "\n";
+ << "\\lyxformat " << LYX_FORMAT << "\n"
+ << "\\begin_document\n";
- // now write out the buffer paramters.
+ // now write out the buffer parameters.
+ ofs << "\\begin_header\n";
params().writeFile(ofs);
-
ofs << "\\end_header\n";
- Paragraph::depth_type depth = 0;
-
- // this will write out all the paragraphs
- // using recursive descent.
- ParagraphList::const_iterator pit = paragraphs().begin();
- ParagraphList::const_iterator pend = paragraphs().end();
- for (; pit != pend; ++pit)
- pit->write(*this, ofs, params(), depth);
+ // write the text
+ ofs << "\n\\begin_body\n";
+ text().write(*this, ofs);
+ ofs << "\n\\end_body\n";
// Write marker that shows file is complete
- ofs << "\n\\end_document" << endl;
+ ofs << "\\end_document" << endl;
// Shouldn't really be needed....
//ofs.close();
// which should include file system full errors.
bool status = true;
- if (!ofs.good()) {
+ if (!ofs) {
status = false;
-#if 0
- if (ofs.bad()) {
- lyxerr << "Buffer::writeFile: BAD ERROR!" << endl;
- } else {
- lyxerr << "Buffer::writeFile: NOT SO BAD ERROR!"
- << endl;
- }
-#endif
+ lyxerr << "File was not closed properly." << endl;
}
return status;
runparams, output_preamble, output_body);
ofs.close();
- if (ofs.fail()) {
- lyxerr << "File was not closed properly." << endl;
- }
+ if (ofs.fail())
+ lyxerr << "File '" << fname << "' was not closed properly." << endl;
}
bool output_preamble, bool output_body)
{
OutputParams runparams = runparams_in;
- niceFile() = runparams.nice; // this will be used by Insetincludes.
// validate the buffer.
lyxerr[Debug::LATEX] << " Validating buffer..." << endl;
- LaTeXFeatures features(*this, params());
+ LaTeXFeatures features(*this, params(), runparams.nice);
validate(features);
lyxerr[Debug::LATEX] << " Buffer validation done." << endl;
texrow().reset();
+
// The starting paragraph of the coming rows is the
// first paragraph of the document. (Asger)
texrow().start(paragraphs().begin()->id(), 0);
// input@path is set when the actual parameter
// original_path is set. This is done for usual tex-file, but not
// for nice-latex-file. (Matthias 250696)
+ // Note that input@path is only needed for something the user does
+ // in the preamble, included .tex files or ERT, files included by
+ // LyX work without it.
if (output_preamble) {
if (!runparams.nice) {
// code for usual, NOT nice-latex-file
texrow().newline();
}
+ // if we are doing a real file with body, even if this is the
+ // child of some other buffer, let's cut the link here.
+ // This happens for example if only a child document is printed.
+ string save_parentname;
+ if (output_preamble) {
+ save_parentname = params().parentname;
+ params().parentname.erase();
+ }
+
+ // the real stuff
latexParagraphs(*this, paragraphs(), os, texrow(), runparams);
+ // Restore the parenthood if needed
+ if (output_preamble)
+ params().parentname = save_parentname;
+
// add this just in case after all the paragraphs
os << endl;
texrow().newline();
lyxerr[Debug::INFO] << "Finished making LaTeX file." << endl;
lyxerr[Debug::INFO] << "Row count was " << texrow().rows() - 1
<< '.' << endl;
-
- // we want this to be true outside previews (for insetexternal)
- niceFile() = true;
}
void Buffer::makeLinuxDocFile(string const & fname,
OutputParams const & runparams,
- bool body_only )
+ bool body_only)
{
ofstream ofs;
if (!openFileWrite(ofs, fname))
return;
- niceFile() = runparams.nice; // this will be used by included files.
-
- LaTeXFeatures features(*this, params());
-
+ LaTeXFeatures features(*this, params(), runparams.nice);
validate(features);
texrow().reset();
ofs << ">\n\n";
if (params().options.empty())
- sgml::openTag(ofs, 0, false, top_element);
+ sgml::openTag(ofs, top_element);
else {
string top = top_element;
top += ' ';
top += params().options;
- sgml::openTag(ofs, 0, false, top);
+ sgml::openTag(ofs, top);
}
}
if (!body_only) {
ofs << "\n\n";
- sgml::closeTag(ofs, 0, false, top_element);
+ sgml::closeTag(ofs, top_element);
}
ofs.close();
- // How to check for successful close
-
- // we want this to be true outside previews (for insetexternal)
- niceFile() = true;
+ if (ofs.fail())
+ lyxerr << "File '" << fname << "' was not closed properly." << endl;
}
if (!openFileWrite(ofs, fname))
return;
- niceFile() = runparams.nice; // this will be used by Insetincludes.
-
- LaTeXFeatures features(*this, params());
+ LaTeXFeatures features(*this, params(), runparams.nice);
validate(features);
texrow().reset();
string top_element = tclass.latexname();
if (!only_body) {
- ofs << subst(tclass.class_header(), "#", top_element);
+ if (runparams.flavor == OutputParams::XML)
+ ofs << "<?xml version=\"1.0\" encoding=\""
+ << params().language->encoding()->Name() << "\"?>\n";
+
+ ofs << "<!DOCTYPE " << top_element << " ";
+
+ if (! tclass.class_header().empty()) ofs << tclass.class_header();
+ else if (runparams.flavor == OutputParams::XML)
+ ofs << "PUBLIC \"-//OASIS//DTD DocBook XML//EN\" "
+ << "\"http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd\"";
+ else
+ ofs << " PUBLIC \"-//OASIS//DTD DocBook V4.2//EN\"";
string preamble = params().preamble;
+ if (runparams.flavor != OutputParams::XML ) {
+ preamble += "<!ENTITY % output.print.png \"IGNORE\">\n";
+ preamble += "<!ENTITY % output.print.pdf \"IGNORE\">\n";
+ preamble += "<!ENTITY % output.print.eps \"IGNORE\">\n";
+ preamble += "<!ENTITY % output.print.bmp \"IGNORE\">\n";
+ }
+
string const name = runparams.nice ? ChangeExtension(pimpl_->filename, ".sgml")
: fname;
preamble += features.getIncludedFiles(name);
string top = top_element;
top += " lang=\"";
- top += params().language->code();
+ if (runparams.flavor == OutputParams::XML)
+ top += params().language->code();
+ else
+ top += params().language->code().substr(0,2);
top += '"';
if (!params().options.empty()) {
top += ' ';
top += params().options;
}
- sgml::openTag(ofs, 0, false, top);
- ofs << "<!-- SGML/XML file was created by LyX " << lyx_version
+ ofs << "<!-- " << ((runparams.flavor == OutputParams::XML)? "XML" : "SGML")
+ << " file was created by LyX " << lyx_version
<< "\n See http://www.lyx.org/ for more information -->\n";
params().getLyXTextClass().counters().reset();
- docbookParagraphs(*this, paragraphs(), ofs, runparams);
- ofs << "\n\n";
- sgml::closeTag(ofs, 0, false, top_element);
+ sgml::openTag(ofs, top);
+ ofs << '\n';
+ docbookParagraphs(paragraphs(), *this, ofs, runparams);
+ sgml::closeTag(ofs, top_element);
ofs.close();
- // How to check for successful close
-
- // we want this to be true outside previews (for insetexternal)
- niceFile() = true;
+ if (ofs.fail())
+ lyxerr << "File '" << fname << "' was not closed properly." << endl;
}
// get LaTeX-Filename
string const name = getLatexName();
- string path = filePath();
-
- string const org_path = path;
- if (lyxrc.use_tempdir || !IsDirWriteable(path)) {
- path = temppath();
- }
+ string const path = temppath();
+ string const org_path = filePath();
Path p(path); // path to LaTeX file
message(_("Running chktex..."));
{
/// if this is a child document and the parent is already loaded
/// Use the parent's list instead [ale990407]
- if (!params().parentname.empty()
- && bufferlist.exists(params().parentname)) {
- Buffer const * tmp = bufferlist.getBuffer(params().parentname);
- if (tmp) {
- tmp->getLabelList(list);
- return;
- }
+ Buffer const * tmp = getMasterBuffer();
+ if (!tmp) {
+ lyxerr << "getMasterBuffer() failed!" << endl;
+ BOOST_ASSERT(tmp);
}
-
- for (inset_iterator it = inset_const_iterator_begin();
- it != inset_const_iterator_end(); ++it) {
- it->getLabelList(*this, list);
+ if (tmp != this) {
+ tmp->getLabelList(list);
+ return;
}
+
+ for (InsetIterator it = inset_iterator_begin(inset()); it; ++it)
+ it.nextInset()->getLabelList(*this, list);
}
// This is also a buffer property (ale)
-void Buffer::fillWithBibKeys(std::vector<std::pair<string, string> > & keys) const
+void Buffer::fillWithBibKeys(std::vector<std::pair<string, string> > & keys)
+ const
{
/// if this is a child document and the parent is already loaded
/// use the parent's list instead [ale990412]
- if (!params().parentname.empty() &&
- bufferlist.exists(params().parentname)) {
- Buffer const * tmp = bufferlist.getBuffer(params().parentname);
- if (tmp) {
- tmp->fillWithBibKeys(keys);
- return;
- }
+ Buffer const * tmp = getMasterBuffer();
+ BOOST_ASSERT(tmp);
+ if (tmp != this) {
+ tmp->fillWithBibKeys(keys);
+ return;
}
- for (inset_iterator it = inset_const_iterator_begin();
- it != inset_const_iterator_end(); ++it) {
+ for (InsetIterator it = inset_iterator_begin(inset()); it; ++it) {
if (it->lyxCode() == InsetOld::BIBTEX_CODE) {
InsetBibtex const & inset =
dynamic_cast<InsetBibtex const &>(*it);
// Take care of l10n/i18n
updateDocLang(to);
- ParIterator end = par_iterator_end();
- for (ParIterator it = par_iterator_begin(); it != end; ++it)
- it->changeLanguage(params(), from, to);
+ for_each(par_iterator_begin(),
+ par_iterator_end(),
+ bind(&Paragraph::changeLanguage, _1, params(), from, to));
}
}
-bool Buffer::isMultiLingual()
+bool Buffer::isMultiLingual() const
{
- ParIterator end = par_iterator_end();
- for (ParIterator it = par_iterator_begin(); it != end; ++it)
+ ParConstIterator end = par_iterator_end();
+ for (ParConstIterator it = par_iterator_begin(); it != end; ++it)
if (it->isMultiLingual(params()))
return true;
}
-void Buffer::inset_iterator::setParagraph()
-{
- while (pit != pend) {
- it = pit->insetlist.begin();
- if (it != pit->insetlist.end())
- return;
- ++pit;
- }
-}
-
-
ParIterator Buffer::getParFromID(int id) const
{
-#warning FIXME: const correctness! (Andre)
- ParIterator it = const_cast<Buffer*>(this)->par_iterator_begin();
- ParIterator end = const_cast<Buffer*>(this)->par_iterator_end();
+ ParConstIterator it = par_iterator_begin();
+ ParConstIterator end = par_iterator_end();
-#warning FIXME, perhaps this func should return a ParIterator? (Lgb)
if (id < 0) {
// John says this is called with id == -1 from undo
lyxerr << "getParFromID(), id: " << id << endl;
bool Buffer::hasParWithID(int id) const
{
- ParConstIterator it = par_iterator_begin();
- ParConstIterator end = par_iterator_end();
-
- if (id < 0) {
- // John says this is called with id == -1 from undo
- lyxerr << "hasParWithID(), id: " << id << endl;
- return 0;
- }
-
- for (; it != end; ++it)
- if (it->id() == id)
- return true;
-
- return false;
-}
-
-
-PosIterator Buffer::pos_iterator_begin()
-{
- return PosIterator(¶graphs(), paragraphs().begin(), 0);
-}
-
-
-PosIterator Buffer::pos_iterator_end()
-{
- return PosIterator(¶graphs(), paragraphs().end(), 0);
+ ParConstIterator it = getParFromID(id);
+ return it != par_iterator_end();
}
ParIterator Buffer::par_iterator_begin()
{
- return ParIterator(paragraphs().begin(), paragraphs());
+ return ::par_iterator_begin(inset());
}
ParIterator Buffer::par_iterator_end()
{
- return ParIterator(paragraphs().end(), paragraphs());
+ return ::par_iterator_end(inset());
}
ParConstIterator Buffer::par_iterator_begin() const
{
- ParagraphList const & pars = paragraphs();
- return ParConstIterator(const_cast<ParagraphList&>(pars).begin(), pars);
+ return ::par_const_iterator_begin(inset());
}
ParConstIterator Buffer::par_iterator_end() const
{
- ParagraphList const & pars = paragraphs();
- return ParConstIterator(const_cast<ParagraphList&>(pars).end(), pars);
+ return ::par_const_iterator_end(inset());
}
}
-bool Buffer::isUnnamed()
+bool Buffer::isUnnamed() const
{
return pimpl_->unnamed;
}
}
-Buffer::inset_iterator::inset_iterator()
- : pit(), pend()
-{}
-
-
-Buffer::inset_iterator::inset_iterator(base_type p, base_type e)
- : pit(p), pend(e)
-{
- setParagraph();
-}
-
-
-Buffer::inset_iterator Buffer::inset_iterator_begin()
-{
- return inset_iterator(paragraphs().begin(), paragraphs().end());
-}
-
-
-Buffer::inset_iterator Buffer::inset_iterator_end()
-{
- return inset_iterator(paragraphs().end(), paragraphs().end());
-}
-
-
-Buffer::inset_iterator Buffer::inset_const_iterator_begin() const
-{
- ParagraphList & pars = const_cast<ParagraphList&>(paragraphs());
- return inset_iterator(pars.begin(), pars.end());
-}
-
-
-Buffer::inset_iterator Buffer::inset_const_iterator_end() const
-{
- ParagraphList & pars = const_cast<ParagraphList&>(paragraphs());
- return inset_iterator(pars.end(), pars.end());
-}
-
-
-Buffer::inset_iterator & Buffer::inset_iterator::operator++()
+Buffer const * Buffer::getMasterBuffer() const
{
- if (pit != pend) {
- ++it;
- if (it == pit->insetlist.end()) {
- ++pit;
- setParagraph();
- }
+ if (!params().parentname.empty()
+ && bufferlist.exists(params().parentname)) {
+ Buffer const * buf = bufferlist.getBuffer(params().parentname);
+ if (buf)
+ return buf->getMasterBuffer();
}
- return *this;
-}
-
-Buffer::inset_iterator Buffer::inset_iterator::operator++(int)
-{
- inset_iterator tmp = *this;
- ++*this;
- return tmp;
-}
-
-
-Buffer::inset_iterator::reference Buffer::inset_iterator::operator*()
-{
- return *it->inset;
+ return this;
}
-Buffer::inset_iterator::pointer Buffer::inset_iterator::operator->()
+MacroData const & Buffer::getMacro(std::string const & name) const
{
- return it->inset;
+ return pimpl_->macros.get(name);
}
-ParagraphList::iterator Buffer::inset_iterator::getPar() const
+bool Buffer::hasMacro(string const & name) const
{
- return pit;
+ return pimpl_->macros.has(name);
}
-lyx::pos_type Buffer::inset_iterator::getPos() const
+void Buffer::insertMacro(string const & name, MacroData const & data)
{
- return it->pos;
+ MacroTable::globalMacros().insert(name, data);
+ pimpl_->macros.insert(name, data);
}
-bool operator==(Buffer::inset_iterator const & iter1,
- Buffer::inset_iterator const & iter2)
+void Buffer::buildMacros()
{
- return iter1.pit == iter2.pit
- && (iter1.pit == iter1.pend || iter1.it == iter2.it);
-}
+ // Start with global table.
+ pimpl_->macros = MacroTable::globalMacros();
-
-bool operator!=(Buffer::inset_iterator const & iter1,
- Buffer::inset_iterator const & iter2)
-{
- return !(iter1 == iter2);
+ // Now add our own.
+ ParagraphList & pars = text().paragraphs();
+ for (size_t i = 0, n = pars.size(); i != n; ++i) {
+ //lyxerr << "searching main par " << i
+ // << " for macro definitions" << std::endl;
+ InsetList::iterator it = pars[i].insetlist.begin();
+ InsetList::iterator end = pars[i].insetlist.end();
+ for ( ; it != end; ++it) {
+ //lyxerr << "found inset code " << it->inset->lyxCode() << std::endl;
+ if (it->inset->lyxCode() == InsetBase::MATHMACRO_CODE) {
+ MathMacroTemplate & mac
+ = static_cast<MathMacroTemplate &>(*it->inset);
+ insertMacro(mac.name(), mac.asMacroData());
+ }
+ }
+ }
}