Properly show labels from broken references in Cross-references dialog

Fix for bug #12456.

The labels are transmitted from Buffer to GuiRef by reference of refs_
in the getLabelList function. Previously, only one string was
transmitted. But I needed both the formatted string, e.g. "x enu:test"
or "Missing: enu:test", as well as the plain label, e.g. "enu:test".
The former is for the list of labels to choose from in GuiRef and the
latter for the label as shown in the line edit that contains the plain
label in order to create a new reference from it. Transmitting both is
what the pair achieves.
This commit is contained in:
Daniel Ramöller 2022-02-16 14:57:06 +01:00 committed by Jean-Marc Lasgouttes
parent 8519e2b074
commit df59649a18
7 changed files with 41 additions and 23 deletions

View File

@ -2389,7 +2389,7 @@ void Buffer::validate(LaTeXFeatures & features) const
}
void Buffer::getLabelList(vector<docstring> & list) const
void Buffer::getLabelList(vector<std::pair<docstring, docstring>> & list) const
{
// If this is a child document, use the master's list instead.
if (parent()) {
@ -2401,7 +2401,7 @@ void Buffer::getLabelList(vector<docstring> & list) const
shared_ptr<Toc> toc = d->toc_backend.toc("label");
for (auto const & tocit : *toc) {
if (tocit.depth() == 0)
list.push_back(tocit.str());
list.push_back(make_pair(tocit.str(), tocit.asString()));
}
}

View File

@ -521,8 +521,8 @@ public:
void invalidateCiteLabels() const;
///
bool citeLabelsValid() const;
///
void getLabelList(std::vector<docstring> &) const;
/// two strings: plain label name and label as gui string
void getLabelList(std::vector<std::pair<docstring, docstring>> &) const;
/// This removes the .aux and .bbl files from the temp dir.
void removeBiblioTempFiles() const;

View File

@ -43,8 +43,8 @@ namespace lyx {
///////////////////////////////////////////////////////////////////////////
TocItem::TocItem(DocIterator const & dit, int d, docstring const & s,
bool output_active, FuncRequest const & action)
: dit_(dit), depth_(d), str_(s), output_(output_active),
bool output_active, bool missing, FuncRequest const & action)
: dit_(dit), depth_(d), str_(s), output_(output_active), missing_(missing),
action_(action)
{
}
@ -65,6 +65,9 @@ docstring const TocItem::asString() const
prefix += cross;
prefix += thin;
}
if (missing_) {
prefix += _("MISSING: ");
}
return prefix + str_;
}

View File

@ -55,12 +55,13 @@ class TocItem
{
public:
/// Default constructor for STL containers.
TocItem() : dit_(0), depth_(0), output_(false) {}
TocItem() : dit_(0), depth_(0), output_(false), missing_(false) {}
///
TocItem(DocIterator const & dit,
int depth,
docstring const & s,
bool output_active,
bool missing = false,
FuncRequest const & action = FuncRequest(LFUN_UNKNOWN_ACTION)
);
///
@ -74,6 +75,8 @@ public:
///
bool isOutput() const { return output_; }
///
bool isMissing() const { return missing_; }
///
void setAction(FuncRequest const & a) { action_ = a; }
/// custom action, or the default one (paragraph-goto) if not customised
@ -92,6 +95,8 @@ private:
docstring str_;
/// Is this item in a note, inactive branch, etc?
bool output_;
/// Is this item missing, e.g. missing label?
bool missing_;
/// Custom action
FuncRequest action_;
};

View File

@ -202,7 +202,7 @@ void GuiRef::refHighlighted(QTreeWidgetItem * sel)
bool const cur_item_selected = sel->isSelected();
if (cur_item_selected)
referenceED->setText(sel->text(0));
referenceED->setText(sel->data(0, Qt::UserRole).toString());
if (at_ref_)
gotoRef();
@ -236,7 +236,7 @@ void GuiRef::refSelected(QTreeWidgetItem * sel)
bool const cur_item_selected = sel->isSelected();
if (cur_item_selected)
referenceED->setText(sel->text(0));
referenceED->setText(sel->data(0, Qt::UserRole).toString());
// <enter> or double click, inserts ref and closes dialog
slotOK();
}
@ -439,13 +439,17 @@ void GuiRef::redoRefs()
// the first item inserted
QString const oldSelection(referenceED->text());
QStringList refsStrings;
QStringList refsNames;
QStringList refsAsStrings;
QStringList refsCategories;
vector<docstring>::const_iterator iter;
vector<std::pair<docstring, docstring>>::const_iterator iter;
bool noprefix = false;
for (iter = refs_.begin(); iter != refs_.end(); ++iter) {
QString const lab = toqstr(*iter);
refsStrings.append(lab);
// the plain label name
QString const lab = toqstr((*iter).first);
refsNames.append(lab);
// the label as gui string
refsAsStrings.append(toqstr((*iter).second));
if (groupCB->isChecked()) {
if (lab.contains(":")) {
QString const pref = lab.split(':')[0];
@ -470,10 +474,10 @@ void GuiRef::redoRefs()
sortingCO->itemData(sortingCO->currentIndex()).toString()
: QString();
if (sort_method == "nocase")
sort(refsStrings.begin(), refsStrings.end(),
sort(refsNames.begin(), refsNames.end(),
caseInsensitiveLessThan /*defined above*/);
else if (sort_method == "case")
sort(refsStrings.begin(), refsStrings.end());
sort(refsNames.begin(), refsNames.end());
if (groupCB->isChecked()) {
QList<QTreeWidgetItem *> refsCats;
@ -481,14 +485,15 @@ void GuiRef::redoRefs()
QString const & cat = refsCategories.at(i);
QTreeWidgetItem * item = new QTreeWidgetItem(refsTW);
item->setText(0, cat);
for (int j = 0; j < refsStrings.size(); ++j) {
QString const & ref = refsStrings.at(j);
for (int j = 0; j < refsNames.size(); ++j) {
QString const & ref = refsNames.at(j);
if ((ref.startsWith(cat + QString(":")))
|| (cat == qt_("<No prefix>")
&& (!ref.mid(1).contains(":") || ref.left(1).contains(":")))) {
QTreeWidgetItem * child =
new QTreeWidgetItem(item);
child->setText(0, ref);
item->setText(0, refsAsStrings.at(j));
item->setData(0, Qt::UserRole, ref);
item->addChild(child);
}
}
@ -497,9 +502,11 @@ void GuiRef::redoRefs()
refsTW->addTopLevelItems(refsCats);
} else {
QList<QTreeWidgetItem *> refsItems;
for (int i = 0; i < refsStrings.size(); ++i) {
for (int i = 0; i < refsNames.size(); ++i) {
QTreeWidgetItem * item = new QTreeWidgetItem(refsTW);
item->setText(0, refsStrings.at(i));
QString const & ref = refsNames.at(i);
item->setText(0, refsAsStrings.at(i));
item->setData(0, Qt::UserRole, ref);
refsItems.append(item);
}
refsTW->addTopLevelItems(refsItems);

View File

@ -106,8 +106,9 @@ private:
int restored_buffer_;
/// store the last active buffer
int active_buffer_;
/// the references
std::vector<docstring> refs_;
/// the references as two strings: plain label name and label as gui string
/// FIXME: might be a good idea to use a custom struct
std::vector<std::pair<docstring, docstring>> refs_;
};
} // namespace frontend

View File

@ -537,7 +537,9 @@ void InsetRef::addToToc(DocIterator const & cpit, bool output_active,
broken_ = true;
setBroken(broken_);
shared_ptr<Toc> toc = backend.toc("label");
toc->push_back(TocItem(cpit, 0, screenLabel(), output_active));
if (TocBackend::findItem(*toc, 0, label) == toc->end())
toc->push_back(TocItem(cpit, 0, label, output_active, true));
toc->push_back(TocItem(cpit, 1, screenLabel(), output_active));
shared_ptr<Toc> toc2 = backend.toc("brokenrefs");
toc2->push_back(TocItem(cpit, 0, screenLabel(), output_active));
}