X-Git-Url: https://git.lyx.org/gitweb/?a=blobdiff_plain;f=src%2Fmathed%2FMacroTable.cpp;h=efb111f84f4741ba3c23d2e0d3a8cebeb5875b90;hb=f1cba8ff64b369792fd49f5ddf90e8126ab476ac;hp=ac2ac88a7602af5c77bf07aaaa530c94edfe77fe;hpb=565475a43917af9c52a3d9d8272e020160d0b971;p=features.git diff --git a/src/mathed/MacroTable.cpp b/src/mathed/MacroTable.cpp index ac2ac88a76..efb111f84f 100644 --- a/src/mathed/MacroTable.cpp +++ b/src/mathed/MacroTable.cpp @@ -3,58 +3,70 @@ * This file is part of LyX, the document processor. * Licence details can be found in the file COPYING. * - * \author André Pönitz + * \author André Pönitz * * Full author contact details are available in file CREDITS. */ #include +#include "InsetMathSqrt.h" #include "MacroTable.h" #include "MathMacroTemplate.h" #include "MathMacroArgument.h" +#include "MathStream.h" #include "MathSupport.h" -#include "InsetMathSqrt.h" - #include "InsetMathNest.h" -#include "Buffer.h" -#include "debug.h" +#include "Buffer.h" #include "DocIterator.h" +#include "InsetList.h" +#include "Text.h" + +#include "support/debug.h" -#include +#include "support/lassert.h" #include +using namespace std; namespace lyx { -using std::endl; -using std::istringstream; -using std::map; -using std::pair; -using std::string; -using std::vector; -using std::size_t; +///////////////////////////////////////////////////////////////////// +// +// MacroData +// +///////////////////////////////////////////////////////////////////// MacroData::MacroData() - : numargs_(0), lockCount_(0), redefinition_(false) + : queried_(true), numargs_(0), optionals_(0), lockCount_(0), + redefinition_(false), type_(MacroTypeNewcommand) {} - -MacroData::MacroData(docstring const & definition, std::vector const & defaults, - int numargs, int optionals, docstring const & display, string const & requires) - : definition_(definition), numargs_(numargs), display_(display), - requires_(requires), lockCount_(0), redefinition_(false), optionals_(optionals), - defaults_(defaults) + + +MacroData::MacroData(Buffer const & buf, DocIterator const & pos) + : buffer_(&buf), pos_(pos), queried_(false), numargs_(0), + optionals_(0), lockCount_(0), redefinition_(false), + type_(MacroTypeNewcommand) { - defaults_.resize(optionals); +} + + +MacroData::MacroData(MathMacroTemplate const & macro) + : queried_(false), numargs_(0), optionals_(0), lockCount_(0), + redefinition_(false), type_(MacroTypeNewcommand) +{ + queryData(macro); } void MacroData::expand(vector const & args, MathData & to) const { + updateData(); + InsetMathSqrt inset; // Hack. Any inset with a cell would do. // FIXME UNICODE asArray(display_.empty() ? definition_ : display_, inset.cell(0)); @@ -80,35 +92,100 @@ void MacroData::expand(vector const & args, MathData & to) const size_t MacroData::optionals() const { + updateData(); return optionals_; } -std::vector const & MacroData::defaults() const +vector const & MacroData::defaults() const { + updateData(); return defaults_; } -// The global table. -MacroTable & MacroTable::globalMacros() +void MacroData::unlock() const { - static MacroTable theGlobalMacros; - return theGlobalMacros; + --lockCount_; + LASSERT(lockCount_ >= 0, /**/); +} + + +void MacroData::queryData(MathMacroTemplate const & macro) const +{ + if (queried_) + return; + + queried_ = true; + definition_ = macro.definition(); + numargs_ = macro.numArgs(); + display_ = macro.displayDefinition(); + redefinition_ = macro.redefinition(); + type_ = macro.type(); + optionals_ = macro.numOptionals(); + + macro.getDefaults(defaults_); +} + + +void MacroData::updateData() const +{ + if (queried_) + return; + + LASSERT(buffer_ != 0, /**/); + + // Try to fix position DocIterator. Should not do anything in theory. + pos_.fixIfBroken(); + + // find macro template + Inset * inset = pos_.nextInset(); + if (inset == 0 || inset->lyxCode() != MATHMACRO_CODE) { + lyxerr << "BUG: No macro template found by MacroData" << endl; + return; + } + + // query the data from the macro template + queryData(static_cast(*inset)); +} + + +void MacroData::write(odocstream & os, bool overwriteRedefinition) const +{ + updateData(); + + // find macro template + Inset * inset = pos_.nextInset(); + if (inset == 0 || inset->lyxCode() != MATHMACRO_CODE) { + lyxerr << "BUG: No macro template found by MacroData" << endl; + return; + } + + // output template + MathMacroTemplate const & tmpl = + static_cast(*inset); + WriteStream wi(os, false, true, false); + tmpl.write(wi, overwriteRedefinition); } -bool MacroTable::has(docstring const & name) const +///////////////////////////////////////////////////////////////////// +// +// The global table of macros +// +///////////////////////////////////////////////////////////////////// + +MacroTable & MacroTable::globalMacros() { - return find(name) != end(); + static MacroTable theGlobalMacros; + return theGlobalMacros; } -MacroData const & MacroTable::get(docstring const & name) const +MacroData const * MacroTable::get(docstring const & name) const { const_iterator it = find(name); - BOOST_ASSERT(it != end()); - return it->second; + return it == end() ? 0 : &it->second; } @@ -123,12 +200,19 @@ void MacroTable::insert(docstring const & def, string const & requires) { //lyxerr << "MacroTable::insert, def: " << to_utf8(def) << endl; MathMacroTemplate mac(def); - MacroData data = mac.asMacroData(); + MacroData data(mac); data.requires() = requires; insert(mac.name(), data); } +void MacroTable::getMacroNames(std::set & names) const +{ + for (const_iterator it = begin(); it != end(); ++it) + names.insert(it->first); +} + + void MacroTable::dump() { lyxerr << "\n------------------------------------------" << endl; @@ -141,38 +225,21 @@ void MacroTable::dump() } -MacroContext::MacroContext(Buffer const & buf, Paragraph const & par) - : buf_(buf), par_(par) -{ -} - - -bool MacroContext::has(docstring const & name) const -{ - // check if it's a local macro - if (macros_.has(name)) - return true; - - // otherwise ask the buffer - return buf_.hasMacro(name, par_); -} +///////////////////////////////////////////////////////////////////// +// +// MacroContext +// +///////////////////////////////////////////////////////////////////// - -MacroData const & MacroContext::get(docstring const & name) const +MacroContext::MacroContext(Buffer const & buf, DocIterator const & pos) + : buf_(buf), pos_(pos) { - // check if it's a local macro - if (macros_.has(name)) - return macros_.get(name); - - // ask the buffer for its macros - return buf_.getMacro(name, par_); } -void MacroContext::insert(docstring const & name, MacroData const & data) +MacroData const * MacroContext::get(docstring const & name) const { - macros_.insert(name, data); + return buf_.getMacro(name, pos_); } - } // namespace lyx