commit cf07d4825f65ab75783bb81d12e882a709aea222
Author: Richard Kimberly Heck <[email protected]>
Date: Tue Jan 5 17:25:27 2021 -0500
Fix bug #11104. Activate refstyle support for InsetMathRef.
At the moment, there is no support for plurals and capitalization.
A long comment explains why. Support could be added for that without
a format change.
---
lib/lyx2lyx/lyx_2_4.py | 40 ++++++++++++++-
src/frontends/qt/GuiRef.cpp | 16 +++----
src/insets/InsetRef.cpp | 34 ++++++-------
src/insets/InsetRef.h | 13 +++--
src/mathed/InsetMathRef.cpp | 113 +++++++++++++++++++++++++++++++++++++++++--
src/mathed/InsetMathRef.h | 6 +--
src/mathed/MathParser.cpp | 3 +-
src/support/lstrings.cpp | 8 +++
src/support/lstrings.h | 2 +
src/version.h | 4 +-
10 files changed, 191 insertions(+), 48 deletions(-)
diff --git a/lib/lyx2lyx/lyx_2_4.py b/lib/lyx2lyx/lyx_2_4.py
index a6ce67a..c82d09f 100644
--- a/lib/lyx2lyx/lyx_2_4.py
+++ b/lib/lyx2lyx/lyx_2_4.py
@@ -3993,6 +3993,40 @@ def revert_hrquotes(document):
document.body[i] = "\\begin_inset Quotes ard"
+def convert_math_refs(document):
+ i = 0
+ while True:
+ i = find_token(document.body, "\\begin_inset Formula", i)
+ if i == -1:
+ break
+ j = find_end_of_inset(document.body, i)
+ if j == -1:
+ document.warning("Can't find end of inset at line %d of body!" % i)
+ i += 1
+ continue
+ while i < j:
+ document.body[i] = document.body[i].replace("\\prettyref",
"\\formatted")
+ i += 1
+
+
+def revert_math_refs(document):
+ i = 0
+ while True:
+ i = find_token(document.body, "\\begin_inset Formula", i)
+ if i == -1:
+ break
+ j = find_end_of_inset(document.body, i)
+ if j == -1:
+ document.warning("Can't find end of inset at line %d of body!" % i)
+ i += 1
+ continue
+ while i < j:
+ document.body[i] = document.body[i].replace("\\formatted",
"\\prettyref")
+ if "\\labelonly" in document.body[i]:
+ document.body[i] = re.sub("\\\\labelonly{([^}]+?)}", "\\1",
document.body[i])
+ i += 1
+
+
##
# Conversion hub
#
@@ -4054,10 +4088,12 @@ convert = [
[597, [convert_libertinus_rm_fonts]],
[598, []],
[599, []],
- [600, []]
+ [600, []],
+ [601, [convert_math_refs]]
]
-revert = [[598, [revert_hrquotes]],
+revert = [[599, [revert_math_refs]],
+ [598, [revert_hrquotes]],
[598, [revert_nopagebreak]],
[597, [revert_docbook_table_output]],
[596, [revert_libertinus_rm_fonts,revert_libertinus_sftt_fonts]],
diff --git a/src/frontends/qt/GuiRef.cpp b/src/frontends/qt/GuiRef.cpp
index c5dd8cd..57859be 100644
--- a/src/frontends/qt/GuiRef.cpp
+++ b/src/frontends/qt/GuiRef.cpp
@@ -145,13 +145,14 @@ void GuiRef::enableView(bool enable)
void GuiRef::enableBoxes()
{
QString const reftype =
- typeCO->itemData(typeCO->currentIndex()).toString();
+ typeCO->itemData(typeCO->currentIndex()).toString();
bool const isFormatted = (reftype == "formatted");
bool const isLabelOnly = (reftype == "labelonly");
bool const usingRefStyle = buffer().params().use_refstyle;
- pluralCB->setEnabled(isFormatted && usingRefStyle);
- capsCB->setEnabled(isFormatted && usingRefStyle);
- noprefixCB->setEnabled(isLabelOnly);
+ bool const intext = bufferview()->cursor().inTexted();
+ pluralCB->setEnabled(intext && isFormatted && usingRefStyle);
+ capsCB->setEnabled(intext && isFormatted && usingRefStyle);
+ noprefixCB->setEnabled(intext && isLabelOnly);
}
@@ -324,11 +325,8 @@ void GuiRef::updateContents()
typeCO->addItem(qt_("on page <page>"), "vpageref");
typeCO->addItem(qt_("<reference> on page <page>"), "vref");
typeCO->addItem(qt_("Textual reference"), "nameref");
- if (bufferview()->cursor().inTexted()) {
- typeCO->addItem(qt_("Formatted reference"), "formatted");
- typeCO->addItem(qt_("Label only"), "labelonly");
- } else
- typeCO->addItem(qt_("Formatted reference"), "prettyref");
+ typeCO->addItem(qt_("Formatted reference"), "formatted");
+ typeCO->addItem(qt_("Label only"), "labelonly");
referenceED->setText(toqstr(params_["reference"]));
diff --git a/src/insets/InsetRef.cpp b/src/insets/InsetRef.cpp
index 200f5e5..cf24571 100644
--- a/src/insets/InsetRef.cpp
+++ b/src/insets/InsetRef.cpp
@@ -174,16 +174,6 @@ bool InsetRef::getStatus(Cursor & cur, FuncRequest const &
cmd,
}
-namespace {
-
-void capitalize(docstring & s) {
- char_type t = uppercase(s[0]);
- s[0] = t;
-}
-
-} // namespace
-
-
// the ref argument is the label name we are referencing.
// we expect ref to be in the form: pfx:suffix.
//
@@ -199,7 +189,8 @@ void capitalize(docstring & s) {
// label, thus: \prettyref{pfx:suffix}.
//
docstring InsetRef::getFormattedCmd(docstring const & ref,
- docstring & label, docstring & prefix, docstring const & caps) const
+ docstring & label, docstring & prefix, bool use_refstyle,
+ bool use_caps)
{
static docstring const defcmd = from_ascii("\\ref");
static docstring const prtcmd = from_ascii("\\prettyref");
@@ -216,11 +207,12 @@ docstring InsetRef::getFormattedCmd(docstring const & ref,
if (prefix.empty()) {
// we have ":xxxx"
+ LYXERR0("Label `" << ref << "' contains nothign before `:'.");
label = ref;
return defcmd;
}
- if (!buffer().params().use_refstyle) {
+ if (!use_refstyle) {
// \prettyref uses the whole label
label = ref;
return prtcmd;
@@ -237,8 +229,8 @@ docstring InsetRef::getFormattedCmd(docstring const & ref,
return defcmd;
}
}
- if (caps == "true") {
- capitalize(prefix);
+ if (use_caps) {
+ prefix = support::capitalize(prefix);
}
return from_ascii("\\") + prefix + from_ascii("ref");
}
@@ -261,7 +253,7 @@ void InsetRef::latex(otexstream & os, OutputParams const &
rp) const
if (rp.inulemcmd > 0)
os << "\\mbox{";
- if (cmd == "eqref" && buffer().params().use_refstyle) {
+ if (buffer().params().use_refstyle && cmd == "eqref") {
// we advertise this as printing "(n)", so we'll do that, at
least
// for refstyle, since refstlye's own \eqref prints, by default,
// "equation n". if one wants \eqref, one can get it by using a
@@ -271,10 +263,12 @@ void InsetRef::latex(otexstream & os, OutputParams const
& rp) const
else if (cmd == "formatted") {
docstring label;
docstring prefix;
+ bool const use_caps = getParam("caps") == "true";
+ bool const use_plural = getParam("plural") == "true";
docstring const fcmd =
- getFormattedCmd(data, label, prefix, getParam("caps"));
+ getFormattedCmd(data, label, prefix, use_caps);
os << fcmd;
- if (buffer().params().use_refstyle && getParam("plural") ==
"true")
+ if (buffer().params().use_refstyle && use_plural)
os << "[s]";
os << '{' << label << '}';
}
@@ -542,9 +536,11 @@ void InsetRef::validate(LaTeXFeatures & features) const
docstring const data = getEscapedLabel(features.runparams());
docstring label;
docstring prefix;
+ bool const use_refstyle = buffer().params().use_refstyle;
+ bool const use_caps = getParam("caps") == "true";
docstring const fcmd =
- getFormattedCmd(data, label, prefix, getParam("caps"));
- if (buffer().params().use_refstyle) {
+ getFormattedCmd(data, label, prefix, use_refstyle,
use_caps);
+ if (use_refstyle) {
features.require("refstyle");
if (prefix == "cha")
features.addPreambleSnippet(from_ascii("\\let\\charef=\\chapref"));
diff --git a/src/insets/InsetRef.h b/src/insets/InsetRef.h
index d18f619..57377e1 100644
--- a/src/insets/InsetRef.h
+++ b/src/insets/InsetRef.h
@@ -90,6 +90,13 @@ public:
//@}
///
bool outputActive() const { return active_; }
+ /// \return the command for a formatted reference to ref
+ /// \param label we're cross-referencing
+ /// \param argument for reference command
+ /// \param prefix of the label (before :)
+ /// Also used by InsetMathRef
+ static docstring getFormattedCmd(docstring const & ref, docstring &
label,
+ docstring & prefix, bool use_refstyle, bool use_caps =
false);
protected:
///
@@ -110,12 +117,6 @@ private:
/// \return the label with things that need to be escaped escaped
docstring getEscapedLabel(OutputParams const &) const;
- /// \return the command for a formatted reference to ref
- /// \param label we're cross-referencing
- /// \param argument for reference command
- /// \param prefix of the label (before :)
- docstring getFormattedCmd(docstring const & ref, docstring & label,
- docstring & prefix, docstring const & caps) const;
///
mutable docstring screen_label_;
diff --git a/src/mathed/InsetMathRef.cpp b/src/mathed/InsetMathRef.cpp
index 9efd865..7170ca6 100644
--- a/src/mathed/InsetMathRef.cpp
+++ b/src/mathed/InsetMathRef.cpp
@@ -12,6 +12,7 @@
#include "InsetMathRef.h"
+#include "BufferParams.h"
#include "BufferView.h"
#include "Buffer.h"
#include "Cursor.h"
@@ -21,14 +22,18 @@
#include "LyX.h"
#include "MathData.h"
#include "MathFactory.h"
+#include "MathStream.h"
#include "MathSupport.h"
#include "ParIterator.h"
#include "xml.h"
#include "insets/InsetCommand.h"
+#include "insets/InsetRef.h"
#include "support/debug.h"
#include "support/gettext.h"
+#include "support/lstrings.h"
+#include "support/textutils.h"
#include <ostream>
@@ -75,7 +80,9 @@ void InsetMathRef::doDispatch(Cursor & cur, FuncRequest & cmd)
MathData ar;
if (createInsetMath_fromDialogStr(cmd.argument(), ar)) {
cur.recordUndo();
+ Buffer & buf = buffer();
*this = *ar[0].nucleus()->asRefInset();
+ setBuffer(buf);
break;
}
}
@@ -170,11 +177,24 @@ docstring const InsetMathRef::screenLabel() const
void InsetMathRef::validate(LaTeXFeatures & features) const
{
+ // This really should not happen here but does.
+ if (!buffer_) {
+ LYXERR0("Unassigned buffer_ in InsetMathRef::write!");
+ LYXERR0("LaTeX output may be wrong!");
+ }
+ bool const use_refstyle =
+ buffer_ && buffer().params().use_refstyle;
+
if (commandname() == "vref" || commandname() == "vpageref")
features.require("varioref");
- else if (commandname() == "prettyref")
- features.require("prettyref");
- else if (commandname() == "eqref")
+ else if (commandname() == "formatted") {
+ if (use_refstyle)
+ features.require("refstyle");
+ else
+ features.require("prettyref");
+ }
+ // if eqref is used with refstyle, we do our own output
+ else if (commandname() == "eqref" && use_refstyle)
features.require("amsmath");
else if (commandname() == "nameref")
features.require("nameref");
@@ -240,14 +260,99 @@ void InsetMathRef::changeTarget(docstring const & target)
}
+void InsetMathRef::write(TeXMathStream & os) const
+{
+ docstring const & cmd = commandname();
+ // This should not happen, but of course it does
+ if (!buffer_) {
+ LYXERR0("Unassigned buffer_ in InsetMathRef::write!");
+ LYXERR0("LaTeX output may be wrong!");
+ }
+ bool const use_refstyle =
+ buffer_ && buffer().params().use_refstyle;
+ bool special_case = cmd == "formatted" ||
+ cmd == "labelonly" ||
+ (cmd == "eqref" && use_refstyle);
+ // are we writing to the LyX file or not in a special case?
+ if (!os.latex() || !special_case) {
+ // if so, then this is easy
+ InsetMathCommand::write(os);
+ return;
+ }
+ // we need to translate 'formatted' to prettyref or refstyle-type
+ // commands and just output the label with labelonly
+ // most of this is borrowed from InsetRef and should be kept in
+ // sync with that.
+ ModeSpecifier specifier(os, currentMode(), lockedMode(), asciiOnly());
+ MathEnsurer ensurer(os, false);
+
+ if (use_refstyle && cmd == "eqref") {
+ // we advertise this as printing "(n)", so we'll do that, at
least
+ // for refstyle, since refstlye's own \eqref prints, by default,
+ // "equation n". if one wants \eqref, one can get it by using a
+ // formatted label in this case.
+ os << '(' << from_ascii("\\ref{") << cell(0) <<
from_ascii("})");
+ }
+ else if (cmd == "formatted") {
+ if (!use_refstyle)
+ os << "\\prettyref{" << cell(0) << "}";
+ else {
+ odocstringstream ods;
+ // get the label we are referencing
+ for (auto const & d : cell(0)) {
+ ods << d;
+ }
+ docstring const ref = ods.str();
+
+ /*
+ At the moment, the 'plural' and 'caps' options will
+ not work here. The reason is that we handle these as
+ 'internal' LyX argumemts, but those are not handled by
+ InsetCommandParams::getCommand, which is what is used
+ in createInsetMath_fromDialogStr to interpret the data
+ coming from the dialog.
+ If this is fixed, then what follows will get the info
+ we need.
+ Fixing it, I think, would mean sub-classing
+ InsetCommandParams to InsetRefParams, and the overriding
+ getCommand.
+ *******************************************************
+ // reset
+ ods.str(docstring());
+ ods.clear();
+ // get the options from the optional argument
+ for (auto const & d : cell(1))
+ ods << d;
+ docstring const options = ods.str();
+ bool const caps = support::contains(options, 'C');
+ bool const plural = support::contains(options, 's');
+ */
+ docstring label;
+ docstring prefix;
+ docstring const fcmd =
+ InsetRef::getFormattedCmd(ref, label, prefix,
true);
+ os << fcmd;
+ //if (plural)
+ // os << "[s]";
+ os << '{' << label << '}';
+ }
+ }
+ else if (cmd == "labelonly") {
+ // noprefix does not work here, for reasons given above.
+ os << cell(0);
+ }
+}
+
+
InsetMathRef::ref_type_info InsetMathRef::types[] = {
{ from_ascii("ref"), from_ascii(N_("Standard[[mathref]]")),
from_ascii(N_("Ref: "))},
{ from_ascii("eqref"), from_ascii(N_("Equation")),
from_ascii(N_("EqRef: "))},
{ from_ascii("pageref"), from_ascii(N_("Page Number")),
from_ascii(N_("Page: "))},
{ from_ascii("vpageref"), from_ascii(N_("Textual Page Number")),
from_ascii(N_("TextPage: "))},
{ from_ascii("vref"), from_ascii(N_("Standard+Textual Page")),
from_ascii(N_("Ref+Text: "))},
- { from_ascii("prettyref"), from_ascii(N_("PrettyRef")),
from_ascii(N_("FormatRef: "))},
+ { from_ascii("formatted"), from_ascii(N_("PrettyRef")),
from_ascii(N_("FormatRef: "))},
{ from_ascii("nameref"), from_ascii(N_("Reference to Name")),
from_ascii(N_("NameRef: "))},
+ { from_ascii("labelonly"), from_ascii(N_("Label Only")),
from_ascii(N_("Label Only: "))},
{ from_ascii(""), from_ascii(""), from_ascii("") }
};
diff --git a/src/mathed/InsetMathRef.h b/src/mathed/InsetMathRef.h
index acbe47b..5527a0d 100644
--- a/src/mathed/InsetMathRef.h
+++ b/src/mathed/InsetMathRef.h
@@ -29,7 +29,7 @@ public:
///
void updateBuffer(ParIterator const &, UpdateType, bool const deleted =
false) override;
///
- //void write(TeXMathStream & os) const override;
+ void write(TeXMathStream & os) const override;
///
void infoize(odocstream & os) const override;
///
@@ -62,10 +62,6 @@ public:
};
static ref_type_info types[];
///
- static int getType(docstring const & name);
- ///
- static docstring const & getName(int type);
- ///
docstring const getTarget() const;
///
InsetCode lyxCode() const override { return MATH_REF_CODE; }
diff --git a/src/mathed/MathParser.cpp b/src/mathed/MathParser.cpp
index 478e906..6d1b747 100644
--- a/src/mathed/MathParser.cpp
+++ b/src/mathed/MathParser.cpp
@@ -1546,7 +1546,8 @@ bool Parser::parse1(InsetMathGrid & grid, unsigned flags,
else if (t.cs() == "ref" || t.cs() == "eqref" || t.cs() ==
"prettyref"
|| t.cs() == "nameref" || t.cs() == "pageref"
- || t.cs() == "vpageref" || t.cs() == "vref") {
+ || t.cs() == "vpageref" || t.cs() == "vref"
+ || t.cs() == "formatted" || t.cs() == "labelonly") {
cell->push_back(MathAtom(new InsetMathRef(buf,
t.cs())));
docstring const opt = parse_verbatim_option();
docstring const ref = parse_verbatim_item();
diff --git a/src/support/lstrings.cpp b/src/support/lstrings.cpp
index 9aac66a..b85307f 100644
--- a/src/support/lstrings.cpp
+++ b/src/support/lstrings.cpp
@@ -543,6 +543,14 @@ docstring const uppercase(docstring const & a)
}
+docstring capitalize(docstring const & s) {
+ docstring ret = s;
+ char_type t = uppercase(ret[0]);
+ ret[0] = t;
+ return ret;
+}
+
+
string const ascii_lowercase(string const & a)
{
string tmp(a);
diff --git a/src/support/lstrings.h b/src/support/lstrings.h
index 9371968..b4f99f8 100644
--- a/src/support/lstrings.h
+++ b/src/support/lstrings.h
@@ -181,6 +181,8 @@ docstring const token(docstring const & a, char_type delim,
int n);
int tokenPos(std::string const & a, char delim, std::string const & tok);
int tokenPos(docstring const & a, char_type delim, docstring const & tok);
+///
+docstring capitalize(docstring const & s);
/// Substitute all \a oldchar with \a newchar
std::string const subst(std::string const & a, char oldchar, char newchar);
diff --git a/src/version.h b/src/version.h
index 7b31131..13cf4d0 100644
--- a/src/version.h
+++ b/src/version.h
@@ -32,8 +32,8 @@ extern char const * const lyx_version_info;
// Do not remove the comment below, so we get merge conflict in
// independent branches. Instead add your own.
-#define LYX_FORMAT_LYX 600 // spitz: hungarian quote style
-#define LYX_FORMAT_TEX2LYX 600
+#define LYX_FORMAT_LYX 601 // rkh: refstyle in math
+#define LYX_FORMAT_TEX2LYX 601
#if LYX_FORMAT_TEX2LYX != LYX_FORMAT_LYX
#ifndef _MSC_VER
--
lyx-cvs mailing list
[email protected]
http://lists.lyx.org/mailman/listinfo/lyx-cvs