X-Git-Url: https://git.lyx.org/gitweb/?a=blobdiff_plain;f=src%2Fmathed%2Fformulabase.C;h=18e1c97ba2a17f4b24e8e18d7bab9366309457b4;hb=30705f0927e5e2a3542ff328847014c43a11e32f;hp=1941b0a61456c01c6852f64169d0710b3991b126;hpb=76ef051b1cb1fb51c3ffd8ccc9105be4471e74d4;p=lyx.git diff --git a/src/mathed/formulabase.C b/src/mathed/formulabase.C index 1941b0a614..18e1c97ba2 100644 --- a/src/mathed/formulabase.C +++ b/src/mathed/formulabase.C @@ -1,4 +1,4 @@ -/* + /* * File: formula.C * Purpose: Implementation of formula inset * Author: Alejandro Aguilar Sierra @@ -23,31 +23,34 @@ #endif #include "formula.h" +#include "formulamacro.h" #include "commandtags.h" #include "math_cursor.h" #include "math_parser.h" #include "BufferView.h" #include "lyxtext.h" +#include "lyxfunc.h" #include "gettext.h" #include "LaTeXFeatures.h" #include "debug.h" -#include "support/LOstream.h" +#include "support/lstrings.h" #include "LyXView.h" #include "Painter.h" #include "font.h" #include "math_arrayinset.h" #include "math_spaceinset.h" -#include "math_deliminset.h" +#include "math_macrotable.h" #include "support/lyxlib.h" #include "mathed/support.h" +#include "undo_funcs.h" -using namespace std; +using std::endl; +using std::ostream; +using std::vector; extern char const * latex_special_chars; -int greek_kb_flag = 0; extern char const * latex_mathenv[]; -LyXFont * Math_Fonts = 0; MathCursor * mathcursor = 0; @@ -63,234 +66,158 @@ void mathed_init_fonts(); string nicelabel(string const & label) { - return label.empty() ? string("(#)") : "(" + label + ")"; + return "(" + (label.empty() ? "#" : label) + ")"; } -} // namespaces - - - -LyXFont WhichFont(short type, int size) +void handleFont(BufferView * bv, MathTextCodes t) { - LyXFont f; - - if (!Math_Fonts) - mathed_init_fonts(); - - switch (type) { - case LM_TC_SYMB: - f = Math_Fonts[2]; - break; - - case LM_TC_BSYM: - f = Math_Fonts[2]; - break; - - case LM_TC_VAR: - case LM_TC_IT: - f = Math_Fonts[0]; - break; - - case LM_TC_BF: - f = Math_Fonts[3]; - break; - - case LM_TC_SF: - f = Math_Fonts[7]; - break; - - case LM_TC_CAL: - f = Math_Fonts[4]; - break; - - case LM_TC_TT: - f = Math_Fonts[5]; - break; - - case LM_TC_SPECIAL: //f = Math_Fonts[0]; break; - case LM_TC_TEXTRM: - case LM_TC_RM: - f = Math_Fonts[6]; - break; - - default: - f = Math_Fonts[1]; - break; - } - - switch (size) { - case LM_ST_DISPLAY: - if (type == LM_TC_BSYM) { - f.incSize(); - f.incSize(); - } - break; - - case LM_ST_TEXT: - break; - - case LM_ST_SCRIPT: - f.decSize(); - break; - - case LM_ST_SCRIPTSCRIPT: - f.decSize(); - f.decSize(); - break; - - default: - lyxerr << "Math Error: wrong font size: " << size << endl; - break; - } - - if (type != LM_TC_TEXTRM) - f.setColor(LColor::math); - - return f; + if (mathcursor->selection()) + bv->lockedInsetStoreUndo(Undo::EDIT); + mathcursor->handleFont(t); } +void handleAccent(BufferView * bv, string const & name) +{ + bv->lockedInsetStoreUndo(Undo::EDIT); + mathcursor->handleAccent(name); +} -namespace { - -void mathed_init_fonts() +void handleDelim(BufferView * bv, int l, int r) { - Math_Fonts = new LyXFont[8]; //DEC cxx cannot initialize all fonts - //at once (JMarc) rc + bv->lockedInsetStoreUndo(Undo::EDIT); + mathcursor->handleDelim(l, r); +} - for (int i = 0 ; i < 8 ; ++i) { - Math_Fonts[i] = LyXFont(LyXFont::ALL_SANE); +bool openNewInset(BufferView * bv, UpdatableInset * new_inset) +{ + LyXText * lt = bv->getLyXText(); + + bv->beforeChange(lt); + finishUndo(); + if (!bv->insertInset(new_inset)) { + delete new_inset; + return false; } - - Math_Fonts[0].setShape(LyXFont::ITALIC_SHAPE); - - Math_Fonts[1].setFamily(LyXFont::SYMBOL_FAMILY); - - Math_Fonts[2].setFamily(LyXFont::SYMBOL_FAMILY); - Math_Fonts[2].setShape(LyXFont::ITALIC_SHAPE); - - Math_Fonts[3].setSeries(LyXFont::BOLD_SERIES); - - Math_Fonts[4].setFamily(LyXFont::SANS_FAMILY); - Math_Fonts[4].setShape(LyXFont::ITALIC_SHAPE); - - Math_Fonts[5].setFamily(LyXFont::TYPEWRITER_FAMILY); - - Math_Fonts[6].setFamily(LyXFont::ROMAN_FAMILY); - - Math_Fonts[7].setFamily(LyXFont::SANS_FAMILY); + new_inset->edit(bv, 0, 0, 0); + return true; } -// returns the nearest enclosing matrix +// returns the nearest enclosing grid MathArrayInset * matrixpar(int & idx) { idx = 0; - return - static_cast - (mathcursor ? mathcursor->enclosing(LM_OT_MATRIX, idx) : 0); + return (mathcursor ? mathcursor->enclosingArray(idx) : 0); } } // namespace anon -InsetFormulaBase::InsetFormulaBase(MathInset * par) - : par_(par) -{} - -InsetFormulaBase::InsetFormulaBase(InsetFormulaBase const & f) - : UpdatableInset(f), par_(static_cast(f.par_->Clone())) -{} -InsetFormulaBase::~InsetFormulaBase() +InsetFormulaBase::InsetFormulaBase() { #ifdef WITH_WARNINGS -#warning leak this for a while... +#warning This is needed as long the math parser is not re-entrant #endif - //delete par_; + MathMacroTable::builtinMacros(); + //lyxerr << "sizeof MathInset: " << sizeof(MathInset) << "\n"; } -void InsetFormulaBase::Write(Buffer const * buf, ostream & os) const +void InsetFormulaBase::read(Buffer const *, LyXLex & lex) { - os << "Formula "; - Latex(buf, os, false, false); + read(lex); } -int InsetFormulaBase::Ascii(Buffer const *, ostream & os, int) const +void InsetFormulaBase::write(Buffer const *, ostream & os) const { - par_->Write(os, false); - return 0; + write(os); } +int InsetFormulaBase::latex(Buffer const *, ostream & os, + bool fragile, bool spacing) const +{ + return latex(os, fragile, spacing); +} -int InsetFormulaBase::Linuxdoc(Buffer const * buf, ostream & os) const +int InsetFormulaBase::ascii(Buffer const *, ostream & os, int spacing) const { - return Ascii(buf, os, 0); + return ascii(os, spacing); } +int InsetFormulaBase::linuxdoc(Buffer const *, ostream & os) const +{ + return linuxdoc(os); +} -int InsetFormulaBase::DocBook(Buffer const * buf, ostream & os) const +int InsetFormulaBase::docBook(Buffer const *, ostream & os) const { - return Ascii(buf, os, 0); + return docBook(os); } + // Check if uses AMS macros -void InsetFormulaBase::Validate(LaTeXFeatures &) const +void InsetFormulaBase::validate(LaTeXFeatures &) const {} -string const InsetFormulaBase::EditMessage() const +string const InsetFormulaBase::editMessage() const { return _("Math editor mode"); } -void InsetFormulaBase::Edit(BufferView * bv, int x, int /*y*/, unsigned int) +void InsetFormulaBase::edit(BufferView * bv, int x, int /*y*/, unsigned int) { mathcursor = new MathCursor(this); if (!bv->lockInset(this)) lyxerr[Debug::MATHED] << "Cannot lock inset!!!" << endl; - par_->Metrics(LM_ST_TEXT); - bv->updateInset(this, false); - if (x == 0) { + metrics(); + //bv->updateInset(this, false); + if (x == 0) mathcursor->first(); - } else { + else mathcursor->last(); - } sel_x = 0; sel_y = 0; sel_flag = false; } -void InsetFormulaBase::InsetUnlock(BufferView * bv) +void InsetFormulaBase::edit(BufferView * bv, bool front) +{ + edit(bv, front ? 0 : 1, 0, 0); +} + + +void InsetFormulaBase::insetUnlock(BufferView * bv) { if (mathcursor) { - if (mathcursor->InMacroMode()) { - mathcursor->MacroModeClose(); - UpdateLocal(bv); + if (mathcursor->inMacroMode()) { + mathcursor->macroModeClose(); + updateLocal(bv, true); } delete mathcursor; + mathcursor = 0; } - mathcursor = 0; bv->updateInset(this, false); } -void InsetFormulaBase::GetCursorPos(BufferView *, int & x, int & y) const +void InsetFormulaBase::getCursorPos(BufferView *, int & x, int & y) const { - mathcursor->GetPos(x, y); - x -= par_->xo(); - y -= par_->yo(); + mathcursor->getPos(x, y); + x -= par()->xo(); + y -= par()->yo(); } -void InsetFormulaBase::ToggleInsetCursor(BufferView * bv) +void InsetFormulaBase::toggleInsetCursor(BufferView * bv) { if (!mathcursor) return; @@ -300,14 +227,12 @@ void InsetFormulaBase::ToggleInsetCursor(BufferView * bv) else { int x; int y; - mathcursor->GetPos(x, y); - //x -= par_->xo(); - y -= par_->yo(); - - LyXFont font = WhichFont(LM_TC_TEXTRM, LM_ST_TEXT); - int const asc = lyxfont::maxAscent(font); - int const desc = lyxfont::maxDescent(font); - + mathcursor->getPos(x, y); + //x -= par()->xo(); + y -= par()->yo(); + int asc; + int desc; + math_font_max_dim(LM_TC_TEXTRM, LM_ST_TEXT, asc, desc); bv->showLockedInsetCursor(x, y, asc, desc); } @@ -315,38 +240,36 @@ void InsetFormulaBase::ToggleInsetCursor(BufferView * bv) } -void InsetFormulaBase::ShowInsetCursor(BufferView * bv, bool) +void InsetFormulaBase::showInsetCursor(BufferView * bv, bool) { if (!isCursorVisible()) { if (mathcursor) { int x; int y; - mathcursor->GetPos(x, y); - x -= par_->xo(); - y -= par_->yo(); - LyXFont font = WhichFont(LM_TC_TEXTRM, LM_ST_TEXT); - int const asc = lyxfont::maxAscent(font); - int const desc = lyxfont::maxDescent(font); + mathcursor->getPos(x, y); + x -= par()->xo(); + y -= par()->yo(); + int asc; + int desc; + math_font_max_dim(LM_TC_TEXTRM, LM_ST_TEXT, asc, desc); bv->fitLockedInsetCursor(x, y, asc, desc); } - ToggleInsetCursor(bv); + toggleInsetCursor(bv); } } -void InsetFormulaBase::HideInsetCursor(BufferView * bv) +void InsetFormulaBase::hideInsetCursor(BufferView * bv) { if (isCursorVisible()) - ToggleInsetCursor(bv); + toggleInsetCursor(bv); } -void InsetFormulaBase::ToggleInsetSelection(BufferView * bv) +void InsetFormulaBase::toggleInsetSelection(BufferView * bv) { - if (!mathcursor) - return; - - bv->updateInset(this, false); + if (mathcursor) + bv->updateInset(this, false); } @@ -356,62 +279,62 @@ vector const InsetFormulaBase::getLabelList() const } -void InsetFormulaBase::UpdateLocal(BufferView * bv) +void InsetFormulaBase::updateLocal(BufferView * bv, bool dirty) { - par_->Metrics(LM_ST_TEXT); - bv->updateInset(this, true); + metrics(); + bv->updateInset(this, dirty); } -void InsetFormulaBase::InsetButtonRelease(BufferView * bv, - int x, int y, int /*button*/) +void InsetFormulaBase::insetButtonRelease(BufferView * bv, + int x, int y, int /*button*/) { if (mathcursor) { - HideInsetCursor(bv); - x += par_->xo(); - y += par_->yo(); - mathcursor->SetPos(x, y); - ShowInsetCursor(bv); + hideInsetCursor(bv); + x += par()->xo(); + y += par()->yo(); + mathcursor->setPos(x, y); + showInsetCursor(bv); if (sel_flag) { sel_flag = false; sel_x = 0; sel_y = 0; - bv->updateInset(this, false); } + bv->updateInset(this, false); } } -void InsetFormulaBase::InsetButtonPress(BufferView * bv, - int x, int y, int /*button*/) +void InsetFormulaBase::insetButtonPress(BufferView * bv, + int x, int y, int /*button*/) { sel_flag = false; sel_x = x; sel_y = y; - if (mathcursor && mathcursor->Selection()) { - mathcursor->SelClear(); + if (mathcursor && mathcursor->selection()) { + mathcursor->selClear(); bv->updateInset(this, false); } } -void InsetFormulaBase::InsetMotionNotify(BufferView * bv, - int x, int y, int /*button*/) +void InsetFormulaBase::insetMotionNotify(BufferView * bv, + int x, int y, int /*button*/) { if (sel_x && sel_y && abs(x-sel_x) > 4 && !sel_flag) { sel_flag = true; - HideInsetCursor(bv); - mathcursor->SetPos(sel_x + par_->xo(), sel_y + par_->yo()); - mathcursor->SelStart(); - ShowInsetCursor(bv); - mathcursor->GetPos(sel_x, sel_y); + hideInsetCursor(bv); + mathcursor->setPos(sel_x + par()->xo(), sel_y + par()->yo()); + mathcursor->selStart(); + showInsetCursor(bv); + mathcursor->getPos(sel_x, sel_y); } else if (sel_flag) { - HideInsetCursor(bv); - x += par_->xo(); - y += par_->yo(); - mathcursor->SetPos(x, y); - ShowInsetCursor(bv); - mathcursor->GetPos(x, y); + hideInsetCursor(bv); + x += par()->xo(); + y += par()->yo(); + mathcursor->setPos(x, y); + showInsetCursor(bv); + mathcursor->getPos(x, y); if (sel_x != x || sel_y != y) bv->updateInset(this, false); sel_x = x; @@ -420,32 +343,32 @@ void InsetFormulaBase::InsetMotionNotify(BufferView * bv, } -void InsetFormulaBase::InsetKeyPress(XKeyEvent *) +void InsetFormulaBase::insetKeyPress(XKeyEvent *) { lyxerr[Debug::MATHED] << "Used InsetFormulaBase::InsetKeyPress." << endl; } + UpdatableInset::RESULT -InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, +InsetFormulaBase::localDispatch(BufferView * bv, kb_action action, string const & arg) { //lyxerr << "InsetFormulaBase::LocalDispatch: act: " << action // << " arg: '" << arg << "' cursor: " << mathcursor << "\n"; - // extern char *dispatch_result; + + static int greek_kb_flag = 0; if (!mathcursor) return UNDISPATCHED; MathTextCodes varcode = LM_TC_MIN; - bool was_macro = mathcursor->InMacroMode(); + bool was_macro = mathcursor->inMacroMode(); bool sel = false; - bool space_on = false; - bool was_selection = mathcursor->Selection(); + bool was_selection = mathcursor->selection(); RESULT result = DISPATCHED; - static MathSpaceInset * sp = 0; - HideInsetCursor(bv); + hideInsetCursor(bv); if (mathcursor->getLastCode() == LM_TC_TEX) varcode = LM_TC_TEX; @@ -460,8 +383,8 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, sel = true; // fall through... case LFUN_RIGHT: - result = DISPATCH_RESULT(mathcursor->Right(sel)); - UpdateLocal(bv); + result = DISPATCH_RESULT(mathcursor->right(sel)); + updateLocal(bv, false); break; @@ -469,8 +392,8 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, sel = true; // fall through case LFUN_LEFT: - result = DISPATCH_RESULT(mathcursor->Left(sel)); - UpdateLocal(bv); + result = DISPATCH_RESULT(mathcursor->left(sel)); + updateLocal(bv, false); break; @@ -478,8 +401,8 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, sel = true; case LFUN_UP: - result = DISPATCH_RESULT(mathcursor->Up(sel)); - UpdateLocal(bv); + result = DISPATCH_RESULT(mathcursor->up(sel)); + updateLocal(bv, false); break; @@ -487,53 +410,51 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, sel = true; case LFUN_DOWN: - result = DISPATCH_RESULT(mathcursor->Down(sel)); - UpdateLocal(bv); + result = DISPATCH_RESULT(mathcursor->down(sel)); + updateLocal(bv, false); break; - case LFUN_HOME: - mathcursor->Home(); - result = DISPATCHED_NOUPDATE; + mathcursor->home(); + updateLocal(bv, false); break; case LFUN_END: - mathcursor->End(); - result = DISPATCHED_NOUPDATE; + mathcursor->end(); + updateLocal(bv, false); break; case LFUN_DELETE_LINE_FORWARD: bv->lockedInsetStoreUndo(Undo::DELETE); - mathcursor->DelLine(); - UpdateLocal(bv); + mathcursor->delLine(); + updateLocal(bv, true); break; case LFUN_TAB: - bv->lockedInsetStoreUndo(Undo::INSERT); - mathcursor->idxRight(); - UpdateLocal(bv); + mathcursor->idxNext(); + updateLocal(bv, false); + break; + + case LFUN_SHIFT_TAB: + mathcursor->idxPrev(); + updateLocal(bv, false); break; case LFUN_TABINSERT: - bv->lockedInsetStoreUndo(Undo::INSERT); - mathcursor->idxRight(); - UpdateLocal(bv); + bv->lockedInsetStoreUndo(Undo::EDIT); + mathcursor->splitCell(); + updateLocal(bv, true); break; case LFUN_BACKSPACE: - if (!mathcursor->InMacroMode() && mathcursor->pos() == 0) { - bv->lockedInsetStoreUndo(Undo::DELETE); - mathcursor->pullArg(); - bv->updateInset(this, true); - break; - } - if (!mathcursor->Left()) - break; - // fall through... + bv->lockedInsetStoreUndo(Undo::DELETE); + mathcursor->backspace(); + bv->updateInset(this, true); + break; case LFUN_DELETE: bv->lockedInsetStoreUndo(Undo::DELETE); - mathcursor->Delete(); + mathcursor->erase(); bv->updateInset(this, true); break; @@ -544,33 +465,35 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, case LFUN_SETXY: { lyxerr << "LFUN_SETXY broken!\n"; - int x, y, x1, y1; + int x; + int y; + int x1; + int y1; istringstream is(arg.c_str()); is >> x >> y; - lyxerr << "LFUN_SETXY: x: " << x << " y: " << y << "\n"; - par_->GetXY(x1, y1); - mathcursor->SetPos(x1 + x, y1 + y); + par()->getXY(x1, y1); + mathcursor->setPos(x1 + x, y1 + y); + updateLocal(bv, false); } break; - // cursor selection ---------------------------- case LFUN_PASTE: if (was_macro) - mathcursor->MacroModeClose(); + mathcursor->macroModeClose(); bv->lockedInsetStoreUndo(Undo::INSERT); - mathcursor->SelPaste(); - UpdateLocal(bv); + mathcursor->selPaste(); + updateLocal(bv, true); break; case LFUN_CUT: bv->lockedInsetStoreUndo(Undo::DELETE); - mathcursor->SelCut(); - UpdateLocal(bv); + mathcursor->selCut(); + updateLocal(bv, true); break; case LFUN_COPY: - mathcursor->SelCopy(); + mathcursor->selCopy(); break; case LFUN_HOMESEL: @@ -581,16 +504,16 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, // --- accented characters ------------------------------ - case LFUN_UMLAUT: mathcursor->setAccent(LM_ddot); break; - case LFUN_CIRCUMFLEX: mathcursor->setAccent(LM_hat); break; - case LFUN_GRAVE: mathcursor->setAccent(LM_grave); break; - case LFUN_ACUTE: mathcursor->setAccent(LM_acute); break; - case LFUN_TILDE: mathcursor->setAccent(LM_tilde); break; - case LFUN_MACRON: mathcursor->setAccent(LM_bar); break; - case LFUN_DOT: mathcursor->setAccent(LM_dot); break; - case LFUN_CARON: mathcursor->setAccent(LM_check); break; - case LFUN_BREVE: mathcursor->setAccent(LM_breve); break; - case LFUN_VECTOR: mathcursor->setAccent(LM_vec); break; + case LFUN_UMLAUT: handleAccent(bv, "ddot"); break; + case LFUN_CIRCUMFLEX: handleAccent(bv, "hat"); break; + case LFUN_GRAVE: handleAccent(bv, "grave"); break; + case LFUN_ACUTE: handleAccent(bv, "acute"); break; + case LFUN_TILDE: handleAccent(bv, "tilde"); break; + case LFUN_MACRON: handleAccent(bv, "bar"); break; + case LFUN_DOT: handleAccent(bv, "dot"); break; + case LFUN_CARON: handleAccent(bv, "check"); break; + case LFUN_BREVE: handleAccent(bv, "breve"); break; + case LFUN_VECTOR: handleAccent(bv, "vec"); break; // Greek mode case LFUN_GREEK: @@ -611,123 +534,112 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, break; // Math fonts - case LFUN_BOLD: mathcursor->toggleLastCode(LM_TC_BF); break; - case LFUN_SANS: mathcursor->toggleLastCode(LM_TC_SF); break; - case LFUN_EMPH: mathcursor->toggleLastCode(LM_TC_CAL); break; - case LFUN_ROMAN: mathcursor->toggleLastCode(LM_TC_RM); break; - case LFUN_CODE: mathcursor->toggleLastCode(LM_TC_TT); break; - case LFUN_DEFAULT: mathcursor->setLastCode(LM_TC_VAR); break; - -#ifndef NO_LATEX -#ifdef WITH_WARNINGS -#warning This needs a fix. - // Can we use the ERT inset here? (Lgb) -#endif - case LFUN_TEX: - // varcode = LM_TC_TEX; - mathcursor->setLastCode(LM_TC_TEX); - bv->owner()->message(_("TeX mode")); + case LFUN_BOLD: handleFont(bv, LM_TC_BF); break; + case LFUN_SANS: handleFont(bv, LM_TC_SF); break; + case LFUN_EMPH: handleFont(bv, LM_TC_CAL); break; + case LFUN_ROMAN: handleFont(bv, LM_TC_RM); break; + case LFUN_CODE: handleFont(bv, LM_TC_TT); break; + case LFUN_DEFAULT: handleFont(bv, LM_TC_VAR); break; + + case LFUN_MATH_MODE: + handleFont(bv, LM_TC_TEXTRM); + //bv->owner()->message(_("math text mode toggled")); break; -#endif + case LFUN_MATH_LIMITS: bv->lockedInsetStoreUndo(Undo::INSERT); if (mathcursor->toggleLimits()) - UpdateLocal(bv); + updateLocal(bv, true); break; case LFUN_MATH_SIZE: if (!arg.empty()) { bv->lockedInsetStoreUndo(Undo::INSERT); latexkeys const * l = in_word_set(arg); - mathcursor->SetSize(MathStyles(l ? l->id : static_cast(-1))); - UpdateLocal(bv); + mathcursor->setSize(MathStyles(l ? l->id : static_cast(-1))); + updateLocal(bv, true); } break; - case LFUN_INSERT_MATH: + case LFUN_INSERT_MATRIX: if (!arg.empty()) { bv->lockedInsetStoreUndo(Undo::INSERT); - mathcursor->Interpret(arg); - UpdateLocal(bv); + mathcursor->interpret("matrix " + arg); + updateLocal(bv, true); } break; - case LFUN_INSERT_MATRIX: - if (mathcursor) { + case LFUN_INSERT_MATH: + if (!arg.empty()) { bv->lockedInsetStoreUndo(Undo::INSERT); - int m = 1; - int n = 1; - string v_align, h_align; - istringstream is(arg.c_str()); - is >> m >> n >> v_align >> h_align; - MathArrayInset * p = new MathArrayInset(m, n); - p->valign(v_align[0]); - p->halign(h_align); - mathcursor->insert(p); - UpdateLocal(bv); + mathcursor->interpret(arg); + updateLocal(bv, true); } break; + case LFUN_MATH_SPACE: + { + bv->lockedInsetStoreUndo(Undo::EDIT); + MathSpaceInset * p = mathcursor->prevSpaceInset(); + if (p) + p->incSpace(); + else + mathcursor->insert(new MathSpaceInset(1)); + updateLocal(bv, true); + break; + } + case LFUN_MATH_DELIM: { bv->lockedInsetStoreUndo(Undo::INSERT); - int ilt = '('; - int irt = '.'; static const string vdelim("(){}[]./|"); - lyxerr << "formulabase::LFUN_MATH_DELIM, arg: '" << arg << "'\n"; + //lyxerr << "formulabase::LFUN_MATH_DELIM, arg: '" << arg << "'\n"; if (arg.empty()) break; + // try to read integers first + int ilt = '('; + int irt = '.'; istringstream is(arg.c_str()); - string lt, rt; - is >> lt >> rt; - lyxerr << "formulabase::LFUN_MATH_DELIM, lt: '" << lt << "'\n"; - lyxerr << "formulabase::LFUN_MATH_DELIM, rt: '" << rt << "'\n"; - - if (lt.size() > 1) { - latexkeys const * l = in_word_set(lt); - if (l) - ilt = l->id; - } else if (vdelim.find(lt[0]) != string::npos) - ilt = lt[0]; - - if (rt.size() > 1) { - latexkeys const * l = in_word_set(rt); - if (l) - irt = l->id; - } else if (vdelim.find(rt[0]) != string::npos) - irt = rt[0]; - - if (mathcursor->selection) { - MathDelimInset * p = new MathDelimInset(ilt, irt); - MathArray ar; - mathcursor->selArray(ar); - lyxerr << "selarray: " << ar << "\n"; - p->cell(0) = ar; - mathcursor->insert(p); - } else { - mathcursor->insert(new MathDelimInset(ilt, irt)); + is >> ilt >> irt; + + if (!is) { // ok, the beasties are no integers... try something else + ilt = '('; + irt = '.'; + + istringstream is(arg.c_str()); + string lt; + string rt; + is >> lt >> rt; + //lyxerr << "formulabase::LFUN_MATH_DELIM, lt: '" << lt << "'\n"; + //lyxerr << "formulabase::LFUN_MATH_DELIM, rt: '" << rt << "'\n"; + + if (lt.size() > 1) { + latexkeys const * l = in_word_set(lt); + if (l) + ilt = l->id; + } else if (vdelim.find(lt[0]) != string::npos) + ilt = lt[0]; + + if (rt.size() > 1) { + latexkeys const * l = in_word_set(rt); + if (l) + irt = l->id; + } else if (vdelim.find(rt[0]) != string::npos) + irt = rt[0]; } - UpdateLocal(bv); + + handleDelim(bv, ilt, irt); + updateLocal(bv, true); break; } case LFUN_PROTECTEDSPACE: + //lyxerr << " called LFUN_PROTECTEDSPACE\n"; bv->lockedInsetStoreUndo(Undo::INSERT); mathcursor->insert(new MathSpaceInset(1)); - space_on = true; - UpdateLocal(bv); - break; - - // Invalid actions under math mode - case LFUN_MATH_MODE: - if (mathcursor->getLastCode() != LM_TC_TEXTRM) { - bv->owner()->message(_("math text mode")); - varcode = LM_TC_TEXTRM; - } else - varcode = LM_TC_VAR; - mathcursor->setLastCode(varcode); + updateLocal(bv, true); break; case LFUN_UNDO: @@ -744,7 +656,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (!p) break; p->halign(arg.size() ? arg[0] : 'c', p->col(idx)); - UpdateLocal(bv); + updateLocal(bv, true); break; } @@ -757,7 +669,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (!p) break; p->valign(arg.size() ? arg[0] : 'c'); - UpdateLocal(bv); + updateLocal(bv, true); break; } @@ -770,7 +682,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (!p) break; p->addRow(p->row(idx)); - UpdateLocal(bv); + updateLocal(bv, true); break; } @@ -783,7 +695,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (!p) break; p->delRow(p->row(idx)); - UpdateLocal(bv); + updateLocal(bv, true); break; } @@ -795,7 +707,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (!p) break; p->addCol(p->col(idx)); - UpdateLocal(bv); + updateLocal(bv, true); break; } @@ -807,7 +719,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (!p) break; p->delCol(p->col(idx)); - UpdateLocal(bv); + updateLocal(bv, true); break; } @@ -818,12 +730,13 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, default: if ((action == -1 || action == LFUN_SELFINSERT) && !arg.empty()) { unsigned char c = arg[0]; - bv->lockedInsetStoreUndo(Undo::INSERT); - if (c == ' ' && mathcursor->getAccent() == LM_hat) { - c = '^'; - mathcursor->setAccent(0); - } + lyxerr << "Action: " << action << endl; + + lyxerr << "char: '" << c << "' int: " << int(c) << endl; + //owner_->getIntl()->getTrans().TranslateAndInsert(c, lt); + //lyxerr << "trans: '" << c << "' int: " << int(c) << endl; + bv->lockedInsetStoreUndo(Undo::INSERT); if (c == 0) { // Dead key, do nothing //lyxerr << "deadkey" << endl; @@ -832,11 +745,11 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (isalpha(c)) { if (mathcursor->getLastCode() == LM_TC_TEX) { - mathcursor->MacroModeOpen(); + mathcursor->macroModeOpen(); mathcursor->clearLastCode(); varcode = LM_TC_MIN; } else if (!varcode) { - short f = mathcursor->getLastCode() ? + MathTextCodes f = mathcursor->getLastCode() ? mathcursor->getLastCode() : mathcursor->nextCode(); varcode = MathIsAlphaFont(f) ? @@ -850,7 +763,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, char greek[26] = {'A', 'B', 'X', 0 , 'E', 0 , 0 , 'H', 'I', 0 , 'K', 0 , 'M', 'N', 'O', 0 , 0 , 'P', 0 , 'T', - 'Y', 0, 0, 0, 0 , 'Z' }; + 0, 0, 0, 0, 0 , 'Z' }; if ('A' <= c && c <= 'Z' && greek[c - 'A']) { char_code = LM_TC_RM; @@ -861,7 +774,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, mathcursor->insert(c, char_code); - if (greek_kb_flag && char_code == LM_TC_RM ) + if (greek_kb_flag && char_code == LM_TC_RM) mathcursor->setLastCode(LM_TC_VAR); varcode = LM_TC_MIN; @@ -873,7 +786,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, mathcursor->insert(c, LM_TC_TEX); if (c == '{') { mathcursor->insert('}', LM_TC_TEX); - mathcursor->Left(); + mathcursor->left(); } mathcursor->clearLastCode(); // varcode = LM_TC_MIN; @@ -882,7 +795,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, mathcursor->clearLastCode(); // varcode = LM_TC_MIN; } else if ('0' <= c && c <= '9' && (varcode == LM_TC_TEX||was_macro)) { - mathcursor->MacroModeOpen(); + mathcursor->macroModeOpen(); mathcursor->clearLastCode(); mathcursor->insert(c, LM_TC_MIN); } else if (('0' <= c && c <= '9') || strchr(";:!|[]().,?", c)) { @@ -895,7 +808,7 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, if (code != LM_TC_TEXTRM) code = LM_TC_BOP; mathcursor->insert(c, code); - } else if (strchr(latex_special_chars, c) && c!= '_') { + } else if (strchr(latex_special_chars, c) && c != '_') { MathTextCodes code = mathcursor->getLastCode(); if (code != LM_TC_TEXTRM) code = LM_TC_SPECIAL; @@ -904,39 +817,35 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, char s[2]; s[0] = c; s[1] = 0; - mathcursor->Interpret(s); - } else if (c == ' ') { + mathcursor->interpret(s); + } else if (c == ' ') { if (!varcode) { - short f = (mathcursor->getLastCode()) ? + MathTextCodes f = (mathcursor->getLastCode()) ? mathcursor->getLastCode() : mathcursor->nextCode(); - varcode = MathIsAlphaFont(f) ? - static_cast(f) : - LM_TC_VAR; + varcode = MathIsAlphaFont(f) ? f : LM_TC_VAR; } - if (varcode == LM_TC_TEXTRM) { + if (varcode == LM_TC_TEXTRM) mathcursor->insert(c, LM_TC_TEXTRM); - } else if (was_macro) { - mathcursor->MacroModeClose(); - } else if (sp) { - int isp = (sp->GetSpace()<5) ? sp->GetSpace()+1: 0; - sp->SetSpace(isp); - space_on = true; - } else { - if (!mathcursor->pop()) - result = FINISHED; + else if (was_macro) + mathcursor->macroModeClose(); + else if (mathcursor->pop()) mathcursor->plainRight(); + else { + // this would not work if the inset is in an table! + //bv->text->cursorRight(bv, true); + result = FINISHED; } } else if (c == '\'' || c == '@') { - mathcursor->insert (c, LM_TC_VAR); + mathcursor->insert(c, LM_TC_VAR); } else if (c == '\\') { if (was_macro) - mathcursor->MacroModeClose(); + mathcursor->macroModeClose(); bv->owner()->message(_("TeX mode")); mathcursor->setLastCode(LM_TC_TEX); } - UpdateLocal(bv); + updateLocal(bv, true); } else if (action == LFUN_MATH_PANEL) { result = UNDISPATCHED; } else { @@ -945,26 +854,18 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, } } - if (mathcursor) - mathcursor->normalize(); + mathcursor->normalize(); - if (mathcursor && was_macro != mathcursor->InMacroMode() - && action >= 0 - && action != LFUN_BACKSPACE) - UpdateLocal(bv); + if (was_macro != mathcursor->inMacroMode() + && action >= 0 && action != LFUN_BACKSPACE) + updateLocal(bv, true); - //if (mathcursor) - // UpdateLocal(bv); - - if (sp && !space_on) - sp = 0; - - if (mathcursor && (mathcursor->Selection() || was_selection)) - ToggleInsetSelection(bv); + if (mathcursor->selection() || was_selection) + toggleInsetSelection(bv); if (result == DISPATCHED || result == DISPATCHED_NOUPDATE || result == UNDISPATCHED) - ShowInsetCursor(bv); + showInsetCursor(bv); else bv->unlockInset(this); @@ -972,64 +873,96 @@ InsetFormulaBase::LocalDispatch(BufferView * bv, kb_action action, } - -/* FIXME: math-greek-toggle seems to work OK, but math-greek doesn't turn - * on greek mode */ -bool math_insert_greek(BufferView * bv, char c) +Inset::Code InsetFormulaBase::lyxCode() const { - if (!bv->available()) - return false; - - if (!isalpha(c)) - return false; - - string tmp; - tmp = c; - if (!bv->theLockingInset() || bv->theLockingInset()->IsTextInset()) { - int greek_kb_flag_save = greek_kb_flag; - InsetFormula * new_inset = new InsetFormula(); - bv->beforeChange(bv->text); - if (!bv->insertInset(new_inset)) { - delete new_inset; - return false; - } - //Update(1);//BUG - new_inset->Edit(bv, 0, 0, 0); - new_inset->LocalDispatch(bv, LFUN_SELFINSERT, tmp); - if (greek_kb_flag_save < 2) { - bv->unlockInset(new_inset); // bv->theLockingInset()); - bv->text->cursorRight(bv, true); - } - } else - if (bv->theLockingInset()->LyxCode() == Inset::MATH_CODE || - bv->theLockingInset()->LyxCode() == Inset::MATHMACRO_CODE) - static_cast(bv->theLockingInset())->LocalDispatch(bv, LFUN_SELFINSERT, tmp); - else - lyxerr << "Math error: attempt to write on a wrong " - "class of inset." << endl; - return true; + return Inset::MATH_CODE; } +void mathDispatchCreation(BufferView * bv, string const & arg, bool display) +{ + if (bv->available()) { +// Feature "Read math inset from selection" disabled. +// // use selection if available.. +// string sel; +// if (action == LFUN_MATH_IMPORT_SELECTION) +// sel = ""; +// else +// sel = bv->getLyXText()->selectionAsString(bv->buffer()); + + InsetFormula * f; +// if (sel.empty()) { + f = new InsetFormula; + if (openNewInset(bv, f)) { + // don't do that also for LFUN_MATH_MODE unless you want end up with + // always changing to mathrm when opening an inlined inset + // -- I really hate "LyXfunc overloading"... + if (display) + f->localDispatch(bv, LFUN_MATH_DISPLAY, string()); + f->localDispatch(bv, LFUN_INSERT_MATH, arg); + } +// } else { +// f = new InsetFormula(sel); +// bv->getLyXText()->cutSelection(bv); +// openNewInset(bv, f); +// } + } + bv->owner()->getLyXFunc()->setMessage(N_("Math editor mode")); +} -Inset::Code InsetFormulaBase::LyxCode() const +void mathDispatchMathDisplay(BufferView * bv, string const & arg) { - return Inset::MATH_CODE; + mathDispatchCreation(bv, arg, true); +} + +void mathDispatchMathMode(BufferView * bv, string const & arg) +{ + mathDispatchCreation(bv, arg, false); } +void mathDispatchMathImportSelection(BufferView * bv, string const & arg) +{ + mathDispatchCreation(bv, arg, true); +} -LyXFont const InsetFormulaBase::ConvertFont(LyXFont const & f) const +void mathDispatchMathMacro(BufferView * bv, string const & arg) { - // We have already discussed what was here - LyXFont font(f); -#ifndef NO_LATEX - font.setLatex(LyXFont::OFF); -#endif - return font; + if (bv->available()) { + if (arg.empty()) + bv->owner()->getLyXFunc()->setErrorMessage(N_("Missing argument")); + else { + string s(arg); + string const s1 = token(s, ' ', 1); + int const na = s1.empty() ? 0 : lyx::atoi(s1); + openNewInset(bv, new InsetFormulaMacro(token(s, ' ', 0), na)); + } + } } -MathInset * InsetFormulaBase::par() const +void mathDispatchMathDelim(BufferView * bv, string const & arg) +{ + if (bv->available()) { + if (openNewInset(bv, new InsetFormula)) + bv->theLockingInset()->localDispatch(bv, LFUN_MATH_DELIM, arg); + } +} + + +void mathDispatchInsertMatrix(BufferView * bv, string const & arg) +{ + if (bv->available()) { + if (openNewInset(bv, new InsetFormula)) + bv->theLockingInset()->localDispatch(bv, LFUN_INSERT_MATRIX, arg); + } +} + +void mathDispatchInsertMath(BufferView * bv, string const & arg) { - return par_; + if (bv->available()) { + if (arg.size() && arg[0] == '\\') + openNewInset(bv, new InsetFormula(arg)); + else + mathDispatchMathMode(bv, arg); + } }