diff --git a/src/CutAndPaste.cpp b/src/CutAndPaste.cpp index 7e980ddd6a..f661b3462b 100644 --- a/src/CutAndPaste.cpp +++ b/src/CutAndPaste.cpp @@ -225,7 +225,7 @@ pasteSelectionHelper(Cursor & cur, ParagraphList const & parlist, // check for duplicates InsetCommand & lab = static_cast(*it); docstring const oldname = lab.getParam("name"); - lab.update(oldname, false); + lab.updateCommand(oldname, false); docstring const newname = lab.getParam("name"); if (oldname != newname) { // adapt the references @@ -240,6 +240,25 @@ pasteSelectionHelper(Cursor & cur, ParagraphList const & parlist, break; } + case BIBITEM_CODE: { + // check for duplicates + InsetCommand & bib = static_cast(*it); + docstring const oldkey = bib.getParam("key"); + bib.updateCommand(oldkey, false); + docstring const newkey = bib.getParam("key"); + if (oldkey != newkey) { + // adapt the references + for (InsetIterator itt = inset_iterator_begin(in); itt != i_end; ++itt) { + if (itt->lyxCode() == CITE_CODE) { + InsetCommand & ref = dynamic_cast(*itt); + if (ref.getParam("key") == oldkey) + ref.setParam("key", newkey); + } + } + } + break; + } + default: break; // nothing } diff --git a/src/insets/InsetBibitem.cpp b/src/insets/InsetBibitem.cpp index 95a138dbe8..a05cbd45b0 100644 --- a/src/insets/InsetBibitem.cpp +++ b/src/insets/InsetBibitem.cpp @@ -12,7 +12,9 @@ #include "InsetBibitem.h" +#include "BiblioInfo.h" #include "Buffer.h" +#include "buffer_funcs.h" #include "BufferParams.h" #include "BufferView.h" #include "Counters.h" @@ -25,8 +27,11 @@ #include "ParagraphList.h" #include "TextClass.h" +#include "frontends/alert.h" + #include "support/lstrings.h" #include "support/docstream.h" +#include "support/gettext.h" #include "support/convert.h" #include @@ -49,6 +54,40 @@ InsetBibitem::InsetBibitem(InsetCommandParams const & p) } +void InsetBibitem::initView() +{ + updateCommand(getParam("key")); +} + + +void InsetBibitem::updateCommand(docstring const & new_key, bool) +{ + docstring const old_key = getParam("key"); + docstring key = new_key; + + BiblioInfo keys; + keys.fillWithBibKeys(&buffer()); + vector bibkeys = keys.getKeys(); + + int i = 1; + + if (find(bibkeys.begin(), bibkeys.end(), key) != bibkeys.end()) { + // generate unique label + key = new_key + '-' + convert(i); + while (find(bibkeys.begin(), bibkeys.end(), key) != bibkeys.end()) { + ++i; + key = new_key + '-' + convert(i); + } + frontend::Alert::warning(_("Keys must be unique!"), + bformat(_("The key %1$s already exists,\n" + "it will be changed to %2$s."), new_key, key)); + } + setParam("key", key); + + lyx::updateLabels(buffer()); +} + + ParamInfo const & InsetBibitem::findInfo(string const & /* cmdName */) { static ParamInfo param_info_; @@ -71,10 +110,12 @@ void InsetBibitem::doDispatch(Cursor & cur, FuncRequest & cmd) cur.noUpdate(); break; } - if (p["key"] != params()["key"]) - cur.bv().buffer().changeRefsIfUnique(params()["key"], - p["key"], CITE_CODE); - setParams(p); + docstring old_key = params()["key"]; + setParam("label", p["label"]); + updateCommand(p["key"]); + if (params()["key"] != old_key) + cur.bv().buffer().changeRefsIfUnique(old_key, + params()["key"], CITE_CODE); } default: diff --git a/src/insets/InsetBibitem.h b/src/insets/InsetBibitem.h index c6e6d70841..c48bc17b68 100644 --- a/src/insets/InsetBibitem.h +++ b/src/insets/InsetBibitem.h @@ -28,6 +28,11 @@ class InsetBibitem : public InsetCommand { public: /// InsetBibitem(InsetCommandParams const &); + /// verify label and update references. + /** + * Overloaded from Inset::initView. + **/ + void initView(); /// void read(Lexer & lex); /// @@ -51,6 +56,8 @@ public: /// static bool isCompatibleCommand(std::string const & s) { return s == "bibitem"; } + /// + void updateCommand(docstring const & new_key, bool dummy = false); protected: /// virtual void doDispatch(Cursor & cur, FuncRequest & cmd); diff --git a/src/insets/InsetCommand.h b/src/insets/InsetCommand.h index 0228a0160c..beada3091a 100644 --- a/src/insets/InsetCommand.h +++ b/src/insets/InsetCommand.h @@ -82,8 +82,8 @@ public: /// Whether this is a command this inset can represent. /// Not implemented here. Must be implemented in derived class. static bool isCompatibleCommand(std::string const & cmd); - /// update label and references. Currently used by InsetLabel. - virtual void update(docstring const &, bool) {}; + /// update label and references. + virtual void updateCommand(docstring const &, bool) {}; protected: /// diff --git a/src/insets/InsetLabel.cpp b/src/insets/InsetLabel.cpp index 0158361ab8..96212d4b9f 100644 --- a/src/insets/InsetLabel.cpp +++ b/src/insets/InsetLabel.cpp @@ -45,11 +45,11 @@ InsetLabel::InsetLabel(InsetCommandParams const & p) void InsetLabel::initView() { - update(getParam("name")); + updateCommand(getParam("name")); } -void InsetLabel::update(docstring const & new_label, bool updaterefs) +void InsetLabel::updateCommand(docstring const & new_label, bool updaterefs) { docstring const old_label = getParam("name"); docstring label = new_label; @@ -148,7 +148,7 @@ void InsetLabel::doDispatch(Cursor & cur, FuncRequest & cmd) cur.noUpdate(); break; } - update(p["name"]); + updateCommand(p["name"]); break; } diff --git a/src/insets/InsetLabel.h b/src/insets/InsetLabel.h index a963448909..4b2d64a751 100644 --- a/src/insets/InsetLabel.h +++ b/src/insets/InsetLabel.h @@ -54,7 +54,7 @@ public: /// void addToToc(ParConstIterator const &) const; /// - void update(docstring const & new_label, bool updaterefs = true); + void updateCommand(docstring const & new_label, bool updaterefs = true); protected: /// void doDispatch(Cursor & cur, FuncRequest & cmd);