+
+bool GuiCitation::initialiseParams(string const & data)
+{
+ InsetCommandMailer::string2params(lfun_name_, data, params_);
+
+ biblio::CiteEngine const engine = buffer().params().getEngine();
+
+ bibkeysInfo_.fillWithBibKeys(&buffer());
+
+ citeStyles_ = biblio::getCiteStyles(engine);
+
+ return true;
+}
+
+
+void GuiCitation::clearParams()
+{
+ params_.clear();
+ bibkeysInfo_.clear();
+}
+
+
+vector<docstring> const GuiCitation::availableKeys() const
+{
+ return bibkeysInfo_.getKeys();
+}
+
+
+vector<docstring> const GuiCitation::availableFields() const
+{
+ return bibkeysInfo_.getFields();
+}
+
+
+vector<docstring> const GuiCitation::availableEntries() const
+{
+ return bibkeysInfo_.getEntries();
+}
+
+
+void GuiCitation::filterByEntryType(
+ vector<docstring> & keyVector, docstring entry_type)
+{
+ if (entry_type.empty())
+ return;
+
+ vector<docstring>::iterator it = keyVector.begin();
+ vector<docstring>::iterator end = keyVector.end();
+
+ vector<docstring> result;
+ for (; it != end; ++it) {
+ docstring const key = *it;
+ BiblioInfo::const_iterator cit = bibkeysInfo_.find(key);
+ if (cit == bibkeysInfo_.end())
+ continue;
+ if (cit->second.entryType() == entry_type)
+ result.push_back(key);
+ }
+ keyVector = result;
+}
+
+
+biblio::CiteEngine GuiCitation::getEngine() const
+{
+ return buffer().params().getEngine();
+}
+
+
+docstring GuiCitation::getInfo(docstring const & key) const
+{
+ if (bibkeysInfo_.empty())
+ return docstring();
+
+ return bibkeysInfo_.getInfo(key);
+}
+
+
+// Escape special chars.
+// All characters are literals except: '.|*?+(){}[]^$\'
+// These characters are literals when preceded by a "\", which is done here
+// @todo: This function should be moved to support, and then the test in tests
+// should be moved there as well.
+static docstring escape_special_chars(docstring const & expr)
+{
+ // Search for all chars '.|*?+(){}[^$]\'
+ // Note that '[' and '\' must be escaped.
+ // This is a limitation of boost::regex, but all other chars in BREs
+ // are assumed literal.
+ static const boost::regex reg("[].|*?+(){}^$\\[\\\\]");
+
+ // $& is a perl-like expression that expands to all
+ // of the current match
+ // The '$' must be prefixed with the escape character '\' for
+ // boost to treat it as a literal.
+ // Thus, to prefix a matched expression with '\', we use:
+ // FIXME: UNICODE
+ return from_utf8(boost::regex_replace(to_utf8(expr), reg, "\\\\$&"));
+}
+
+
+vector<docstring> GuiCitation::searchKeys(
+ vector<docstring> const & keys_to_search, bool only_keys,
+ docstring const & search_expression, docstring field,
+ bool case_sensitive, bool regex)
+{
+ vector<docstring> foundKeys;
+
+ docstring expr = trim(search_expression);
+ if (expr.empty())
+ return foundKeys;
+
+ if (!regex)
+ // We must escape special chars in the search_expr so that
+ // it is treated as a simple string by boost::regex.
+ expr = escape_special_chars(expr);
+
+ boost::regex reg_exp;
+ try {
+ reg_exp.assign(to_utf8(expr), case_sensitive ?
+ boost::regex_constants::normal : boost::regex_constants::icase);
+ } catch (boost::regex_error & e) {
+ // boost::regex throws an exception if the regular expression is not
+ // valid.
+ LYXERR(Debug::GUI, e.what());
+ return vector<docstring>();
+ }
+
+ vector<docstring>::const_iterator it = keys_to_search.begin();
+ vector<docstring>::const_iterator end = keys_to_search.end();
+ for (; it != end; ++it ) {
+ BiblioInfo::const_iterator info = bibkeysInfo_.find(*it);
+ if (info == bibkeysInfo_.end())
+ continue;
+
+ BibTeXInfo const & kvm = info->second;
+ string data;
+ if (only_keys)
+ data = to_utf8(*it);
+ else if (field.empty())
+ data = to_utf8(*it) + ' ' + to_utf8(kvm.allData());
+ else if (kvm.hasField(field))
+ data = to_utf8(kvm.getValueForField(field));
+
+ if (data.empty())
+ continue;
+
+ try {
+ if (boost::regex_search(data, reg_exp))
+ foundKeys.push_back(*it);
+ }
+ catch (boost::regex_error & e) {
+ LYXERR(Debug::GUI, e.what());
+ return vector<docstring>();
+ }
+ }
+ return foundKeys;
+}
+
+
+Dialog * createGuiCitation(GuiView & lv) { return new GuiCitation(lv); }
+
+