mirror of
https://git.lyx.org/repos/lyx.git
synced 2024-11-09 18:31:04 +00:00
Math commands used in text mode now always use the current selection as contents
(#9762) * fixes a bug where this was already the expected behaviour of math-subscript and math-superscript but failed. * corrects the behaviour where if there is \newcommand in the selection, then a corresponding macro template is introduced instead of a math inset. * fixes a bug where math-display, math-subscript and math-supscript would also introduce such a macro template in a way unrelated to their function. Now it only happens with math-mode without arguments. * fixes a bug where a text that does not denote a macro definition, e.g. "aaa\newcommandaaa", would produce \invalidmacro.
This commit is contained in:
parent
699a6db9fa
commit
61145265fc
119
src/Text3.cpp
119
src/Text3.cpp
@ -132,7 +132,7 @@ static void finishChange(Cursor & cur, bool selecting)
|
||||
}
|
||||
|
||||
|
||||
static void mathDispatch(Cursor & cur, FuncRequest const & cmd, bool display)
|
||||
static void mathDispatch(Cursor & cur, FuncRequest const & cmd)
|
||||
{
|
||||
cur.recordUndo();
|
||||
docstring sel = cur.selectionAsString(false);
|
||||
@ -152,45 +152,39 @@ static void mathDispatch(Cursor & cur, FuncRequest const & cmd, bool display)
|
||||
LATTEST(old_pos == cur.pos());
|
||||
#endif
|
||||
cur.nextInset()->edit(cur, true);
|
||||
// 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)
|
||||
cur.dispatch(FuncRequest(LFUN_MATH_DISPLAY));
|
||||
// Avoid an unnecessary undo step if cmd.argument
|
||||
// is empty
|
||||
if (!cmd.argument().empty())
|
||||
cur.dispatch(FuncRequest(LFUN_MATH_INSERT,
|
||||
cmd.argument()));
|
||||
if (cmd.action() != LFUN_MATH_MODE)
|
||||
// LFUN_MATH_MODE has a different meaning in math mode
|
||||
cur.dispatch(cmd);
|
||||
} else {
|
||||
// create a macro if we see "\\newcommand"
|
||||
// somewhere, and an ordinary formula
|
||||
// otherwise
|
||||
if (sel.find(from_ascii("\\newcommand")) == string::npos
|
||||
&& sel.find(from_ascii("\\newlyxcommand")) == string::npos
|
||||
&& sel.find(from_ascii("\\def")) == string::npos)
|
||||
{
|
||||
InsetMathHull * formula = new InsetMathHull(cur.buffer());
|
||||
string const selstr = to_utf8(sel);
|
||||
istringstream is(selstr);
|
||||
Lexer lex;
|
||||
InsetMathHull * formula = new InsetMathHull(cur.buffer());
|
||||
string const selstr = to_utf8(sel);
|
||||
istringstream is(selstr);
|
||||
Lexer lex;
|
||||
lex.setStream(is);
|
||||
if (!formula->readQuiet(lex)) {
|
||||
// No valid formula, let's try with delims
|
||||
is.str("$" + selstr + "$");
|
||||
lex.setStream(is);
|
||||
if (!formula->readQuiet(lex)) {
|
||||
// No valid formula, let's try with delims
|
||||
is.str("$" + selstr + "$");
|
||||
lex.setStream(is);
|
||||
if (!formula->readQuiet(lex)) {
|
||||
// Still not valid, leave it as is
|
||||
valid = false;
|
||||
delete formula;
|
||||
cur.insert(sel);
|
||||
} else
|
||||
cur.insert(formula);
|
||||
} else
|
||||
cur.insert(formula);
|
||||
} else {
|
||||
cur.insert(new MathMacroTemplate(cur.buffer(), sel));
|
||||
// Still not valid, leave it as is
|
||||
valid = false;
|
||||
delete formula;
|
||||
cur.insert(sel);
|
||||
}
|
||||
}
|
||||
if (valid) {
|
||||
cur.insert(formula);
|
||||
cur.nextInset()->edit(cur, true);
|
||||
LASSERT(cur.inMathed(), return);
|
||||
cur.pos() = 0;
|
||||
cur.resetAnchor();
|
||||
cur.setSelection(true);
|
||||
cur.pos() = cur.lastpos();
|
||||
if (cmd.action() != LFUN_MATH_MODE)
|
||||
// LFUN_MATH_MODE has a different meaning in math mode
|
||||
cur.dispatch(cmd);
|
||||
cur.clearSelection();
|
||||
cur.pos() = cur.lastpos();
|
||||
}
|
||||
}
|
||||
if (valid)
|
||||
@ -2015,22 +2009,38 @@ void Text::dispatch(Cursor & cur, FuncRequest & cmd)
|
||||
changeDepth(cur, INC_DEPTH);
|
||||
break;
|
||||
|
||||
case LFUN_MATH_DISPLAY:
|
||||
mathDispatch(cur, cmd, true);
|
||||
break;
|
||||
|
||||
case LFUN_REGEXP_MODE:
|
||||
regexpDispatch(cur, cmd);
|
||||
break;
|
||||
|
||||
case LFUN_MATH_MODE:
|
||||
if (cmd.argument() == "on")
|
||||
case LFUN_MATH_MODE: {
|
||||
if (cmd.argument() == "on" || cmd.argument() == "") {
|
||||
// don't pass "on" as argument
|
||||
// (it would appear literally in the first cell)
|
||||
mathDispatch(cur, FuncRequest(LFUN_MATH_MODE), false);
|
||||
else
|
||||
mathDispatch(cur, cmd, false);
|
||||
docstring sel = cur.selectionAsString(false);
|
||||
MathMacroTemplate * macro = new MathMacroTemplate(cur.buffer());
|
||||
// create a macro template if we see "\\newcommand" somewhere, and
|
||||
// an ordinary formula otherwise
|
||||
if (!sel.empty()
|
||||
&& (sel.find(from_ascii("\\newcommand")) != string::npos
|
||||
|| sel.find(from_ascii("\\newlyxcommand")) != string::npos
|
||||
|| sel.find(from_ascii("\\def")) != string::npos)
|
||||
&& macro->fromString(sel)) {
|
||||
cur.recordUndo();
|
||||
replaceSelection(cur);
|
||||
cur.insert(macro);
|
||||
} else {
|
||||
// no meaningful macro template was found
|
||||
delete macro;
|
||||
mathDispatch(cur,FuncRequest(LFUN_MATH_MODE));
|
||||
}
|
||||
} else
|
||||
// The argument is meaningful
|
||||
// We replace cmd with LFUN_MATH_INSERT because LFUN_MATH_MODE
|
||||
// has a different meaning in math mode
|
||||
mathDispatch(cur, FuncRequest(LFUN_MATH_INSERT,cmd.argument()));
|
||||
break;
|
||||
}
|
||||
|
||||
case LFUN_MATH_MACRO:
|
||||
if (cmd.argument().empty())
|
||||
@ -2058,27 +2068,16 @@ void Text::dispatch(Cursor & cur, FuncRequest & cmd)
|
||||
}
|
||||
break;
|
||||
|
||||
// passthrough hat and underscore outside mathed:
|
||||
case LFUN_MATH_DISPLAY:
|
||||
case LFUN_MATH_SUBSCRIPT:
|
||||
mathDispatch(cur, FuncRequest(LFUN_SELF_INSERT, "_"), false);
|
||||
break;
|
||||
case LFUN_MATH_SUPERSCRIPT:
|
||||
mathDispatch(cur, FuncRequest(LFUN_SELF_INSERT, "^"), false);
|
||||
break;
|
||||
|
||||
case LFUN_MATH_INSERT:
|
||||
case LFUN_MATH_AMS_MATRIX:
|
||||
case LFUN_MATH_MATRIX:
|
||||
case LFUN_MATH_DELIM:
|
||||
case LFUN_MATH_BIGDELIM: {
|
||||
cur.recordUndo();
|
||||
cap::replaceSelection(cur);
|
||||
cur.insert(new InsetMathHull(cur.buffer(), hullSimple));
|
||||
checkAndActivateInset(cur, true);
|
||||
LASSERT(cur.inMathed(), break);
|
||||
cur.dispatch(cmd);
|
||||
case LFUN_MATH_BIGDELIM:
|
||||
mathDispatch(cur, cmd);
|
||||
break;
|
||||
}
|
||||
|
||||
case LFUN_FONT_EMPH: {
|
||||
Font font(ignore_font, ignore_language);
|
||||
|
@ -243,7 +243,8 @@ MacroTable::iterator
|
||||
MacroTable::insert(Buffer * buf, docstring const & def)
|
||||
{
|
||||
//lyxerr << "MacroTable::insert, def: " << to_utf8(def) << endl;
|
||||
MathMacroTemplate mac(buf, def);
|
||||
MathMacroTemplate mac(buf);
|
||||
mac.fromString(def);
|
||||
MacroData data(buf, mac);
|
||||
return insert(mac.name(), data);
|
||||
}
|
||||
|
@ -425,26 +425,20 @@ MathMacroTemplate::MathMacroTemplate(Buffer * buf, docstring const & name, int n
|
||||
}
|
||||
|
||||
|
||||
MathMacroTemplate::MathMacroTemplate(Buffer * buf, docstring const & str)
|
||||
: InsetMathNest(buf, 3), numargs_(0), optionals_(0),
|
||||
type_(MacroTypeNewcommand), lookOutdated_(true)
|
||||
bool MathMacroTemplate::fromString(docstring const & str)
|
||||
{
|
||||
buffer_ = buf;
|
||||
initMath();
|
||||
|
||||
MathData ar(buf);
|
||||
MathData ar(buffer_);
|
||||
mathed_parse_cell(ar, str, Parse::NORMAL);
|
||||
if (ar.size() != 1 || !ar[0]->asMacroTemplate()) {
|
||||
lyxerr << "Cannot read macro from '" << ar << "'" << endl;
|
||||
asArray(from_ascii("invalidmacro"), cell(0));
|
||||
// FIXME: The macro template does not make sense after this.
|
||||
// The whole parsing should not be in a constructor which
|
||||
// has no chance to report failure.
|
||||
return;
|
||||
// The macro template does not make sense after this.
|
||||
return false;
|
||||
}
|
||||
operator=( *(ar[0]->asMacroTemplate()) );
|
||||
|
||||
updateLook();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
@ -34,8 +34,8 @@ public:
|
||||
std::vector<MathData> const & optionalValues = std::vector<MathData>(),
|
||||
MathData const & def = MathData(),
|
||||
MathData const & display = MathData());
|
||||
///
|
||||
MathMacroTemplate(Buffer * buf, const docstring & str);
|
||||
/// parses from string, returns false if failed
|
||||
bool fromString (const docstring & str);
|
||||
///
|
||||
bool editable() const { return true; }
|
||||
///
|
||||
|
Loading…
Reference in New Issue
Block a user